DEV Community

cadguide.tools
cadguide.tools

Posted on Originally published at a11ykit.site

10 Common ARIA Mistakes in React & Next.js (And How to Fix Them)

As web applications become more dynamic, developers increasingly reach for ARIA (Accessible Rich Internet Applications) attributes to make complex widgets accessible.

However, the First Rule of ARIA is famously: "Don't use ARIA if you can use native HTML." Misusing ARIA can actually make an interface less accessible than having no ARIA at all.

Here are the 10 most frequent ARIA anti-patterns we see in modern React and Next.js codebases, and how to fix them.


1. The Fake Button: <div onClick={...}>

// ❌ WRONG
<div className="btn" onClick={handleClick}>Submit</div>

// ✅ RIGHT
<button type="button" onClick={handleClick}>Submit</button>
Enter fullscreen mode Exit fullscreen mode

Native <button> elements come for free with keyboard focus (Tab), activation via Enter and Space, and proper accessibility tree roles.


2. Redundant ARIA Roles

// ❌ Redundant
<button role="button">Click me</button>
<nav role="navigation">...</nav>
Enter fullscreen mode Exit fullscreen mode

Modern screen readers already understand HTML5 semantic tags. Adding duplicate roles creates noise and bloat.


3. Missing aria-expanded on Collapsible Accordions & Dropdowns

Screen reader users need to know whether an accordion panel or mobile menu is currently open or closed:

// ✅ Accessible Accordion Trigger
<button
  type="button"
  aria-expanded={isOpen}
  aria-controls="faq-content-1"
  onClick={() => setIsOpen(!isOpen)}
>
  What is WCAG 2.2?
</button>
<div id="faq-content-1" hidden={!isOpen}>
  WCAG 2.2 is the latest W3C accessibility recommendation...
</div>
Enter fullscreen mode Exit fullscreen mode

4. Unlabelled Icon Buttons

// ❌ Screen reader announces: "Button" (No context!)
<button onClick={handleSearch}><SearchIcon /></button>

// ✅ Accessible
<button onClick={handleSearch} aria-label="Search articles">
  <SearchIcon aria-hidden="true" />
</button>
Enter fullscreen mode Exit fullscreen mode

5. Misusing aria-hidden="true" on Focusable Elements

If an element is focusable via keyboard, hiding it from the accessibility tree causes a "ghost focus" trap:

// ❌ Confusing keyboard trap
<button aria-hidden="true" onClick={openModal}>Open</button>
Enter fullscreen mode Exit fullscreen mode

🛠️ Need Pre-Built Accessible ARIA Markup?

Instead of guessing ARIA attributes from scratch, you can generate verified, copy-pasteable HTML/JSX patterns for 20+ UI components (tabs, modals, tooltips, comboboxes, breadcrumbs):

👉 Generate verified ARIA patterns with A11yKit ARIA Generator

What's the trickiest accessible widget you've had to build in React? Let's discuss below!

Top comments (0)