您的位置:首页 > 移动开发 > Unity3D

unity3d框架研究之事件处理中心

2016-10-06 11:35 337 查看
代码内容不是本人原创的,请原谅我斗胆作为原创发表:

首先是事件异常类,用于处理事件异常的,下面是代码

namespace Need.Mx
{
using System;

[Serializable]
public class EventException : Exception
{
public EventException(string message) : base(message)
{
}

public EventException(string message, Exception innerException) : base(message, innerException)
{
}
}
}



然后,下面是装载事件的控制类,代码简单易懂,除了原有的注释外,我不好添加注释,因为有点画蛇添足的感觉......
namespace Need.Mx
{
using System;
using System.Collections.Generic;
/// <summary>
/// 由EventDispatcher持有,请不用直接使用此类。
/// </summary>
public class EventController
{
//永久性的消息,在Cleanup的时候,这些消息的响应是不会被清理的。
private List<string> m_permanentEvents = new List<string>();
private Dictionary<string, Delegate> m_theRouter = new Dictionary<string, Delegate>();

public void AddEventListener(string eventType, Action handler)
{
this.OnListenerAdding(eventType, handler);
this.m_theRouter[eventType] = (Action)Delegate.Combine((Action)this.m_theRouter[eventType], handler);
}

public void AddEventListener<T>(string eventType, Action<T> handler)
{
this.OnListenerAdding(eventType, handler);
this.m_theRouter[eventType] = (Action<T>)Delegate.Combine((Action<T>)this.m_theRouter[eventType], handler);
}
public void AddEventListener<T, U>(string eventType, Action<T, U> handler)
{
this.OnListenerAdding(eventType, handler);
this.m_theRouter[eventType] = (Action<T, U>)Delegate.Combine((Action<T, U>)this.m_theRouter[eventType], handler);
}
public void AddEventListener<T, U, V>(string eventType, Action<T, U, V> handler)
{
this.OnListenerAdding(eventType, handler);
this.m_theRouter[eventType] = (Action<T, U, V>)Delegate.Combine((Action<T, U, V>)this.m_theRouter[eventType], handler);
}
public void AddEventListener<T, U, V, W>(string eventType, Action<T, U, V, W> handler)
{
this.OnListenerAdding(eventType, handler);
this.m_theRouter[eventType] = (Action<T, U, V, W>)Delegate.Combine((Action<T, U, V, W>)this.m_theRouter[eventType], handler);
}
public void Cleanup()
{
List<string> list = new List<string>();
foreach (KeyValuePair<string, Delegate> pair in this.m_theRouter)
{
bool flag = false;
foreach (string str in this.m_permanentEvents)
{
if (pair.Key == str)
{
flag = true;
break;
}
}
if (!flag)
{
list.Add(pair.Key);
}
}
foreach (string str in list)
{
this.m_theRouter.Remove(str);
}
}
public bool ContainsEvent(string eventType)
{
return this.m_theRouter.ContainsKey(eventType);
}
public void MarkAsPermanent(string eventType)
{
this.m_permanentEvents.Add(eventType);
}

private void OnListenerAdding(string eventType, Delegate listenerBeingAdded)
{
if (!this.m_theRouter.ContainsKey(eventType))
{
this.m_theRouter.Add(eventType, null);
}
Delegate delegate2 = this.m_theRouter[eventType];
if ((delegate2 != null) && (delegate2.GetType() != listenerBeingAdded.GetType()))
{
throw new EventException(string.Format("Try to add not correct event {0}. Current type is {1}, adding type is {2}.", eventType, delegate2.GetType().Name, listenerBeingAdded.GetType().Name));
}
}

private void OnListenerRemoved(string eventType)
{
if (this.m_theRouter.ContainsKey(eventType) && (this.m_theRouter[eventType] == null))
{
this.m_theRouter.Remove(eventType);
}
}

private bool OnListenerRemoving(string eventType, Delegate listenerBeingRemoved)
{
if (!this.m_theRouter.ContainsKey(eventType))
{
return false;
}
Delegate delegate2 = this.m_theRouter[eventType];
if ((delegate2 != null) && (delegate2.GetType() != listenerBeingRemoved.GetType()))
{
throw new EventException(string.Format("Remove listener {0}\" failed, Current type is {1}, adding type is {2}.", eventType, delegate2.GetType(), listenerBeingRemoved.GetType()));
}
return true;
}

public void RemoveEventListener(string eventType, Action handler)
{
if (this.OnListenerRemoving(eventType, handler))
{
this.m_theRouter[eventType] = (Action)Delegate.Remove((Action)this.m_theRouter[eventType], handler);
this.OnListenerRemoved(eventType);
}
}
public void RemoveEventListener<T>(string eventType, Action<T> handler)
{
if (this.OnListenerRemoving(eventType, handler))
{
this.m_theRouter[eventType] = (Action<T>)Delegate.Remove((Action<T>)this.m_theRouter[eventType], handler);
this.OnListenerRemoved(eventType);
}
}

public void RemoveEventListener<T, U>(string eventType, Action<T, U> handler)
{
if (this.OnListenerRemoving(eventType, handler))
{
this.m_theRouter[eventType] = (Action<T, U>)Delegate.Remove((Action<T, U>)this.m_theRouter[eventType], handler);
this.OnListenerRemoved(eventType);
}
}

public void RemoveEventListener<T, U, V>(string eventType, Action<T, U, V> handler)
{
if (this.OnListenerRemoving(eventType, handler))
{
this.m_theRouter[eventType] = (Action<T, U, V>)Delegate.Remove((Action<T, U, V>)this.m_theRouter[eventType], handler);
this.OnListenerRemoved(eventType);
}
}

public void RemoveEventListener<T, U, V, W>(string eventType, Action<T, U, V, W> handler)
{
if (this.OnListenerRemoving(eventType, handler))
{
this.m_theRouter[eventType] = (Action<T, U, V, W>)Delegate.Remove((Action<T, U, V, W>)this.m_theRouter[eventType], handler);
this.OnListenerRemoved(eventType);
}
}

public void TriggerEvent(string eventType)
{
Delegate delegate2;
if (this.m_theRouter.TryGetValue(eventType, out delegate2))
{
Delegate[] invocationList = delegate2.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
Action action = invocationList[i] as Action;
if (action == null)
{
throw new EventException(string.Format("TriggerEvent {0} error: types of parameters are not match.", eventType));

}
try
{
action();
}
catch (Exception exception)
{
string.Format(exception.Message);
}
}
}
}

public void TriggerEvent<T>(string eventType, T arg1)
{
Delegate delegate2;
if (this.m_theRouter.TryGetValue(eventType, out delegate2))
{
Delegate[] invocationList = delegate2.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
Action<T> action = invocationList[i] as Action<T>;
if (action == null)
{
throw new EventException(string.Format("TriggerEvent {0} error: types of parameters are not match.", eventType));
}
try
{
action(arg1);
}
catch (Exception exception)
{
// Log output
string.Format(exception.Message);
}
}
}
}

