]> source.dussan.org Git - jquery.git/commitdiff
Fix #12868. Use native focus/blur to get event order right.
authorDave Methvin <dave.methvin@gmail.com>
Fri, 23 Nov 2012 20:03:55 +0000 (15:03 -0500)
committerDave Methvin <dave.methvin@gmail.com>
Sat, 24 Nov 2012 19:44:39 +0000 (14:44 -0500)
src/event.js
test/unit/event.js

index aeee603f7d1818af1976c05356acbdf89d49a419..e92336a917bcf21b1f7946019b7eb10d6c666c57 100644 (file)
@@ -526,16 +526,34 @@ jQuery.event = {
                click: {
                        // For checkbox, fire native event so checked state will be right
                        trigger: function() {
-                               if ( jQuery.nodeName( this, "input") && this.type === "checkbox" && this.click ) {
+                               if ( jQuery.nodeName( this, "input" ) && this.type === "checkbox" && this.click ) {
                                        this.click();
                                        return false;
                                }
                        }
                },
                focus: {
+                       // Fire native event if possible so blur/focus sequence is correct
+                       trigger: function() {
+                               if ( this !== document.activeElement && this.focus ) {
+                                       try {
+                                               this.focus();
+                                               return false;
+                                       } catch ( e ) {
+                                               // IE<9 dies on focus to hidden element (#1486,#12518)
+                                               // If this happens, let .trigger() run the handlers
+                                       }
+                               }
+                       },
                        delegateType: "focusin"
                },
                blur: {
+                       trigger: function() {
+                               if ( this === document.activeElement && this.blur ) {
+                                       this.blur();
+                                       return false;
+                               }
+                       },
                        delegateType: "focusout"
                },
 
index f2f3cddd4b35ea9a2de11b11f16e9f6dd79e95d5..5fd3c1ca78143dd0adce26a328951cf112cd599b 100644 (file)
@@ -2860,6 +2860,50 @@ test("checkbox state (#3827)", function() {
        jQuery( cb ).triggerHandler( "click" );
 });
 
+test("focus-blur order (#12868)", function() {
+       expect( 5 );
+
+       var $text = jQuery("#text1"),
+               $radio = jQuery("#radio1").focus(),
+               order;
+
+       // IE6-10 fire focus/blur events asynchronously; this is the resulting mess.
+       // IE's browser window must be topmost for this to work properly!!
+       stop();
+       $radio[0].focus();
+
+       setTimeout( function() {
+
+               $text
+                       .on( "focus", function(){
+                               equal( order++, 1, "text focus" );
+                       })
+                       .on( "blur", function(){
+                               equal( order++, 0, "text blur" );
+                       });
+               $radio
+                       .on( "focus", function(){
+                               equal( order++, 1, "radio focus" );
+                       })
+                       .on( "blur", function(){
+                               equal( order++, 0, "radio blur" );
+                       });
+
+               // Enabled input getting focus
+               order = 0;
+               equal( document.activeElement, $radio[0], "radio has focus" );
+               $text.focus();
+               setTimeout( function() {
+                       equal( document.activeElement, $text[0], "text has focus" );
+
+                       // Run handlers without native method on an input
+                       order = 1;
+                       $radio.triggerHandler( "focus" );
+                       start();
+               }, 50 );
+       }, 50 );
+});
+
 test("fixHooks extensions", function() {
        expect( 2 );