3.2.1 On Focus
What it requires
When any component receives keyboard focus, it must not automatically trigger a change of context. Moving focus to a control — by tabbing, clicking, or scripting — is allowed to do nothing visible beyond the normal focus indicator. It must not, on its own, do things like open a new window, move focus elsewhere, submit a form, or otherwise substantially rearrange the page.
A “change of context” means a major change a user could miss: a new window or tab, a change of user agent, a change of viewport, a shift of focus to a different component, or content change that significantly alters the page’s meaning. The criterion is about receiving focus only — acting on a deliberate activation (a click or Enter) is covered separately by 3.2.2 On Input.
- Keyboard-only users, who tab through controls to explore a page — an unexpected jump or new window strands them away from where they were.
- Screen reader users, who may not perceive that the window, focus, or page meaning changed, and lose their place.
- People with cognitive or attention disabilities, who are disoriented by content that shifts without a deliberate action.
- Low-vision and magnification users, whose narrow viewport makes an unannounced context change easy to miss entirely.
How to detect it
| Check | What to look for |
|---|---|
| Keyboard tabbing | Tab through every focusable control. Focus arriving should never open a new window, submit, or jump focus elsewhere. |
| Select & menu controls | Focus (not change) a native select or custom menu — it must not
navigate or reload on focus alone. |
| Screen reader | Confirm focus moves predictably and the reading position is not silently relocated. |
| Zoom / small viewport | At 200%+ zoom, verify focus does not cause off-screen content shifts you can’t see. |
| Automated tools | Tools like axe cannot reliably catch this — it is behavioural and needs manual keyboard testing. |
How to fix it
- Never wire navigation, submission, or window-opening to a
focusevent. Use deliberate activation events (click,changevia Enter/Space) instead. - For dropdowns, let focus and arrow-key browsing reveal options without acting; only act when the user explicitly confirms a choice.
- Don’t auto-submit forms or move focus when a field is reached during tabbing.
- Provide a visible control (button or link) for any action, so the user triggers the context change on purpose.
<!-- Focus reveals options; action waits for a deliberate change -->
<label for="country">Country</label>
<select id="country" name="country">
<option value="">Choose…</option>
<option value="ie">Ireland</option>
</select>
<button type="submit">Apply</button>
Copy-paste tests
Automated coverage
There is no fully automated axe-core rule for 3.2.1 On Focus — it is behavioural, so it needs manual review. Use the console check and steps below to surface suspects, then verify each by keyboard.
Run this in the browser console
// READ-ONLY: flags controls that may act on focus. Review each by keyboard.
const suspects = [...document.querySelectorAll('[onfocus], select, [role="menu"], [role="listbox"]')];
suspects.forEach(el => el.style.outline = '2px solid orange');
console.table(suspects.map(el => ({
tag: el.tagName.toLowerCase(),
id: el.id || null,
onfocus: el.getAttribute('onfocus') || null,
role: el.getAttribute('role') || null
})));
What to check manually: Tab onto each flagged control and confirm that merely receiving focus opens no new window/tab, submits nothing, and never moves focus elsewhere — no script can confirm whether a context change actually fires on focus.
Related
- All WCAG 2.2 success criteria
- Browse the Learn catalog
- Keyboard & focus — focus order, indicators, and predictable focus behaviour.