Ejemplo n.º 1
0
class RamboStateStanding(State):
    name = "standing"

    def __init__(self, brain):
        super().__init__(brain)
        self.canAttackTimer = Timer()


    def on_enter(self):
        self.canAttackTimer.setTimer(2.0)

        meGroupId = self.brain.owner.world.component_for_entity(
                self.brain.owner.entity, system.groupid.GroupId)
        messaging.add(
            type=MessageType.EntityStanding,
            groupId=meGroupId.getId(),
            data=None
        )

    def process(self, dt):
        self.canAttackTimer.advance(dt)
        self.tryAttack()


    def tryAttack(self):
        if self.canAttackTimer.timeIsUp():
            self.brain.pop()
            self.brain.push("attacking")
Ejemplo n.º 2
0
class DragonStateChase(StateChase):
    def __init__(self, brain):
        super().__init__(brain)
        self.canSkillTimer = Timer()

    def on_enter(self):
        super().on_enter()
        self.canSkillTimer.setTimer(3.0)

    def process(self, dt):
        super().process(dt)
        self.canSkillTimer.advance(dt)

    def trySkill(self):
        if self.canSkillTimer.timeIsUp():
            meRenderable = self.brain.owner.world.component_for_entity(
                self.brain.owner.entity, system.graphics.renderable.Renderable)
            locCenter = meRenderable.getLocationCenter()
            messaging.add(type=MessageType.EmitParticleEffect,
                          data={
                              'location': locCenter,
                              'effectType': ParticleEffectType.dragonExplosion,
                              'damage': 50,
                              'byPlayer': False,
                              'direction': Direction.none,
                          })
            self.canSkillTimer.reset()
Ejemplo n.º 3
0
class Player():
    def __init__(self):
        self.name = 'Player'
        self.points = 0
        self.isPlayer = True
        self.isAttacking = False
        self.isAlive = True

        self.attackTimer = Timer(0.0)

    def advance(self, deltaTime: float):
        self.attackTimer.advance(deltaTime)

        if self.attackTimer.timeIsUp():
            self.isAttacking = False
            self.attackTimer.setActive(False)

    def setAttacking(self, attackTime: float):
        self.isAttacking = True

        self.attackTimer.setTimer(attackTime)
        self.attackTimer.start()

    def setAlive(self, alive):
        self.isAlive = alive

    def __repr__(self):
        return "Player"
Ejemplo n.º 4
0
class Texture(object):
    def __init__(self, type, width=0, height=0, name=''):
        self.type = type
        self.width: int = width
        self.height: int = height
        self.active: bool = True
        self.name = name

        # color related
        self.overwriteColorTimer = Timer(0.25, active=False)
        self.overwriteColor = None

    def init(self):
        pass

    def draw(self, viewport):
        pass

    def advance(self, deltaTime: float):
        # reset overwrite color
        if self.overwriteColorTimer.timeIsUp():
            self.overwriteColor = None
            self.overwriteColorTimer.stop()
        self.overwriteColorTimer.advance(deltaTime)

    def setOverwriteColorFor(self, time: float, color: Color):
        if self.overwriteColorTimer.isActive():
            logger.debug("{} Color already active on new set color".format(
                self.name))

        self.overwriteColor = color
        self.overwriteColorTimer.setTimer(time)
        self.overwriteColorTimer.reset()

    def advanceStep(self):
        pass

    def setActive(self, active: bool):
        self.active = active

    def isActive(self) -> bool:
        return self.active

    def setName(self, name: str):
        self.name = name

    def __repr__(self):
        return self.name
Ejemplo n.º 5
0
class StateAttack(State):
    name = "attack"

    def __init__(self, brain):
        State.__init__(self, brain)
        self.attackTimer = Timer(instant=True)


    def on_enter(self):
        meEnemy = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.enemy.Enemy)
        meGroupId = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.groupid.GroupId)

        self.attackTimer.setTimer(meEnemy.enemyInfo.attackTime)
        self.setTimer(meEnemy.enemyInfo.attackStateTime)

        messaging.add(
            type=MessageType.EntityAttack,
            groupId=meGroupId.getId(),
            data=None
        )


    def process(self, dt):
        self.attackTimer.advance(dt)

        if self.attackTimer.timeIsUp():
            logger.info(self.name + " I'm attacking, via offensiveattack!")
            self.attackTimer.reset()
            offensiveAttack = self.brain.owner.world.component_for_entity(
                self.brain.owner.entity, OffensiveAttack)
            offensiveAttack.attack()

        if self.timeIsUp():
            # too long attacking. lets switch to chasing
            logger.info("{}: Too long attacking, switch to chasing".format(self.owner))
            self.brain.pop()
            self.brain.push("chase")
