6

Imagine I have a div A, which is absolute positioned. Inside this div A, there may be several input controls. I want all of these controls to be inaccessible through click events. I also want to prevent them to be accessible through tab, that is, gaining focus. I want them to be like dead, but not visually disabled.

What is the best way to achieve that?

Andre Pena
  • 56,650
  • 48
  • 196
  • 243
  • Most overlays trap keypresses inside the form that is in the overlay and only allow for tab to work when in the overlay. Add an event handler on the document and if that gets hit, cancel the tab. – epascarello Dec 20 '15 at 15:45
  • Would adding the disabled attribute to the input work? (i.e., ) – nocturns2 Dec 20 '15 at 17:40

2 Answers2

2

You can prevent mouse actions with pointer-events: none:

To prevent the contents from being focusable, you can do some of these:

  • Set a negative tabindex to each element which has a tabindex focus flag set by default

    Technically the element will still be focusable, but it won't be reached using sequential focus navigation.

  • Make them inert

    However, I don't know any way do do this except with a modal dialog, which makes the entire document inert.

  • Disable each element

    Note not all elements can be disabled

  • Use JS to undo focus.

    Note the focus (nor focusin) event is not cancelable, but you can undo it with .blur().

    Since focus doesn't bubble, if you want event delegation you must listen to capture phase

    element.addEventListener('focus', function(event) {
      event.target.blur();
    }, true);
    

Example:

document.querySelector('div').addEventListener('focus', function(e) {
  e.target.blur();
}, true);
div {
  pointer-events: none;
}
<div>
  <button type="button">I am a button</button>
  <input type="button" value="I am an input button" />
  <input type="text" value="I am a text button" />
  <a href="javascript:void(0)">I am an anchor</a>
</div>
Oriol
  • 274,082
  • 63
  • 437
  • 513
  • Add `tabindex="-1"` as attribute for the inputs / buttons, which will make it non-focusable with tab too! (Ref: http://stackoverflow.com/questions/3682812/disabling-tab-focus-on-form-elements) – Tᴀʀᴇǫ Mᴀʜᴍᴏᴏᴅ Dec 20 '15 at 15:52
1

There are a couple of ways to do it. One is to set tabindex of all the elements to -1. The other is to not worry about tabindex and just block tab if you are not in the modal.

This is the basic idea, not a full solution for allowing tabs. This allows you to see how to detect if you are in the modal to allow for tab and cancels it when you are not in the modal.

You would need to add more logic to the code to see if you are in the last textbox on the modal or if you are on the first with shift tab.

(function () {
    var allow = false,
        isModalActive = true;
    document.getElementById("overlay").addEventListener("keydown",  function(evt){
        var keyCode = evt.keyCode || evt.which;
        if (keyCode === 9) {
           allow=true;  
        }
        //TODO FOR YOU determine if the current element is on the last textbox and than you would need to loop to the first element in the textbox.   Also need to detect if it is shift tab for the first element...
      
    });
    document.body.addEventListener("keydown", function(evt){
        var keyCode = evt.keyCode || evt.which;
        if (isModalActive && keyCode === 9 && !allow) {
            evt.preventDefault();
        }
        allow=false;
    });
}());
#overlay{
  border: 1px solid black;
  background-color: #CCC;
  padding: 2em;
}
<input type="text">
<div id="overlay">
    <input type="text"> 
    <input type="text">
    <input type="text">
</div>
<input type="text">
 
epascarello
  • 204,599
  • 20
  • 195
  • 236