# # Hero.py # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; version 2 of the License. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # Copyright # Author: Nicholas F. Hoover # Contributors: # Created: 2007.07.22 # Last Modified: 2007.11.07 # import pygame from Character import Character from Animation import Animation from PowerUp import PowerUp class Hero(Character): """A playable character""" HERO_NAME = '' STATUS_TICKS_BETWEEN_UPDATES = 20 STATUS_UPDATES_PER_SFX = 5 REGEN_AMOUNT_PER_TICK = 1 NUM_ANIMATIONS = 11 (IDLE, WALK_UP, WALK_DOWN, WALK_SIDE, ATTACK1, ATTACK2, SPECIAL1, SPECIAL2, EAT, PICKUP, USE) = range(NUM_ANIMATIONS) LEFT = NUM_ANIMATIONS DEFAULT_ANIMATION = IDLE ACTIONS = [ATTACK1, ATTACK2, SPECIAL1, SPECIAL2, EAT, PICKUP, USE] MAX_POWERUPS_EAT = 3 MAX_POWERUPS_PICKUP = 1 ##################### # INVENTORY BONUSES # ##################### FAST_SOUL_INTERCEPT = 0 FAST_SOUL_SLOPE = 10 FAST_SOUL_MAX = 6 STRONG_SOUL_INTERCEPT = 5 STRONG_SOUL_SLOPE = 20 STRONG_SOUL_MAX = 5 FAT_SOUL_INTERCEPT = 0 FAT_SOUL_SLOPE = 10 FAT_SOUL_MAX = 5 ############# # FUNCTIONS # ############# def __init__(self): Character.__init__(self) self.statusFunctions = [] self.reset() def reset(self): Character.reset(self) self.speed_bonus = 0 self.toughness_bonus = 0 self.regen_bonus = 0 self.statusUpdateCount = 0 #hunger/regen self.sfxUpdateCount = 0 self.effects = [] self.nextAction = self.IDLE self.nextFacing = self.facing self.inventory = range(PowerUp.NUM_ANIMATIONS) for i in range(PowerUp.NUM_ANIMATIONS): self.inventory[i] = 0 ########### # Updates # ########### def doStatusUpdate(self): self.statusUpdateCount += 1 if self.statusUpdateCount == self.STATUS_TICKS_BETWEEN_UPDATES: self.statusUpdateCount = 0 self.doRegen() for function in self.statusFunctions: if callable(function): function() self.doEffects() self.doInventoryBonuses() elif self.statusUpdateCount == self.STATUS_TICKS_BETWEEN_UPDATES/2: self.sfxUpdateCount += 1 if self.sfxUpdateCount == self.STATUS_UPDATES_PER_SFX: self.playSound(self.HERO_NAME + '_Misc') ######### # STATS # ######### def doRegen(self): self.incHealth(self.REGEN_AMOUNT_PER_TICK + self.regen_bonus) def decHealth(self, amount): if amount > self.toughness_bonus: amount -= self.toughness_bonus #do toughness prevHealth = self.health Character.decHealth(self, amount) if prevHealth > 20 and self.health <= 20: self.playSound(self.HERO_NAME + '_LowHealth') def doInventoryBonuses(self): #speed if self.inventory[PowerUp.DEAD_FASTKID] > self.FAST_SOUL_INTERCEPT: self.speed_bonus = (self.inventory[PowerUp.DEAD_FASTKID] - self.FAST_SOUL_INTERCEPT) / self.FAST_SOUL_SLOPE if self.speed_bonus > self.FAST_SOUL_MAX: self.speed_bonus = self.FAST_SOUL_MAX else: self.speed_bonus = 0 #toughness if self.inventory[PowerUp.DEAD_STRONGKID] > self.STRONG_SOUL_INTERCEPT: self.toughness_bonus = (self.inventory[PowerUp.DEAD_STRONGKID] - self.STRONG_SOUL_INTERCEPT) / self.STRONG_SOUL_SLOPE if self.toughness_bonus > self.STRONG_SOUL_MAX: self.toughness_bonus = self.STRONG_SOUL_MAX else: self.toughness_bonus = 0 #regen if self.inventory[PowerUp.DEAD_FATKID] > self.FAT_SOUL_INTERCEPT: self.regen_bonus = (self.inventory[PowerUp.DEAD_FATKID] - self.FAT_SOUL_INTERCEPT) / self.FAT_SOUL_SLOPE if self.regen_bonus > self.FAT_SOUL_MAX: self.regen_bonus = self.FAT_SOUL_MAX else: self.regen_bonus = 0 ############# # INVENTORY # ############# def _useItem(self, item): #decrement count self.inventory[item] -= 1 #apply effect powerup = PowerUp(0, item) for effect in powerup.effects: self.addEffect(effect) def addItem(self, item): #increment count self.inventory[item] += 1 def viewItemCount(self, item): return self.inventory[item] def useItem(self, item): if self.canAct() and self.inventory[item] > 0: self.setAnimation(self.USE) self._useItem(item) if item == PowerUp.DRUGS: self.playSound(self.HERO_NAME + '_Drugs') else: self.playSound(self.HERO_NAME + '_Eat') ########### # ACTIONS # ########### def attack1(self): if self.canAct(): self.setAnimation(self.ATTACK1) self.playSound(self.HERO_NAME + '_Punch') def attack2(self): if self.canAct(): self.setAnimation(self.ATTACK2) self.playSound(self.HERO_NAME + '_Kick') def eat(self): if self.canAct(): self.setAnimation(self.EAT) def pickup(self): if self.canAct(): self.setAnimation(self.PICKUP) def specialAttack1(self): pass def specialAttack2(self): pass def createAttack1Sprite(self): return 0 def createAttack2Sprite(self): return 0 def createSpecialAttack1Sprite(self): return 0 def createSpecialAttack2Sprite(self): return 0