Three jsdom axe scans covering the user-facing surface of the canvas.
The scans surfaced two real a11y bugs which are fixed in this same
commit:
1. PerformancePopover — VProgressLinear (advancing aggregate) had no
accessible name. Added aria-label that announces "X van Y secties
afgerond (N%)".
2. AddPerformanceDialog — the icon-only close button (×) was missing
aria-label. Added 'Sluiten'.
Test scenarios:
- PerformanceBlock with focus
- PerformancePopover open
- AddPerformanceDialog open
Page-level axe rules (region, page-has-heading-one, landmark-one-main,
color-contrast) are disabled for fragment scans — they only make sense
on a full page, and color-contrast resolution is jsdom-blind. Both are
covered by Playwright CT in TEST-INFRA-001 / TEST-VISUAL-001.
Test count: 380 → 383.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
11 tests for useTimetableKeyboard (RFC v0.2 D20):
- Arrow Left → nudge(-SNAP_MIN, 0, 0)
- Arrow Right → nudge(+SNAP_MIN, 0, 0)
- Shift+Arrow → nudge(±60min)
- Arrow Up/Down → ±lane
- Shift+Arrow Up/Down → ±stage
- ] / [ → cycle stages preserving time + lane
- Enter → openPopover with the selected performance
- Delete → remove with the selected performance
- Space → drag mode + aria-live announce; Arrow keys accumulate; Enter
commits with the cumulative offset; aria-live announces 'bevestigd'
- Esc cancels keyboard drag, no mutation, aria-live announces 'geannuleerd'
- all keys are no-ops when no performance is selected
Tests the composable directly with a host component that owns a focusable
canvas root and exposes the spies + announce ref — much more reliable
than mounting the whole timetable page (heavy + asynchronous).
Test count: 369 → 380.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>