消息分发机制,实现战场与UI通信功能

1.首先是单例模式通用类

using UnityEngine;

public class Singleton<T> where T : new()
{
protected static T _Instance = default(T);

public static T Instance
{
get
{
if (_Instance == null)
{
_Instance = new T();
}
return _Instance;
}
}
}

public class SingletonMonobehaviour<T> : MonoBehaviour where T : SingletonMonobehaviour<T>
{
private static T _Instance;

public static T Instance
{
get
{
if (_Instance == null)
{
_Instance = (T)GameObject.FindObjectOfType(typeof(T));
if (_Instance == null)
{
GameObject instanceObject = new GameObject(typeof(T).Name);
_Instance = instanceObject.AddComponent<T>();
}
_Instance.OnInstance();
}
return _Instance;
}
}
public virtual void OnInstance()
{ }
}

2// 全局消息派发机制管理器
public class EventDispatchManager : Singleton<EventDispatchManager>
{
private readonly EventDispatcher m_globalDispatcher = new EventDispatcher();

public void AddGlobalEvent(NtfMessageTypeEnum typeEnum, EventDispatcher.FuncCallback func)
{
m_globalDispatcher.AddEvent(typeEnum, func);
}

public void RemoveGlobalEvent(NtfMessageTypeEnum typeEnum, EventDispatcher.FuncCallback func)
{
m_globalDispatcher.RemoveEvent(typeEnum, func);
}

public void DispatchGlobalMessage(NtfMessageTypeEnum typeEnum, params object[] args)
{
m_globalDispatcher.DispatchMessage(typeEnum, args);
}
}

3

// 消息派发器,如果有需要小范围的派发,就自己new一个用就好了
public class EventDispatcher
{
public delegate void FuncCallback(NtfMessageTypeEnum typeEnum, params object[] args);

private NtfMessageTypeEnum m_typeEnum = NtfMessageTypeEnum.None;
private Dictionary<NtfMessageTypeEnum, List<FuncCallback>> m_functionDictionary = new Dictionary<NtfMessageTypeEnum, List<FuncCallback>>();
private Dictionary<NtfMessageTypeEnum, List<FuncCallback>> m_tempDictionary = new Dictionary<NtfMessageTypeEnum, List<FuncCallback>>();

// 注册消息
public void AddEvent(NtfMessageTypeEnum typeEnum, FuncCallback function)
{
if (!m_functionDictionary.ContainsKey(typeEnum))
{
m_functionDictionary.Add(typeEnum, new List<FuncCallback>());
}
m_functionDictionary[typeEnum].Add(function);
}

// 删除消息
public void RemoveEvent(NtfMessageTypeEnum typeEnum, FuncCallback function)
{
if (m_functionDictionary.ContainsKey(typeEnum))
{
// 如果当前要删除的消息正好是正在派发的消息类型,为了避免迭代器失效,先保存至临时空间,等该条消息派发完毕再删除
if (typeEnum == m_typeEnum)
{
if (!m_tempDictionary.ContainsKey(typeEnum))
m_functionDictionary[typeEnum] = new List<FuncCallback>();
m_tempDictionary[typeEnum].Add(function);
}
else
{
m_functionDictionary[typeEnum].Remove(function);
if (m_functionDictionary[typeEnum].Count == 0)
m_functionDictionary.Remove(typeEnum);
}
}
}

// 消息派发
// 仅限unity单线程这么使用,如果是多线程的情况,该方法不支持
public void DispatchMessage(NtfMessageTypeEnum typeEnum, params object[] args)
{
m_typeEnum = typeEnum;
if (m_functionDictionary.ContainsKey(typeEnum) && m_functionDictionary[typeEnum].Count > 0)
{
foreach (var function in m_functionDictionary[typeEnum])
{
try
{
function(typeEnum, args);
}
catch (Exception e)
{
Debug.LogError("Error in dispatching message: " + e.Message);
}
}
}

// 本次派发结束之后,删除临时消息
if (m_tempDictionary.ContainsKey(typeEnum))
{
foreach (var function in m_tempDictionary[typeEnum])
{
if (m_functionDictionary.ContainsKey(typeEnum))
{
m_functionDictionary[typeEnum].Remove(function);
if (m_functionDictionary[typeEnum].Count == 0)
m_functionDictionary.Remove(typeEnum);
}
}
m_tempDictionary.Remove(typeEnum);
}

m_typeEnum = NtfMessageTypeEnum.None;
}
}

原文地址:https://www.cnblogs.com/xwwFrank/p/6889186.html