Question

I'm working with Twitter Bootstrap at the moment, and I'm encountering a strange problem in the tabindex of a modal:

I'm trying to tab through the form elements inside the modal, but after the last button the focus disappeared before coming back to the close button. I added a line in console that logs which element is being focused, and it turned out to be the modal itself, even though it has tabindex="-1".

I'm unable to share my code, but a quick look at the Bootstrap docs told me that it also happens in their example modal. The problem is reproducable:

  1. Visit http://getbootstrap.com/2.3.2/javascript.html#modals
  2. Open the demo modal ("Launch Demo Modal" button)
  3. Tab through the fields. You'll lose focus after "Save changes" before it comes back to the close button.

Putting this in console will log whenever the modal (or in fact any element with tabindex="-1") gains focus.

$('[tabindex="-1"]').focus(function(){
    console.log('Focus is on an element with negative tabindex')
});

(It also logs it when you click on the modal obviously, but that's out of scope).

Why does this happen? How can I prevent this? Is this a browser bug, a bug/feature of Twitter Bootstrap, or something else entirely?

Was it helpful?

Solution

Interesting find. It appears to be some sort of bug or behavior introduced by bootstrap; Very odd behavior for tab index -1.

Here is one work around using jQuery, which involves setting a first and last id on the first and last tab-able elements on the modal.

$('#myModal').keydown(function(e){
  if($('#last').is(":focus") && (e.which || e.keyCode) == 9){
    e.preventDefault();
    $('#first').focus();
  }
});

Example

http://www.bootply.com/96858

OTHER TIPS

Thanks to Trevor. This is my final code:

$('.modal').keydown(function(e){
        var $focusable = $(this).find("button, [href], input, select, textarea, [tabindex]:not([tabindex='-1'])");
        if($focusable.last().is(":focus") && !e.shiftKey && e.key == "Tab"){
                e.preventDefault();
                $focusable.first().focus();
        }
        else
            if($focusable.first().is(":focus") && e.shiftKey  && e.key == "Tab"){
            e.preventDefault();
            $focusable.last().focus();
        }

    });

actually focus in going on your main modal div, you can check it by below code

#yourModalId:focus
{
    background-color:yellow;
    border:1px solid red;
}

HTML CODE

 <div id="yourModalId" class="modal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true"></div>
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top