Unity3D设计模式之命令者模式
发表于2018-07-12
设计模式分很多种,大家或多或少的都有些了解,但真的说到掌握,可能很多人都没什么信心,为此为了加深大家对设计模式的理解,下面就给大家介绍下设计模式中的命令者模式。
命令者模式的定义
“行为请求者”与“行为实现者”通常呈现一种“紧耦合”。但在某些场合,比如要对行为进行“记录、撤销/重做、事务”等处理,这种无法抵御变化的紧耦合是不合适的。在这种情况下,如何将“行为请求者”与“行为实现者”解耦?将一组行为抽象为对象,实现二者之间的松耦合。这就是命令模式。
命令者模式的原理
命令者模式举例—>FSM状态机
首先分析:共同的特性
1.切换到另一种状态时都要先退出当前状态
2.进入要切换的状态
3.每一帧 处理当前的状态涉及的逻辑
接下来上代码
using System.Collections; using System.Collections.Generic; using UnityEngine; //抽象出的父类 public abstract class FSMBase { protected Animator animator; public FSMBase(Animator temAnimator) { animator = temAnimator; } //进入状态 public abstract void OnEnter(); //当前状态 public abstract void Update(); //离开状态 public abstract void OnLeave(); } //管理类 public class FSMManager { /// <summary> /// 当前添加的状态数 /// </summary> byte currentIndex; /// <summary> /// 当前的状态值 /// </summary> int currentState; //将所有的动画管理起来 FSMBase[] allState; /// <summary> /// count当前动画的数量 /// </summary> /// <param name="count"></param> public FSMManager(int count) { allState = new FSMBase[count]; currentIndex = 0; currentState = -1; } /// <summary> /// 将所有的状态添加到数组 /// </summary> /// <param name="temBase"></param> public void AddState(FSMBase temBase) { if (currentIndex < allState.Length) { allState[currentIndex] = temBase; currentIndex++; } } /// <summary> /// 切换到某一个状态 /// </summary> /// <param name="index"></param> public void ChangeState(byte index) { //判断当前状态是否等于要切换的状态 if (currentState != index) { if (currentState != -1) { //退出当前状态 allState[currentState].OnLeave(); } //切换到目标状态 allState[index].OnEnter(); //记录当前状态 currentState = index; } } public void Update() { if (currentState != -1) { allState[currentState].Update(); } } } public class FSM : MonoBehaviour { // Use this for initialization void Start () { } // Update is called once per frame void Update () { } }
using System; using System.Collections; using System.Collections.Generic; using UnityEngine; public class PlayerIdle : FSMBase { public PlayerIdle(Animator temAnimator) : base(temAnimator) { } public override void OnEnter() { animator.SetInteger("StateIndex", 0); } public override void OnLeave() { } public override void Update() { } } public class PlayerWalk : FSMBase { public PlayerWalk(Animator temAnimator) : base(temAnimator) { } public override void OnEnter() { animator.SetInteger("StateIndex", 1); } public override void OnLeave() { } public override void Update() { } } public class PlayerRun : FSMBase { public PlayerRun(Animator temAnimator) : base(temAnimator) { } public override void OnEnter() { animator.SetInteger("StateIndex", 2); } public override void OnLeave() { } public override void Update() { } } public class PlayerAttack : FSMBase { public PlayerAttack(Animator temAnimator) : base(temAnimator) { } public override void OnEnter() { animator.SetInteger("StateIndex", 3); } public override void OnLeave() { } public override void Update() { } } public class PlayerAnimation0 : MonoBehaviour { FSMManager animatorManager; public enum AnimatorState { Idle, Walk, Run, Attack, MaxValue } // Use this for initialization void Start () { animatorManager = new FSMManager((int)AnimatorState.MaxValue); Animator ani = gameObject.GetComponent<Animator>(); PlayerIdle idle = new PlayerIdle(ani); animatorManager.AddState(idle); PlayerWalk walk = new PlayerWalk(ani); animatorManager.AddState(walk); PlayerRun run = new PlayerRun(ani); animatorManager.AddState(run); PlayerAttack attack = new PlayerAttack(ani); animatorManager.AddState(attack); } // Update is called once per frame void Update () { if (Input.GetKeyDown(KeyCode.A)) { ChangeState((int)AnimatorState.Attack); } } public void ChangeState(byte index) { animatorManager.ChangeState(index); } }
优点
1.两个状态之间的耦合性比较低
2.可扩展性比较强
来自:https://blog.csdn.net/battletiger/article/details/78020310