When I first read about HTML attribute called inert (opens in new window) I immediately wanted to use it on all my custom modals. Some testing showed me it wasn’t supported in any of my browsers and I had to reach for inert polyfill (opens in new window), feeling bad about adding even more JavaScript to the project.
What does inert really do? Well it’s like aria-hidden="true"
, but also prevents interaction on all interactive elements under it. This was not an easy task before (still isn’t if you have to support Internet Explorer). But support was not there.
Typical usage of inert for easier understanding:
<body>
<main inert>
<!-- content with interactive elements now actually inerted - all interactive elements unreachable, nothing exposed to assistive technology -->
<button>Action</button><!-- can't click, can't press, can't touch, can't tab to -->
</main>
<!-- this is reachable -->
<div role="dialog">
<h1>Are you sure?</h1>
<button>OK</button><button>Close</button>
</div>
</body>
Times have changed and inert support in the browsers is currently extremely good (opens in new window), if you don’t have to support Internet Explorer of course. There is browser support and there is also assistive technology support that is vital, so I was happy to read a message from Michael Fairchild when he also confirmed that inert is working fine for all of the critical assistive technologies as well (opens in new window).
Checking a11ysupport.io for inert support (opens in new window) is pleasantly green visually, meaning all tests pass. Tests include all main screen-readers, and all main voice control technologies which is pretty rare in reality.
So if you have to support ARIA made dialogs (I guess that a lot of websites and web applications still have to use ARIA made dialogs instead of native HTML elements) you have a possibility to drop inert polyfill (if you have actually thought of it in the first place).
Mobile screen-readers benefit most from inert
I’ve remembered that ARIA made modals actually worked quite nice with desktop screen-readers, even if they didn’t use inert to prevent user interaction behind dialogs. I wasn’t sure about mobile screen-readers though. So I decided to test the situation and used famous Bootstrap (v 4) modal component (opens in new window) to do so.
By using TalkBack on my Android phone and VoiceOver on my iPhone I could actually navigate behind modal as it was not there at all if I wanted. Modal was preventing this when I used NVDA though.
I tried to add a new GitHub issue or suggestion but as the framework is so popular it was already done by others. I’ve found two related issues there, one suggesting to just use the native HTML dialog element (opens in new window) which seems to be stale from December 2022. And the other one called “iOS and Voiceover ignores the focus trap trick for modal dialogs” (opens in new window), also stale but from march 2021. The default demo in version 4 was missing the aria-modal="true"
and that was also the reason I could reach the content behind it on mobile with a screen-reader. That’s mentioned in the GitHub issue, but it was never closed.
When checking Bootstrap modal in version 5 they added the role="dialog"
and aria-modal="true"
automatically, so it worked fine – preventing content behind modal to be reached with screen-readers.
So if you can’t add aria-modal="true"
you should be using inert on all other siblings of the modal. Otherwise mobile screen-reader users can still reach behind modal.
Inert is useful beyond dialogs
I guess that main use case of inert is to prevent all (!) users to get behind dialogs / modals and so on. But modals are not the only use case. I’ve seen some other use cases that need to disable interactivity behind exposed user interface just like in modal scenario but may not be clear to all developers. One of them is certainly navigation that pops out or over parts of page and is kind of modal but not really. Or so called drawer navigation that can occur when user presses the navigation menu item.
So basically content rendered in the backstage, waiting to be invoked at a later time. Like modals but not a modal. Off-screen menu, in some cases even content in accordions that are using height or opacity instead of visibility and so on.
So inert can be useful beyond dialogs in some cases and it is a good thing that it’s finally gained almost perfect support (not counting Internet Explorer).
Additional resources
- WICG page about inert on GitHub (opens in new window) provides excellent explanation.
- Chrome Developers “Introducing Inert” (opens in new window) has some nice basic examples.
- “Using the HTML inert property to manage user focus” on LogRocked (opens in new window) makes some good points as well.