Unity3D StateMachine扩展优化

1.Unity3D StateMachine正常的状态下是每个动做结束后没有回调,所以有时候我们要判断当前不是哪一个动作是要做什么的,如下:


public class TestJS : MonoBehaviour {
    public Animator                      _animator;
    private AnimatorTransitionInfo _changeAnimator;

    void Update () {
        _changeAnimator = _animator.GetAnimatorTransitionInfo(0);
        if (!_changeAnimator.IsName("xxx"))
        {
            //Do Sth 
        }
    }
}

2.这时我们就可以优化:对他们每次,进入结束弄一个回调=>状态改变:
这里写图片描述
在AnimationStateMachine里面写结束,进入的回调。

using UnityEngine;
using System.Collections;
using UnityEngine.Experimental.Director;

public class AnimationStateMachine : StateMachineBehaviour
{
    public System.Action<int> EnterStateCallback;
    public System.Action<int> ExitStateCallback;

    public override void OnStateEnter(Animator animator, AnimatorStateInfo stateInfo, int layerIndex)
    {
        base.OnStateEnter(animator, stateInfo, layerIndex);
        if (EnterStateCallback != null)
        {
            EnterStateCallback(stateInfo.fullPathHash);
        }
    }

    public override void OnStateMachineEnter(Animator animator, int stateMachinePathHash)
    {
        base.OnStateMachineEnter(animator, stateMachinePathHash);
        if (EnterStateCallback != null)
        {
            EnterStateCallback(stateMachinePathHash);
        }
    }

    public override void OnStateMachineExit(Animator animator, int stateMachinePathHash)
    {
        base.OnStateMachineExit(animator, stateMachinePathHash);
        if (ExitStateCallback != null)
        {
            ExitStateCallback(stateMachinePathHash);
        }
    }

    public override void OnStateExit(Animator animator, AnimatorStateInfo stateInfo, int layerIndex)
    {
        base.OnStateExit(animator, stateInfo, layerIndex);
        if (ExitStateCallback != null)
        {
            ExitStateCallback(stateInfo.fullPathHash);
        }
    }
}

3.这些回调还没有被初始化,此时在应用这个AnimatorControl的物体上添加脚本进行初始化:

using UnityEngine;
using System.Collections;

public class ParkourPlayerAnimatorController : MonoBehaviour
{
    //引用
    private ParkourPlayerAnimationHash animHash;

    private int random;

    public Animator flyRobot;
    [SerializeField]
    private Animator playerAnimator;
    public ParkourAnimationStates CurrentAnimationState { get; private set; }

    // Use this for initialization
    void Awake()
    {
        random = Random.Range(0,3);
        animHash = GetComponent<ParkourPlayerAnimationHash>();
        //最重要的在这边初始化回调函数因为结束回调暂时还可以省略,所以只是初始化进入某个动画的回调:
        AnimationStateMachine[] _animStateMachine =
        playerAnimator.GetBehaviours<AnimationStateMachine>();
        for (int i = 0; i < _animStateMachine.Length; i++)
        {
            _animStateMachine[i].EnterStateCallback = SetCurrentAnimationState;
        }
    }

    // Update is called once per frame
    void Update()
    {

    }
    //可以保存一个CurrentAnimationState 的状态而不用像1.在Update一直判断。
    void SetCurrentAnimationState(int hashName)
    {
        if (hashName == animHash.RunState)
        {
            CurrentAnimationState = ParkourAnimationStates.Run;
        }
        else if (hashName == animHash.RollState)
        {
            CurrentAnimationState = ParkourAnimationStates.Roll;
        }
        else if (hashName == animHash.JumpState || hashName == animHash.JumpState1 || hashName == animHash.JumpState2)
        {
            CurrentAnimationState = ParkourAnimationStates.Jump;
        }
        else if (hashName == animHash.MoveSideState)
        {
            CurrentAnimationState = ParkourAnimationStates.MoveSide;
        }
        else if (hashName == animHash.FallState)
        {
            CurrentAnimationState = ParkourAnimationStates.Fall;
        }
        else if (hashName == animHash.FlyTrigger)
        {
            CurrentAnimationState = ParkourAnimationStates.Fly;
        }
    }

