← All criteria

Operable · Level A · 2.4.3

Focus Order

When a page can be navigated by pressing Tab in sequence, that sequence has to stay logical enough to preserve meaning and operability. It doesn't have to match the visual layout exactly — but it can't be arbitrary either.

  • Low vision
  • Cognitive
  • Motor
The problem, in practice — select the image to enlarge it
A page compared with disorienting versus logical focus order. 'Disoriented focus order' shows a page with logo, nav links, an image, a welcome card, and a news section, where numbered focus stops jump erratically from the nav to the news section to the image and back, leaving a confused user unsure what just happened. 'Logical focus order' shows the same layout with focus moving in a clean numbered sequence through the nav, then the welcome card and its button, then the email field and subscribe button, then the news section, matching a predictable reading flow. Paired examples below contrast focus jumping to unrelated items or following visual placement instead of logical sequence with focus flowing from main content to sidebar and following header, nav, main, footer in order.

How to recognize it

Tab through the page from the top and watch where focus lands each time, without touching the mouse. Three patterns fail this: focus jumping from a form's first field to an unrelated part of the page before coming back to the second field; a modal dialog that opens without focus moving into it, so Tab keeps walking through the page hidden behind it; and dynamically injected content — an autocomplete list, an expanded accordion panel — that's placed at the end of the DOM even though it visually appears in the middle of the page, so focus order visually teleports. None of this requires the tab order to match left-to-right, top-to-bottom reading order exactly — the actual bar is lower than that: does the sequence stay logical enough that you're not left disoriented about what you just interacted with?

How to fix it

The most common cause is DOM order silently drifting away from visual order — CSS (flexbox/grid order, absolute positioning) can make something appear first without it being first in the markup, and Tab always follows DOM order, not the visual one. Fix the DOM order itself rather than patching the visual result with CSS. For dialogs and other content that appears dynamically, move focus into it programmatically the moment it becomes visible, and return focus to whatever triggered it when it closes. A modal also needs role="dialog" (or role="alertdialog") and aria-modal="true" on its container — that's a 4.1.2 requirement, not a 2.4.3 one, but the two go hand in hand in practice: moving focus into a container that has no role tells a screen reader user where they landed but not that they're now inside a dialog. Test this the same way a keyboard user would: by actually tabbing through, not by reading the code.

Example

Avoid

<form>
  <input name="email" style="order: 2">
  <input name="name" style="order: 1">
</form>
<div id="modal" hidden>
  <h2>Confirm delete</h2>
</div>

function openModal() {
  modal.hidden = false;
  // no role, and focus never moves — Tab keeps walking through the page behind it
}
<div id="page-content">...</div>
<div id="accordion-panel-2" hidden>Revealed in the middle of the page, but rendered at the very end of the DOM</div>

Prefer

<form>
  <input name="name">
  <input name="email">
</form>
<div id="modal" role="dialog" aria-modal="true" aria-labelledby="modal-title" hidden>
  <h2 id="modal-title">Confirm delete</h2>
</div>

function openModal() {
  modal.hidden = false;
  modal.querySelector('h2').focus();
}
<div id="page-content">
  ...
  <div id="accordion-panel-2" hidden>Rendered right where it visually appears, in DOM order</div>
</div>

Resources