Lesson 17 of 30
A modal isn't just an overlay with a darker backdrop — it's a promise that keyboard focus stays inside it until the user decides, and returns exactly where it left off when they're done. Break either half of that promise and it's a real, common accessibility bug.
12 min read
Every option explains itself — why the right one is right, and why each wrong one is wrong. Miss one and it comes back later on a spaced-repetition schedule.
Question 1 of 3
What actually distinguishes a modal overlay from a non-modal overlay like a popover or dropdown?
Hints without spoilers, and a plain explanation of why a wrong answer was wrong — answered only from this lesson. Free account, no card.
Sign up freeWhat interviewers actually ask about this, and what a strong answer has to cover.
A strong answer covers
Likely follow-ups
Modal overlays block interaction with the rest of the page and demand a decision before the user can go back to it — a delete confirmation, a required setup step. Non-modal overlays (a popover, a dropdown menu, a toast) coexist with the page: the user can ignore them, click elsewhere, and they'll dismiss without forcing a choice. The distinction isn't the backdrop or the visual style — a popover can have a subtle shadow and a modal can have none — it's whether the background stays interactive.
Once something is a true modal, two behaviors aren't optional polish, they're the actual contract:
<body>. Otherwise a keyboard user has to re-navigate from scratch to find where they were.<dialog> versus a hand-rolled overlay<dialog id="confirm">
<p>Delete this item?</p>
<button value="cancel">Cancel</button>
<button value="confirm">Delete</button>
</dialog>
const trigger = document.querySelector("#delete-btn");
const dialog = document.querySelector("#confirm");
trigger.addEventListener("click", () => dialog.showModal());
// showModal() traps focus inside the dialog and makes the rest of the page inert automatically
dialog.addEventListener("close", () => trigger.focus());
// returning focus is still the author's job — no browser API does this part for you
Idle — a trigger button sits on the page. The modal is closed and focus is wherever the user left it.
The native <dialog> element's showModal() is one of the rare cases where the platform does the hard part for free: focus trapping and marking the background inert are both handled automatically. A hand-rolled position: fixed overlay built from a plain <div> has to reimplement that manually — tracking the first and last focusable elements inside it and intercepting Tab at the boundaries. What neither approach gives you for free is returning focus to the trigger on close — that line is always the author's responsibility, native or custom.
<body> on close is a common half-fix. It stops focus from vanishing entirely, but a keyboard user still has to tab all the way from the top of the page to get back to where they were — the fix is a specific return target, not just "somewhere valid.""Why does this modal feel broken when I use only the keyboard" is a real, specific diagnostic question — the strong answer names focus trapping and return-to-trigger by name, and can describe what a platform primitive like <dialog> handles automatically versus what a hand-rolled overlay still has to implement manually.