Assuming we have a DOM:
...
<div>
// child nodes
</div>
<div id="needsToNotBeFocusable">
// child nodes
</div>
...
Is there a way to make <div id="needsToNotBeFocusable">
and its child nodes not focusable?
Setting tabindex="-1"
on each child node will ruin already existing tabindexes.
Assuming we have a DOM:
...
<div>
// child nodes
</div>
<div id="needsToNotBeFocusable">
// child nodes
</div>
...
Is there a way to make <div id="needsToNotBeFocusable">
and its child nodes not focusable?
Setting tabindex="-1"
on each child node will ruin already existing tabindexes.
- Can you explain more about your question? child nodes should not be a highlight? – Karthick Nagarajan Commented Nov 13, 2019 at 15:44
-
Is
needsToNotBeFocusable
not visible or something? – epascarello Commented Nov 13, 2019 at 15:46 -
@karthicknagarajan child nodes shouldn't be able to receive keyboard focus, just like if every single one of them has attribute
tabindex="-1"
– da0k0B0y Commented Nov 13, 2019 at 15:47 - If the div in question is within a single form, check this out: stackoverflow./a/17186342/1394872 – Darvanen Commented Aug 11, 2021 at 3:41
- Does this answer your question? Make an HTML element non-focusable – rozsazoltan Commented Jan 10, 2024 at 12:15
3 Answers
Reset to default 8You can now achieve this by adding the inert attribute to <div id="needsToNotBeFocusable">
:
input {display:block}
<div>
inside plain div: <input>
<div>
<div id="needsToNotBeFocusable" inert>
inside inert div: <input>
</div>
<div>
inside plain div: <input>
<div>
The inert global attribute is a Boolean attribute indicating that the browser will ignore the element. With the inert attribute, all of the element's flat tree descendants (such as modal s) that don't otherwise escape inertness are ignored. The inert attribute also makes the browser ignore input events sent by the user, including focus-related events and events from assistive technologies.
Firstly, there's a distinction between "not-focusable by tab key" and "never-focusable (programmatically, by click, or by tab)". The former is achieved with setting the tabindex="-1"
attribute, the latter by adding a disabled
attribute.
input {display:block}
<input>
<input>
disabled: <input disabled>
tab -1: <input tabindex="-1">
<input>
<input>
Setting tabindex="-1" on each child node will ruin already existing tabindexes.
I don't see what you mean. How could tabindex be ruined for a un-tab-focusable element?
Is there a way to make and its child nodes not focusable?
Div's can't be focused in the normal sense (though they can be scrolled to). But making its children unfocusable simply requires iterating its children (possibly multiple levels deep) and either settint tabindex
or disabled
.
let recursiveUnfocusable = el => {
el.disabled = true;
[...el.children].forEach(recursiveUnfocusable);
};
let div = document.querySelector('#needsToNotBeFocusable');
recursiveUnfocusable(div);
...
<div>
<input><input><input>
</div>
<div id="needsToNotBeFocusable">
<input><input><input>
<div>
<input><input><input>
</div>
</div>
...
You probably want to use data attributes to hold the tab index and set it when you enable it.
document.querySelector("#inp1").addEventListener("input", function() {
var enabled = this.value.length > 0
document.querySelectorAll("#needsToNotBeFocusable [data-index]").forEach(function(elem) {
elem.tabIndex = enabled ? elem.dataset.index : -1
})
})
<div>
<input id="inp1" tabIndex="1" placeholder="tab 1" />
</div>
<div id="needsToNotBeFocusable">
<input data-index="2" tabIndex="-1" placeholder="tab 2" />
<input data-index="5" tabIndex="-1" placeholder="tab 5" />
<input data-index="3" tabIndex="-1" placeholder="tab 3" />
<input data-index="6" tabIndex="-1" placeholder="tab 6" />
<input data-index="4" tabIndex="-1" placeholder="tab 4" />
</div>
<input tabIndex="7" placeholder="tab 7"/>