1 /** 2 * Event 3 * 4 * Event api wrapper 5 * @todo Add method for triggering events 6 */ 7 (function (undefined){ 8 9 "use strict"; 10 11 var _add_remove, e, _attach_delegate; 12 13 _add_remove = function (sel, event, callback, add) 14 { 15 var i, len; 16 17 // Multiple events? Run recursively! 18 if ( ! event.match(/^([\w\-]+)$/)) 19 { 20 event = event.split(" "); 21 22 len = event.length; 23 24 for (i = 0; i < len; i++) 25 { 26 _add_remove(sel, event[i], callback, add); 27 } 28 29 return; 30 } 31 32 // Bind the event 33 (add === true) 34 ? sel.addEventListener(event, callback, false) 35 : sel.removeEventListener(event, callback, false); 36 }; 37 38 _attach_delegate = function(sel, target, event, callback) 39 { 40 // attach the listener to the parent object 41 _add_remove(sel, event, function(e){ 42 43 var elem, t; 44 45 // Get the live version of the target selector 46 t = $_.$(target, sel); 47 48 // Check each element to see if it matches the target 49 for(elem in t) 50 { 51 // Fire target callback when event bubbles from target 52 if(e.target == t[elem]) 53 { 54 // Trigger the event callback 55 callback.call(t[elem], e); 56 57 // Stop event propegation 58 e.stopPropagation(); 59 } 60 } 61 62 }, true); 63 }; 64 65 // -------------------------------------------------------------------------- 66 67 /** 68 * Event Listener module 69 * 70 * @namespace 71 * @name event 72 * @memberOf $_ 73 */ 74 e = { 75 /** 76 * Create a custom event 77 * 78 * @memberOf $_.event 79 * @name create 80 * @function 81 * @example Eg. var event = $_("#selector").event.create('foo', {}); 82 * @param string name 83 * @param [object] data 84 * @return object 85 */ 86 create: function(name, data) 87 { 88 // Do a terrible browser-sniffic hack because I don't know of a good 89 // feature test 90 if (/MSIE|Trident/i.test(navigator.userAgent)) 91 { 92 // Okay, I guess we have to do this the hard way... :( 93 // Microsoft, your browser still sucks 94 var e = document.createEvent('CustomEvent'); 95 e.initCustomEvent(name, true, true, data); 96 97 return e; 98 } 99 else 100 { 101 return new CustomEvent(name, data); 102 } 103 }, 104 /** 105 * Adds an event that returns a callback when triggered on the selected 106 * event and selector 107 * 108 * @memberOf $_.event 109 * @name add 110 * @function 111 * @example Eg. $_("#selector").event.add("click", do_something()); 112 * @param string event 113 * @param function callback 114 */ 115 add: function (event, callback) 116 { 117 $_.each(function(e){ 118 _add_remove(e, event, callback, true); 119 }); 120 }, 121 /** 122 * Removes an event bound the the specified selector, event type, and callback 123 * 124 * @memberOf $_.event 125 * @name remove 126 * @function 127 * @example Eg. $_("#selector").event.remove("click", do_something()); 128 * @param string event 129 * @param string callback 130 */ 131 remove: function (event, callback) 132 { 133 $_.each(function(e){ 134 _add_remove(e, event, callback, false); 135 }); 136 }, 137 /** 138 * Binds a persistent event to the document 139 * 140 * @memberOf $_.event 141 * @name live 142 * @function 143 * @example Eg. $_.event.live(".button", "click", do_something()); 144 * @param string target 145 * @param string event 146 * @param function callback 147 */ 148 live: function (target, event, callback) 149 { 150 _attach_delegate(document.documentElement, target, event, callback); 151 }, 152 /** 153 * Binds an event to a parent object 154 * 155 * @memberOf $_.event 156 * @name delegate 157 * @function 158 * @example Eg. $_("#parent").delegate(".button", "click", do_something()); 159 * @param string target 160 * @param string event_type 161 * @param function callback 162 */ 163 delegate: function (target, event, callback) 164 { 165 $_.each(function(e){ 166 _attach_delegate(e, target, event, callback); 167 }); 168 }, 169 /** 170 * Trigger an event to fire 171 * 172 * @memberOf $_.event 173 * @name trigger 174 * @function 175 * @example Eg. $_("#my_id").trigger('click'); 176 * @param string target 177 * @param object event 178 * @return bool 179 */ 180 trigger: function(event) 181 { 182 var target = this.el; 183 return target.dispatchEvent(event); 184 } 185 }; 186 187 $_.ext('event', e); 188 189 }());