Keyboard Navigation: Every Function Without a Mouse
Full keyboard operability is one of the most fundamental WCAG and BFSG requirements. Criterion 2.1.1 requires that all functions of a website are reachable via keyboard without requiring specific timing for individual keystrokes. Yet according to a W3C/WAI analysis, 86% (project experience) of all websites violate at least one keyboard-related WCAG criterion. For users who cannot operate a mouse, such as people with motor impairments, screen reader users or power users, every missing keyboard support is an insurmountable barrier.
Why Keyboard Navigation Is Essential
The keyboard is the most universal input device for accessible web use. Screen readers are based on keyboard commands, voice control software translates voice commands into keyboard actions, switch devices for people with severe motor impairments emulate keystrokes. When a website is keyboard-operable, it automatically works with these assistive technologies as well.
Furthermore, many people without disabilities also use the keyboard as their primary navigation tool. Developers who quickly switch between form fields, users with repetitive strain injury who avoid mouse movements, and power users who use keyboard shortcuts for efficiency all rely on consistent keyboard navigation. A website that is unusable via keyboard excludes a significant portion of its users.
WCAG defines several criteria for keyboard navigation: 2.1.1 Keyboard (Level A) requires basic reachability of all functions, 2.1.2 No Keyboard Trap (Level A) prohibits focus traps, 2.4.3 Focus Order (Level A) requires a meaningful focus order, and 2.4.7 Focus Visible (Level AA) requires visible focus indicators. These criteria form the minimum requirement for BFSG compliance.
Tab Order and DOM Order
Tab order determines the sequence in which elements receive focus when the user presses the Tab key. By default, tab order follows DOM order: elements are focused in the order they appear in the HTML source. This natural order is almost always correct. Only interactive elements like links, buttons, form fields and elements with tabindex="0" are part of the tab order.
A common error is using CSS layout techniques like Flexbox with order or CSS Grid that decouple visual order from DOM order. If the visual order on screen reads left to right A, B, C but the DOM order is B, A, C, focus appears to jump arbitrarily, disorienting keyboard users.
The tabindex attribute should be used with great caution. tabindex="0" makes an element focusable and inserts it into the natural tab order. tabindex="-1" makes an element programmatically focusable (via JavaScript) but removes it from tab order. Positive tabindex values like tabindex="1" or tabindex="5" are almost always an error as they create an artificial order that is unmaintainable with page changes.
Skip Links: Bypassing Navigation
Skip links allow keyboard users to bypass recurring page elements like header and navigation and jump directly to the main content. Without skip links, keyboard users must tab through all navigation links on every page before reaching the actual content. With a navigation containing 20 links, that means 20 tab presses before the first content link.
A skip link is the first focusable link on the page and points to the beginning of the main content (typically the element). It is visually hidden by default and appears only when focused via keyboard. The CSS implementation uses position: absolute and transform: translateY(-100% (project experience)) in the normal state and shows the link visibly on :focus.
On complex pages, multiple skip links can be useful: Skip to content, Skip to search, Skip to navigation. These are implemented as a compact list at the page beginning. The target anchor needs tabindex="-1" so focus is correctly set and the screen reader reads the main content. Accessible web development implements skip links as a standard feature.
Skip Links
First focusable link on the page. Jumps to main content. Visible only on keyboard focus. Required per WCAG 2.4.1.
Focus Management
On page changes, modal openings and dynamic content, focus must be actively managed.
No Keyboard Traps
User must be able to leave every element via keyboard. Modals need Escape closing and focus return.
Logical Tab Order
DOM order = visual order. No positive tabindex. CSS order not for interactive elements.
Visible Focus
:focus-visible with 3:1 contrast and 2px minimum width. Never outline:none without replacement.
Custom Widgets
Tabs, accordions, dropdowns and sliders need full keyboard support per WAI-ARIA Patterns.
Detecting and Avoiding Keyboard Traps
A keyboard trap occurs when keyboard focus can navigate into an element but cannot leave it via keyboard. WCAG criterion 2.1.2 (Level A) explicitly prohibits keyboard traps. Common causes are embedded content like iFrames with third-party widgets, video players without keyboard controls, WYSIWYG editors and canvas elements.
The only permissible exception is modal dialogs where focus is intentionally trapped within the modal (focus trap). This focus trap is desired and necessary so keyboard users do not accidentally navigate behind the modal. However, the focus trap must meet two conditions: the modal must be closable via the Escape key, and after closing, focus must return to the triggering element.
To test for keyboard traps, a simple manual test suffices: starting at the page beginning, navigate through the entire page with the Tab key. At every point, the user must be able to continue navigating via Tab or Shift+Tab. If focus gets stuck at a point and neither Tab nor Shift+Tab nor Escape allows further movement, a keyboard trap is present.
Focus Management for Dynamic Content
When page content changes dynamically, such as opening a modal, loading new content or switching a tab, focus must be actively managed. Without focus management, focus remains where the action was triggered while new content appears elsewhere on the page. Keyboard users must then laboriously navigate to the new content.
When opening a modal, focus is set to the first focusable element in the modal, typically the heading or close button. When closing, focus returns to the element that opened the modal. In tab interfaces, focus is set to the associated tab panel when a tab is activated. For infinite-scroll content, focus is set to the beginning of the new content.
In single-page applications (SPAs), focus management during route changes is particularly important. When the user clicks a link and a new page loads without a full page reload, focus must be set to the beginning of the new content. Otherwise focus remains on the old link and the screen reader user does not notice the change.
Roving Tabindex: Managing Complex Navigation Groups
In navigation groups like tab bars, toolbars or menus with many entries, the roving tabindex is the recommended pattern: only the currently active element receives tabindex="0", all others tabindex="-1". Arrow keys shift the active index, and Tab exits the entire group. This pattern drastically reduces the number of tab stops -- a toolbar with 20 icons requires only a single tab stop instead of twenty.
The alternative to roving tabindex is aria-activedescendant: the container remains focused, and the currently active child element is referenced via attribute. This pattern is particularly suited for listboxes, comboboxes and grid widgets. Both patterns are documented in the WAI-ARIA Authoring Practices 1.2 and are supported by all common screen readers.
Custom Widgets: Tabs, Accordions and Dropdowns
Custom widgets like tab interfaces, accordions, dropdown menus and carousels require full keyboard support per the WAI-ARIA Authoring Practices. A tab interface is navigated between tabs via arrow keys, activated via Enter or Space, and the Tab key leaves the widget and jumps to the next focusable element after the tab panel.
Accordions support Enter or Space to open and close, arrow keys to navigate between accordion headers, Home for the first header and End for the last. Dropdown menus open via Enter or Space or down-arrow, close via Escape, and menu items are navigated via arrow keys. These patterns are documented in the WAI-ARIA Authoring Practices and form the standard.
Implementation requires JavaScript for event handling: keydown events capture the pressed key and execute the corresponding action. ARIA attributes communicate state to screen readers: aria-expanded for open accordions, aria-selected for active tabs, aria-haspopup for dropdown triggers. The correct combination of keyboard interaction and ARIA semantics is the core of accessible custom widgets.
ARIA Patterns: Keyboard Control for Complex Interactions
The WAI-ARIA Authoring Practices define standardized keyboard patterns for common widget types. A datepicker, for example, uses arrow keys to navigate between days, Page Up/Down for months, Home/End for week start and end, and Enter for selection. These patterns are not recommendations but expectations: users of assistive technologies have learned that a widget with the role "grid" operates this way. If the implementation deviates, the widget is effectively unusable.
Keyboard control of drag-and-drop interactions is particularly demanding. Visual drag-and-drop operations must provide an equivalent keyboard alternative -- such as Space to pick up an element, arrow keys to move it and Enter to place it. Comfortable implementations additionally provide live region announcements stating the current state: "Element picked up. Position 2 of 5. Press down arrow to move." These text announcements make the interaction comprehensible for screen reader users without missing visual information.
Designing Focus Indicators
WCAG criterion 2.4.7 (Level AA) requires that keyboard focus is visible. In practice, this means a visual ring or highlight around the focused element. The browser's default focus indicator is functionally sufficient but is considered visually disruptive by many designers and removed via outline: none. This is only permitted when an equivalent or better replacement is implemented.
The CSS pseudo-class :focus-visible resolves the dilemma between design aesthetics and accessibility. It shows the focus indicator only during keyboard navigation, not on mouse clicks. Browsers implement a heuristic that detects whether focus was triggered by keyboard or mouse interaction. This keeps the design clean for mouse users while keyboard users receive a clear focus indicator.
A good focus indicator is at least 2 pixels wide, has a contrast of at least 3:1 against the background, uses a distinctive color that stands out from the primary design, and has a slight offset so it is not obscured by the element. On pages with varying backgrounds, a double outline in a light and a dark color is recommended.
Systematically Testing Keyboard Navigation
The keyboard test is one of the simplest yet most informative accessibility tests. It requires no special tools, just the computer's keyboard. The tester navigates with Tab, Shift+Tab, Enter, Space, Escape and arrow keys through the entire page, systematically checking: Is every interactive element reachable? Is the focus order logical? Is focus always visible? Are there keyboard traps?
In addition to manual testing, automated testing tools and browser developer tools can identify basic keyboard problems: missing focusable elements, tabindex misuse and missing ARIA attributes. However, these tools do not replace manual testing, as they cannot check complex interaction patterns and focus flows. A professional WCAG audit combines both approaches for complete coverage.
Systematic testing also reveals edge cases that rarely occur in normal usage flow: what happens when a modal dialog opens while focus is on an element outside the dialog? Is focus correctly moved into the dialog and returned after closing? What happens with dynamically loaded content -- is focus set to the new content or does it remain on the triggering element? These detail questions determine whether keyboard navigation not only works technically but also provides a comfortable user experience.