accessibility

Navigating the 2025 WCAG Guidelines: Essential Accessibility Practices for QA Engineers to Ensure Compliance

Master accessibility with the 2025 WCAG guidelines—vital tips for QA engineers to guarantee compliance and create inclusive digital experiences.

October 10, 2025
WCAG QAengineers accessibility compliance inclusive-design digital-experiences web-standards
17 min read

Why accessibility testing matters more in 2025

Accessibility is no longer a nice-to-have; it’s a baseline requirement for responsible engineering, risk management, and product quality. In 2025, the practical standard to test against is WCAG 2.2 Level AA. While some organizations still reference 2.1 AA, WCAG 2.2 is a W3C Recommendation with new criteria that directly impact QA workflows and test plans. It reflects real user needs—especially for keyboard users, low-vision users, and people with cognitive disabilities—and aligns with global policy momentum, including the EU’s European Accessibility Act (applicable mid-2025 for many consumer-facing products) and increasing enforcement under the ADA and other regional regulations.

This guide distills the 2025 essentials for QA engineers: what changed in WCAG 2.2, how to test efficiently, common failure patterns, and how to embed accessibility into your test strategy so you can guarantee compliance and deliver inclusive experiences.

Note: This article provides practical guidance, not legal advice. Always verify local regulatory requirements and your organization’s policy baseline.


WCAG in 2025: what QA engineers need to know

  • WCAG 2.2 is the current benchmark for most teams. It adds new Level AA criteria around focus visibility, target sizes, dragging movements, visible controls, consistent help, redundant entry, and accessible authentication.
  • WCAG 2.1 and 2.0 are still referenced in some laws and contracts. If your policy says “2.1 AA,” test those, but adopting 2.2 AA now reduces future rework.
  • WCAG 3.0 (a.k.a. “Silver”) remains an evolving draft. Don’t wait for it—build maturity on 2.2 AA now.

Practical takeaway: Set your organization’s accessibility acceptance bar to WCAG 2.2 Level AA. Track any gaps with 2.1 AA that your contracts/regulators still require.


High-impact changes in WCAG 2.2 (and how QA should test them)

Below are the additions and changes QA engineers will encounter most often. Each item includes what it means, how to test, and common pitfalls.

Focus not obscured and focus appearance

  • What it means:

    • Keyboard focus must be clearly visible.
    • The focus indicator can’t be covered by sticky headers/footers, popovers, chat widgets, or cookie banners.
    • The indicator itself must be sufficiently visible and meet specific appearance requirements at AA.
  • How to test:

    1. Use only the keyboard (Tab/Shift+Tab, arrow keys) to navigate every interactive element.
    2. Confirm the focus ring is visible at all times, not hidden by overlays.
    3. Verify the indicator is thick and contrasted enough to stand out. Try a 400% zoom and high-contrast OS modes to ensure it remains visible.
  • Common pitfalls:

    • Default focus rings removed in CSS with no replacement.
    • Sticky headers obscuring focus on anchor targets or inputs.
    • Barely visible focus indicators (e.g., a faint 1px gray outline on gray backgrounds).
  • Example CSS:

    /* Ensure a visible, consistent focus indicator */
    :where(a, button, input, [role="button"], [tabindex]):focus-visible {
      outline: 3px solid #005fcc; /* high-contrast color */
      outline-offset: 2px;
      border-radius: 4px;
    }
    
    /* Prevent overlays from covering focus—manage stacking contexts thoughtfully */
    .sticky-header {
      position: sticky;
      top: 0;
      z-index: 100;
    }
    
    /* Place focusable content above sticky elements when scrolled into view */
    .focus-anchor:focus {
      scroll-margin-top: 80px; /* header height + spacing */
    }
    