Ejemplo n.º 6
0
class StateChase(State):
    name = "chase"

    def __init__(self, brain):
        State.__init__(self, brain)
        meEnemy = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.enemy.Enemy)

        # basically move speed
        self.lastInputTimer = Timer(meEnemy.enemyInfo.chaseStepDelay,
                                    instant=True)

        # try attacking when timer is finished
        self.canAttackTimer = Timer()

        # we need to know player location, or we could just handle on every new
        # PlayerLocation message
        self.lastKnownPlayerPosition = None

    def on_enter(self):
        meEnemy = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.enemy.Enemy)

        stateTimeRnd = random.randrange(-100 * meEnemy.enemyInfo.chaseTimeRnd,
                                        100 * meEnemy.enemyInfo.chaseTimeRnd)
        self.setTimer(meEnemy.enemyInfo.chaseTime + (stateTimeRnd / 100))

        self.canAttackTimer.setTimer(meEnemy.enemyInfo.enemyCanAttackPeriod)
        self.canAttackTimer.reset()

        if not Config.allowEnemyAttacking:
            self.canAttackTimer.setActive(False)

    def tryAttacking(self):
        if self.canAttackTimer.timeIsUp():
            logger.debug("{}: Check if i can attack player".format(self.name))
            if self.canAttackPlayer():
                if (EntityFinder.numEnemiesInState(self.brain.owner.world,
                                                   'attack') <
                        Config.maxEnemiesInStateAttacking):
                    self.brain.pop()
                    self.brain.push("attackwindup")

            self.canAttackTimer.reset()

    def tryMoving(self):
        # only move if we can not hit him (even on cooldown)
        # this is quiet... taxing. and not really necessary?
        # if not self.canAttackPlayer():

        if True:
            # movement speed, and direction
            if self.lastInputTimer.timeIsUp():
                self.getInputChase()
                self.lastInputTimer.reset()

    def trySkill(self):
        # stickfigure has no skills
        pass

    def process(self, dt):
        meAttackable = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.attackable.Attackable)

        if meAttackable.isStunned:
            return

        self.lastInputTimer.advance(dt)
        self.canAttackTimer.advance(dt)

        # update player position if new location
        self.checkForNewPlayerPosition()

        self.tryAttacking()
        # note that if we want to attack, as identified a few lines above,
        # we will be in state attackWindup, and not reach here
        self.trySkill()
        self.tryMoving()

        # switch to wander if exhausted
        if self.timeIsUp():
            logger.debug("{}: Too long chasing, switching to wander".format(
                self.owner))
            self.brain.pop()
            self.brain.push("wander")

    def checkForNewPlayerPosition(self):
        # check if there are any new player position messages
        for message in messaging.getByType(MessageType.PlayerLocation):
            self.lastKnownPlayerPosition = message.data

    def canAttackPlayer(self):
        if self.lastKnownPlayerPosition is None:
            # we may not yet have received a location.
            # find it directly via player entity
            # this is every time we go into chase state
            playerEntity = EntityFinder.findPlayer(self.brain.owner.world)
            # player not spawned
            if playerEntity is not None:
                playerRenderable = self.brain.owner.world.component_for_entity(
                    playerEntity, system.graphics.renderable.Renderable)
                self.lastKnownPlayerPosition = playerRenderable.getLocationAndSize(
                )

        canAttack = AiHelper.canAttackPlayer(self.brain.owner,
                                             self.lastKnownPlayerPosition)

        return canAttack

    def getInputChase(self):
        meGroupId = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.groupid.GroupId)
        meRenderable = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.graphics.renderable.Renderable)

        if not Config.allowEnemyMovement:
            return

        moveX, moveY, dontChangeDirection = AiHelper.getAttackVectorToPlayer(
            self.owner, meRenderable)

        # only move if we really move a character
        if moveX != 0 or moveY != 0:
            directMessaging.add(
                groupId=meGroupId.getId(),
                type=DirectMessageType.moveEnemy,
                data={
                    'x': moveX,
                    'y': moveY,
                    'dontChangeDirection': dontChangeDirection,
                    'updateTexture': True,
                    'force': False,
                },
            )
