Web Accessibility (a11y) & WAI-ARIA
Design inclusive, legal-compliant web applications for screen readers, keyboard-only navigators, and motor-impaired users following WCAG 2.2 guidelines.
1. What is Web Accessibility & the POUR Principles?
Accessibility (a11y) is the practice of ensuring web applications are completely usable by everyone, including people with visual, auditory, motor, or cognitive disabilities. Modern enterprise applications (Google, Microsoft, Apple) mandate strict compliance with the Web Content Accessibility Guidelines (WCAG 2.2).
💡 Real-World Analogy: Wheelchair Ramps & Tactile Pavement
Think of web accessibility like urban architectural design:
• Wheelchair Ramps & Automatic Doors: Equivalent to full keyboard navigation without requiring a physical mouse.
• Braille Signs & Audio Crosswalk Beeps: Equivalent to Screen Reader announcements (`alt`, `aria-label`, `aria-live`).
• High-Contrast Subway Maps: Equivalent to WCAG 4.5:1 Color Contrast ratios for low-vision readers.
Perceivable
Multi-Sensory Delivery
- Text alternatives for non-text content (
alt). - Captions & transcripts for audio/video.
- Minimum 4.5:1 color contrast for text.
Operable
Keyboard-First Control
- All actions usable via Tab and Enter.
- No keyboard traps or unexpected loops.
- Top-of-page Skip Links for main content.
Understandable & Robust
Predictable & Semantic
- Clear error identification and form hints.
- Standard HTML elements recognized by assistive tech.
- Valid document hierarchy (
lang,h1-h6).
2. The First Rule of ARIA & Semantic Defaults
WAI-ARIA (Accessible Rich Internet Applications) is a W3C specification that adds roles, states, and properties to HTML. However, ARIA does not add keyboard handling, focusability, or built-in styling.
"If you can use a native HTML element or attribute with the semantics and behavior you require already built-in, instead of re-purposing an element and adding an ARIA role, state, or property to make it accessible, then DO SO."
<!-- ❌ BAD: Fake div button requiring manual tabindex, keydown enter/space listeners, and focus styles -->
<div role="button" tabindex="0" onclick="openModal()" onkeydown="handleKey(event)">
Open Assessment
</div>
<!-- ✅ GOOD: Native semantic button with built-in Tab focus, Space/Enter trigger, and disabled state -->
<button type="button" onclick="openModal()">
Open Assessment
</button>
3. Accessible UI Components in Production
Interactive widgets like accordions, dialogs, and notifications require precise state attributes (aria-expanded, aria-controls, aria-live) to inform screen reader users of state changes:
<!-- 1. Accessible Accordion with Toggle State -->
<div class="accordion-item">
<button type="button"
aria-expanded="true"
aria-controls="faq-content"
class="accordion-trigger">
Frontend Engineering Curriculum Breakdown
<span aria-hidden="true">▾</span>
</button>
<div id="faq-content" role="region">
<p>Round 1: Cognitive Assessment (90 mins)</p>
<p>Round 2: Technical Coding & DSA (45 mins)</p>
</div>
</div>
<!-- 2. Live Toast Announcement for Async Updates -->
<div aria-live="polite" role="status" class="toast-box">
✓ Progress saved to cloud storage!
</div>
4. `aria-label` vs `aria-labelledby` vs `aria-describedby`
| Attribute | Value Expected | Purpose & Primary Use Case |
|---|---|---|
aria-label |
String text (e.g. "Close dialog") |
Provides an accessible label directly on elements with no visible text (icon buttons, search inputs). |
aria-labelledby |
Target element ID (e.g. "modal-title") |
Points to a visible heading/text node that acts as the element's primary title. |
aria-describedby |
Target element ID (e.g. "pass-hint") |
Points to auxiliary descriptive text (e.g., password format rules, field error messages). |
aria-hidden="true" |
Boolean | Hides purely visual decorative icons/SVGs from screen reader traversal. |
5. Master Tabindex Values
| Tabindex Value | Keyboard Tab Order | JavaScript Focusable (`.focus()`) | Interview Best Practice |
|---|---|---|---|
tabindex="0" |
Natural sequential flow | ✅ Yes | Makes custom interactive elements keyboard-focusable in normal sequence. |
tabindex="-1" |
Skipped by Tab | ✅ Yes | Used for modal containers, error banners, or elements focused programmatically via JS. |
tabindex="1+" |
Forced ahead of natural flow | ✅ Yes | ❌ Anti-Pattern! Breaks intuitive reading order and confuses keyboard users. |
6. Test Your Knowledge: Accessibility (a11y) & ARIA
Verify your mastery of WCAG principles, semantic contrast, and ARIA live regions:
🎯 Placement Interview Master Takeaways
- Always prefer semantic HTML over ARIA: A native
<button>has native focus, keyboard triggers (Space/Enter), and form integration built-in without fragile custom JS. - Never break natural Tab flow: Avoid
tabindex="1+"at all costs. Restrict values strictly to0(natural tab flow) and-1(programmatic focus). - Live region announcements: Use
aria-live="polite"for status indicators, andaria-live="assertive"for critical error banners.