Target size (minimum)

  • What it means:

    • Click/tap targets must be big enough to hit without surgical precision—typically at least 24 by 24 CSS pixels, with a few exceptions (e.g., inline text links with sufficient spacing).
  • How to test:

    • On mobile and desktop, measure the clickable area, not just the visible icon.
    • Use dev tools to confirm the hit zone meets 24x24 CSS pixels minimum, or has sufficient spacing around smaller targets.
  • Common pitfalls:

    • Tiny icon-only buttons with 16x16 hit areas.
    • Dense lists of small inline controls like save/delete icons with no padding.
  • Quick fix:

    .icon-button {
      display: inline-flex;
      align-items: center;
      justify-content: center;
      min-width: 24px;
      min-height: 24px;
      padding: 4px; /* increase hit area without enlarging icon */
    }
    

Dragging movements

  • What it means:

    • If users must drag (e.g., sliders, kanban boards), provide an alternative without dragging, such as click/tap controls or keyboard arrows.
  • How to test:

    • Try completing tasks using only keyboard.
    • For touch, try completing tasks without drag; e.g., tap arrows to move items or use a context menu.
  • Common pitfalls:

    • Sliders and drag-and-drop lists with no keyboard or non-drag alternative.
    • Trackpad/touch gestures assumed as the only interaction.
  • Example pattern:

    • For a kanban card: provide “Move left/right” buttons visible on focus and accessible via keyboard; add ARIA announcements when moved.

Visible controls

  • What it means:

    • Controls needed to complete a task must be visible without hover or focus. If controls appear only on hover (e.g., a hidden delete button), they must become visible when the element receives keyboard focus.
  • How to test:

    • Navigate via keyboard and ensure that actionable controls are visible at the moment they’re relevant.
    • On touch devices, verify no “hover-only” affordances block progression.
  • Common pitfalls:

    • Hidden action icons that appear on mouse hover but are inaccessible or undiscoverable to keyboard and touch users.
    • “Invisible” filters or progress buttons disguised as icons with no visible cues.

Consistent help

  • What it means:

    • If a page offers help mechanisms (chat, help phone number, contact link), keep their location and presentation consistent across pages.
  • How to test:

    • Navigate through flows with help mechanisms; confirm their placement and labeling remain consistent.
  • Common pitfalls:

    • Support links jump around page layouts.
    • Inconsistent “Help,” “Support,” and “Contact” labels.

Redundant entry

  • What it means:

    • Don’t force users to re-enter data they already provided. Auto-fill or allow selection of previously entered info.
  • How to test:

    • Complete a multi-step form and confirm values persist or can be selected without re-typing.
    • Check that address, email, and account details are retained where appropriate.
  • Common pitfalls:

    • Checkout flows asking for the same address multiple times.
    • Account setup repeating known data.

Accessible authentication

  • What it means:

    • Logins and verifications must not rely on memorization or solving complicated puzzles. Provide alternatives: copy/paste allowed, “show password,” password manager support, passkeys, or device authentication.
  • How to test:

    • Ensure username and password fields support paste from password managers.
    • Verify “show password” toggles are keyboard accessible and announced to screen readers.
    • CAPTCHAs must have accessible alternatives.
  • Common pitfalls:

    • Disabling paste on password fields.
    • Image CAPTCHAs without accessible alternatives.
    • Visual-only puzzles.
  • Example HTML:

    <label for="password">Password</label>
    <input id="password" name="password" type="password" autocomplete="current-password">
    <button type="button" aria-pressed="false" aria-controls="password" id="togglePassword">Show password</button>
    <script>
      const toggle = document.getElementById('togglePassword');
      const input = document.getElementById('password');
      toggle.addEventListener('click', () => {
        const isText = input.type === 'text';
        input.type = isText ? 'password' : 'text';
        toggle.setAttribute('aria-pressed', String(!isText));
        toggle.textContent = isText ? 'Show password' : 'Hide password';
      });
    </script>
    