public void TriggerEvent<T, U>(string eventType, T arg1, U arg2)
{
Delegate delegate2;
if (this.m_theRouter.TryGetValue(eventType, out delegate2))
{
Delegate[] invocationList = delegate2.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
Action<T, U> action = invocationList[i] as Action<T, U>;
if (action == null)
{
throw new EventException(string.Format("TriggerEvent {0} error: types of parameters are not match.", eventType));
}
try
{
action(arg1, arg2);
}
catch (Exception exception)
{
// Log output
string.Format(exception.Message);
}
}
}
}

public void TriggerEvent<T, U, V>(string eventType, T arg1, U arg2, V arg3)
{
Delegate delegate2;
if (this.m_theRouter.TryGetValue(eventType, out delegate2))
{
Delegate[] invocationList = delegate2.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
Action<T, U, V> action = invocationList[i] as Action<T, U, V>;
if (action == null)
{
throw new EventException(string.Format("TriggerEvent {0} error: types of parameters are not match.", eventType));
}
try
{
action(arg1, arg2, arg3);
}
catch (Exception exception)
{
// Log output
string.Format(exception.Message);
}
}
}
}

public void TriggerEvent<T, U, V, W>(string eventType, T arg1, U arg2, V arg3, W arg4)
{
Delegate delegate2;
if (this.m_theRouter.TryGetValue(eventType, out delegate2))
{
Delegate[] invocationList = delegate2.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
Action<T, U, V, W> action = invocationList[i] as Action<T, U, V, W>;
if (action == null)
{
throw new EventException(string.Format("TriggerEvent {0} error: types of parameters are not match.", eventType));
}
try
{
action(arg1, arg2, arg3, arg4);
}
catch (Exception exception)
{
// Log output
string.Format(exception.Message);
}
}
}
}

