Skip to content

Accessibility

A media button is a native <button> — usually icon-only and placed over imagery — that controls media playback, so it follows the WAI-ARIA Button pattern and meets WCAG 2.1 AA. With no visible label and an unpredictable surface behind it, an accessible media button hinges on three things: an explicit accessible name, an icon hidden from assistive technology, and enough contrast — for both the icon and its focus ring — over whatever media sits beneath it.

  • The icon must keep at least 3:1 contrast against the button fill on every background it can land on — busy imagery, video frames, gradients. Where the media is variable or user-supplied, add a scrim behind the button so it sits on a stable, high-contrast layer. Source: WCAG 1.4.11 Non-text Contrast.
  • Playback state must never be conveyed by colour alone — the play and pause icons already differ in shape; keep that distinction rather than relying on a colour swap to tell the two apart. Source: WCAG 1.4.1 Use of Color.
  • The focus ring must stay visible and meet contrast over both light and dark media — it’s the only cue a keyboard user gets for a control with no label. Don’t override its colour; it’s tuned to remain visible across both contrast modes. Source: WCAG 2.4.7 Focus Visible.
  • Use semantic colour tokens (e.g. foreground/neutral/default) rather than fixed values, so the icon and ring adapt correctly across themes, contrast modes, and surfaces.
  • Both production sizes clear the WCAG AA target-size minimum — Small is 40 × 40 and Large is 64 × 64, well above the 24 × 24 floor. Don’t shrink the visible footprint below Small; if a denser layout needs it, switch to Icon Button instead. Keep at least one button-width of clear space between adjacent media buttons so their targets never overlap. Source: WCAG 2.5.8 Target Size (Minimum).

A media button is a native <button>, so it is focusable and operable from the keyboard (Enter / Space) with no extra wiring — never style a <div> or <a> to stand in for it. Because it is icon-only, its accessible name has to come from an aria-label, and a play / pause or mute / unmute control exposes its on/off state with aria-pressed; the decorative glyph stays out of the accessibility tree. When a progress ring is present, its role="progressbar" semantics are documented on the Develop tab — surface meaningful playback milestones through an aria-live region rather than announcing the ring itself. The per-element roles, names, and states are in the Labelling elements section below.

Give every element the role, name, and state assistive technology needs.

Button

The native <button> carries its own role and keyboard operation. Because it has no visible text, give it an accessible name with aria-label ("Play", "Pause", "Mute") and keep that name matching the action the button will perform.

Icon

The glyph is decorative — mark it aria-hidden="true" so it isn’t announced separately. The button’s aria-label is the single source of the accessible name.

Toggle state

For play / pause and mute / unmute, expose the two-state nature with aria-pressed and flip the aria-label in step with it, so sighted and screen-reader users read the same current state.

Disabled

Use the native disabled attribute — not an .is-disabled class — so the control is announced as unavailable and skipped in the tab order.

Source: WCAG 4.1.2 Name, Role, Value.