Ejemplo n.º 7
0
class StateAttack(State):
    name = "attack"

    def __init__(self, brain):
        State.__init__(self, brain)
        self.attackMoveTimer = Timer()  # Timer(0.5, instant=False) # windup and cooldown


    def on_enter(self):
        meEnemy = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.enemy.Enemy)
        meGroupId = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.groupid.GroupId)

        messaging.add(
            type=MessageType.EntityAttack,
            groupId=meGroupId.getId(),
            data=None
        )

        # self.attackTimer.setTimer(meEnemy.enemyInfo.attackTime)
        # self.setTimer(meEnemy.enemyInfo.attackTime)
        self.stepsTodo = 30
        self.attackMoveTimer.init()
        self.attackMoveTimer.setTimer(0.1)
        self.setTimer(3.0)

        # even though we attack multiple times (each step)
        # only send EntityAttack once (change animation)
        messaging.add(
            type=MessageType.EntityAttack,
            groupId=meGroupId.getId(),
            data={}
        )


    def process(self, dt):
        self.attackMoveTimer.advance(dt)

        # check if we got stunned
        meAttackable = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.gamelogic.attackable.Attackable)
        if meAttackable.isStunned:
            self.brain.pop()
            self.brain.push("chase")

        # check if we should do one attack step
        if self.attackMoveTimer.timeIsUp():
            logger.info("{}: I'm attacking, step {}".format(self.owner, self.stepsTodo))

            if self.stepsTodo > 0:
                self.attackMoveTimer.reset()
                self.stepsTodo -= 1

                meRenderable = self.brain.owner.world.component_for_entity(
                    self.brain.owner.entity, Renderable)
                meGroupId = self.brain.owner.world.component_for_entity(
                    self.brain.owner.entity, system.groupid.GroupId)

                if self.stepsTodo % 2 == 0:
                    offensiveAttack = self.brain.owner.world.component_for_entity(
                        self.brain.owner.entity, OffensiveAttack)
                    offensiveAttack.attack()

                if meRenderable.direction is Direction.left:
                    x = -1
                else:
                    x = 1
                directMessaging.add(
                    groupId = meGroupId.getId(),
                    type = DirectMessageType.moveEnemy,
                    data = {
                        'x': x,
                        'y': 0,
                        'dontChangeDirection': False,
                        'updateTexture': False,
                        'force': True
                    },
                )
            else:
                self.attackMoveTimer.stop()

        if self.timeIsUp():
            # too long attacking. lets switch to chasing
            logger.info("{}: Too long attacking, switch to chasing".format(
                self.owner))
            self.brain.pop()
            self.brain.push("chase")
