Typeahead With Keyboard Navigation
Search-as-you-type with debouncing, request cancellation, arrow-key navigation and the combobox roles.
React · JavaScript — Pratik Rai ·
A select built from scratch — keyboard navigation, focus management, outside-click and the full ARIA listbox contract.
Build a dropdown with no <select> and no library. In the interview this was reported from, the build was followed by a long discussion of design decisions, edge cases, accessibility, state management and performance — so everything past "it opens and closes" is the actual round.
The key modelling decision is separating the highlight from the selection. They feel like one thing and are not: arrowing down moves a highlight and must not commit a value, because someone browsing the list has not chosen yet. Two pieces of state, and aria-activedescendant exists precisely to describe that split — focus stays on the trigger while the announced option moves.
Two details separate a careful implementation from a quick one. Outside dismissal should listen for pointerdown rather than click: a press that begins inside the list and releases outside never produces a click on the document, so the list stays open. And closing must return focus to the trigger — without it, a keyboard user who presses Escape has focus on an element that no longer exists and is dropped at the top of the document.
The honest thing to say at the end is that for a plain single-select, a native <select> gets all of this for free and behaves better on mobile. Knowing when to build this — custom option rendering, multi-select, async loading — and when not to is the senior half of the answer.
Goal: Build a dropdown that works entirely from the keyboard and announces itself correctly.
Continue learning with these related challenges
Search-as-you-type with debouncing, request cancellation, arrow-key navigation and the combobox roles.
React · JavaScript — Pratik Rai ·
A pagination control that always shows the first, last and current pages, collapsing every gap into a single ellipsis.
React · JavaScript — Pratik Rai ·
Given a flat array of items with parentId, render them as nested tabs at arbitrary depth.
React · JavaScript — Pratik Rai ·
Search-as-you-type with debouncing, request cancellation, arrow-key navigation and the combobox roles.
React · JavaScript
Pratik Rai ·
A pagination control that always shows the first, last and current pages, collapsing every gap into a single ellipsis.
React · JavaScript
Pratik Rai ·
Given a flat array of items with parentId, render them as nested tabs at arbitrary depth.
React · JavaScript
Pratik Rai ·