Unity3D C#事件管理:EventManager
原文地址:http://bbs.9ria.com/thread-153258-1-1.html
原project地址:https://github.com/djandrew/UnityEventManager
多年的Flash开发。我很赞赏Flash的事件系统。
Uinty对象通信所使用的方法SendMessage在多数情况下是工作正常,但假设在一个具有无数引用其它对象的GameObject的大型项目进行反射,那问题就来了。
我用C#在Uinty中所写的第一个东西,就是管理抽象类的事件管理系统。
究其核心。EventManager使用也是SendMessage。并对游戏对象[gameObject]有直接引用,但若有事件发生。其便会对需求进行分解,不同的类间会有信息共享,这样事件对象就知道怎样互相通信。
若有不论什么建议或修正。欢迎留言。
EventManager.cs(十按。本链接为凝视译版,若认为某译不妥请对比英文版自行勘误)
- /*
- Event Manager
- Static manager for handling an event driven communication model in Unity.
- This is similar to Adobe Flash's event listener model used in ActionScript.
- Copyright © 2012 Dustin Andrew
- dustin.andrew@gmail.com
- http://www.dustinandrew.me/
- This program is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- http://www.gnu.org/licenses/
- */
- /*
- * Setup:
- * Create an empty GameObject and add the EventManager script to it.
- * Create custom event classes that extend the CustomEvent.
- *
- * Restrictions & Tips:
- * DO NOT add event listeners in the Awake() method!
- * This is used by the EventManager to initialize.
- * Change this class' Execution Order to before default time if you need to work around this.
- * Use the Start() method to setup your events.
- * Make event listener callback functions public.
- * Extend the CustomEvent class when creating your events.
- * Use custom variables in your custom events over the arguments hashtable to maintain class abstraction
- * Clean up and remove event listeners when objects are destroyed.
- * Events are not received if the listener gameObject.active is false.
- *
- * Examples:
- *
- * // setup event listeners
- * void Start() {
- * EventManager.instance.addEventListener(CustomEventObj.EVENT_TO_LISTEN_TO, gameObject, "OnSomethingHappened");
- * }
- *
- * // remove event listeners
- * void OnDestroy() {
- * if (gameObject) {
- * // remove a single event
- * EventManager.instance.removeEventListener(CustomEventObj.EVENT_TO_LISTEN_TO, gameObject);
- * // remove all events
- * EventManager.instance.removeAllEventListeners(gameObject);
- * }
- * }
- *
- * // get values passed by events
- * public void OnSomethingHappened(CustomEventObj evt) {
- * Debug.Log((datatype)evt.arguments["value"]);
- * // or if using custom vars instead of arguments hashtable
- * Debug.Log(evt.rockOn);
- * }
- *
- * // dispatch events
- * void TriggerEvent() {
- * CustomEventObj evt = new CustomEventObj(CustomEventObj.EVENT_TO_TRIGGER);
- * evt.arguments.Add("value", 3);
- * EventManager.instance.dispatchEvent(evt);
- * }
- *
- * // create custom events
- * using UnityEngine;
- * using System.Collections;
- *
- * public class CustomEventObj : CustomEvent {
- *
- * // event types
- * public static string MY_EVENT_1 = "my_event_1";
- * public static string MY_EVENT_2 = "my_event_2";
- *
- * // optionally add custom variables instead of using the arguments hashtable
- * public int myCustomEventVar1 = 0;
- * public bool rockOn = true;
- *
- * public CustomEventObj(string eventType = "") {
- * type = eventType;
- * }
- * }
- *
- */
- using UnityEngine;
- using System.Collections;
- // internal event listener model
- internal class EventListener {
- public string name;
- public GameObject listener;
- public string function;
- }
- // Custom event class, extend when creating custom events
- public class CustomEvent {
- private string _type;
- private Hashtable _arguments = new Hashtable();
- // constructor
- public CustomEvent(string eventType = "") {
- _type = eventType;
- }
- // the type of event
- public string type {
- get { return _type; }
- set { _type = value; }
- }
- // the arguments to pass with the event
- public Hashtable arguments {
- get { return _arguments; }
- set { _arguments = value; }
- }
- }
- public class EventManager : MonoBehaviour {
- // singleton instance
- public static EventManager instance;
- // settings
- public bool allowSingleton = true; // EventManager class will transfer between scene changes.
- public bool allowWarningOutputs = true;
- public bool allowDebugOutputs = true;
- private static bool _created = false;
- private Hashtable _listeners = new Hashtable();
- // setup singleton if allowed
- public void Awake() {
- if (!_created && allowSingleton) {
- DontDestroyOnLoad(this);
- instance = this;
- _created = true;
- Setup();
- } else {
- if (allowSingleton) {
- if (EventManager.instance.allowWarningOutputs) {
- Debug.LogWarning("Only a single instance of " + this.name + " should exists!");
- }
- Destroy(gameObject);
- } else {
- instance = this;
- Setup();
- }
- }
- }
- // clear events on quit
- public void OnApplicationQuit() {
- _listeners.Clear();
- }
- // PUBLIC *******************************
- // Add event listener
- public bool addEventListener(string eventType, GameObject listener, string function) {
- if (listener == null || eventType == null) {
- if (allowWarningOutputs) {
- Debug.LogWarning("Event Manager: AddListener failed due to no listener or event name specified.");
- }
- return false;
- }
- recordEvent(eventType);
- return recordListener(eventType, listener, function);
- }
- // Remove event listener
- public bool removeEventListener(string eventType, GameObject listener) {
- if (!checkForEvent(eventType)) return false;
- ArrayList listenerList = _listeners[eventType] as ArrayList;
- foreach (EventListener callback in listenerList) {
- if (callback.name == listener.GetInstanceID().ToString()) {
- listenerList.Remove(callback);
- return true;
- }
- }
- return false;
- }
- // Remove all event listeners
- public void removeAllEventListeners(GameObject listener) {
- foreach (EventListener callback in _listeners) {
- if (callback.listener.GetInstanceID().ToString() == listener.GetInstanceID().ToString()) {
- _listeners.Remove(callback);
- }
- }
- }
- // Dispatch an event
- public bool dispatchEvent(CustomEvent evt) {
- string eventType = evt.type;
- if (!checkForEvent(eventType)) {
- if (allowWarningOutputs) {
- Debug.LogWarning("Event Manager: Event \"" + eventType + "\" triggered has no listeners!");
- }
- return false;
- }
- ArrayList listenerList = _listeners[eventType] as ArrayList;
- if (allowDebugOutputs) {
- Debug.Log("Event Manager: Event " + eventType + " dispatched to " + listenerList.Count + ((listenerList.Count == 1) ? " listener." : " listeners."));
- }
- foreach (EventListener callback in listenerList) {
- if (callback.listener && callback.listener.active) {
- callback.listener.SendMessage(callback.function, evt, SendMessageOptions.DontRequireReceiver);
- }
- }
- return false;
- }
- // PRIVATE *******************************
- private void Setup() {
- // TO DO: Self create GameObject if not already created
- }
- // see if event already exists
- private bool checkForEvent(string eventType) {
- if (_listeners.ContainsKey(eventType)) return true;
- return false;
- }
- // record event, if it doesn't already exists
- private bool recordEvent(string eventType) {
- if (!checkForEvent(eventType)) {
- _listeners.Add(eventType, new ArrayList());
- }
- return true;
- }
- // delete event, if not already removed
- private bool deleteEvent(string eventType) {
- if (!checkForEvent(eventType)) return false;
- _listeners.Remove(eventType);
- return true;
- }
- // check if listener exists
- private bool checkForListener(string eventType, GameObject listener) {
- if (!checkForEvent(eventType)) {
- recordEvent(eventType);
- }
- ArrayList listenerList = _listeners[eventType] as ArrayList;
- foreach (EventListener callback in listenerList) {
- if (callback.name == listener.GetInstanceID().ToString()) return true;
- }
- return false;
- }
- // record listener, if not already recorded
- private bool recordListener(string eventType, GameObject listener, string function) {
- if (!checkForListener(eventType, listener)) {
- ArrayList listenerList = _listeners[eventType] as ArrayList;
- EventListener callback = new EventListener();
- callback.name = listener.GetInstanceID().ToString();
- callback.listener = listener;
- callback.function = function;
- listenerList.Add(callback);
- return true;
- } else {
- if (allowWarningOutputs) {
- Debug.LogWarning("Event Manager: Listener: " + listener.name + " is already in list for event: " + eventType);
- }
- return false;
- }
- }
- }
复制代码
原文链接:http://www.dustinandrew.me/blog/2012/10/9/unity3d-c-event-manager.html
翻译词数:225
Unity3D C#事件管理:EventManager的更多相关文章
- phalcon: plugin 结合Manager事件管理、dispatcher调度控制器 监听sql日志记录或其他拦截出来
可能用到的类 phalcon\mvc\use\plugin Phalcon\Mvc\Dispatcher as MvcDispatcher Phalcon\Events\Manager as Even ...
- storm事件管理器EventManager源码分析-event.clj
storm事件管理器定义在event.clj中,主要功能就是通过独立线程执行"事件处理函数".我们可以将"事件处理函数"添加到EventManager的阻塞队列 ...
- zendframework 事件管理(二)
首先需要明确的几个问题: Q1.什么是事件? A:事件就是一个有名字的行为.当这个行为发生的时候,称这个事件被触发. Q2.监听器又是什么? A:监听器决定了事件的逻辑表达,由事件触发.监听器和事件往 ...
- zendframework 事件管理(一)
zend里的事件管理器主要是为了实现: 1.观察者模式 2.面向切面设计 3.事件驱动构架 事件管理最基本的功能是将监听器与事件连接或断开.不论时连接还是断开都是通过shared collection ...
- 自定义事件类EventManager (TS中...args的使用例子)
一个自定义事件类 初衷是使用Egret的事件有两点比较麻烦 1 在事件处理函数时,需要从e中获取data hander(e:egret.Event){ let data = e.data; } 2 ...
- 服务器文档下载zip格式 SQL Server SQL分页查询 C#过滤html标签 EF 延时加载与死锁 在JS方法中返回多个值的三种方法(转载) IEnumerable,ICollection,IList接口问题 不吹不擂,你想要的Python面试都在这里了【315+道题】 基于mvc三层架构和ajax技术实现最简单的文件上传 事件管理
服务器文档下载zip格式 刚好这次项目中遇到了这个东西,就来弄一下,挺简单的,但是前台调用的时候弄错了,浪费了大半天的时间,本人也是菜鸟一枚.开始吧.(MVC的) @using Rattan.Co ...
- cocos2d-js v3事件管理器
总概: 1.时间监听器(cc.EventListener)封装用户的事件处理逻辑. 2.事件管理器(cc.eventManager)管理用户注册的事件监听器. 3.事件对象(cc.Event)包含事件 ...
- JavaScript 事件管理
在设计JavaScript xxsdk的时候考虑到能让调用者参与到工作流程中来,开始用了回调函数.如下: this.foo = function(args,callbackFn) { //do som ...
- jquery技巧之让任何组件都支持类似DOM的事件管理
本文介绍一个jquery的小技巧,能让任意组件对象都能支持类似DOM的事件管理,也就是说除了派发事件,添加或删除事件监听器,还能支持事件冒泡,阻止事件默认行为等等.在jquery的帮助下,使用这个方法 ...
随机推荐
- DataSet之增删改查操作(DataGridView绑定)
DataSet数据集,数据缓存在客户端内存中,支持断开式连接.DataGridView控件绑定DataSet时,它自动的改变的DS的行的状态,而且在做增删改查的时候,可以借助SqlCommandBui ...
- PS如何精确设置参考线,标尺,辅助线
如图所示,我要均分画布的垂直方向为三份.因为要图标的三个位置文件吻合的很精确.我们先拉好头尾两条辅助线 在标尺上右击可以切换显示的单位,但是还是不够精确.因为这个画布是64×192的.我要64×64给 ...
- 2、cas4.0 单点登录 之 cas-client
cas4.0 单点登录 之 cas-client cas4.0 单点登录 之 https证书已经做好了证书的准备工作.如今结合cas-server来配置单点登录: 一.安装cas服务端(cas-ser ...
- v-if 条件渲染分组
因为 v-if 是一个指令,所以必须将它添加到一个元素上.但是如果想切换多个元素呢?此时可以把一个 <template> 元素当做不可见的包裹元素,并在上面使用 v-if.最终的渲染结果将 ...
- 【VBA】复制单元格批注
只复制单元格的批注该怎么操作呢?代码如下: Public Sub 复制单元格批注() Dim range1 As range Dim range2 As range '清除G列 Columns(&qu ...
- Linux 查看某个程序所在端口的 PID
lsof -i:8085 加入显示的是2001 kill 2001 就可以杀死程序了
- 使用ALAssetsLibrary读取所有照片
一. ALAssetsLibrary 介绍 ALAssetsLibrary 提供了访问iOS设备下”照片”应用下所有照片和视频的接口: 从 ALAssetsLibrary 中可读取所有的相册数据,即 ...
- Ubuntu Server 命令行下显示中文乱码(菱形)解决办法
如果Ubuntu Server在安装过程中,选择的是中文(很多新手都会在安装时选择中文,便于上手),这样在完成安装后,系统默认的语言将会是中文zh_CN.UTF- 8.但问题是我们安装的是服务器,只需 ...
- mysqldump默认参数add-drop-table
mysqldump默认参数add-drop-table 原创 2014年01月28日 11:35:18 9214 接到一个同事电话,说UAT环境上的一张表被删了,要恢复一下.原来是新项目UAT,从测试 ...
- VS里用Sos扩展调试CLR总结
暂时不用Windbg,用VS来调试CLR. 1) Enable unmanaged debugging 2) Load sos.dll into vs. !DumpHead -type SimpleC ...