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
