Unity 游戏框架搭建 2019 (四十九) 关于发送事件的简单封装

在上一篇,我们在 MonoBehaviourSimplify 中集成了消息功能。而在做消息功能的过程中,又接触了对象池实现了一个非常简单版本。

今天呢我们在接着学习。

我们先回顾下 MonoBehaviourSimplify 中关于消息功能的使用方法。

注册消息,直接用 RegisterMsg,而注销则在 OnDestroy 的时候统一进行注销。
那么单独注销时候怎么办呢?这是第一个问题。

第二个问题是,发送消息,我们使用的是 MsgDispatcher.Send 这个方法。
和我们的注册消息的方法不是统一的。这是第二个问题。

第一个问题

第一个问题解决很简单,只要增加针对一个消息注销的方法就好了。
代码如下:

public partial class MonoBehaviourSimplify
{
	protected void UnRegisterMsg(string msgName)
	{
		var selectedRecords = mMsgRecorder.FindAll(recorder => recorder.Name == msgName);

		selectedRecords.ForEach(selectRecord =>
		{
			MsgDispatcher.UnRegister(selectRecord.Name, selectRecord.OnMsgReceived);
                mMsgRecorder.Remove(selectRecord);
			selectRecord.Recycle();
		});

		selectedRecords.Clear();
	}

	protected void UnRegisterMsg(string msgName, Action<object> onMsgReceived)
	{
		var selectedRecords = mMsgRecorder.FindAll(recorder => recorder.Name == msgName && recorder.OnMsgReceived == onMsgReceived);

		selectedRecords.ForEach(selectRecord =>
		{
			MsgDispatcher.UnRegister(selectRecord.Name, selectRecord.OnMsgReceived);
                mMsgRecorder.Remove(selectRecord);
			selectRecord.Recycle();
		});

		selectedRecords.Clear();
	}
}

FindAll 是一个查询方法,在 mMsgRecorder 内查询出所有符合条件的项。代码没有太大的难度。

不过在使用上要注意一下,如果是要重复注册并且需要注销的消息,最好是用成员方法来接收,而不是用委托接收,原因是如果是单独注销这类消息的时候,最好是用上边代码的第二种注销方法,用第一种的话,可能把当前脚本之前注册的同名消息都会注销掉。不过这是极少数的情况,一般笔者些项目根本用不到单独注销,而是全部交给了 OnDestroy 处理。

这样第一个问题算是解决了

接下来是我们第二个问题。

第二个问题:

第二个问题是 API 不统一的问题。这个问题要解决起来很简单。只要实现一个 Send 方法就好了,而 Send 中主要逻辑有 MsgDispatcher.Send 完成。

代码如下:

protected void SendMsg(string msgName, object data)
{
	MsgDispatcher.Send(msgName, data);
}

到此呢,我们的 API 就统一了。而第十四个示例也就算 OK 了。

全部代码如下:

using System;
using UnityEngine;

namespace QFramework
{
    public partial class MonoBehaviourSimplify
    {
        protected void UnRegisterMsg(string msgName)
        {
            var selectedRecords = mMsgRecorder.FindAll(recorder => recorder.Name == msgName);

            selectedRecords.ForEach(selectRecord =>
            {
                MsgDispatcher.UnRegister(selectRecord.Name, selectRecord.OnMsgReceived);
                mMsgRecorder.Remove(selectRecord);
            });

            selectedRecords.Clear();
        }

        protected void UnRegisterMsg(string msgName, Action<object> onMsgReceived)
        {
            var selectedRecords = mMsgRecorder.FindAll(recorder =>
                recorder.Name == msgName && recorder.OnMsgReceived == onMsgReceived);

            selectedRecords.ForEach(selectRecord =>
            {
                MsgDispatcher.UnRegister(selectRecord.Name, selectRecord.OnMsgReceived);
                mMsgRecorder.Remove(selectRecord);
            });

            selectedRecords.Clear();
        }

        protected void SendMsg(string msgName, object data)
        {
            MsgDispatcher.Send(msgName, data);
        }
    }

    public class UnifyAPIStyle : MonoBehaviourSimplify
    {
#if UNITY_EDITOR
        [UnityEditor.MenuItem("QFramework/14.统一 API 风格", false, 14)]
        private static void MenuClicked()
        {
            UnityEditor.EditorApplication.isPlaying = true;

            new GameObject("MsgReceiverObj")
                .AddComponent<UnifyAPIStyle>();
        }
#endif
        
        private void Awake()
        {
            RegisterMsg("OK", data =>
            {
                Debug.Log(data);
                
                UnRegisterMsg("OK");
            });    
        }

        private void Start()
        {
            SendMsg("OK","hello");
            SendMsg("OK","hello");   
        }

        protected override void OnBeforeDestroy()
        {
            
        }
    }
}

示例代码很简单,执行的结果如下图所示:
006tNc79gy1fzft6bnqe4j30wa0a8759.jpg

菜单栏如下图:
006tNc79gy1fzft6ektrqj30ke0hiwtf.jpg

目录如下图:
006tNc79gy1fzft6ir1uej30ie0ekmzc.jpg

这样我们的第十四个示例就完成了,可以进行一次导出了。

今天的内容就这些,我们下一篇再见,拜拜~

转载请注明地址:凉鞋的笔记:liangxiegame.com

更多内容

  • QFramework 地址:https://github.com/liangxiegame/QFramework

  • QQ 交流群:623597263

  • Unity 进阶小班

    • 主要训练内容:
      • 框架搭建训练(第一年)
      • 跟着案例学 Shader(第一年)
      • 副业的孵化(第二年、第三年)
    • 权益、授课形式等具体详情请查看《小班产品手册》:https://liangxiegame.com/master/intro
  • 关注公众号:liangxiegame 获取第一时间更新通知及更多的免费内容。

猜你喜欢

转载自blog.csdn.net/u010125551/article/details/106381814