public Dictionary<string, Delegate> TheRouter
{
get
{
return this.m_theRouter;
}
}
}
}

接着是提供一个对外的公共接口内,主要是为了降低耦合,然代码可以复用

namespace Need.Mx
{
using System;
using System.Collections.Generic;
/// <summary>
/// 用于注册和触发带有0~4各个参数的Event回调。
/// 游戏事件触发全部在EventDispatcher中。
/// </summary>
public class EventDispatcher
{
private static EventController m_eventController = new EventController();

//注册参数类型不同的消息调用;
public static void AddEventListener<T>(string eventType, Action<T> handler)
{
m_eventController.AddEventListener<T>(eventType, handler);
}

public static void AddEventListener(string eventType, Action handler)
{
m_eventController.AddEventListener(eventType, handler);
}

public static void AddEventListener<T, U>(string eventType, Action<T, U> handler)
{
m_eventController.AddEventListener<T, U>(eventType, handler);
}

public static void AddEventListener<T, U, V>(string eventType, Action<T, U, V> handler)
{
m_eventController.AddEventListener<T, U, V>(eventType, handler);
}

public static void AddEventListener<T, U, V, W>(string eventType, Action<T, U, V, W> handler)
{
m_eventController.AddEventListener<T, U, V, W>(eventType, handler);
}

public static void Cleanup()
{
m_eventController.Cleanup();
}

//添加在清理时不被干掉的event类型;
public static void MarkAsPermanent(string eventType)
{
m_eventController.MarkAsPermanent(eventType);
}

public static void RemoveEventListener<T>(string eventType, Action<T> handler)
{
m_eventController.RemoveEventListener<T>(eventType, handler);
}

public static void RemoveEventListener(string eventType, Action handler)
{
m_eventController.RemoveEventListener(eventType, handler);
}

public static void RemoveEventListener<T, U>(string eventType, Action<T, U> handler)
{
m_eventController.RemoveEventListener<T, U>(eventType, handler);
}

public static void RemoveEventListener<T, U, V>(string eventType, Action<T, U, V> handler)
{
m_eventController.RemoveEventListener<T, U, V>(eventType, handler);
}

public static void RemoveEventListener<T, U, V, W>(string eventType, Action<T, U, V, W> handler)
{
m_eventController.RemoveEventListener<T, U, V, W>(eventType, handler);
}

public static void TriggerEvent(string eventType)
{
m_eventController.TriggerEvent(eventType);
}

public static void TriggerEvent<T>(string eventType, T arg1)
{
m_eventController.TriggerEvent<T>(eventType, arg1);
}

public static void TriggerEvent<T, U>(string eventType, T arg1, U arg2)
{
m_eventController.TriggerEvent<T, U>(eventType, arg1, arg2);
}

public static void TriggerEvent<T, U, V>(string eventType, T arg1, U arg2, V arg3)
{
m_eventController.TriggerEvent<T, U, V>(eventType, arg1, arg2, arg3);
}

public static void TriggerEvent<T, U, V, W>(string eventType, T arg1, U arg2, V arg3, W arg4)
{
m_eventController.TriggerEvent<T, U, V, W>(eventType, arg1, arg2, arg3, arg4);
}

public static Dictionary<string, Delegate> TheRouter
{
get
{
return m_eventController.TheRouter;
}
}
}
}

最后,我说一下我的一些见解:
在对外提供公共接口内里面的这一句:

private static EventController m_eventController = new EventController();我觉得可以使用继承,更加好,这样不会把程序写死了,可以让后面的然继续拓展。
当然这个只是我的一个浅陋意见而已。毕竟我研究这一部分也花了好几天的时间,才能略懂一二。

这只是need.mx包里面的一部分,以后有时间会继续研究其他部分的
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: