Make import candidate selection a native radiogroup - #136
Merged
Conversation
The iTunes match candidates in SearchResultBlock were bare clickable <div>s — no role, no tabIndex, no keyboard path, nothing exposed to assistive tech. They are now <button role="radio"> rows inside a labelled role="radiogroup" using the wizard's existing roving pattern (lib/use-roving-radiogroup.ts): Tab enters the group on the chosen row (first row when nothing is chosen, via rovingTabIndex), arrows move with selection-follows-focus, and clicking/Space on the chosen row still clears it — the hook's checked guard keeps arrow passes from clearing rows on the way through. Details: - group aria-label carries the query (new i18n key onboard.search_block.candidates_group_aria, en + zh) - the decorative checkmark span is aria-hidden and the candidate icon alt is empty — the row's accessible name is the candidate name/dev text, not repeated image alt - .candidate-row CSS neutralises UA button chrome; layout unchanged - the fixme-gated keyboard spec in onboarding-keyboard.spec.ts is now live and guards the arrow-selection contract (Shift+Tab into the group, ArrowDown selects the alternate candidate) Verified: full Playwright suite 34 passed / 0 skipped (axe scan of the match step, keyboard specs, and all click-based candidate flows); 438 unit tests; typecheck, lint, and locale parity clean. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
The iTunes match candidates in the onboarding wizard's
SearchResultBlockwere bare clickable<div>s — no role, no tabIndex, no keyboard path, invisible to assistive tech. This converts them to<button role="radio">rows inside a labelledrole="radiogroup", reusing the wizard's existing roving-radiogroup pattern (lib/use-roving-radiogroup.ts, the same one the method and AI-provider cards use):rovingTabIndex); arrows move with selection-follows-focus; Home/End and RTL flipping come with the shared hook.aria-labelcarries the query (new i18n keyonboard.search_block.candidates_group_aria, en + zh).aria-hiddenand the candidate icon's alt is now empty, so the row's accessible name is the candidate name/developer text rather than the name read twice..candidate-rowCSS neutralises the UA button chrome — visual layout is unchanged.Test changes
The
fixme-gated candidate-selection spec intests/e2e/onboarding-keyboard.spec.ts— committed with the a11y gate (#134) as this fix's acceptance test — is now live: it walks the wizard keyboard-only, steps into the radiogroup with Shift+Tab, and selects the non-default Apple candidate with ArrowDown, asserting focus,aria-checked, and thechosenstate.Verification
onboard-import.spec.ts.pnpm typecheck,pnpm lint,pnpm lint:i18n(4,760 keys at parity) all clean.🤖 Generated with Claude Code