Ejemplo n.º 8
0
class SceneIntro(SceneBase):
    def __init__(self, viewport, world):
        super().__init__(world=world, viewport=viewport)

        self.textureEmiter = TextureEmiter(viewport=viewport, world=world)
        renderableCache.init(viewport=viewport)

        textureCopter = PhenomenaTexture(
            phenomenaType=PhenomenaType.roflcopter,
            name="Scene1 chopper")
        self.copterSpawn = Coordinates(13, -1 * textureCopter.height)
        renderableCopter = Renderable(
            texture=textureCopter,
            viewport=self.viewport,
            coordinates=self.copterSpawn,
            active=True,
        )

        texturePlayer = CharacterTexture(
            characterAnimationType=CharacterAnimationType.standing,
            characterTextureType=CharacterTextureType.player,
            name='Scene1 Player')
        coordinates = Coordinates(24, 13)
        renderablePlayer = Renderable(
            texture=texturePlayer,
            viewport=self.viewport,
            coordinates=coordinates,
            active=True,
        )

        textureEnemy = CharacterTexture(
            characterAnimationType=CharacterAnimationType.standing,
            characterTextureType=CharacterTextureType.player,
            name='Scene1 Enemy')
        coordinates = Coordinates(Config.columns, 13)
        renderableEnemy = Renderable(
            texture=textureEnemy,
            viewport=self.viewport,
            coordinates=coordinates,
            active=True,
        )

        self.renderableCopter = renderableCopter
        self.renderablePlayer = renderablePlayer
        self.renderableEnemy = renderableEnemy

        self.myTimer = Timer(0.5)
        self.state = IntroSceneState.wait1
        self.name = "Scene1 - Intro Animation"
        self.anyKeyFinishesScene = True

        self.init()


    def advance(self, dt):
        self.myTimer.advance(dt)
        self.handleState()


    def enter(self):
        self.addRenderable(self.renderableCopter)


    def sceneIsFinished(self) -> bool:
        if self.state is IntroSceneState.done:
            return True
        else:
            return False


    def handleState(self):
        # interactive, aka a hack, but it works
        if (self.state is IntroSceneState.wait1
                or self.state is IntroSceneState.flydown
                or self.state is IntroSceneState.drop
                or self.state is IntroSceneState.flyup):

            c1, a1 = ColorPalette.getColorByColor(Color.blue)
            c2, a2 = ColorPalette.getColorByColor(Color.brightblue)
            self.viewport.addstr(5, 40,  "N Key Rollover", c1, a1)
            self.viewport.addstr(6, 40,  "Escape from Hong Kong", c2, a2)

            c3, a3 = ColorPalette.getColorByColor(Color.cyan)
            self.viewport.addstr(8, 40,  "Moving: arrow keys, shift to strafe", c3, a3)
            self.viewport.addstr(9, 40,  "Select attack: 1 2 3 4", c3, a3)
            self.viewport.addstr(10, 40, "Attack       : space", c3, a3)
            self.viewport.addstr(11, 40, "Skills       : q w e r", c3, a3)
            self.viewport.addstr(12, 40, "Heal, Port   : f g", c3, a3)

        # state
        if self.state is IntroSceneState.wait1:
            # for next scene: Flydown
            if self.myTimer.timeIsUp():
                self.state = IntroSceneState.flydown
                self.myTimer.setTimer(0.1)
                self.renderableCopter.setActive(True)
                logger.debug("Scene: Go to State: Flydown")

        elif self.state is IntroSceneState.flydown:
            if self.myTimer.timeIsUp():
                self.myTimer.reset()
                self.renderableCopter.coordinates.y += 1

            # for next scene: Drop
            if self.renderableCopter.coordinates.y == 8:
                self.myTimer.setTimer(0.1)
                logger.debug("Scene: Go to State: Drop")
                self.addRenderable(self.renderablePlayer)
                self.state = IntroSceneState.drop

        elif self.state is IntroSceneState.drop:
            # for next scene: Flyup
            if self.myTimer.timeIsUp():
                self.myTimer.reset()
                self.renderableCopter.coordinates.y -= 1

            if self.renderableCopter.coordinates.y == self.copterSpawn.y:
                self.myTimer.setTimer(0.1)
                self.addRenderable(self.renderableEnemy)
                self.renderableEnemy.texture.changeAnimation(
                    CharacterAnimationType.walking, direction=Direction.left)
                self.state = IntroSceneState.spawnenemy
                self.isShowMap = True
                logger.info("Scene: Go to State: SpawnEnemy")

        elif self.state is IntroSceneState.spawnenemy:
            if self.myTimer.timeIsUp():
                self.myTimer.reset()
                self.renderableEnemy.coordinates.x -= 1
                self.renderableEnemy.advanceStep()

            if (self.renderableEnemy.coordinates.x
                    == self.renderablePlayer.coordinates.x + 15):
                self.renderableEnemy.texture.changeAnimation(
                    CharacterAnimationType.standing, direction=Direction.none)
                self.myTimer.setTimer(2.0)
                self.state = IntroSceneState.speakenemy
                self.textureEmiter.showSpeechBubble(
                    'The princess is in another castle...',
                    time=3.0,
                    parentRenderable=self.renderableEnemy
                )

        elif self.state is IntroSceneState.speakenemy:
            if self.myTimer.timeIsUp():

                self.state = IntroSceneState.leaveenemy
                self.renderableEnemy.texture.changeAnimation(
                    CharacterAnimationType.walking, direction=Direction.right)
                self.myTimer.setTimer(0.1)

        elif self.state is IntroSceneState.leaveenemy:
            if self.myTimer.timeIsUp():
                self.myTimer.reset()
                self.renderableEnemy.advanceStep()
                self.renderableEnemy.coordinates.x += 1

            if (self.renderableEnemy.coordinates.x
                    == Config.columns):
                self.state = IntroSceneState.done


        elif self.state is IntroSceneState.done:
            pass
