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