Focus visible level change

  • What changed:
    • Focus Visible is treated with increased importance. Many teams now enforce stronger focus visibility by default. In practice, don’t remove outline unless you replace it with an equal or better indicator.

A 2025 accessibility test plan for QA engineers

A robust plan balances automated scanning, manual testing, assistive technology checks, and mobile coverage. Use this structure as a baseline and tailor to your product.

1) Define your baseline and scope

  • Policy baseline: WCAG 2.2 Level AA.
  • Platforms:
    • Desktop: Chrome, Firefox, Safari, Edge
    • Mobile: iOS Safari, Android Chrome
  • Assistive technologies (AT):
    • Screen readers: NVDA + Firefox (Windows), JAWS + Chrome (Windows if available), VoiceOver + Safari (macOS and iOS), TalkBack + Chrome (Android)
  • User settings:
    • Zoom (up to 400%), reduced motion, high contrast/forced colors, dark mode
  • Content types:
    • Web app flows, PDFs, emails, third-party widgets, embedded video/players

2) Automate early and often

  • Static analysis and runtime scanners:
    • axe DevTools / axe-core (integrate with Jest, Cypress, Playwright)
    • Pa11y CI for site-wide scanning
    • Lighthouse accessibility score for incremental checks (not a conformance checker)
  • Example: Jest + axe
    import { configureAxe } from 'jest-axe';
    import '@testing-library/jest-dom';
    import { render } from '@testing-library/react';
    import React from 'react';
    import Component from './Component';
    
    const axe = configureAxe({
      rules: {
        // optionally configure or disable rules per component, but avoid blanket disables
      },
    });
    
    test('Component has no a11y violations', async () => {
      const { container } = render(<Component />);
      const results = await axe(container);
      expect(results).toHaveNoViolations();
    });
    
  • Example: Cypress + axe
    // cypress/support/e2e.js
    import 'cypress-axe';
    
    // cypress/e2e/flow.cy.js
    describe('Checkout flow', () => {
      it('has no critical accessibility violations', () => {
        cy.visit('/checkout');
        cy.injectAxe();
        cy.checkA11y(null, { includedImpacts: ['critical', 'serious'] });
      });
    });
    

Tips:

  • Treat automated findings as unit tests for accessibility regressions.
  • Gate merges on “no critical/serious” issues; track moderate/minor with SLAs.

3) Manual keyboard testing

  • Steps:
    • Tab through the interface; verify visible, logical focus order.
    • Activate all controls with keyboard (Enter/Space).
    • Ensure no keyboard traps (Esc or standard keys move focus out of dialogs/menus).
    • Confirm skip links and landmark navigation exist and work.
  • Quick checks:
    • Is the currently focused element obvious?
    • Can you complete key tasks without a mouse?

4) Screen reader testing essentials

  • NVDA + Firefox (Windows), VoiceOver + Safari (macOS/iOS) provide strong coverage.

  • Core tasks:

    • Read page title, headings, and landmarks.
    • Navigate forms: labels must match visible text; errors announced; hints read in order.
    • Interactive components expose correct roles, names, and states.
    • Dynamic updates announce via aria-live or focus management.
  • Example: Accessible name equals visible label

    <!-- Good: accessible name matches visible label -->
    <label for="email">Email</label>
    <input id="email" name="email" type="email" autocomplete="email">
    

5) Visual checks: contrast, reflow, zoom

  • Contrast:
    • Text: 4.5:1 for body text; 3:1 for large text (18pt/24px regular or 14pt/18.66px bold).
    • UI components and focus indicators need sufficient contrast against adjacent colors.
    • Use tools: axe DevTools color checks, WCAG Contrast Checker, or browser dev tools.
  • Reflow and zoom:
    • At 400% zoom, content should not require two-dimensional scrolling (except for complex data tables or images).
    • Ensure off-canvas menus or sticky elements don’t block content.

