Home | History | Annotate | Download | only in replicaisland
      1 /*
      2  * Copyright (C) 2010 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.replica.replicaisland;
     18 
     19 /**
     20  * A general-purpose animation selection system for animating enemy characters.  Most enemy
     21  * characters behave similarly, so this code tries to decide which animation bets fits their current
     22  * state.  Other code (such as enemy AI) may move these characters around and change the current
     23  * ActionType, which will result in this code figuring out which sequence of animations is best to
     24  * play.
     25  */
     26 public class EnemyAnimationComponent extends GameComponent {
     27 
     28     public enum EnemyAnimations {
     29         IDLE,
     30         MOVE,
     31         ATTACK,
     32         HIDDEN,
     33         APPEAR,
     34     }
     35 
     36     private enum AnimationState {
     37         IDLING,
     38         MOVING,
     39         HIDING,
     40         APPEARING,
     41         ATTACKING
     42     }
     43 
     44     private SpriteComponent mSprite;
     45     private AnimationState mState;
     46     private boolean mFacePlayer;
     47 
     48     public EnemyAnimationComponent() {
     49         super();
     50         setPhase(ComponentPhases.ANIMATION.ordinal());
     51         reset();
     52     }
     53 
     54     @Override
     55     public void reset() {
     56         mState = AnimationState.IDLING;
     57         mFacePlayer = false;
     58         mSprite = null;
     59     }
     60 
     61     @Override
     62     public void update(float timeDelta, BaseObject parent) {
     63         if (mSprite != null) {
     64             GameObject parentObject = (GameObject) parent;
     65             final float velocityX = parentObject.getVelocity().x;
     66 
     67             GameObject.ActionType currentAction = parentObject.getCurrentAction();
     68 
     69             switch(mState) {
     70                 case IDLING:
     71                     mSprite.playAnimation(EnemyAnimations.IDLE.ordinal());
     72                     if (mFacePlayer) {
     73                         facePlayer(parentObject);
     74                     }
     75 
     76                     if (currentAction == GameObject.ActionType.ATTACK) {
     77                         mState = AnimationState.ATTACKING;
     78                     } else if (currentAction == GameObject.ActionType.HIDE) {
     79                         mState = AnimationState.HIDING;
     80                     } else if (Math.abs(velocityX) > 0.0f) {
     81                         mState = AnimationState.MOVING;
     82                     }
     83 
     84                     break;
     85 
     86                 case MOVING:
     87                     mSprite.playAnimation(EnemyAnimations.MOVE.ordinal());
     88                     final float targetVelocityX = parentObject.getTargetVelocity().x;
     89 
     90                     if (!Utils.close(velocityX, 0.0f)) {
     91                         if (velocityX < 0.0f && targetVelocityX < 0.0f) {
     92                             parentObject.facingDirection.x = -1.0f;
     93                         } else if (velocityX > 0.0f && targetVelocityX > 0.0f) {
     94                             parentObject.facingDirection.x = 1.0f;
     95                         }
     96                     }
     97                     if (currentAction == GameObject.ActionType.ATTACK) {
     98                         mState = AnimationState.ATTACKING;
     99                     } else if (currentAction == GameObject.ActionType.HIDE) {
    100                         mState = AnimationState.HIDING;
    101                     } else if (Math.abs(velocityX) == 0.0f) {
    102                         mState = AnimationState.IDLING;
    103                     }
    104                     break;
    105                 case ATTACKING:
    106                     mSprite.playAnimation(EnemyAnimations.ATTACK.ordinal());
    107                     if (currentAction != GameObject.ActionType.ATTACK
    108                             && mSprite.animationFinished()) {
    109                         mState = AnimationState.IDLING;
    110                     }
    111                     break;
    112                 case HIDING:
    113                     mSprite.playAnimation(EnemyAnimations.HIDDEN.ordinal());
    114                     if (currentAction != GameObject.ActionType.HIDE) {
    115                         mState = AnimationState.APPEARING;
    116                     }
    117                     break;
    118                 case APPEARING:
    119                     if (mFacePlayer) {
    120                         facePlayer(parentObject);
    121                     }
    122 
    123                     mSprite.playAnimation(EnemyAnimations.APPEAR.ordinal());
    124                     if (mSprite.animationFinished()) {
    125                         mState = AnimationState.IDLING;
    126                     }
    127                     break;
    128 
    129             }
    130 
    131 
    132         }
    133     }
    134 
    135     private void facePlayer(GameObject parentObject) {
    136         GameObjectManager manager = sSystemRegistry.gameObjectManager;
    137         if (manager != null) {
    138             GameObject player = manager.getPlayer();
    139             if (player != null) {
    140                 if (player.getPosition().x < parentObject.getPosition().x) {
    141                     parentObject.facingDirection.x = -1.0f;
    142                 } else {
    143                     parentObject.facingDirection.x = 1.0f;
    144                 }
    145             }
    146         }
    147     }
    148 
    149     public void setSprite(SpriteComponent sprite) {
    150         mSprite = sprite;
    151     }
    152 
    153     public void setFacePlayer(boolean facePlayer) {
    154         mFacePlayer = facePlayer;
    155     }
    156 }
    157