Skip to main content

Toggle Button

A button that switches between two states such as active and inactive. Use for immediate, reversible binary actions that do not require form submission. Don't use when the toggle controls a persistent system setting.

Figma Storybook Docs

Description

What it does

A toggle button switches between two mutually exclusive states — typically active and inactive — on press. The visual treatment clearly communicates the current state so users can see what is on or off at a glance.

Where it appears

Filter bars, toolbar controls, and list views where users need to switch a view mode or apply a reversible filter. Common in Open Point consultation management screens and stakeholder list views.

Why it exists

A plain button communicates an action; a toggle button communicates a persistent state. It replaces checkbox-style controls when the interaction is immediate (no Save step) and the binary choice is best expressed as a pressable affordance rather than a form field.

Dependencies

Button, Switch

Anatomy

PartRequired?Notes
Container Required The pressable surface. Carries background, border, and border-radius. Minimum 44x44px touch target.
Label Required Short text describing the state or action. Should read as a noun or adjective, not a verb — for example 'Active', not 'Activate'.
Leading icon Optional Reinforces meaning visually. Use a wa-icon element. Particularly useful when the label alone may not be scannable at small sizes.
Focus ring Required 3px solid ring using --op-color-interactive-focus. Always visible on keyboard focus; never suppressed.
State indicator (pressed fill) Required The background and border change between inactive and active states. Must meet 3:1 non-text contrast ratio for the state boundary.

Variants

Default (outlined inactive / filled active)

The standard toggle pattern. Inactive state is outlined; active state is filled with --op-color-interactive-default.

Use for most toggle button needs — filter pills, view mode switchers, and toolbar controls.

Subtle (ghost inactive / tinted active)

Lower visual weight. Inactive has no border or fill; active uses a tinted background.

Use inside dense toolbars or when the toggle sits alongside other high-emphasis controls and visual noise needs to be reduced.

Icon-only

No visible label — icon communicates the toggle state.

Use only when the icon is universally understood (e.g. a bookmark or star) and when space is extremely constrained. Always pair with a visible tooltip and an aria-label.

States

State Behaviour
Inactive (default) Button is rendered in its rest appearance — outlined border, no fill, label in --op-color-text-primary. Pressing transitions to active.
Active (pressed) Background fills with --op-color-interactive-default. Label and icon use --op-color-text-on-interactive. aria-pressed is set to 'true'.
Hover (inactive) Background tints with --op-color-interactive-hover at low opacity. Cursor is pointer.
Hover (active) Background shifts to --op-color-interactive-hover. Indicates the press will deactivate.
Focus 3px focus ring appears using --op-color-interactive-focus. Ring is offset 2px from the container edge. Visible in both inactive and active states.
Disabled Opacity 0.4. Pointer-events none. aria-disabled='true'. Do not use disabled as a permanent state — if the action is never available, remove the control.
Loading Rare. If the toggle triggers an async action, replace the label with a wa-spinner and set aria-busy='true' until resolved. Prevent re-press during loading.

Usage guidelines

When to use

  • Switching a view between two modes, such as 'Map view' and 'List view' on a stakeholder directory.
  • Toggling a filter on or off in a consultation submissions list, such as filtering by 'Unread' or 'Flagged'.
  • Activating or deactivating a display option that takes effect immediately without a form submission, such as showing or hiding archived records.
  • Toolbar controls in rich-text or map editors where a mode can be turned on or off.

When not to use

  • When the setting persists beyond the current session and affects other users or system-level configuration — use a Switch with a Save action instead.
  • When there are more than two states — use a segmented control or radio button group.
  • When the action is destructive or irreversible — use a Button with a confirmation dialog.
  • Inside a form that requires submission to apply changes — use a Checkbox or Switch form field instead.
  • As a navigation element — use a Tab or Link.

Do / Don't

Do

Label the toggle with its state noun, for example 'Active' or 'Pinned', so screen readers and sighted users can tell the current state.

Don't

Label with a verb like 'Activate' — this describes an action, not a state, and becomes misleading once the button is pressed.

Do

Group related toggle buttons using role='group' with an aria-label describing the group.

Don't

Scatter independent toggle buttons without grouping context — users relying on assistive technology lose the relationship between controls.

Do

Use the icon-only variant only with a wa-tooltip and aria-label.

Don't

Rely solely on colour or icon to communicate state — always include a text label or accessible name.

Do

Keep labels short — one or two words. If the label needs more than three words, reconsider the control type.

Don't

Write sentence-length labels. Toggle buttons are not for complex choices.

Was this page helpful?

Updated 9 September 2026