6) Motion, gestures, and timing

  • Respect prefers-reduced-motion; provide non-animated alternatives.
  • Provide alternatives to complex gestures (drag/pinch).
  • Timeouts: Warn users, allow extension, and don’t unexpectedly expire form sessions.

7) Forms and error handling

  • Each input must have a programmatic label (label element or aria-label).

  • Display inline error messages programmatically associated with inputs via aria-describedby or similar.

  • Provide clear instructions, not placeholder-only guidance.

  • Preserve data when errors occur.

  • Don’t require re-entry of known information (redundant entry).

  • Example: Error announcement

    <label for="postal">Postal code</label>
    <input id="postal" name="postal" aria-describedby="postal-hint postal-error">
    <div id="postal-hint">Use 5 digits.</div>
    <div id="postal-error" role="alert" class="error">Enter a valid postal code.</div>
    

8) Media, PDFs, and third-party content

  • Video: provide captions; audio description or alternative for essential visuals.
  • PDFs: tag structure, specify reading order, and include alt text.
  • Third-party widgets:
    • Evaluate their accessibility; test with keyboard and screen reader.
    • If not compliant, create a risk register, mitigation plan, or replace the component.
    • Provide accessible alternatives when possible.

Component-level QA checklists and examples

Use these quick checks in your test sessions.

Links and buttons

  • Links navigate; buttons act on the current page—use semantic elements accordingly.

  • Accessible name describes destination or action (avoid “Click here”).

  • State and role correct: toggle buttons use aria-pressed; expanded/collapsed controls use aria-expanded.

  • Example:

    <!-- Toggle details button -->
    <button aria-expanded="false" aria-controls="details" id="toggle-details">More details</button>
    <div id="details" hidden>...</div>
    
    <script>
      const btn = document.getElementById('toggle-details');
      const panel = document.getElementById('details');
      btn.addEventListener('click', () => {
        const expanded = btn.getAttribute('aria-expanded') === 'true';
        btn.setAttribute('aria-expanded', String(!expanded));
        panel.hidden = expanded;
      });
    </script>
    

Forms

  • Labels programmatically associated; visible labels match accessible names.
  • Group related inputs with fieldset/legend (e.g., radio groups).
  • Error messages specific and associated; announce on submission or focus.
  • Support autofill attributes (e.g., autocomplete="email").

Dialogs and modals

  • Open: move focus to the first focusable element inside the dialog.

  • Trap focus within; close with Esc; return focus to the trigger on close.

  • Provide accessible name via aria-labelledby or aria-label.

  • Example:

    <button id="openDialog">Open dialog</button>
    <div role="dialog" aria-modal="true" aria-labelledby="dTitle" hidden id="dialog">
      <h2 id="dTitle">Confirm delete</h2>
      <p>Are you sure?</p>
      <button id="confirm">Delete</button>
      <button id="cancel">Cancel</button>
    </div>
    <script>
      const trigger = document.getElementById('openDialog');
      const dialog = document.getElementById('dialog');
      const cancel = document.getElementById('cancel');
    
      function openDialog() {
        dialog.hidden = false;
        dialog.querySelector('button').focus();
        document.addEventListener('keydown', onKeydown);
      }
      function closeDialog() {
        dialog.hidden = true;
        trigger.focus();
        document.removeEventListener('keydown', onKeydown);
      }
      function onKeydown(e) {
        if (e.key === 'Escape') closeDialog();
      }
      trigger.addEventListener('click', openDialog);
      cancel.addEventListener('click', closeDialog);
    </script>
    

Navigation and headings

  • One H1 per page; logical H2/H3 nesting.
  • Use landmarks: header, nav, main, aside, footer, and ARIA roles where necessary.
  • Provide skip link to main content, visible on keyboard focus.

Tables and data

  • Proper headers with th and scope or headers/id for complex tables.
  • Avoid using tables for layout.
  • Offer responsive alternatives that preserve relationships at small breakpoints (e.g., transform headers into labels within cells).