Ejemplo n.º 9
0
class RamboStateAttacking(State):
    name = "attacking"

    def __init__(self, brain):
        super().__init__(brain)
        self.cooldownTimer = Timer()
        self.attackingTimer = Timer()

    def on_enter(self):
        self.cooldownTimer.setTimer(0.5)
        self.attackingTimer.setTimer(4.0)

        playerEntity = EntityFinder.findPlayer(self.brain.owner.world)
        if playerEntity is None:
            return

        meRenderable = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.graphics.renderable.Renderable)
        meGroupId = self.brain.owner.world.component_for_entity(
            self.brain.owner.entity, system.groupid.GroupId)

        self.turnIfNecessary(playerEntity, meRenderable, meGroupId)

        # attack
        messaging.add(type=MessageType.EntityAttack,
                      groupId=meGroupId.getId(),
                      data=None)

    def turnIfNecessary(self, playerEntity, meRenderable, meGroupId):
        playerRenderable = self.brain.owner.world.component_for_entity(
            playerEntity, system.graphics.renderable.Renderable)
        x, y = AiHelper.getVectorToPlayer(source=meRenderable.coordinates,
                                          dest=playerRenderable.getLocation())

        if x > 0:
            playerDir = Direction.right
            cx = 1
        else:
            playerDir = Direction.left
            cx = -1

        if playerDir is not meRenderable.getDirection():
            directMessaging.add(
                groupId=meGroupId.getId(),
                type=DirectMessageType.moveEnemy,
                data={
                    'x': cx,
                    'y': 0,
                    'dontChangeDirection': False,
                    'updateTexture': False,
                    'force': False,
                },
            )

    def process(self, dt):
        self.cooldownTimer.advance(dt)
        self.attackingTimer.advance(dt)
        self.tryShooting()

    def tryShooting(self):
        if self.attackingTimer.timeIsUp():
            self.brain.pop()
            self.brain.push('standing')

        if self.cooldownTimer.timeIsUp():
            meRenderable = self.brain.owner.world.component_for_entity(
                self.brain.owner.entity, system.graphics.renderable.Renderable)
            locCenter = meRenderable.getAttackBaseLocation()
            messaging.add(type=MessageType.EmitParticleEffect,
                          data={
                              'location': locCenter,
                              'effectType': ParticleEffectType.bullet,
                              'damage': 50,
                              'byPlayer': False,
                              'direction': meRenderable.getDirection(),
                          })
            self.cooldownTimer.reset()
