Enable
>

Accessible Dropdowns/Drawers/Expando

HTML5 version using details and summary tags

There are small bugs with this solution with some screen reader/browser combinations.

This should be the ideal solution, since it is a native HTML5 control that doesn't require JavaScript. However, there are some issues:

These issues have been around for a while (see Graham Armfield's article about the details tag from 2019). I hope that browser manufacturers can fix their accessibility APIs so this can work correctly in all platforms.

Information on the HTML5 details tag.

This is the contents of the dropdown. For more information about the HTML5 details and summary tags, read the following documents:

Code Walkthrough of the Above Example

Below is the HTML of the above example. Use the dropdown to highlight each of the individual steps that makes the example accessible.

☜ Scroll to read full source ☞

                    
                

HTML5 dropdown with checkboxes

Frequently, there is a requirement to create a "multi-select selectbox". It is possible to do this with the <select> tag, but many users (sighted and blind) have difficulty using them and don't even know they are multi-selectable. I have found making dropdowns with checkboxes inside is a better solution, and can be done easily with native HTML5 components without ARIA.

Products
Products

Code Walkthrough of the Above Example

Below is the HTML of the above example. Use the dropdown to highlight each of the individual steps that makes the example accessible.

☜ Scroll to read full source ☞

                    
                

ARIA version

This is best solution for both new and existing work.
This solution described below is available as an NPM module. (Module installation instructions)

Even though this is not native, it is pretty easy to set up. There is really one HTML attribute that you have to change with JavaScript when the drawer opens or closes: aria-expanded. I just use CSS to style it depending what that attribute is set to, and everything just works.

This is the contents of the dropdown. For more information about the aria-expanded, read the following documents:

Code Walkthrough of the Above Example

Below is the HTML of the above example. Use the dropdown to highlight each of the individual steps that makes the example accessible.

☜ Scroll to read full source ☞

                    
                

ARIA dropdown with checkboxes

This is a better solution that using multi-select <select> boxes, in my opinion.

Frequently, there is a requirement to create a "multi-select selectbox". It is possible to do this with the <select> tag, but many users (sighted, partially sighted and non-sighted) have difficulty using them and don't even know they are multi-selectable (the comments in Juan Manuel Ramallo's blog post, Does anyone else think HTML5 multiple select sucks? agrees, and the comments in the post show a lot of developers agree). I have found making dropdowns with checkboxes inside is a better solution, and this can be done without a lot of effort.

Code Walkthrough of the Above Example

Below is the HTML of the above example. Use the dropdown to highlight each of the individual steps that makes the example accessible.

☜ Scroll to read full source ☞

                    
                

Installation Instructions

You can load this JavaScript library into your application in serveral ways:

If you haven't done so already, choosing which you should use is obviously a major architectural decision. Here are a few articles that will help you decide:

Important Note On The CSS Classes Used In This Module:

This module requires specific CSS class names to be used in order it to work correctly. These CSS classes begin with enable-drawer__. Please see the documentation above to see where these CSS classes are inserted.

Using NPM/Webpack to load ES6 Modules:

  1. Install the enable-a11y NPM project.
  2. Edit your webpack.config.json file to resolve the ~ modifier by adding the following:
    ☜ Scroll to read full source ☞
    module.exports = { ... resolve: { extensions: ['.js', '.jsx', '.scss', '.css', '*.html'], modules: [ path.resolve('./src/js'), path.resolve('./node_modules') ], alias: { '~enable-a11y': path.resolve(__dirname, 'node_modules/enable-a11y') }, ... }, ... }
  3. You can use the module like this:
    ☜ Scroll to read full source ☞
    // import the JS module import enableDrawer from '~enable-a11y/js/modules/enable-drawer'; // import the CSS for the module import '~enable-a11y/css/enable-drawer'; // How to initialize the enableDrawer library enableDrawer.init(); // Note that this component will work with DOM elements coded like // the examples above added after page load. There is no need to call // an .add() method, like we do with the Enable combobox component.
  4. Alternatively, if you are using LESS you can include the styles in your project's CSS using:
    ☜ Scroll to read full source ☞
    @import '~enable-a11y/css/enable-drawer';
    (If you are using it in your CSS, you will have to add the .css suffix)

Using NPM/Webpack to Load Modules Using CommonJS Syntax

  1. Install the enable-a11y NPM project.
  2. You can import the module using require like this:
    ☜ Scroll to read full source ☞
    var enableDrawer = require('enable-a11y/enable-drawer').default; ... enableDrawer.init();
  3. You will have to include the CSS as well in your project's CSS using:
    ☜ Scroll to read full source ☞
    @import '~enable-a11y/css/enable-drawer';

Using ES6 modules natively.

This is the method that this page you are reading now loads the scripts.

  1. Grab the source by either using NPM, grabbing a ZIP file or cloning the enable source code from github.
  2. If you want to load the module as a native ES6 module, copy js/modules/enable-drawer.js , and css/enable-drawer.css from the repo and put them in the appropriate directories in your project (all JS files must be in the same directory).
  3. Load the CSS in the head of you document:
    ☜ Scroll to read full source ☞
    <html> <head> ... <link rel="stylesheet" href="path-to/css/enable-drawer.css" > ... </head> <body> ... </body> </html>
  4. Load your scripts using the follwing code (NOTE: you must use <script type="module">):
    ☜ Scroll to read full source ☞
    <script type="module"> import enableDrawer from "path-to/enable-drawer.js" enableDrawer.init(); </script>

Using ES4

Just do the same as the ES6 method, except you should get the JavaScript files from the js/modules/es4 directory instead of the js/modules/:
☜ Scroll to read full source ☞
<script src="path-to/es4/enable-drawer.js"></script>