Add custom events to custom objects

Source: Internet
Author: User

JavaScript does not have its own event system. With the help of Dom's Event System, if Javascript objects are only involved, the system will stop. The following is a counterfeit product. Do not expect events to bubble up.

If (typeof array. Prototype. foreach! = "Function") {array. prototype. foreach = function (FN, scope) {for (VAR I = 0, n = This. length >>> 0; I <n; I ++) {I in this & FN. call (scope, this [I], I, this) }}var eventdispatcher = {$ A: function (iterable) {return array. prototype. slice. call (iterable)}, createevents: function () {This. _ listeners ={}; var names = This. events | [], name, type; names. foreach (function (type) {name = "on" + type. replace (/_ ([A-Z])/ G, function ($1, $2) {return $2. touppercase ()}). replace (/^ \ W/, function (s) {return S. touppercase () ;}); If (typeof this [name] === "undefined") {This [name] = function () {var ARGs = This. $ A (arguments); return this. attachevent. apply (this, [type]. concat (ARGs) }}, this)}, hasevent: function (type) {return (this. _ listeners [type] instanceof array & this. _ listeners [type]. length> 0) ;}, attachevent: funct Ion () {var ARGs = this. $ A (arguments), type = args. Shift (), callback = args. Shift (); If (! This. hasevent (type) This. _ listeners [type] = []; var listeners = This. _ listeners [type]; listeners. push ({callback: callback, argS: ARGs}) ;}, detachevent: function (type, callback) {If (this. hasevent (type) {var listeners = This. _ listeners [type], listener; If (typeof callback = "undefined") {delete this. _ listeners [type];} else {for (VAR I = 0, n = listeners. length; I <n; I ++) {If (listeners [I]. callback = Cal Lback) {listeners. splice (I, 1); Return ;}}}}, fireevent: function () {var ARGs = This. $ A (arguments), type = args. shift (); If (! This. hasevent (type) return; var listeners = This. _ listeners [type]; listeners. foreach (function (listener) {listener. callback. apply (this, listener. args. concat (ARGs)}, this );}}

Strictly speaking, this is not a class. It should be called an interface. When the target class implements it (turning the eventdispatcher member into a member of the target class) and provides an events String Array member in the prototype, we call createevents, it has event-like behavior, because there is no Dom monitoring, we need fireevent to trigger the event.

Example:

 
VaR person = function (name) {This. name = Name} person. prototype = {events: ["layout"]} var include = function (concrete, interface) {// use the ruby naming method, used to add an instance Member for (VAR prop in Interface) {concrete. prototype [prop] = interface [prop];} include (person, eventdispatcher); var P = new person ("situ zhengmei") p. createevents () p. onlayout (function (name) {alert (name)}); p. onlayout (function (name) {alert (name + "!! ")}); P. fireevent (" layout "," parameter ") // The" parameter "is displayed in sequence !! "

<Br/> <! Doctype HTML> <br/> <pead> <br/> <title> JavaScript Custom Event by situ zhengmei </title> </P> <p> <meta http-equiv = "Content-Type" content = "text/html; charset = UTF-8 "/> </P> <p> </pead> <br/> <body> <br/> <div> situ zhengmei </div> </P> <p> <SCRIPT type = "text/JavaScript"> <br/> If (typeof array. prototype. foreach! = "Function") {<br/> array. prototype. foreach = function (FN, scope) {<br/> for (VAR I = 0, n = This. length >>> 0; I <n; I ++) {<br/> I in this & FN. call (scope, this [I], I, this) <br/>}< br/> var eventdispatcher ={< br/> $ A: function (iterable) {<br/> return array. prototype. slice. call (iterable) <br/>}, <br/> createevents: function () {<br/> This. _ listeners ={}; <br/> var names = This. events | [], Name, type; <br/> names. foreach (function (type) {<br/> name = "on" + type. replace (/_ ([A-Z])/g, function ($1, $2) {<br/> return $2. touppercase () <br/> }). replace (/^ \ W/, function (s) {<br/> return S. touppercase (); <br/>}); </P> <p> If (typeof this [name] = "undefined ") {<br/> This [name] = function () {<br/> var ARGs = This. $ A (arguments); <br/> return this. attachevent. apply (this, [type]. concat (ARGs) <br/>} <Br/>}< br/>}, this) <br/>}, <br/> hasevent: function (type) {<br/> return (this. _ listeners [type] instanceof array & this. _ listeners [type]. length> 0); <br/>}, <br/> attachevent: function () {<br/> var ARGs = This. $ A (arguments), <br/> type = args. shift (), callback = args. shift (); <br/> If (! This. hasevent (type) <br/> This. _ listeners [type] = []; <br/> var listeners = This. _ listeners [type]; <br/> listeners. push ({callback: callback, argS: ARGs}); <br/>}, <br/> detachevent: function (type, callback) {<br/> If (this. hasevent (type) {<br/> var listeners = This. _ listeners [type], listener; <br/> If (typeof callback = "undefined") {<br/> delete this. _ listeners [type]; <br/>} else {<br/> for (VAR I = 0, n = listeners. length; I <n; I ++) {<br/> If (listeners [I]. callback === callback) {<br/> listeners. splice (I, 1); <br/> return; <br/>}< br/> }, <br/> fireevent: function () {<br/> var ARGs = This. $ A (arguments), type = args. shift (); <br/> If (! This. hasevent (type) return; <br/> var listeners = This. _ listeners [type]; <br/> listeners. foreach (function (listener) {<br/> listener. callback. apply (this, listener. args. concat (ARGs) <br/>}, this); <br/>}</P> <p> var person = function (name) {<br/> This. name = Name <br/>}< br/> person. prototype = {<br/> events: ["layout"] <br/>}< br/> var include = function (concrete, interface) {// use a ruby-style name Method, used to add instance members <br/> for (VAR prop in Interface) {<br/> concrete. prototype [prop] = interface [prop]; <br/>}< br/> include (person, eventdispatcher ); <br/> var P = new person ("situ zhengmei") <br/> P. createevents () <br/> P. onlayout (function (name) {<br/> alert (name) <br/>}); <br/> P. onlayout (function (name) {<br/> alert (name + "!! ") <Br/>}); <br/> P. fireevent (" layout "," parameter ") //" parameter "is displayed in sequence !! "<Br/> </SCRIPT> </P> <p> </body> <br/> </ptml> <br/>

RunCode

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.