Unity3D EventMgr事件订阅与发布详解

前言

EventMgr事件订阅与发布机制是开发中常用的一种设计模式。本文将详细介绍Unity3D中EventMgr的使用方法,包括技术详解和代码实现。

对惹,这里有一 个游戏开发交流小组,希望大家可以点击进来一起交流一下开发经验呀!

一、事件订阅与发布简介

在游戏开发中,经常需要实现不同模块之间的通信,例如玩家行为触发了某个事件,需要通知其他模块做出相应的反应。传统的方法是直接调用其他模块的方法,但这种方式会导致模块之间的耦合度过高,不利于代码的维护和扩展。

事件订阅与发布机制可以有效解决这个问题,它将事件的发布者和订阅者解耦,让它们之间只通过事件的方式进行通信。发布者将事件发布到一个中心管理器中,订阅者通过订阅感兴趣的事件来接收通知。这种方式使得模块之间的依赖关系更加灵活,代码结构更加清晰。

二、EventMgr的实现

在Unity3D中,我们可以通过编写一个EventMgr类来实现事件订阅与发布机制。下面是一个简单的EventMgr类的实现:

复制代码
using System;
using System.Collections;
using System.Collections.Generic;

public class EventMgr
{
    private static EventMgr instance;
    private Dictionary<string, Action<object>> eventDict;

    public static EventMgr Instance
    {
        get
        {
            if (instance == null)
            {
                instance = new EventMgr();
            }
            return instance;
        }
    }

    private EventMgr()
    {
        eventDict = new Dictionary<string, Action<object>>();
    }

    public void Subscribe(string eventName, Action<object> callback)
    {
        if (!eventDict.ContainsKey(eventName))
        {
            eventDict[eventName] = callback;
        }
        else
        {
            eventDict[eventName] += callback;
        }
    }

    public void Unsubscribe(string eventName, Action<object> callback)
    {
        if (eventDict.ContainsKey(eventName))
        {
            eventDict[eventName] -= callback;
            if (eventDict[eventName] == null)
            {
                eventDict.Remove(eventName);
            }
        }
    }

    public void Publish(string eventName, object data)
    {
        if (eventDict.ContainsKey(eventName))
        {
            eventDict[eventName]?.Invoke(data);
        }
    }
}

在EventMgr类中,我们定义了一个静态的Instance属性,用来获取EventMgr的实例。在构造函数中初始化了一个eventDict字典,用来存储事件名和对应的回调函数。

Subscribe方法用来订阅事件,它接收两个参数:事件名和回调函数。如果事件名在eventDict中不存在,则直接将回调函数添加到eventDict中;如果事件名已经存在,则将回调函数追加到已有的回调函数链表中。

Unsubscribe方法用来取消订阅事件,它接收两个参数:事件名和回调函数。如果事件名在eventDict中存在,则从对应的回调函数链表中移除指定的回调函数,并且如果链表为空,则将事件名从eventDict中移除。

Publish方法用来发布事件,它接收两个参数:事件名和传递的数据。如果事件名在eventDict中存在,则依次调用对应的回调函数,并将数据传递给它们。

三、EventMgr的使用示例

下面我们通过一个简单的示例来演示EventMgr的使用方法。假设我们有两个模块:Player和UI,Player模块中的玩家行为会触发事件,UI模块需要根据事件做出相应的反应。

首先,我们在Player模块中定义一个Player类,用来模拟玩家的行为:

复制代码
using UnityEngine;

public class Player : MonoBehaviour
{
    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            EventMgr.Instance.Publish("PlayerJump", null);
        }
    }
}

在Player类中,我们监听玩家按下空格键的事件,并通过EventMgr发布"PlayerJump"事件。

然后,我们在UI模块中定义一个UI类,用来订阅"PlayerJump"事件并做出反应:

复制代码
using UnityEngine;

public class UI : MonoBehaviour
{
    private void Start()
    {
        EventMgr.Instance.Subscribe("PlayerJump", OnPlayerJump);
    }

    private void OnPlayerJump(object data)
    {
        Debug.Log("Player jumped!");
    }

    private void OnDestroy()
    {
        EventMgr.Instance.Unsubscribe("PlayerJump", OnPlayerJump);
    }
}

在UI类中,我们在Start方法中订阅"PlayerJump"事件,并指定回调函数为OnPlayerJump。在OnPlayerJump方法中,我们输出一条日志表示玩家跳跃了。在OnDestroy方法中,我们取消订阅"PlayerJump"事件。

通过以上代码,我们实现了Player模块和UI模块之间的通信,它们之间的耦合度很低,代码结构更加清晰。

四、总结

EventMgr是一种常用的设计模式,它可以有效解决模块之间的通信问题,使得代码结构更加清晰和灵活。在Unity3D中,我们可以通过编写一个简单的EventMgr类来实现事件订阅与发布机制。通过本文的介绍和示例,希望读者能够更好地理解EventMgr的使用方法,并在实际项目中应用它来提高代码的可维护性和扩展性。

更多教学视频

Unity3D​www.bycwedu.com/promotion_channels/2146264125

相关推荐
码智社2 小时前
AES加密原理详解及Java实现加解密实战
java·开发语言
AI云海2 小时前
python 列表、元组、集合和字典
开发语言·python
萧瑟余晖3 小时前
JDK 26 新特性详解
java·开发语言
马优晨4 小时前
Freemarker 完整讲解(后端 Java 模板引擎)
java·开发语言·freemarker·freemarker 完整讲解·freemarker模板引擎
人邮异步社区6 小时前
怎么把C语言学到精通?
c语言·开发语言
心平气和量大福大6 小时前
C#-WPF-控件-TextBox 数据绑定
开发语言·c#·wpf
ttwuai7 小时前
Cursor 生成 CRUD 后,Go 后台接口别只测 200:JWT、RBAC 和 tenant_id 怎么验
开发语言·后端·golang
এ慕ོ冬℘゜7 小时前
前端基础:什么是时间戳?JS获取时间戳三种方法与实战用途
开发语言·前端·javascript
执明wa7 小时前
LayoutInflater详解: XML是如何变成View的?
android·xml·开发语言·android studio
一次旅行7 小时前
Python+大模型端到端自动化日报系统
开发语言·python·自动化