Ejemplo n.º 10
0
class Particle(object):
    def __init__(
        self,
        viewport =None,
        x :int =0,
        y :int =0,
        life :int =0,
        angle :float =0,
        speed :int =1,
        fadeout :bool =True,
        charType :int =0,
        byStep :bool =False,
        active :bool =False,
        damage :int =0,
        damageEveryStep :bool =False,
        byPlayer :bool =True,
    ):
        self.viewport = viewport
        self.movementTimer = Timer()
        self.init(
            x=x, y=y, life=life, angle=angle, speed=speed, fadeout=fadeout,
            byStep=byStep, charType=charType, active=active,
            damage=damage,
            damageEveryStep=damageEveryStep,
            byPlayer=byPlayer)


    def init(
        self,
        x :int =0,
        y :int =0,
        life :int =0,
        angle :float =0,
        speed :int =1,
        fadeout :bool =True,
        byStep :bool =False,
        charType :int =0,
        active :bool =False,
        damage :int =0,
        damageEveryStep :bool =False,
        byPlayer :bool =True,
        color =None,
    ):
        self.x = x
        self.y = y
        self.life = life
        self.originalLife = life
        self.angle = angle
        self.speed = speed
        self.fadeout = fadeout
        self.byStep = byStep
        self.charType = charType
        self.damage = damage
        self.damageEveryStep = damageEveryStep
        self.byPlayer = byPlayer

        self.angleInRadians = angle * math.pi / 180
        self.velocity = {
            'x': speed * math.cos(self.angleInRadians),
            'y': -speed * math.sin(self.angleInRadians)
        }

        self.color, self.attr = ColorPalette.getColorByColor(Color.brightmagenta)
        if color is not None:
            self.color = color[0]
            self.attr = color[1]

        self.setChar()

        self.rx = 0.0
        self.ry = 0.0

        self.movementTimer.setTimer(self.speed)
        self.active = active


    def __repr__(self):
        return "Particle {}/{}".format(
            self.x, self.y
        )


    def advance(self, dt):
        if self.active is False:
            return

        if self.byStep:
            return

        self.movementTimer.advance(dt)

        self.makeStep(dt)


    def fadeoutSetColor(self):
        if self.life > (self.originalLife / 2):
            self.attr = Screen.A_BOLD
        else:
            self.attr = Screen.A_NORMAL


    def setChar(self):
        if self.charType == 0:
            pass

        elif self.charType == 1:
            if self.life > ((self.originalLife / 3) * 2):
                self.char = 'O'
            elif self.life < ((self.originalLife / 3) * 1):
                self.char = '.'
            else:
                self.char = 'o'

        elif self.charType == 2:
            if self.life > ((self.originalLife / 3) * 2):
                self.char = '#'
            elif self.life < ((self.originalLife / 3) * 1):
                self.char = ':'
            else:
                self.char = '|'

        elif self.charType == 3:
            if self.life > ((self.originalLife / 3) * 2):
                self.char = 'O'
            elif self.life < ((self.originalLife / 3) * 1):
                self.char = '.'
            else:
                self.char = 'o'

        elif self.charType == 4:
            if self.life > ((self.originalLife / 3) * 2):
                self.char = '¦'
            elif self.life < ((self.originalLife / 3) * 1):
                self.char = '.'
            else:
                self.char = ':'

        elif self.charType == 5:
            self.char = '-'

        else:
            raise Exception("Invalid charType: {}".format(self.charType))


    def makeStep(self, dt, adjustLife=True):
        if self.life <= 0:
            self.active = False
            return

        if self.fadeout:
            self.fadeoutSetColor()
        self.setChar()

        if self.speed > 0:
            xFloat = self.velocity['x'] * (dt * 100) + self.rx
            yFloat = self.velocity['y'] * (dt * 100) + self.ry

            xChange = int(round(xFloat))
            yChange = int(round(yFloat))

            # accumulate pos we could not handle yet
            changeRestX = xFloat - xChange - self.rx
            changeRestY = yFloat - yChange - self.ry

            self.rx += changeRestX
            self.ry += changeRestY

            # change pos
            self.x += xChange
            self.y += yChange

            if (self.damageEveryStep and self.damage > 0
                    and (xChange != 0 or yChange != 0)):
                # hitLocations = [Coordinates(self.x, self.y)]
                hitLocations = []
                hitLocations.append(self)
                messaging.add(
                    type=MessageType.AttackAt,
                    data= {
                        'hitLocations': hitLocations,
                        'damage': self.damage,
                        'byPlayer': self.byPlayer,
                        'direction': Direction.none,
                        'knockback': False,
                        'stun': False,
                        'sourceRenderable': None,
                    }
                )

            if False:
                logging.info("Real change:  X: {}  Y: {}".format(xFloat, yFloat))
                logging.info("Round change: X: {}  Y: {}".format(xChange, yChange))
                logging.info("Change Rest:  X: {}  Y: {}".format(changeRestX, changeRestY))
                logging.info("New    Rest:  X: {}  Y: {}".format(self.rx, self.ry))
                logging.info("New    Pos:   X: {}  Y: {}".format(self.x, self.y))

        if adjustLife:
            self.life -= 1


    def draw(self):
        self.viewport.addstr(
            self.y, self.x, self.char, self.color, self.attr)


    def isActive(self):
        return self.active


    def setActive(self, active):
        self.active = active