Carousels and auto-advancing content

  • Pause/stop/hide controls available and keyboard accessible.
  • No automatic movement without controls to pause (respect reduced motion).
  • Announce slide changes if automatic, but avoid interrupting user’s reading.

Infinite scroll and dynamic updates

  • Provide a “Load more” button rather than endless auto-loading where possible.
  • Maintain focus context after loading; move focus to a sensible position (e.g., first new item) or announce updates via aria-live.

Writing accessibility into acceptance criteria

Quality is easier when “done” means “accessible.” Include these patterns in your user stories:

  • Keyboard
    • All interactive elements are reachable and operable with keyboard only; focus is always visible and not obscured.
  • Focus order
    • Tabbing follows visual flow; modals trap focus and return it on close.
  • Names, roles, states
    • Controls expose correct semantics; visible labels match accessible names.
  • Contrast and visibility
    • Text contrasts at least 4.5:1; focus indicators are clearly visible; targets meet minimum size.
  • Forms and errors
    • Each input has a label; errors are specific, announced to assistive tech, and associated to the fields; previously entered data persists.
  • Authentication
    • Paste is allowed; password managers work; accessible CAPTCHA or alternatives provided.
  • Motion and gestures
    • Provide non-drag alternatives; respect reduced motion system preferences.

Example acceptance criteria for a new “Filter” panel:

  • Filter toggle button has a visible label; announces expanded/collapsed state.
  • Filter panel opens as a dialog with aria-modal and a descriptive heading.
  • Keyboard focus moves into the panel on open, stays trapped, and returns to the toggle on close.
  • All controls have labels; checkboxes and radios are grouped with a legend.
  • Apply button is reachable by keyboard; panel can be closed with Esc.
  • Focus indicators are visible; contrast meets minimums.

Common failure patterns (and how to fix them fast)

  • Removing focus outlines for “clean” visuals
    • Fix: Provide custom, high-contrast focus states; test against real backgrounds.
  • Hidden controls that only appear on hover
    • Fix: Also show on focus; avoid hiding critical controls.
  • Icon-only buttons with no accessible name
    • Fix: Add aria-label or include visually hidden text that matches the visible tooltip content.
  • Mismatched label and accessible name
    • Fix: Ensure the accessible name equals the visible label text for voice control users and consistency.
  • Drag-only interactions
    • Fix: Offer tap/click alternatives and keyboard commands; announce state changes.
  • Preventing paste in password fields
    • Fix: Allow paste; support password managers; provide passkeys where available.
  • Low contrast text and focus indicators
    • Fix: Adopt design tokens that enforce accessible color combinations.
  • Inconsistent help/contact affordances across steps
    • Fix: Fix location and labels; ensure parity across pages.
  • Sticky elements covering focused content
    • Fix: Use scroll-margin-top; adjust z-index and layering; ensure focus is never behind overlays.

Triaging accessibility defects like a pro

Each finding should include:

  • The impacted WCAG criterion (e.g., “Focus not obscured; target size minimum; accessible authentication”).
  • Severity and user impact (who is blocked and how).
  • Repro steps with URLs, screenshots, and if applicable, short video or GIF.
  • Environment details (browser, OS, AT versions).
  • Proposed remediation with code examples or design references.

Example report:

  • Summary: “Focus indicator obscured by sticky header on Search Results.”
  • Impact: Keyboard users cannot see which item is focused, causing navigation errors.
  • Steps: Go to /search?q=keyboard; Tab to results; focus is covered by header.
  • Expected: Focus ring fully visible; content scrolls under header with spacing.
  • Fix hint: Add scroll-margin-top to anchor targets; verify z-index stacking contexts.

Severity suggestions:

  • Blocker: Prevents task completion (e.g., keyboard trap, inaccessible authentication).
  • High: Major barrier (e.g., missing labels on key forms, invisible focus).
  • Medium: Significant friction (e.g., low contrast in secondary areas).
  • Low: Cosmetic or minor redundancies.

