"""The base module for L{th.Item.Item} types. This module should only be imported by C{th.data.Items}. """ from .. import Item, Utl, Ifc import th class Kind(object): """The base class representing a type of L{th.Item.Item}. Each Kind instance is a singleton of a Kind subclass. Kind subclasses define an item type's attributes and methods. This class should not be instantiated directly. @ivar pc_only: True to make this item only able to be picked up by the player character. @ivar fixed: True to make this item unable to be picked up. @ivar tainted_chance: An integer, 0-100, representing the percentage of Items of this type that are generated tainted. @ivar using_does_not_destroy: True if using this item should not implicitly call L{th.Item.Item.destroy}. @ivar use_type: An integer representing what kind of item this is for use by the Monster AI. See L{th.Item} for possible values. @ivar armor: Nonzero to make an item type into wearable armor. @ivar damage: Nonzero to make an item type into a wieldable weapon. @ivar to_hit: For weapons, an accuracy modifier applied when calculating whether an attack hit. Positive values increase accuracy and negative values decrease accuracy. @ivar deadly_weapon: True if killing a human with this weapon counts as a plausible murder. (i.e. baseball bats but not magical cookies.) @ivar heal: Nonzero to make an item type into edible food. @ivar veg_level: L{th.Item.VEGETARIAN} for vegetarian food and L{th.Item.VEGAN} for vegan food. @ivar tasty: The message to be displayed when the food is eaten. """ _obj = None def __new__(cls): if not cls._obj: obj = object.__new__(cls) obj.set_default() cls._obj = obj return cls._obj def make(self, **options): """Make a new L{th.Item.Item} instance of this Kind. @param options: Other attributes to set on the created Item. These will override any defaults. @returns: L{th.Item.Item} """ tmp = Item.Item() tmp.kind = self if self.tainted_chance > Utl.rn(100): tmp.tainted = True self.xmake(tmp) for key, value in options.iteritems(): setattr(tmp, key, value) return tmp def set_default(self): """Sets the default attributes on the Kind. This method is used as __init__ might be called multiple times, which would override a Kind's with the defaults if its attributes were changed at runtime. """ self.using_does_not_destroy = True self.fixed = False self.pc_only = False self.veg_level = 0 self.tasty = "This tastes uninteresting." self.name = '' self.adesc = '' self.deadly_weapon = False self.damage = 0 self.heal = 0 self.to_hit = 0 self.armor = 0 self.tainted_chance = 0 self.use_type = 0 self.xinit() if not self.adesc: self.adesc = 'a %s' % self.name def xinit(self): pass def xmake(self, obj): pass def monUse(self, itm, user, here): """Called to check if an item can be used by a monster. @param itm: The item being used. @type itm: L{th.Item.Item} @param user: The monster using the item. This will never be L{g.player}. @type user: L{th.Monster.Monster} @param here: Where the item might be used. @type here: L{th.Node.Node} @returns: True if the monster can use the item. """ return False def use(self, itm, user, here): """Called when a monster is using an item. @param itm: The item being used. @type itm: L{th.Item.Item} @param user: The monster using the item. @type user: L{th.Monster.Monster} @param here: Where the item is being used. @type here: L{th.Node.Node} @returns: True if the monster was successfully used, and False if the monster's turn is not over. """ return Item.HANDLED_NONE def used_as_weapon(self, itm, wielder, here, target, hit): pass def eat(self, itm, eater, here): if self.heal > 0: return Item.HANDLED_NONE else: return Item.RETURN_FALSE def drop(self, itm, dropper, here): """Called when an item is being dropped. @param itm: The item being dropped. @type itm: L{th.Item.Item} @param dropper: The monster dropping the item. @type dropper: L{th.Monster.Monster} @param here: Where the item is being dropped. @type here: L{th.Node.Node} @returns: True if the item can be dropped. """ return Item.HANDLED_NONE def drop_action(self, itm, dropper, here): pass def drop_update(self, itm, dropper, here): pass def check_drop(self, itm, dropper, here): """Called when an item might be forcibly dropped. This is called when the item might be forcibly dropped from a monster. The check done must be nondestructive. The item will not be worn or wielded. @param itm: The item in question. @type itm: L{th.Item.Item} @param wearer: The monster holding the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being held. @type here: L{th.Node.Node} @returns: True if calling L{drop} will succeed. """ return True def get(self, itm, dropper, here): """Called when an item is being dropped. @param itm: The item being dropped. @type itm: L{th.Item.Item} @param dropper: The monster dropping the item. @type dropper: L{th.Monster.Monster} @param here: Where the item is being dropped. @type here: L{th.Node.Node} @returns: True if the item can be dropped. """ return Item.HANDLED_NONE def get_action(self, itm, dropper, here): pass def get_update(self, itm, dropper, here): pass def check_get(self, itm, dropper, here): """Called when an item might be forcibly dropped. This is called when the item might be forcibly dropped from a monster. The check done must be nondestructive. The item will not be worn or wielded. @param itm: The item in question. @type itm: L{th.Item.Item} @param wearer: The monster holding the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being held. @type here: L{th.Node.Node} @returns: True if calling L{drop} will succeed. """ return True def wear(self, itm, wearer, here): """Called when a monster is wearing an item. @param itm: The item being worn. @type itm: L{th.Item.Item} @param wearer: The monster wearing the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being worn. @type here: L{th.Node.Node} @returns: True if the item can be picked up. """ if self.armor > 0: return Item.HANDLED_NONE else: return Item.RETURN_FALSE def wear_action(self, itm, dropper, here): pass def wear_update(self, itm, dropper, here): pass def check_wear(self, itm, dropper, here): """Called when an item might be forcibly dropped. This is called when the item might be forcibly dropped from a monster. The check done must be nondestructive. The item will not be worn or wielded. @param itm: The item in question. @type itm: L{th.Item.Item} @param wearer: The monster holding the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being held. @type here: L{th.Node.Node} @returns: True if calling L{drop} will succeed. """ return True def unwear(self, itm, unwearer, here): """Called to check if an item can be picked up. @param itm: The item being picked up. @type itm: L{th.Item.Item} @param getter: The monster picking up the item. @type getter: L{th.Monster.Monster} @param here: Where the item is being picked up. @type here: L{th.Node.Node} @returns: True if the item can be picked up. """ return Item.HANDLED_NONE def unwear_action(self, itm, dropper, here): pass def unwear_update(self, itm, dropper, here): pass def check_unwear(self, itm, wearer, here): """Called when an item might be forcibly unworn. This is called when the item might be forcibly removed from a monster. The check done must be nondestructive. @param itm: The item in question. @type itm: L{th.Item.Item} @param wearer: The monster wearing the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being worn. @type here: L{th.Node.Node} @returns: True if calling L{unwear} will succeed. """ return True def wield(self, itm, wielder, here): if self.damage > 0: return Item.HANDLED_NONE else: return Item.RETURN_FALSE def wield_action(self, itm, dropper, here): pass def wield_update(self, itm, dropper, here): pass def check_wield(self, itm, dropper, here): """Called when an item might be forcibly dropped. This is called when the item might be forcibly dropped from a monster. The check done must be nondestructive. The item will not be worn or wielded. @param itm: The item in question. @type itm: L{th.Item.Item} @param wearer: The monster holding the item. @type wearer: L{th.Monster.Monster} @param here: Where the item is being held. @type here: L{th.Node.Node} @returns: True if calling L{drop} will succeed. """ return True def unwield(self, itm, wielder, here): return Item.HANDLED_NONE def unwield_action(self, itm, dropper, here): pass def unwield_update(self, itm, dropper, here): pass def check_unwield(self, itm, wielder, here): """Called when an item might be forcibly unwielded. This is called when the item might be forcibly unwielded. The check done must be nondestructive. @param itm: The item in question. @type itm: L{th.Item.Item} @param wielder: The monster wielding the item. @type wielder: L{th.Monster.Monster} @param here: Where the item is being wielded. @type here: L{th.Node.Node} @returns: True if calling L{unwield} will succeed. """ return True # Might as well add a dynamic interface for it. def supercharge(self, itm, owner, taint): Ifc.your('%s absorbs some %s yolk.' % (self.name, Utl.rn(th.data.Items.egg_colors))) itm.tainted = taint