Skip to main content
Dublin Library

The Publishing Project

Creating custom buttons (2): Toggle Buttons

 

In a previous post, we discussed what it takes to create action buttons that execute a specific action. In this post, we'll discuss toggle buttons, a special type of button that changes based on the status of the button, like if the audio track is playing or not. ## Toggle button Like we did with the action button, we need to look at the roles and attributes we need to have in a custom button. The biggest difference is the `aria-pressed` attribute we will add programmatically. This attribute tells assistive technology tools whether the button is pressed or not. | Role | Attribute | Element | Usage | | --- | --- | --- | --- | | button | | div | Identifies the element as a button widget.

Accessible name for the button is defined by the text content of the element. | | | tabindex="0" | div, a | Includes the element in the tab sequence.

Needed on the a element because it does not have an href attribute | | | aria-pressed="false" | a | Identifies the button as a toggle button.

Indicates the toggle button is not pressed | | | aria-pressed="true" | a | Identifies the button as a toggle button.

Indicates the toggle button is pressed. | With that in mind, the structure of the HTML we will use for this example is almost identical to the action button from the previous post. ```html
Play
``` All the work for the toggle is done in Javascript. I've broken the code into sections to make it easier to explain: The first action is to capture a reference to the element we use as a toggle. ```js const toggleButton = document.getElementById("toggle"); ``` The `toggleButtonClickHandler` function checks if we're working with a real button or elements with a role of button then we execute the `toggleButtonState` function passing the event as the function parameter. ```js function toggleButtonClickHandler(event) { if ( event.currentTarget.tagName === "button" || event.currentTarget.getAttribute("role") === "button" ) { toggleButtonState(event.currentTarget); } } ``` The `toggleButtonKeydownHandler` function handles the keyboard navigation. It tests if the key pressed is either the `Space` or `Enter` key and runs the `toggleButtonState` function. We use the [event.key](https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/key) read-only property to identify the key that was pressed and only execute the `toggleButtonState` function if the user clicked the `space bar` or `enter` keys. Older examples use the [event.keyCode](https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/keyCode) property to read the key that was pressed but the property has been deprecated and it is system-dependent. For the spacebar key detection we use two possible values: - `Spacebar` will work with older browsers - The space string (`" "`) works in modern browsers. ```js function toggleButtonKeydownHandler(event) { if ( event.key === "Spacebar" || event.key === " " || event.key === "Enter") { toggleButtonState(event.currentTarget); } } ``` `toggleButtonState` is where we do the bulk of the work. We first create a constant to set the `aria-pressed` attribute to true by default. We then use a [ternary operator](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Conditional_Operator) to set the `aria-pressed` attribute. It toggles between true and false based on the existing value of the attribute. We then use the value of the `aria-pressed` attribute to change the text of the button. If the value of `aria-pressed` is true, we set the text to the string `Play`, otherwise, we set the text of the button to the string `False`. ```js function toggleButtonState(button) { const isAriaPressed = button.getAttribute("aria-pressed") === "true"; button.setAttribute("aria-pressed", isAriaPressed ? "false" : "true"); if (isAriaPressed) { button.textContent = "Play"; } else { button.textContent = "Pause"; } } ``` Finally, we add event listeners for the `pointerdown` and `keydown` events. ```js toggleButton.addEventListener("pointerdown", toggleButtonClickHandler); toggleButton.addEventListener("keydown", toggleButtonKeydownHandler); ``` The full example is here:

Edit on Github