25

I've been some testing reserching for this other question, when I noticed something very peculiar. FF4/5 fail to fire the focus jQuery event. The other question which might be considered a duplicate was closed and accepted without a real answer.

For the question itself, I tried the following simple bit of code:

$('#target').focusout(function() {
    $(this).focus();
});

It works well in Chrome and in IE, but it fails on FF. Here's the jsFiddle for the lazy ones among us.

Can anyone explain this behavior? Or is it a known bug?

Community
  • 1
  • 1
Madara's Ghost
  • 172,118
  • 50
  • 264
  • 308

4 Answers4

49

I think I ran into this before, and if I recall correctly it seemed to be some kind of reentrancy problem. My impression was that because FF is already in the process of transitioning focus, it won't let you initiate another focus transition. I believe my workaround was something like

$('#target').focusout(function() {
    setTimeout(function() {
        $(this).focus();
    }, 0);
});
chaos
  • 122,029
  • 33
  • 303
  • 309
  • This is the workaround I was provided and it worked perfectly. – Somk Aug 12 '11 at 22:09
  • 4
    +1 because `focus()` does work in Firefox. It is only when contained inside this `focusout()` that seems to be causing the trouble. – tw16 Aug 12 '11 at 22:21
  • Actually setTimeout(func, 0) should be sufficient, as the function is taken out of the context of the executing thread and executed immediately afterwards. 100ms could cause some flickering :) – Jørgen Aug 12 '11 at 22:21
  • 2
    Confirmed that a timeout of 0 will work. Also it's not just focusout() but any action that involves a focus change, in my case just a simple .click() handler. – Swanny Apr 22 '13 at 22:37
  • 1
    I just found out that you might need to wait until the page is ready. I was trying to set the focus form an AJAX loaded content and was able to get the result with the following code:jQuery(document).ready(function() { setTimeout(function() { jQuery('input[name=your-name]').focus(); }, 1500); }); – Camaleo Apr 01 '14 at 11:57
3

The manual says aboult .focus() call

This method is a shortcut for .trigger('focus')

and from the .trigger() topic

Although .trigger() simulates an event activation, complete with a synthesized event object, it does not perfectly replicate a naturally-occurring event.

So as I understand it, the call $(this).focus(); is supposed to trigger the OnFocus event (if there is one attached to the object) but is not quaranteed to actually set/change the focused object.

Marcel Korpel
  • 21,536
  • 6
  • 60
  • 80
ain
  • 22,394
  • 3
  • 54
  • 74
0

This worked for me in Firefox 38. I needed to test different delay ms. Thanks to @camaleo comment.

$(document).ready(function() {
setTimeout(function() { $('#myid').focus(); }, 100);
});
daniel
  • 3,105
  • 4
  • 39
  • 48
0

The focus seems to work now in the latest Firefox without the need of the setTimeout function.

If you want to also select the input field you will have to make use of the .select() function though as document.execCommand('SelectAll'); doesn't seem to work on Firefox either.

So having the input field first focused and then selected you then can copy it or do whatever you want with it.

In my use case I required to copy the url from the input field if someone pressed on the copy button:

$(".copyURL").click(function(){ 
    $(this).prev().focus().select();
    document.execCommand("Copy",false,null);
});

I hope this could help anyone else who's searching for this problem!

Rafaël De Jongh
  • 898
  • 2
  • 14
  • 32
  • I just downloaded the latest firefox (v50.1) and found it did not correct the issue. Perhaps the linux version doesn't have the bug fixed? Meanwhile, many thanks to @chaos for the focusout and setTimeout (using 0 ms) trick. That did solve the problem. – tgoneil Jan 10 '17 at 01:09