您当前的位置: 首页 >  unity

幻世界

暂无认证

  • 0浏览

    0关注

    237博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

【Unity开发小技巧】FMS有限状态机详解

幻世界 发布时间:2021-09-01 11:05:08 ,浏览量:0

欢迎加入Unity业内qq交流群:956187480 qq扫描二维码加群

 在实际开发中很多时候对某类别的对象都需要有多种状态的管理和切换,这个时候我们就可以引入FMS状态机概念,有限状态机主要有三要素:状态的切换跳转,状态跳转的判断,以及在具体某状态下的行为执行,下面就带着大家来制作一个简易状态机。

1.定义状态接口

这个接口里面定义一些接口方法成员,主要是让其具体的状态子类继承并实现这些方法,这里我们定义了Enter进入某状态,执行某状态,重置某状态,退出某状态;这些方法是可以自定义的没有固定格式,甚至只定义一个enter进入也可以,具体实现还是要在具体状态类里面实现

public interface IState{
    void Enter();
    void Excute();
    void Reset();
    void Exit();
}
2.创建状态基类BaseState

BaseState是各种状态的基类,实现Istate的所有接口成员方法

IState {  
    public BaseState( ){}
    public virtual void Enter(){}
    public virtual void Excute(){}
    public virtual void Exit(){}
    public virtual void Reset(){}
}
3.创建各种具体的状态类

比如AttackState

public class AttackState : BaseState {
   
    public override void Enter()
    {
        base.Enter();
        Debug.Log("进入攻击模式......");
    }
    public override void Excute()
    {
        base.Excute();
        Debug.Log("执行攻击模式......");
    }
    public override void Exit()
    {
        base.Exit();
        Debug.Log("退出攻击模式......");
    }
4.创建状态管理器

管理器主要作用就是管理和切换状态

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class StateType : MonoBehaviour
{
    //初始
    public const int DEFULT = 0;
    //待机
    public const int IDLE = 1;
    //移动
    public const int MOVE = 2;
    //跑开
    public const int RUNAWAY = 3;
    //攻击
    public const int ATTACK = 4;
}
public delegate void CallBack();

public class StateManager : BaseManager {
    public IState _currentState;
    public int _currentStateType;
    protected Dictionary _statePool;
    protected override void Awake()
    {
        base.Awake();
        _statePool = new Dictionary();
        ChangeState(StateType.IDLE);

    }

    protected override void Update()
    {
        base.Update();
        if (Input.GetKeyDown(KeyCode.C))
        {
            if (_currentStateType + 1>4)
            {
                _currentStateType = 0;
            }
            ChangeState(_currentStateType+1);
        }
    }
    public virtual void ChangeState(int stateType, CallBack callBack=null)
    {
        if (_currentState != null)
        {
            if (_currentStateType == stateType)
            {
                _currentState.Reset();
                return;
            }
            else
            {
                _currentState.Exit();
            }
        }
        if (_statePool.ContainsKey(stateType))
        {
            _currentState = _statePool[stateType];
        }
        else
        {
            _currentState = CreateState(stateType);
            _statePool[stateType] = _currentState;
        }
        _currentStateType = stateType;
        Debug.Log(_currentStateType);
        _currentState.Enter();
        _currentState.Excute();
        callBack?.Invoke();
    }

    public static BaseState CreateState(int state)
    {
        BaseState product = null;
        switch (state)
        {
            case StateType.IDLE:
                {
                    product = new IdleState();
                    break;
                }
            case StateType.MOVE:
                {
                    product = new MoveState();
                    break;
                }
            case StateType.ATTACK:
                {
                    product = new AttackState();
                    break;
                }
            case StateType.RUNAWAY:
                {
                    product = new RunState();
                    break;
                }

            default:
                {
                    Debug.LogWarning("not exist state:" + state);
                    break;
                }
        }
        return product;
    }
}

欢迎加入Unity业内qq交流群:956187480

qq扫描二维码加群

关注
打赏
1660704426
查看更多评论
立即登录/注册

微信扫码登录

0.0365s