X-Git-Url: http://git.asbjorn.biz/?a=blobdiff_plain;f=src%2Fevent.js;h=b4650ae5a3dd6103007c5e3ba0c38a8c9eb232ce;hb=98c7248518f9a2082ccf50240b5ab44bf98d7b5e;hp=8ec1d4f369461620555405c8596ca2a58a0c13eb;hpb=0474917c9d82fa13d865282d2da2d3cb6e5b89ec;p=jquery.git diff --git a/src/event.js b/src/event.js index 8ec1d4f..b4650ae 100644 --- a/src/event.js +++ b/src/event.js @@ -42,8 +42,16 @@ jQuery.event = { } // Init the element's event structure - var events = jQuery.data( elem, "events" ) || jQuery.data( elem, "events", {} ), - handle = jQuery.data( elem, "handle" ), eventHandle; + var elemData = jQuery.data( elem ); + + // If no elemData is found then we must be trying to bind to one of the + // banned noData elements + if ( !elemData ) { + return; + } + + var events = elemData.events || (elemData.events = {}), + handle = elemData.handle, eventHandle; if ( !handle ) { eventHandle = function() { @@ -54,13 +62,7 @@ jQuery.event = { undefined; }; - handle = jQuery.data( elem, "handle", eventHandle ); - } - - // If no handle is found then we must be trying to bind to one of the - // banned noData elements - if ( !handle ) { - return; + handle = elemData.handle = eventHandle; } // Add elem as a property of the handle function @@ -70,15 +72,11 @@ jQuery.event = { // Handle multiple events separated by a space // jQuery(...).bind("mouseover mouseout", fn); - types = types.split( /\s+/ ); + types = types.split(" "); - var type, i = 0; + var type, i = 0, namespaces; while ( (type = types[ i++ ]) ) { - // Namespaced event handlers - var namespaces = type.split("."); - type = namespaces.shift(); - if ( i > 1 ) { handler = jQuery.proxy( handler ); @@ -87,7 +85,16 @@ jQuery.event = { } } - handler.type = namespaces.slice(0).sort().join("."); + // Namespaced event handlers + if ( type.indexOf(".") > -1 ) { + namespaces = type.split("."); + type = namespaces.shift(); + handler.type = namespaces.slice(0).sort().join("."); + + } else { + namespaces = []; + handler.type = ""; + } // Get the current list of functions bound to this event var handlers = events[ type ], @@ -104,6 +111,7 @@ jQuery.event = { // Bind the global event handler to the element if ( elem.addEventListener ) { elem.addEventListener( type, handle, false ); + } else if ( elem.attachEvent ) { elem.attachEvent( "on" + type, handle ); } @@ -114,6 +122,8 @@ jQuery.event = { var modifiedHandler = special.add.call( elem, handler, data, namespaces, handlers ); if ( modifiedHandler && jQuery.isFunction( modifiedHandler ) ) { modifiedHandler.guid = modifiedHandler.guid || handler.guid; + modifiedHandler.data = modifiedHandler.data || handler.data; + modifiedHandler.type = modifiedHandler.type || handler.type; handler = modifiedHandler; } } @@ -138,7 +148,13 @@ jQuery.event = { return; } - var events = jQuery.data( elem, "events" ), ret, type, fn; + var elemData = jQuery.data( elem ); + + if ( !elemData ) { + return; + } + + var events = elemData.events, ret, type, fn; if ( events ) { // Unbind all events for the element @@ -146,6 +162,7 @@ jQuery.event = { for ( type in events ) { this.remove( elem, type + (types || "") ); } + } else { // types is actually an event object here if ( types.type ) { @@ -155,16 +172,27 @@ jQuery.event = { // Handle multiple events separated by a space // jQuery(...).unbind("mouseover mouseout", fn); - types = types.split(/\s+/); - var i = 0; + types = types.split(" "); + + var i = 0, all, namespaces, namespace; + while ( (type = types[ i++ ]) ) { - // Namespaced event handlers - var namespaces = type.split("."); - type = namespaces.shift(); - var all = !namespaces.length, - cleaned = jQuery.map( namespaces.slice(0).sort(), fcleanup ), - namespace = new RegExp("(^|\\.)" + cleaned.join("\\.(?:.*\\.)?") + "(\\.|$)"), - special = this.special[ type ] || {}; + all = type.indexOf(".") < 0; + namespaces = null; + + if ( !all ) { + // Namespaced event handlers + namespaces = type.split("."); + type = namespaces.shift(); + + namespace = new RegExp("(^|\\.)" + + jQuery.map( namespaces.slice(0).sort(), fcleanup ).join("\\.(?:.*\\.)?") + "(\\.|$)") + + } else { + namespaces = []; + } + + var special = this.special[ type ] || {}; if ( events[ type ] ) { // remove the given handler for the given type @@ -190,14 +218,12 @@ jQuery.event = { for ( ret in events[ type ] ) { break; } + if ( !ret ) { if ( !special.teardown || special.teardown.call( elem, namespaces ) === false ) { - if ( elem.removeEventListener ) { - elem.removeEventListener( type, jQuery.data( elem, "handle" ), false ); - } else if ( elem.detachEvent ) { - elem.detachEvent( "on" + type, jQuery.data( elem, "handle" ) ); - } + removeEvent( elem, type, elemData.handle ); } + ret = null; delete events[ type ]; } @@ -209,13 +235,19 @@ jQuery.event = { for ( ret in events ) { break; } + if ( !ret ) { - var handle = jQuery.data( elem, "handle" ); + var handle = elemData.handle; if ( handle ) { handle.elem = null; } - jQuery.removeData( elem, "events" ); - jQuery.removeData( elem, "handle" ); + + delete elemData.events; + delete elemData.handle; + + if ( jQuery.isEmptyObject( elemData ) ) { + jQuery.removeData( elem ); + } } } }, @@ -297,9 +329,12 @@ jQuery.event = { } else if ( !event.isDefaultPrevented() ) { var target = event.target, old, - isClick = jQuery.nodeName(target, "a") && type === "click"; + isClick = jQuery.nodeName(target, "a") && type === "click", + special = jQuery.event.special[ type ] || {}; + + if ( (!special._default || special._default.call( elem, event ) === false) && + !isClick && !(target && target.nodeName && jQuery.noData[target.nodeName.toLowerCase()]) ) { - if ( !isClick && !(target && target.nodeName && jQuery.noData[target.nodeName.toLowerCase()]) ) { try { if ( target[ type ] ) { // Make sure that we don't accidentally re-trigger the onFOO events @@ -490,6 +525,14 @@ jQuery.event = { } }; +var removeEvent = document.removeEventListener ? + function( elem, type, handle ) { + elem.removeEventListener( type, handle, false ); + } : + function( elem, type, handle ) { + elem.detachEvent( "on" + type, handle ); + }; + jQuery.Event = function( src ) { // Allow instantiation without the 'new' keyword if ( !this.preventDefault ) { @@ -726,10 +769,7 @@ jQuery.event.special.change = { // information/focus[in] is not needed anymore beforeactivate: function( e ) { var elem = e.target; - - if ( elem.nodeName.toLowerCase() === "input" && elem.type === "radio" ) { - jQuery.data( elem, "_change_data", getVal(elem) ); - } + jQuery.data( elem, "_change_data", getVal(elem) ); } }, setup: function( data, namespaces, fn ) { @@ -797,11 +837,16 @@ jQuery.each(["bind", "one"], function( i, name ) { return fn.apply( this, arguments ); }) : fn; - return type === "unload" && name !== "one" ? - this.one( type, data, fn ) : - this.each(function() { - jQuery.event.add( this, type, handler, data ); - }); + if ( type === "unload" && name !== "one" ) { + this.one( type, data, fn ); + + } else { + for ( var i = 0, l = this.length; i < l; i++ ) { + jQuery.event.add( this[i], type, handler, data ); + } + } + + return this; }; }); @@ -812,12 +857,14 @@ jQuery.fn.extend({ for ( var key in type ) { this.unbind(key, type[key]); } - return this; + + } else { + for ( var i = 0, l = this.length; i < l; i++ ) { + jQuery.event.remove( this[i], type, fn ); + } } - return this.each(function() { - jQuery.event.remove( this, type, fn ); - }); + return this; }, trigger: function( type, data ) { return this.each(function() {