<button>
<svg aria-hidden="true" focusable="false">
<path d="..." />
</svg>
<span class="callout">Big</span>
Sale!
</button>
<button type="button">
<span role="img" aria-label="Fox">
🦊
</span>
Button
</button>
You may also want to use ARIA attributes for styling, which is a neat way to encourage using them correctly: https://css-tricks.com/user-facing-state/
button[aria-pressed="true"] { }
button[aria-pressed="false"] { }
Attach a click handler to a button that only runs once. To make that clear to the user, disable the button on click as well.
document.querySelector("button").addEventListener('click', function(event) {
event.currentTarget.setAttribute("disabled", true);
}, {
once: true
});
Then you would intentionally un-disable the button and reattach the handler when necessary.
Removing focus styles from clicks and not keyboard events has limited, but increasing, browser support
:focus:not(:focus-visible) {
outline: 0;
}
aria-pressed
: Turns a button into a toggle, between aria-pressed="true" and aria-pressed="false". More on button toggles, which can also be done with role="switch" and aria-checked="true".aria-expanded
: If the button controls the open/closed state of another element (like a dropdown menu), you apply this attribute to indicate that like aria-expanded="true".
Focus management isn't just for dialogs. If clicking a button runs a calculation and changes a value on the page, there is no context change there, meaning focus should remain on the button. If the button does something like "move to next page," the focus should be moved to the start of that next page.
The classic Apple guideline for the minimum size for a touch target (button) is 44x44pt.