Building Accessible Components with Vanilla JavaScript
In today’s digital landscape, web accessibility is not just a necessity; it’s a fundamental principle that guides design and development. Building components that everyone can use, regardless of their abilities, includes using Semantic HTML and ensuring that your site can be navigated effectively with assistive technologies. This article will walk you through how to create accessible UI components using vanilla JavaScript, focusing on enhancing user experience for all.
Understanding Accessibility
Web accessibility refers to the practice of making websites usable for people of all abilities and disabilities. According to the World Health Organization, over a billion people live with some form of disability. If your web application is not accessible, you are alienating a significant portion of your audience.
Accessibility standards such as the Web Content Accessibility Guidelines (WCAG) outline how to create user-friendly components. These guidelines categorize accessible practices into four principles: Perceivable, Operable, Understandable, and Robust (POUR).
Setting the Stage: Semantic HTML
Before diving into JavaScript, it’s essential to understand the role of semantic HTML. Using the right HTML elements improves accessibility significantly. For example, instead of using div elements for buttons or links, utilize button, anchor, and other semantic elements. This approach helps screen readers interpret your content correctly.
Example of Semantic HTML
<button type="button" aria-label="Close" onclick="closeModal()">
Close
</button>
<a href="https://example.com" target="_blank" rel="noopener noreferrer">
Visit Example
</a>
Creating Accessible Components with Vanilla JavaScript
Now, let’s build a few essential components using vanilla JavaScript. We will cover a modal dialog, a dropdown menu, and a simple tooltip, ensuring each is accessible out-of-the-box.
1. Accessible Modal Dialog
A modal dialog is a component that appears on top of an application’s main content, often used to ask for user confirmation or display important information. Here’s how you can create an accessible modal:
<button id="openModal">Open Modal</button>
<div id="modal" role="dialog" aria-labelledby="modalTitle" aria-modal="true" style="display: none;">
<h2 id="modalTitle">Modal Title</h2>
<p>This is a modal dialog that requires user interaction.</p>
<button id="closeModal">Close</button>
</div>
const modal = document.getElementById('modal');
const openModalButton = document.getElementById('openModal');
const closeModalButton = document.getElementById('closeModal');
openModalButton.onclick = function() {
modal.style.display = 'block';
modal.focus();
document.addEventListener('keydown', handleKeydown);
}
closeModalButton.onclick = function() {
closeModal();
}
function closeModal() {
modal.style.display = 'none';
document.removeEventListener('keydown', handleKeydown);
}
function handleKeydown(event) {
if (event.key === 'Escape') {
closeModal();
}
}
In this modal example:
- We use role=”dialog” to define it as a dialog.
- The aria-labelledby attribute maps the title of the modal for screen readers.
- We listen for the “Escape” key to close the modal for enhanced usability.
2. Accessible Dropdown Menu
Dropdown menus can pose significant challenges for accessibility. Here’s one way to implement an accessible dropdown menu:
<div class="dropdown">
<button id="dropdownButton" aria-haspopup="true" aria-expanded="false">Select an option</button>
<ul id="dropdownMenu" role="menu" style="display: none;">
<li role="menuitem"><a href="#item1">Item 1</a></li>
<li role="menuitem"><a href="#item2">Item 2</a></li>
<li role="menuitem"><a href="#item3">Item 3</a></li>
</ul>
</div>
const dropdownButton = document.getElementById('dropdownButton');
const dropdownMenu = document.getElementById('dropdownMenu');
dropdownButton.onclick = function() {
const expanded = dropdownButton.getAttribute('aria-expanded') === 'true' || false;
dropdownButton.setAttribute('aria-expanded', !expanded);
dropdownMenu.style.display = expanded ? 'none' : 'block';
}
This implementation features:
- Usage of aria-haspopup to signal that the button controls a dropdown.
- aria-expanded gives information about the current state of the dropdown.
- A clear role for items within the menu defined using role=”menuitem”.
3. Accessible Tooltips
Tooltips can enhance user experience by providing additional context. Here’s a basic implementation:
<button id="tooltipButton" aria-describedby="tooltip">Hover me</button>
<div id="tooltip" role="tooltip" style="display: none;">This is a tooltip message.</div>
const tooltipButton = document.getElementById('tooltipButton');
const tooltip = document.getElementById('tooltip');
tooltipButton.onmouseenter = function() {
tooltip.style.display = 'block';
}
tooltipButton.onmouseleave = function() {
tooltip.style.display = 'none';
}
In this tooltip demonstration:
- aria-describedby associates the button with its tooltip for screen readers.
- It’s essential to manage display styles to ensure tooltips are visible during hover interactions.
Testing for Accessibility
Creating accessible components is essential, but testing is equally important. Here are some effective methods you can use:
- Use Screen Readers: Tools like NVDA, JAWS, or VoiceOver will help you understand the experience of users with visual impairments.
- Color Contrast Checkers: Online tools can help ensure your text is readable against its background.
- Automated Testing Tools: Tools like Axe and Lighthouse can identify accessibility issues in your application.
- User Testing: Including users with disabilities in your testing phase will provide invaluable feedback on your components.
Final Thoughts
Building accessible components with vanilla JavaScript requires careful attention to semantic HTML, proper ARIA practices, and a user-first mindset. As web developers, it’s our responsibility to ensure that our applications can be used by everyone, regardless of their abilities.
By implementing the accessible components and testing practices detailed in this article, you not only create a better experience for all users but also expand your reach and adherence to legal requirements.
Remember, accessibility is an ongoing process; keep learning and adapting your components as best practices evolve and improve. Happy coding!
