Lightweight JavaScript Dropdown Menu: Easy Code Examples

Written by

in

Building an accessible JavaScript dropdown menu requires combining semantic HTML, explicit ARIA (Accessible Rich Internet Applications) attributes, and explicit keyboard event listeners. This ensures that people navigating with screen readers or keyboard-only setups can seamlessly use your interface.

The structural blueprint, standard requirements, and core code needed to construct a robust, WCAG-compliant dropdown are outlined below. 1. Semantic HTML Structure

Always use a

Use code with caution. Core ARIA Attributes

aria-haspopup=“true”: Alerts screen readers that activating this button reveals a sub-menu popup.

aria-expanded=“false”: Dynamically tells the user if the panel is currently open or closed.

aria-controls=“dropdown-menu”: Explicitly binds the trigger button to the menu container’s ID.

role=“menu” and role=“menuitem”: Configures the list structural hierarchy to match assistive reader standards.

tabindex=“-1”: Keeps hidden individual list items out of the default sequential browser Tab order. Navigation will instead be manually managed via arrow keys. 2. Required Behavioral JavaScript

The core script must control state toggling, manage dynamic focus index placement, and support global escape triggers. javascript

const button = document.getElementById(‘dropdown-btn’); const menu = document.getElementById(‘dropdown-menu’); const menuItems = menu.querySelectorAll(‘[role=“menuitem”]’); let currentIndex = -1; // Toggle Menu Open/Closed function toggleMenu(open) { button.setAttribute(‘aria-expanded’, open); if (open) { menu.removeAttribute(‘hidden’); } else { menu.setAttribute(‘hidden’, “); currentIndex = -1; button.focus(); // Return focus to trigger } } // Click Trigger Events button.addEventListener(‘click’, () => { const isOpen = button.getAttribute(‘aria-expanded’) === ‘true’; toggleMenu(!isOpen); }); // Manage Global and Keyboard Navigation Focus button.addEventListener(‘keydown’, (e) => { if (e.key === ‘ArrowDown’ || e.key === ‘ ’ || e.key === ‘Enter’) { e.preventDefault(); toggleMenu(true); currentIndex = 0; menuItems[0].focus(); } }); menu.addEventListener(‘keydown’, (e) => { if (e.key === ‘Escape’) { toggleMenu(false); } else if (e.key === ‘ArrowDown’) { e.preventDefault(); currentIndex = (currentIndex + 1) % menuItems.length; menuItems[currentIndex].focus(); } else if (e.key === ‘ArrowUp’) { e.preventDefault(); currentIndex = (currentIndex - 1 + menuItems.length) % menuItems.length; menuItems[currentIndex].focus(); } }); // Close menu when clicking outside document.addEventListener(‘click’, (e) => { if (!button.contains(e.target) && !menu.contains(e.target)) { toggleMenu(false); } }); Use code with caution. 3. Accessible CSS States

Comments

Leave a Reply

Your email address will not be published. Required fields are marked *

More posts