Example #1
0
    public void SkeletonStateMachine()
    {
        switch (ActiveState)
        {
        case SkeletonState.ATTACK:
        {
            if (!inAttack && anim.GetBool("AttackEnded"))         //start attack
            {
                inAttack = true;
                anim.SetBool("Attack", true);
                if (boostCoroutine != null)
                {
                    StopCoroutine(boostCoroutine);
                }
                nav.angularSpeed = angularSpeedBase * 0.75f;         //we want that the enemy spins to the enemy position, but more slow
                //this change will reverted at the end of animation
            }
            else
            {
                if (inAttack && anim.GetBool("AttackEnded"))              //attack ended
                {
                    boostCoroutine = StartCoroutine(BoostAngularSpeed()); //we boost the speed when the enemy finish the atack
                    inAttack       = false;
                    SetAttackID(anim.GetInteger("AttackID"));
                    nextAtack   = attackList.GetNextAttack();
                    ActiveState = SkeletonState.CHASE;
                    nav.SetDestination(target);
                }
                else         //in attack anim
                {
                    FaceObjective(target);
                    SetIsAttacking(anim.GetBool("CalculateDamage"));
                    if (weaponHitbox.GetHitted() && GetIsAttacking())
                    {
                        if (GetAttackID() != anim.GetInteger("AttackID"))         //if this enemy dont has attack yet
                        {
                            if (weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>() != null)
                            {
                                weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>().ChangeStats(CombatStatsType.HP, -GetDamage());        //do damage
                                SetAttackID(anim.GetInteger("AttackID"));
                                weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>().SetEnemyLastAttackID(GetAttackID());
                            }
                        }
                        else
                        {
                            if (GetAttackID() != weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>().GetEnemyLastAttackID())
                            {
                                if (weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>() != null)
                                {
                                    weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>().ChangeStats(CombatStatsType.HP, -GetDamage());
                                    weaponHitbox.GetHittedEnemy().GetComponentInParent <PlayerCombat>().SetEnemyLastAttackID(GetAttackID());
                                }

                                //if we hit 2 enemies we have this case
                            }
                            else
                            {
                                //El problema esta es que si golpeamos a más de un enemigo y por casualidad tiene el segundo (o posteriores)
                                //enemigos que reciben el golpe tienen como ultima id del golpe la id de ataque este enemigo, el sistema se cree
                                //que este enemigo ya ha sido golpeado. En el juego actualmente este error no puede pasar, pero si por ejemplo
                                //hacemos que el jugador tenga una mascota o invocacion, el error si ocurrira, para solucionarlo podriamos poner
                                //una lista en cada combatiente, con la id del ser, y la ultima id del hit, de esta forma arreglariamos el problema
                                //
                            }
                        }
                    }
                }
            }

            break;
        }

        case SkeletonState.CHASE:
        {
            nav.SetDestination(target);
            break;
        }

        case SkeletonState.HOLD:
        {
            if (!FaceAndCheckObjective(hold.DirectionToFace(), 2f))         //This will be better if we check once per second instead 1 per frame
            {
                ActiveState = SkeletonState.RETURNING_TO_POSITION;
            }

            break;
        }

        case SkeletonState.PATROL:
        {
            if (transform.position.x <= target.x + 0.4f && transform.position.x >= target.x - 0.4f && transform.position.z <= target.z + 0.4f && transform.position.z >= target.z - 0.4f)
            {
                target = patrol.GetNewWaipoint(target);
                nav.SetDestination(target);
            }
            break;
        }

        case SkeletonState.PLAYER_LOST:
        {
            if (transform.position.x <= target.x + 0.4f && transform.position.x >= target.x - 0.4f && transform.position.z <= target.z + 0.4f && transform.position.z >= target.z - 0.4f)
            {
                if (!chase.GetWaiting())
                {
                    chase.InLastKnowPosition();
                }
                if (chase.GetEndChase())
                {
                    if (staticEnemy)
                    {
                        target = hold.ReturnToPosition();
                        nav.SetDestination(target);
                        ActiveState = SkeletonState.RETURNING_TO_POSITION;
                    }
                    else
                    {
                        target = patrol.GetClosestWaipoint(transform.position);
                        nav.SetDestination(target);
                        ActiveState = SkeletonState.PATROL;
                    }
                }
            }
            break;
        }

        case SkeletonState.RETURNING_TO_POSITION:
        {
            if (transform.position.x <= target.x + 0.4f && transform.position.x >= target.x - 0.4f && transform.position.z <= target.z + 0.4f && transform.position.z >= target.z - 0.4f)
            {
                if (FaceAndCheckObjective(hold.DirectionToFace(), 2f))
                {
                    ActiveState = SkeletonState.HOLD;
                }
                else
                {
                    FaceObjective(hold.DirectionToFace());
                }
            }
            break;
        }

        case SkeletonState.DIED:
        {
            break;
        }
        }
    }