Cleaned up a bunch of the event code, removed .oneEvent() and .unEvent().
[jquery.git] / src / event / event.js
1 /*
2  * A number of helper functions used for managing events.
3  * Many of the ideas behind this code orignated from 
4  * Dean Edwards' addEvent library.
5  */
6 jQuery.event = {
7
8         // Bind an event to an element
9         // Original by Dean Edwards
10         add: function(element, type, handler, data) {
11                 // For whatever reason, IE has trouble passing the window object
12                 // around, causing it to be cloned in the process
13                 if ( jQuery.browser.msie && element.setInterval != undefined )
14                         element = window;
15
16                 // if data is passed, bind to handler
17                 if( data ) 
18                         handler.data = data;
19
20                 // Make sure that the function being executed has a unique ID
21                 if ( !handler.guid )
22                         handler.guid = this.guid++;
23
24                 // Init the element's event structure
25                 if (!element.events)
26                         element.events = {};
27
28                 // Get the current list of functions bound to this event
29                 var handlers = element.events[type];
30
31                 // If it hasn't been initialized yet
32                 if (!handlers) {
33                         // Init the event handler queue
34                         handlers = element.events[type] = {};
35
36                         // Remember an existing handler, if it's already there
37                         if (element["on" + type])
38                                 handlers[0] = element["on" + type];
39                 }
40
41                 // Add the function to the element's handler list
42                 handlers[handler.guid] = handler;
43
44                 // And bind the global event handler to the element
45                 element["on" + type] = this.handle;
46
47                 // Remember the function in a global list (for triggering)
48                 if (!this.global[type])
49                         this.global[type] = [];
50                 this.global[type].push( element );
51         },
52
53         guid: 1,
54         global: {},
55
56         // Detach an event or set of events from an element
57         remove: function(element, type, handler) {
58                 if (element.events)
59                         if ( type && type.type )
60                                 delete element.events[ type.type ][ type.handler.guid ];
61                         else if (type && element.events[type])
62                                 if ( handler )
63                                         delete element.events[type][handler.guid];
64                                 else
65                                         for ( var i in element.events[type] )
66                                                 delete element.events[type][i];
67                         else
68                                 for ( var j in element.events )
69                                         this.remove( element, j );
70         },
71
72         trigger: function(type,data,element) {
73                 // Clone the incoming data, if any
74                 data = jQuery.makeArray(data || []);
75
76                 // Handle a global trigger
77                 if ( !element ) {
78                         var g = this.global[type];
79                         if ( g )
80                                 for ( var i = 0, gl = g.length; i < gl; i++ )
81                                         this.trigger( type, data, g[i] );
82
83                 // Handle triggering a single element
84                 } else if ( element["on" + type] ) {
85                         // Pass along a fake event
86                         data.unshift( this.fix({ type: type, target: element }) );
87
88                         // Trigger the event
89                         element["on" + type].apply( element, data );
90                 }
91         },
92
93         handle: function(event) {
94                 if ( typeof jQuery == "undefined" ) return false;
95
96                 // Empty object is for triggered events with no data
97                 event = jQuery.event.fix( event || window.event || {} ); 
98
99                 // returned undefined or false
100                 var returnValue;
101
102                 var c = this.events[event.type];
103
104                 var args = [].slice.call( arguments, 1 );
105                 args.unshift( event );
106
107                 for ( var j in c ) {
108                         // Pass in a reference to the handler function itself
109                         // So that we can later remove it
110                         args[0].handler = c[j];
111                         args[0].data = c[j].data;
112
113                         if ( c[j].apply( this, args ) === false ) {
114                                 event.preventDefault();
115                                 event.stopPropagation();
116                                 returnValue = false;
117                         }
118                 }
119
120                 // Clean up added properties in IE to prevent memory leak
121                 if (jQuery.browser.msie) event.target = event.preventDefault = event.stopPropagation = event.handler = event.data = null;
122
123                 return returnValue;
124         },
125
126         fix: function(event) {
127                 // Fix target property, if necessary
128                 if ( !event.target && event.srcElement )
129                         event.target = event.srcElement;
130
131                 // Calculate pageX/Y if missing and clientX/Y available
132                 if ( typeof event.pageX == "undefined" && typeof event.clientX != "undefined" ) {
133                         var e = document.documentElement, b = document.body;
134                         event.pageX = event.clientX + (e.scrollLeft || b.scrollLeft);
135                         event.pageY = event.clientY + (e.scrollTop || b.scrollTop);
136                 }
137                                 
138                 // check if target is a textnode (safari)
139                 if (event.target.nodeType == 3) {
140                         // store a copy of the original event object 
141                         // and clone because target is read only
142                         var originalEvent = event;
143                         event = jQuery.extend({}, originalEvent);
144                         
145                         // get parentnode from textnode
146                         event.target = originalEvent.target.parentNode;
147                         
148                         // add preventDefault and stopPropagation since 
149                         // they will not work on the clone
150                         event.preventDefault = function() {
151                                 return originalEvent.preventDefault();
152                         };
153                         event.stopPropagation = function() {
154                                 return originalEvent.stopPropagation();
155                         };
156                 }
157                 
158                 // fix preventDefault and stopPropagation
159                 if (!event.preventDefault)
160                         event.preventDefault = function() {
161                                 this.returnValue = false;
162                         };
163                         
164                 if (!event.stopPropagation)
165                         event.stopPropagation = function() {
166                                 this.cancelBubble = true;
167                         };
168                         
169                 return event;
170         }
171 };
172
173 jQuery.fn.extend({
174
175         /**
176          * Binds a handler to a particular event (like click) for each matched element.
177          * The event handler is passed an event object that you can use to prevent
178          * default behaviour. To stop both default action and event bubbling, your handler
179          * has to return false.
180          *
181          * In most cases, you can define your event handlers as anonymous functions
182          * (see first example). In cases where that is not possible, you can pass additional
183          * data as the second paramter (and the handler function as the third), see 
184          * second example.
185          *
186          * @example $("p").bind( "click", function() {
187          *   alert( $(this).text() );
188          * } )
189          * @before <p>Hello</p>
190          * @result alert("Hello")
191          *
192          * @example var handler = function(event) {
193          *   alert(event.data.foo);
194          * };
195          * $("p").bind( "click", {foo: "bar"}, handler)
196          * @result alert("bar")
197          * @desc Pass some additional data to the event handler.
198          *
199          * @example $("form").bind( "submit", function() { return false; } )
200          * @desc Cancel a default action and prevent it from bubbling by returning false
201          * from your function.
202          *
203          * @example $("form").bind( "submit", function(event) {
204          *   event.preventDefault();
205          * } );
206          * @desc Cancel only the default action by using the preventDefault method.
207          *
208          *
209          * @example $("form").bind( "submit", function(event) {
210          *   event.stopPropagation();
211          * } )
212          * @desc Stop only an event from bubbling by using the stopPropagation method.
213          *
214          * @name bind
215          * @type jQuery
216          * @param String type An event type
217          * @param Object data (optional) Additional data passed to the event handler as event.data
218          * @param Function fn A function to bind to the event on each of the set of matched elements
219          * @cat Events
220          */
221         bind: function( type, data, fn ) {
222                 return this.each(function(){
223                         jQuery.event.add( this, type, fn || data, data );
224                 });
225         },
226         
227         /**
228          * Binds a handler to a particular event (like click) for each matched element.
229          * The handler is executed only once for each element. Otherwise, the same rules
230          * as described in bind() apply.
231          The event handler is passed an event object that you can use to prevent
232          * default behaviour. To stop both default action and event bubbling, your handler
233          * has to return false.
234          *
235          * In most cases, you can define your event handlers as anonymous functions
236          * (see first example). In cases where that is not possible, you can pass additional
237          * data as the second paramter (and the handler function as the third), see 
238          * second example.
239          *
240          * @example $("p").one( "click", function() {
241          *   alert( $(this).text() );
242          * } )
243          * @before <p>Hello</p>
244          * @result alert("Hello")
245          *
246          * @name one
247          * @type jQuery
248          * @param String type An event type
249          * @param Object data (optional) Additional data passed to the event handler as event.data
250          * @param Function fn A function to bind to the event on each of the set of matched elements
251          * @cat Events
252          */
253         one: function( type, data, fn ) {
254                 return this.each(function(){
255                         jQuery.event.add( this, type, function(event) {
256                                 jQuery(this).unbind(event);
257                                 return (fn || data).apply( this, arguments);
258                         }, data);
259                 });
260         },
261
262         /**
263          * The opposite of bind, removes a bound event from each of the matched
264          * elements. You must pass the identical function that was used in the original
265          * bind method.
266          *
267          * @example $("p").unbind( "click", function() { alert("Hello"); } )
268          * @before <p onclick="alert('Hello');">Hello</p>
269          * @result [ <p>Hello</p> ]
270          *
271          * @name unbind
272          * @type jQuery
273          * @param String type An event type
274          * @param Function fn A function to unbind from the event on each of the set of matched elements
275          * @cat Events
276          */
277
278         /**
279          * Removes all bound events of a particular type from each of the matched
280          * elements.
281          *
282          * @example $("p").unbind( "click" )
283          * @before <p onclick="alert('Hello');">Hello</p>
284          * @result [ <p>Hello</p> ]
285          *
286          * @name unbind
287          * @type jQuery
288          * @param String type An event type
289          * @cat Events
290          */
291
292         /**
293          * Removes all bound events from each of the matched elements.
294          *
295          * @example $("p").unbind()
296          * @before <p onclick="alert('Hello');">Hello</p>
297          * @result [ <p>Hello</p> ]
298          *
299          * @name unbind
300          * @type jQuery
301          * @cat Events
302          */
303         unbind: function( type, fn ) {
304                 return this.each(function(){
305                         jQuery.event.remove( this, type, fn );
306                 });
307         },
308
309         /**
310          * Trigger a type of event on every matched element.
311          *
312          * @example $("p").trigger("click")
313          * @before <p click="alert('hello')">Hello</p>
314          * @result alert('hello')
315          *
316          * @name trigger
317          * @type jQuery
318          * @param String type An event type to trigger.
319          * @cat Events
320          */
321         trigger: function( type, data ) {
322                 return this.each(function(){
323                         jQuery.event.trigger( type, data, this );
324                 });
325         },
326
327         // We're overriding the old toggle function, so
328         // remember it for later
329         _toggle: jQuery.fn.toggle,
330         
331         /**
332          * Toggle between two function calls every other click.
333          * Whenever a matched element is clicked, the first specified function 
334          * is fired, when clicked again, the second is fired. All subsequent 
335          * clicks continue to rotate through the two functions.
336          *
337          * Use unbind("click") to remove.
338          *
339          * @example $("p").toggle(function(){
340          *   $(this).addClass("selected");
341          * },function(){
342          *   $(this).removeClass("selected");
343          * });
344          * 
345          * @name toggle
346          * @type jQuery
347          * @param Function even The function to execute on every even click.
348          * @param Function odd The function to execute on every odd click.
349          * @cat Events
350          */
351         toggle: function() {
352                 // save reference to arguments for access in closure
353                 var a = arguments;
354                 return typeof a[0] == "function" && typeof a[1] == "function" ? this.click(function(e) {
355                         // Figure out which function to execute
356                         this.lastToggle = this.lastToggle == 0 ? 1 : 0;
357                         
358                         // Make sure that clicks stop
359                         e.preventDefault();
360                         
361                         // and execute the function
362                         return a[this.lastToggle].apply( this, [e] ) || false;
363                 }) :
364                 
365                 // Otherwise, execute the old toggle function
366                 this._toggle.apply( this, arguments );
367         },
368         
369         /**
370          * A method for simulating hovering (moving the mouse on, and off,
371          * an object). This is a custom method which provides an 'in' to a 
372          * frequent task.
373          *
374          * Whenever the mouse cursor is moved over a matched 
375          * element, the first specified function is fired. Whenever the mouse 
376          * moves off of the element, the second specified function fires. 
377          * Additionally, checks are in place to see if the mouse is still within 
378          * the specified element itself (for example, an image inside of a div), 
379          * and if it is, it will continue to 'hover', and not move out 
380          * (a common error in using a mouseout event handler).
381          *
382          * @example $("p").hover(function(){
383          *   $(this).addClass("over");
384          * },function(){
385          *   $(this).addClass("out");
386          * });
387          *
388          * @name hover
389          * @type jQuery
390          * @param Function over The function to fire whenever the mouse is moved over a matched element.
391          * @param Function out The function to fire whenever the mouse is moved off of a matched element.
392          * @cat Events
393          */
394         hover: function(f,g) {
395                 
396                 // A private function for handling mouse 'hovering'
397                 function handleHover(e) {
398                         // Check if mouse(over|out) are still within the same parent element
399                         var p = (e.type == "mouseover" ? e.fromElement : e.toElement) || e.relatedTarget;
400         
401                         // Traverse up the tree
402                         while ( p && p != this ) try { p = p.parentNode } catch(e) { p = this; };
403                         
404                         // If we actually just moused on to a sub-element, ignore it
405                         if ( p == this ) return false;
406                         
407                         // Execute the right function
408                         return (e.type == "mouseover" ? f : g).apply(this, [e]);
409                 }
410                 
411                 // Bind the function to the two event listeners
412                 return this.mouseover(handleHover).mouseout(handleHover);
413         },
414         
415         /**
416          * Bind a function to be executed whenever the DOM is ready to be
417          * traversed and manipulated. This is probably the most important 
418          * function included in the event module, as it can greatly improve
419          * the response times of your web applications.
420          *
421          * In a nutshell, this is a solid replacement for using window.onload, 
422          * and attaching a function to that. By using this method, your bound Function 
423          * will be called the instant the DOM is ready to be read and manipulated, 
424          * which is exactly what 99.99% of all Javascript code needs to run.
425          * 
426          * Please ensure you have no code in your &lt;body&gt; onload event handler, 
427          * otherwise $(document).ready() may not fire.
428          *
429          * You can have as many $(document).ready events on your page as you like.
430          * The functions are then executed in the order they were added.
431          *
432          * @example $(document).ready(function(){ Your code here... });
433          *
434          * @name ready
435          * @type jQuery
436          * @param Function fn The function to be executed when the DOM is ready.
437          * @cat Events
438          */
439         ready: function(f) {
440                 // If the DOM is already ready
441                 if ( jQuery.isReady )
442                         // Execute the function immediately
443                         f.apply( document );
444                         
445                 // Otherwise, remember the function for later
446                 else {
447                         // Add the function to the wait list
448                         jQuery.readyList.push( f );
449                 }
450         
451                 return this;
452         }
453 });
454
455 jQuery.extend({
456         /*
457          * All the code that makes DOM Ready work nicely.
458          */
459         isReady: false,
460         readyList: [],
461         
462         // Handle when the DOM is ready
463         ready: function() {
464                 // Make sure that the DOM is not already loaded
465                 if ( !jQuery.isReady ) {
466                         // Remember that the DOM is ready
467                         jQuery.isReady = true;
468                         
469                         // If there are functions bound, to execute
470                         if ( jQuery.readyList ) {
471                                 // Execute all of them
472                                 for ( var i = 0; i < jQuery.readyList.length; i++ )
473                                         jQuery.readyList[i].apply( document );
474                                 
475                                 // Reset the list of functions
476                                 jQuery.readyList = null;
477                         }
478                         // Remove event lisenter to avoid memory leak
479                         if ( jQuery.browser.mozilla || jQuery.browser.opera )
480                                 document.removeEventListener( "DOMContentLoaded", jQuery.ready, false );
481                 }
482         }
483 });
484
485 new function(){
486
487         /**
488          * Bind a function to the scroll event of each matched element.
489          *
490          * @example $("p").scroll( function() { alert("Hello"); } );
491          * @before <p>Hello</p>
492          * @result <p onscroll="alert('Hello');">Hello</p>
493          *
494          * @name scroll
495          * @type jQuery
496          * @param Function fn A function to bind to the scroll event on each of the matched elements.
497          * @cat Events/Browser
498          */
499
500         /**
501          * Trigger the scroll event of each matched element. This causes all of the functions
502          * that have been bound to thet scroll event to be executed.
503          *
504          * @example $("p").scroll();
505          * @before <p onscroll="alert('Hello');">Hello</p>
506          * @result alert('Hello');
507          *
508          * @name scroll
509          * @type jQuery
510          * @cat Events/Browser
511          */
512
513         /**
514          * Bind a function to the submit event of each matched element.
515          *
516          * @example $("#myform").submit( function() {
517          *   return $("input", this).val().length > 0;
518          * } );
519          * @before <form id="myform"><input /></form>
520          * @desc Prevents the form submission when the input has no value entered.
521          *
522          * @name submit
523          * @type jQuery
524          * @param Function fn A function to bind to the submit event on each of the matched elements.
525          * @cat Events/Form
526          */
527
528         /**
529          * Trigger the submit event of each matched element. This causes all of the functions
530          * that have been bound to thet submit event to be executed.
531          *
532          * Note: This does not execute the submit method of the form element! If you need to
533          * submit the form via code, you have to use the DOM method, eg. $("form")[0].submit();
534          *
535          * @example $("form").submit();
536          * @desc Triggers all submit events registered for forms, but does not submit the form
537          *
538          * @name submit
539          * @type jQuery
540          * @cat Events/Form
541          */
542
543         /**
544          * Bind a function to the focus event of each matched element.
545          *
546          * @example $("p").focus( function() { alert("Hello"); } );
547          * @before <p>Hello</p>
548          * @result <p onfocus="alert('Hello');">Hello</p>
549          *
550          * @name focus
551          * @type jQuery
552          * @param Function fn A function to bind to the focus event on each of the matched elements.
553          * @cat Events/UI
554          */
555
556         /**
557          * Trigger the focus event of each matched element. This causes all of the functions
558          * that have been bound to thet focus event to be executed.
559          *
560          * Note: This does not execute the focus method of the underlying elements! If you need to
561          * focus an element via code, you have to use the DOM method, eg. $("#myinput")[0].focus();
562          *
563          * @example $("p").focus();
564          * @before <p onfocus="alert('Hello');">Hello</p>
565          * @result alert('Hello');
566          *
567          * @name focus
568          * @type jQuery
569          * @cat Events/UI
570          */
571
572         /**
573          * Bind a function to the keydown event of each matched element.
574          *
575          * @example $("p").keydown( function() { alert("Hello"); } );
576          * @before <p>Hello</p>
577          * @result <p onkeydown="alert('Hello');">Hello</p>
578          *
579          * @name keydown
580          * @type jQuery
581          * @param Function fn A function to bind to the keydown event on each of the matched elements.
582          * @cat Events/Keyboard
583          */
584
585         /**
586          * Trigger the keydown event of each matched element. This causes all of the functions
587          * that have been bound to thet keydown event to be executed.
588          *
589          * @example $("p").keydown();
590          * @before <p onkeydown="alert('Hello');">Hello</p>
591          * @result alert('Hello');
592          *
593          * @name keydown
594          * @type jQuery
595          * @cat Events/Keyboard
596          */
597
598         /**
599          * Bind a function to the dblclick event of each matched element.
600          *
601          * @example $("p").dblclick( function() { alert("Hello"); } );
602          * @before <p>Hello</p>
603          * @result <p ondblclick="alert('Hello');">Hello</p>
604          *
605          * @name dblclick
606          * @type jQuery
607          * @param Function fn A function to bind to the dblclick event on each of the matched elements.
608          * @cat Events/Mouse
609          */
610
611         /**
612          * Trigger the dblclick event of each matched element. This causes all of the functions
613          * that have been bound to thet dblclick event to be executed.
614          *
615          * @example $("p").dblclick();
616          * @before <p ondblclick="alert('Hello');">Hello</p>
617          * @result alert('Hello');
618          *
619          * @name dblclick
620          * @type jQuery
621          * @cat Events/Mouse
622          */
623
624         /**
625          * Bind a function to the keypress event of each matched element.
626          *
627          * @example $("p").keypress( function() { alert("Hello"); } );
628          * @before <p>Hello</p>
629          * @result <p onkeypress="alert('Hello');">Hello</p>
630          *
631          * @name keypress
632          * @type jQuery
633          * @param Function fn A function to bind to the keypress event on each of the matched elements.
634          * @cat Events/Keyboard
635          */
636
637         /**
638          * Trigger the keypress event of each matched element. This causes all of the functions
639          * that have been bound to thet keypress event to be executed.
640          *
641          * @example $("p").keypress();
642          * @before <p onkeypress="alert('Hello');">Hello</p>
643          * @result alert('Hello');
644          *
645          * @name keypress
646          * @type jQuery
647          * @cat Events/Keyboard
648          */
649
650         /**
651          * Bind a function to the error event of each matched element.
652          *
653          * @example $("p").error( function() { alert("Hello"); } );
654          * @before <p>Hello</p>
655          * @result <p onerror="alert('Hello');">Hello</p>
656          *
657          * @name error
658          * @type jQuery
659          * @param Function fn A function to bind to the error event on each of the matched elements.
660          * @cat Events/Browser
661          */
662
663         /**
664          * Trigger the error event of each matched element. This causes all of the functions
665          * that have been bound to thet error event to be executed.
666          *
667          * @example $("p").error();
668          * @before <p onerror="alert('Hello');">Hello</p>
669          * @result alert('Hello');
670          *
671          * @name error
672          * @type jQuery
673          * @cat Events/Browser
674          */
675
676         /**
677          * Bind a function to the blur event of each matched element.
678          *
679          * @example $("p").blur( function() { alert("Hello"); } );
680          * @before <p>Hello</p>
681          * @result <p onblur="alert('Hello');">Hello</p>
682          *
683          * @name blur
684          * @type jQuery
685          * @param Function fn A function to bind to the blur event on each of the matched elements.
686          * @cat Events/UI
687          */
688
689         /**
690          * Trigger the blur event of each matched element. This causes all of the functions
691          * that have been bound to thet blur event to be executed.
692          *
693          * Note: This does not execute the blur method of the underlying elements! If you need to
694          * blur an element via code, you have to use the DOM method, eg. $("#myinput")[0].blur();
695          *
696          * @example $("p").blur();
697          * @before <p onblur="alert('Hello');">Hello</p>
698          * @result alert('Hello');
699          *
700          * @name blur
701          * @type jQuery
702          * @cat Events/UI
703          */
704
705         /**
706          * Bind a function to the load event of each matched element.
707          *
708          * @example $("p").load( function() { alert("Hello"); } );
709          * @before <p>Hello</p>
710          * @result <p onload="alert('Hello');">Hello</p>
711          *
712          * @name load
713          * @type jQuery
714          * @param Function fn A function to bind to the load event on each of the matched elements.
715          * @cat Events/Browser
716          */
717
718         /**
719          * Trigger the load event of each matched element. This causes all of the functions
720          * that have been bound to thet load event to be executed.
721          *
722          * Marked as private: Calling load() without arguments throws exception because the ajax load
723          * does not handle it.
724          *
725          * @example $("p").load();
726          * @before <p onload="alert('Hello');">Hello</p>
727          * @result alert('Hello');
728          *
729          * @name load
730          * @private
731          * @type jQuery
732          * @cat Events/Browser
733          */
734
735         /**
736          * Bind a function to the select event of each matched element.
737          *
738          * @example $("p").select( function() { alert("Hello"); } );
739          * @before <p>Hello</p>
740          * @result <p onselect="alert('Hello');">Hello</p>
741          *
742          * @name select
743          * @type jQuery
744          * @param Function fn A function to bind to the select event on each of the matched elements.
745          * @cat Events/Form
746          */
747
748         /**
749          * Trigger the select event of each matched element. This causes all of the functions
750          * that have been bound to thet select event to be executed.
751          *
752          * @example $("p").select();
753          * @before <p onselect="alert('Hello');">Hello</p>
754          * @result alert('Hello');
755          *
756          * @name select
757          * @type jQuery
758          * @cat Events/Form
759          */
760
761         /**
762          * Bind a function to the mouseup event of each matched element.
763          *
764          * @example $("p").mouseup( function() { alert("Hello"); } );
765          * @before <p>Hello</p>
766          * @result <p onmouseup="alert('Hello');">Hello</p>
767          *
768          * @name mouseup
769          * @type jQuery
770          * @param Function fn A function to bind to the mouseup event on each of the matched elements.
771          * @cat Events/Mouse
772          */
773
774         /**
775          * Trigger the mouseup event of each matched element. This causes all of the functions
776          * that have been bound to thet mouseup event to be executed.
777          *
778          * @example $("p").mouseup();
779          * @before <p onmouseup="alert('Hello');">Hello</p>
780          * @result alert('Hello');
781          *
782          * @name mouseup
783          * @type jQuery
784          * @cat Events/Mouse
785          */
786
787         /**
788          * Bind a function to the unload event of each matched element.
789          *
790          * @example $("p").unload( function() { alert("Hello"); } );
791          * @before <p>Hello</p>
792          * @result <p onunload="alert('Hello');">Hello</p>
793          *
794          * @name unload
795          * @type jQuery
796          * @param Function fn A function to bind to the unload event on each of the matched elements.
797          * @cat Events/Browser
798          */
799
800         /**
801          * Trigger the unload event of each matched element. This causes all of the functions
802          * that have been bound to thet unload event to be executed.
803          *
804          * @example $("p").unload();
805          * @before <p onunload="alert('Hello');">Hello</p>
806          * @result alert('Hello');
807          *
808          * @name unload
809          * @type jQuery
810          * @cat Events/Browser
811          */
812
813         /**
814          * Bind a function to the change event of each matched element.
815          *
816          * @example $("p").change( function() { alert("Hello"); } );
817          * @before <p>Hello</p>
818          * @result <p onchange="alert('Hello');">Hello</p>
819          *
820          * @name change
821          * @type jQuery
822          * @param Function fn A function to bind to the change event on each of the matched elements.
823          * @cat Events/Form
824          */
825
826         /**
827          * Trigger the change event of each matched element. This causes all of the functions
828          * that have been bound to thet change event to be executed.
829          *
830          * @example $("p").change();
831          * @before <p onchange="alert('Hello');">Hello</p>
832          * @result alert('Hello');
833          *
834          * @name change
835          * @type jQuery
836          * @cat Events/Form
837          */
838
839         /**
840          * Bind a function to the mouseout event of each matched element.
841          *
842          * @example $("p").mouseout( function() { alert("Hello"); } );
843          * @before <p>Hello</p>
844          * @result <p onmouseout="alert('Hello');">Hello</p>
845          *
846          * @name mouseout
847          * @type jQuery
848          * @param Function fn A function to bind to the mouseout event on each of the matched elements.
849          * @cat Events/Mouse
850          */
851
852         /**
853          * Trigger the mouseout event of each matched element. This causes all of the functions
854          * that have been bound to thet mouseout event to be executed.
855          *
856          * @example $("p").mouseout();
857          * @before <p onmouseout="alert('Hello');">Hello</p>
858          * @result alert('Hello');
859          *
860          * @name mouseout
861          * @type jQuery
862          * @cat Events/Mouse
863          */
864
865         /**
866          * Bind a function to the keyup event of each matched element.
867          *
868          * @example $("p").keyup( function() { alert("Hello"); } );
869          * @before <p>Hello</p>
870          * @result <p onkeyup="alert('Hello');">Hello</p>
871          *
872          * @name keyup
873          * @type jQuery
874          * @param Function fn A function to bind to the keyup event on each of the matched elements.
875          * @cat Events/Keyboard
876          */
877
878         /**
879          * Trigger the keyup event of each matched element. This causes all of the functions
880          * that have been bound to thet keyup event to be executed.
881          *
882          * @example $("p").keyup();
883          * @before <p onkeyup="alert('Hello');">Hello</p>
884          * @result alert('Hello');
885          *
886          * @name keyup
887          * @type jQuery
888          * @cat Events/Keyboard
889          */
890
891         /**
892          * Bind a function to the click event of each matched element.
893          *
894          * @example $("p").click( function() { alert("Hello"); } );
895          * @before <p>Hello</p>
896          * @result <p onclick="alert('Hello');">Hello</p>
897          *
898          * @name click
899          * @type jQuery
900          * @param Function fn A function to bind to the click event on each of the matched elements.
901          * @cat Events/Mouse
902          */
903
904         /**
905          * Trigger the click event of each matched element. This causes all of the functions
906          * that have been bound to thet click event to be executed.
907          *
908          * @example $("p").click();
909          * @before <p onclick="alert('Hello');">Hello</p>
910          * @result alert('Hello');
911          *
912          * @name click
913          * @type jQuery
914          * @cat Events/Mouse
915          */
916
917         /**
918          * Bind a function to the resize event of each matched element.
919          *
920          * @example $("p").resize( function() { alert("Hello"); } );
921          * @before <p>Hello</p>
922          * @result <p onresize="alert('Hello');">Hello</p>
923          *
924          * @name resize
925          * @type jQuery
926          * @param Function fn A function to bind to the resize event on each of the matched elements.
927          * @cat Events/Browser
928          */
929
930         /**
931          * Trigger the resize event of each matched element. This causes all of the functions
932          * that have been bound to thet resize event to be executed.
933          *
934          * @example $("p").resize();
935          * @before <p onresize="alert('Hello');">Hello</p>
936          * @result alert('Hello');
937          *
938          * @name resize
939          * @type jQuery
940          * @cat Events/Browser
941          */
942
943         /**
944          * Bind a function to the mousemove event of each matched element.
945          *
946          * @example $("p").mousemove( function() { alert("Hello"); } );
947          * @before <p>Hello</p>
948          * @result <p onmousemove="alert('Hello');">Hello</p>
949          *
950          * @name mousemove
951          * @type jQuery
952          * @param Function fn A function to bind to the mousemove event on each of the matched elements.
953          * @cat Events/Mouse
954          */
955
956         /**
957          * Trigger the mousemove event of each matched element. This causes all of the functions
958          * that have been bound to thet mousemove event to be executed.
959          *
960          * @example $("p").mousemove();
961          * @before <p onmousemove="alert('Hello');">Hello</p>
962          * @result alert('Hello');
963          *
964          * @name mousemove
965          * @type jQuery
966          * @cat Events/Mouse
967          */
968
969         /**
970          * Bind a function to the mousedown event of each matched element.
971          *
972          * @example $("p").mousedown( function() { alert("Hello"); } );
973          * @before <p>Hello</p>
974          * @result <p onmousedown="alert('Hello');">Hello</p>
975          *
976          * @name mousedown
977          * @type jQuery
978          * @param Function fn A function to bind to the mousedown event on each of the matched elements.
979          * @cat Events/Mouse
980          */
981
982         /**
983          * Trigger the mousedown event of each matched element. This causes all of the functions
984          * that have been bound to thet mousedown event to be executed.
985          *
986          * @example $("p").mousedown();
987          * @before <p onmousedown="alert('Hello');">Hello</p>
988          * @result alert('Hello');
989          *
990          * @name mousedown
991          * @type jQuery
992          * @cat Events/Mouse
993          */
994          
995         /**
996          * Bind a function to the mouseover event of each matched element.
997          *
998          * @example $("p").mouseover( function() { alert("Hello"); } );
999          * @before <p>Hello</p>
1000          * @result <p onmouseover="alert('Hello');">Hello</p>
1001          *
1002          * @name mouseover
1003          * @type jQuery
1004          * @param Function fn A function to bind to the mousedown event on each of the matched elements.
1005          * @cat Events/Mouse
1006          */
1007
1008         /**
1009          * Trigger the mouseover event of each matched element. This causes all of the functions
1010          * that have been bound to thet mousedown event to be executed.
1011          *
1012          * @example $("p").mouseover();
1013          * @before <p onmouseover="alert('Hello');">Hello</p>
1014          * @result alert('Hello');
1015          *
1016          * @name mouseover
1017          * @type jQuery
1018          * @cat Events/Mouse
1019          */
1020
1021         var e = ("blur,focus,load,resize,scroll,unload,click,dblclick," +
1022                 "mousedown,mouseup,mousemove,mouseover,mouseout,change,select," + 
1023                 "submit,keydown,keypress,keyup,error").split(",");
1024
1025         // Go through all the event names, but make sure that
1026         // it is enclosed properly
1027         for ( var i = 0; i < e.length; i++ ) new function(){
1028                         
1029                 var o = e[i];
1030                 
1031                 // Handle event binding
1032                 jQuery.fn[o] = function(f){
1033                         return f ? this.bind(o, f) : this.trigger(o);
1034                 };
1035                         
1036         };
1037         
1038         // If Mozilla is used
1039         if ( jQuery.browser.mozilla || jQuery.browser.opera )
1040                 // Use the handy event callback
1041                 document.addEventListener( "DOMContentLoaded", jQuery.ready, false );
1042         
1043         // If IE is used, use the excellent hack by Matthias Miller
1044         // http://www.outofhanwell.com/blog/index.php?title=the_window_onload_problem_revisited
1045         else if ( jQuery.browser.msie ) {
1046         
1047                 // Only works if you document.write() it
1048                 document.write("<scr" + "ipt id=__ie_init defer=true " + 
1049                         "src=//:><\/script>");
1050         
1051                 // Use the defer script hack
1052                 var script = document.getElementById("__ie_init");
1053                 
1054                 // script does not exist if jQuery is loaded dynamically
1055                 if ( script ) 
1056                         script.onreadystatechange = function() {
1057                                 if ( this.readyState != "complete" ) return;
1058                                 this.parentNode.removeChild( this );
1059                                 jQuery.ready();
1060                         };
1061         
1062                 // Clear from memory
1063                 script = null;
1064         
1065         // If Safari  is used
1066         } else if ( jQuery.browser.safari )
1067                 // Continually check to see if the document.readyState is valid
1068                 jQuery.safariTimer = setInterval(function(){
1069                         // loaded and complete are both valid states
1070                         if ( document.readyState == "loaded" || 
1071                                 document.readyState == "complete" ) {
1072         
1073                                 // If either one are found, remove the timer
1074                                 clearInterval( jQuery.safariTimer );
1075                                 jQuery.safariTimer = null;
1076         
1077                                 // and execute any waiting functions
1078                                 jQuery.ready();
1079                         }
1080                 }, 10); 
1081
1082         // A fallback to window.onload, that will always work
1083         jQuery.event.add( window, "load", jQuery.ready );
1084         
1085 };
1086
1087 // Clean up after IE to avoid memory leaks
1088 if (jQuery.browser.msie)
1089         jQuery(window).bind("unload", function() {
1090                 var global = jQuery.event.global;
1091                 for ( var type in global ) {
1092                         var els = global[type], i = els.length;
1093                         if ( i && type != 'unload' )
1094                                 do
1095                                         jQuery.event.remove(els[i-1], type);
1096                                 while (--i);
1097                 }
1098         });