Embedding accessibility into your SDLC

  • Shift-left in design
    • Run accessibility reviews on wireframes; define color tokens and focus styles early.
    • Require component specs to include names/roles/states, keyboard behavior, and error patterns.
  • Component libraries
    • Centralize accessible components (buttons, dialogs, tabs, menus). Test once, reuse everywhere.
    • Don’t wrap native controls with divs if native semantics suffice.
  • CI/CD gates
    • Block merges on critical/serious automated violations; add manual checkpoints in release checklists.
  • Training and pairing
    • Pair QA with designers and engineers during implementation to prevent rework.
    • Run periodic audits with experts and users with disabilities.
  • Vendor management
    • Request accessibility conformance statements (ACR/VPAT).
    • Test vendor components; demand roadmaps for gaps or provide accessible alternatives.

Mobile and cross-platform considerations

  • iOS + VoiceOver, Android + TalkBack
    • Ensure rotor actions and swipe orders align with visual order.
    • Touch target minimums are crucial; add padding around icons.
  • System settings
    • Respect prefers-reduced-motion and bold text/large text settings.
    • Test zoom and dynamic type; ensure text scales without clipping or truncation.
  • Gestures and affordances
    • Provide button alternatives to swipe/drag.
    • Avoid hover-dependent interactions; touch has no hover.

Quick-start accessibility toolkit for QA in 2025

  • Extensions and tools
    • axe DevTools, WAVE, Accessibility Insights
    • Screen readers: NVDA, VoiceOver, TalkBack
    • Contrast checkers: Stark, WebAIM Contrast Checker
  • Checklists
    • Keyboard-only traversal
    • Forms and errors
    • Focus visibility and not obscured
    • Target size and touch
    • Authentication flow
    • Media captions and descriptions
  • Scripts and guides
    • Keyboard test script: 5-minute pass over core paths before code freeze.
    • Color token reference: approved pairs for accessible contrast.
    • Component behavior docs: what “good” looks like for dialogs, menus, and tabs.

Putting it all together: a sample week for accessibility QA

  • Monday: Review new tickets; add accessibility acceptance criteria; run component-level Jest + axe tests.
  • Tuesday: Manual keyboard and screen reader smoke tests on the latest build; file defects with clear repro and SC references.
  • Wednesday: Pair with engineers on fixes; validate focus styles, target sizes, and form labels; retest with NVDA/VoiceOver.
  • Thursday: Run Cypress + axe across critical paths; verify no critical/serious violations; execute mobile checks on iOS/Android.
  • Friday: Accessibility sign-off: confirm all blockers resolved; document waivers for third-party gaps with mitigations; update regression checklist.

Final thoughts: aim for delightful, not just compliant

Compliance keeps you out of trouble; inclusive design wins customers. WCAG 2.2 AA is the 2025 baseline, and QA engineers play the pivotal role in making it real. Focus on what users experience: visible focus, clear labels, forgiving forms, keyboard-first operability, and predictable interactions. Automate what you can, but never skip human testing—especially with assistive technologies and real devices.

If you do just three things this quarter:

  1. Enforce visible focus and unobscured focus everywhere.
  2. Fix forms: labels, errors, persistence, and accessible authentication.
  3. Increase target sizes and provide non-drag alternatives for all interactions.

With these practices embedded in your test strategy, you’ll deliver accessible, compliant, and genuinely better digital experiences in 2025 and beyond.

Share this article
Last updated: October 10, 2025

Related accessibility Posts

Explore more insights on web performance, security, and quality

Improving Web Accessibility with WCAG 2.1 Compliance

Master the essentials of WCAG 2.1 to lead your website towards enhanced accessib...

Want to Improve Your Website?

Get comprehensive website analysis and optimization recommendations.
We help you enhance performance, security, quality, and content.