# -*- coding: utf-8 -*-

from nbt import *

class ItemError(Exception):
    pass

class Item:

    count = 0

    def __init__(self, id = 'stone', name = None, lore = None, model = None, Itype = 'None', rank = None, stats = None, cost = 0, element = None, use = None, custom_on = False, custom_off = False, holder = True, set = None, other = None, bought = False):
        str_arg = {id:"Id must be a str", Itype:"Itype must be a str", set:"Set must be a str of the scoreboard", other:"Other must be a str", model:"Model must be a str"}
        for arg in str_arg :
            if not isinstance(arg, (str, type(None))):
                raise ItemError(str_arg[arg])
        if not isinstance(name, (JTxt, JLine, type(None))):
            raise ItemError('Name must be a Json obj.')
        if not isinstance(lore, (Lore, type(None))):
            raise ItemError('Lore must be a lsit of Json obj.')
        if rank not in ['a','b','c','d','s',None]:
            raise ItemError('Rank must be a, b, c, d, s.')
        if not isinstance(stats, Stats):
            raise ItemError('stats must be Stats obj')
        if element not in (None, 'air', 'fire', 'water', 'earth', 'dark','thunder'):
            raise ItemError('Element must be None or air, fire, water, earth, dark')
        if use not in ['arch','instant','click_keep','other',None]:
            raise ItemError('use must be arch, instant, click_keep or other')

        self.id  = id
        self.type = Itype
        self.rank = rank
        self.name = name if isinstance(name, JLine) else JLine([name])
        self.lore = lore
        self.model = model
        self.Icount = Item.count
        self.custom_on = custom_on
        self.custom_off = custom_off
        self.cost = cost
        self.element = element
        self.use = use
        self.holder = holder
        self.other = other
        self.color = None
        self.armor_piece = None
        self.stats = stats
        self.set = set
        self.bought = bought

        if self.rank != None:
            self.lore.newline(self.json_rank())
        if self.cost > 0:
            self.lore.newline(self.json_cost())
        if self.use != None:
            self.lore.newline(self.json_use())
        for par in self.stats.lore():
            self.lore.newline(par)

        Item.count += 1

    def name_plain_(self):
        if self.name != None:
            return self.name.plain_()
        else:
            return str(self.Icount)

    def name_plain(self):
        if self.name != None:
            return self.name.plain()
        else:
            return str(self.Icount)

    def json_rank(self):
        list = {'s':'dark_green', 'a':'dark_red', 'b':'dark_purple', 'c':'gold', 'd':'red'}
        return JPar([JLine([JTxt('Rank: ','gray'), JTxt(self.rank.upper(), list[self.rank])])])

    def json_cost(self):
        return JPar([JLine([JTxt('Cost: ','gray'), JTxt(str(self.cost), 'dark_aqua')])])

    def json_use(self):
        list = {'arch':"Arch",'instant':'Click','click_keep':'Click & Keep', 'other':'Other'}
        return JPar([JLine([JTxt('Use: ','gray'), JTxt(list[self.use], 'dark_gray')])])

    def data(self):
        name = self.name.get() if self.name != None else ''
        lore = self.lore.get() if self.lore != None else ''
        color = ',color:'+str(self.color) if self.color != None else ''
        display = ",display:{{Name:{0},Lore:{1}{2}}}".format(name, lore, color)

        name_ = self.name.plain_() if self.name != None else 'None'
        model = ",CustomModelData:{0}".format(self.model) if self.model != None else ''
        other = ","+self.other if self.other != None else ''

        nbt = "{{Unbreakable:1b,Armory:1b,HideFlags:7,item_uuid:{},name:{},type:{},rank:{},cost:{},element:{},use:{},{}{}{}{}{}}}".format(self.Icount, name_, self.type, self.rank, self.cost, self.element, self.use, self.stats.nbt(), model, display, other, self.stats.attibutes(self.armor_piece))

        return nbt

class Wand(Item):

    def __init__(self, name, lore, rank, model = None, stats = Stats(), custom_on = False, custom_off = False, cost = 0, element = None, use = "arch", holder = True, set = None, other = None, bought = False):
        super().__init__('carrot_on_a_stick', name, lore, model, 'wand', rank, stats, cost, element, use, custom_on, custom_off, holder, set, other, bought)


class Passive(Item):

    def __init__(self, name, lore, rank, model = None, stats = Stats(), custom_on = False, custom_off = False, cost = 0, element = None, use = None, holder = True, set = None, other = None, bought = False):
        super().__init__('stick', name, lore, model, 'passive', rank, stats, cost, element, use, custom_on, custom_off, holder, set, other, bought)

class Armor(Item):

    def __init__(self, id, name, lore, rank, model = None, stats = Stats(), custom_on = False, custom_off = False, cost = 0, element = None, use = None, holder = True, color = None, set = None, other = None, bought = False):
        super().__init__(id, name, lore, model, 'armor', rank, stats, cost, element, use, custom_on, custom_off, holder, set, other, bought)

        if not isinstance(color, (int, type(None))):
            raise ItemError('Color must be a str int.')

        self.color = color
        if 'helmet' in id:
            self.armor_piece = 'head'
        elif 'chestplate' in id:
            self.armor_piece = 'chest'
        elif 'leggings' in id:
            self.armor_piece = 'legs'
        else:
            self.armor_piece = 'feet'


class Weapon(Item):

    def __init__(self, name, lore, rank, id = 'wooden_sword', model = None, stats = Stats(), custom_on = False, custom_off = False, cost = 0, element = None, use = None, holder = True, set = None, other = None, bought = False):
        super().__init__(id, name, lore, model, 'weapon', rank, stats, cost, element, use, custom_on, custom_off, holder, set, other, bought)
