事件是一种叫作观察者的设计模式,这是一种建立松散耦合的技术。观察者模式由两类对象组成:主体和观察者。主体负责发布事件。同时观察者经过订阅这些事件来观察该主体。该模式的一个关键概念是主体并不知道观察者的任何事情,也就是说它能够独自存在并正常运做即便观察者不存在。从另外一方面来讲。观察者知道主体并能注册事件的回调函数(事件处理程序),涉及到Dom上时,Dom元素即是主体,你的事件处理代码即是观察者。javascript
事件是与Dom交互的最多见的方式,但它们也能够用于非Dom代码中--经过实现自定义事件。java
自定义事件背后的概念是建立一个管理事件的对象。让其余对象监听那些事件。实现此功能的基本模式能够定义以下:设计模式
function EventTarget(name1) { this.name = name1; this.handlers = {} } EventTarget.prototype = { constructor: EventTarget, addHandler: function(type, handler) { console.log(type); //刚开始只有type并无为this.handlers[type]赋值 if (typeof this.handlers[type] == "undefined") { this.handlers[type] = []; console.log("hi") } //接着执行push this.handlers[type].push(handler); console.log(this.handlers[type]); }, fire: function(event) { if (!event.target) { event.target = this; console.log("not have eventTarget") } if (this.handlers[event.type] instanceof Array) { console.log("isArray") var handlers = this.handlers[event.type]; //循环执行多个事件 for (var i = 0, len = handlers.length; i < len; i++) { handlers[i](event); } } }, removeHandler: function(type, handler) { if (this.handlers[type] instanceof Array) { var handlers = this.handlers[type]; for (var i = 0, len = handlers.length; i < len; i++) { if (handlers[i] === handler) { break; } } handlers.splice(i, 1); } console.log(handlers); } }
而后使用EventTarget类型的自定义事件:函数
function handleMessage(event) { alert("Message received:" + event.message); } //建立一个新对象 var target = new EventTarget() //添加一个事件处理程序 target.addHandler("message",handleMessage) //触发事件 target.fire({type:"message",message:"Hello World"}) //删除事件处理程序 target.removeHandler("message",handleMessage); //触发事件不会执行 target.fire({type:"message",message:"Hello Worldmmm"})
在这段代码中,定义了handleMessage()函数用于处理message事件。它接受event对象并输出message属性。调用target对象的addHandler()方法并传给"message"以及hadleMessage()函数。在接下来的一行,调用了fire()函数,并传给了2个属性,即type和message的对象。而后删除了事件处理程序,这样即便事件再次出发,也不会显示任何警告框。this
由于这种功能是封装在一种自定义类型中的,其它对象能够继承EventTarget并得到这个行为prototype
function Person(name) { this.name = name; this.etarget = new EventTarget(this.name) } Person.prototype = { constructor: Person, addMessage: function(type, fn) { this.etarget.addHandler(type, fn) }, say: function(message) { this.etarget.fire({ type: "message", message: message }) console.log(this.name) } } function handleMessage(event) { console.log(event) //弹出NICHOLAS--SAYS:hi there alert(event.target.name + "---says:" + event.message); } //建立新Person实例 var person = new Person("NICHOLAS"); person.addMessage("message", handleMessage); person.say("hi there")