    public void Run()
    {
        playerAnimator.SetBool(animHash.RunBool, true);
    }

    public void Stop()
    {
        playerAnimator.SetBool(animHash.RunBool, false);
    }

    public void PlayJump()
    {

        switch (random % 3)
        {
            case 0:
                playerAnimator.SetTrigger(animHash.JumpTrigger);
                break;
            case 1:
                playerAnimator.SetTrigger(animHash.JumpTrigger1);
                break;
            case 2:
                playerAnimator.SetTrigger(animHash.JumpTrigger2);
                break;
        }
        random++;
    }

    public void PlayRoll()
    {
        playerAnimator.SetTrigger(animHash.RollTrigger);
    }

    public void PlayMoveSideLeft()
    {
        playerAnimator.SetTrigger(animHash.MoveSideLeftTrigger);
    }

    public void PlayMoveSideRight()
    {
        playerAnimator.SetTrigger(animHash.MoveSideRightTrigger);
    }

    public void PlayFly()
    {
        playerAnimator.SetTrigger(animHash.FlyTrigger);
    }

    public void PlayFall()
    {
        playerAnimator.SetTrigger(animHash.FallTrigger);
    }

    public void PlayCatchRob()
    {
        playerAnimator.SetTrigger("Catch");
    }

    public void PlayFlyRobot()
    {
        playerAnimator.SetTrigger(animHash.FlyTrigger);
    }
}
  1. 在3中有一个引用到animHash判断每个动画SetCurrentAnimationState(int hashName)是否相等,来记录
using UnityEngine;
using System.Collections;

public class ParkourPlayerAnimationHash : MonoBehaviour
{
    public int IdleState { get; private set; }
    public int RunState { get; private set; }
    public int JumpState { get; private set; }
    public int JumpState1 { get; private set; }
    public int JumpState2 { get; private set; }
    public int MoveSideState { get; private set; }
    public int RollState { get; private set; }
    public int FallState { get; private set; }

    public int RunBool { get; private set; }

    public int JumpTrigger { get; private set; }
    public int JumpTrigger1 { get; private set;}
    public int JumpTrigger2 { get; private set;}

    public int RollTrigger { get; private set; }
    public int FallTrigger { get; private set; }
    public int FlyTrigger  { get; private set; } 
    public int MoveSideLeftTrigger { get; private set; }
    public int MoveSideRightTrigger { get; private set; }


    // Use this for initialization
    void Awake()
    {
        IdleState = Animator.StringToHash("Base Layer.待机");
        RunState = Animator.StringToHash("Base Layer.跑步");
        JumpState = Animator.StringToHash("Base Layer.跳");
        JumpState1 = Animator.StringToHash("Base Layer.跳1");
        JumpState2 = Animator.StringToHash("Base Layer.跳2");
        MoveSideState = Animator.StringToHash("Base Layer.侧移");
        RollState = Animator.StringToHash("Base Layer.下滑");
        FallState = Animator.StringToHash("Base Layer.摔倒");

        FlyTrigger = Animator.StringToHash("Fly");
        RunBool = Animator.StringToHash("Run");
        JumpTrigger = Animator.StringToHash("Jump");
        JumpTrigger1 = Animator.StringToHash("Jump1");
        JumpTrigger2 = Animator.StringToHash("Jump2");
        RollTrigger = Animator.StringToHash("Roll");
        FallTrigger = Animator.StringToHash("Fall");
        MoveSideLeftTrigger = Animator.StringToHash("MoveSideLeft");
        MoveSideRightTrigger = Animator.StringToHash("MoveSideRight");
    }
}

这里写图片描述


All our dreams can come true, if we have thecourage to pursue them.
我们所有的梦想都可以成真,只要我们有勇气去追求它们。
————沃尔特·迪斯尼

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值