C#、Unity支持泛型T的EventManager 事件管理器
介绍
用子类继承基类的方式,强制转换,减少装箱拆箱。缺点是不能清楚知道事件名对应几个变量,需要自己定义的时候留意一下,如果有更好的方式可以交流一下。
单例
public class Singleton<T> where T : class, new()
{
private static T instance;
private static readonly object syslock = new object();
public static T Instance
{
get
{
if (instance == null)
{
//线程安全
lock (syslock)
{
if (instance == null)
{
instance = new T();
}
}
}
return instance;
}
}
}
EventManager源码
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class EventManager : Singleton<EventManager>
{
public delegate void EventDelegate();
public delegate void EventDelegate<T>(T t);
public delegate void EventDelegate<T, U>(T t, U u);
public delegate void EventDelegate<T, U, V>(T t, U u, V v);
private Dictionary<string, Delegate> eventListeners = new Dictionary<string, Delegate>();
public void RegisterEvent(string eventName, EventDelegate handler)
{
if (!eventListeners.ContainsKey(eventName))
{
eventListeners[eventName] = handler;
}
}
public void RegisterEvent<T>(string eventName, EventDelegate<T> handler)
{
if (!eventListeners.ContainsKey(eventName))
{
eventListeners[eventName] = handler;
}
}
public void RegisterEvent<T, U>(string eventName, EventDelegate<T, U> handler)
{
if (!eventListeners.ContainsKey(eventName))
{
eventListeners[eventName] = handler;
}
}
public void RegisterEvent<T, U, V>(string eventName, EventDelegate<T, U, V> handler)
{
if (!eventListeners.ContainsKey(eventName))
{
eventListeners[eventName] = handler;
}
}
public void RemoveEvent(string eventName)
{
if (eventListeners.ContainsKey(eventName))
{
eventListeners.Remove(eventName);
}
}
public void RemoveEvent<T>(string eventName)
{
if (eventListeners.ContainsKey(eventName))
{
eventListeners.Remove(eventName);
}
}
public void RemoveEvent<T, U>(string eventName)
{
if (eventListeners.ContainsKey(eventName))
{
eventListeners.Remove(eventName);
}
}
public void RemoveEvent<T, U, V>(string eventName)
{
if (eventListeners.ContainsKey(eventName))
{
eventListeners.Remove(eventName);
}
}
public void DispatchEvent(string eventName)
{
if (eventListeners.TryGetValue(eventName, out Delegate handler))
{
((EventDelegate)handler)();
}
}
public void DispatchEvent<T>(string eventName, T t)
{
if (eventListeners.TryGetValue(eventName, out Delegate handler))
{
((EventDelegate<T>)handler)(t);
}
}
public void DispatchEvent<T, U>(string eventName, T t, U u)
{
if (eventListeners.TryGetValue(eventName, out Delegate handler))
{
((EventDelegate<T, U>)handler)(t, u);
}
}
public void DispatchEvent<T, U, V>(string eventName, T t, U u, V v)
{
if (eventListeners.TryGetValue(eventName, out Delegate handler))
{
((EventDelegate<T, U, V>)handler)(t, u, v);
}
}
}
使用案例
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class TestPanel : MonoBehaviour
{
Text text;
public void Awake()
{
EventManager.Instance.RegisterEvent<int, int, string>("TestPanel", TestText);
}
void Start()
{
text = GetComponent<Text>("Text");
EventManager.Instance.DispatchEvent<int, int, string>("TestPanel", 1, 1, "TestPanel");
}
private void TestText(int i, int j, string name)
{
text.text = i.ToString() + j.ToString() + name;
}
private void OnDestroy()
{
EventManager.Instance.RemoveEvent<int, int, string>("TestPanel");
}
}