Skip to content

Toolbar

A named row of related controls: one tab stop, arrow keys between controls.

  • Free core, MIT
  • Version 2.0.0-rc.1
  • APG pattern: Toolbar

Examples

These are the real React components. Use them with a mouse, touch or keyboard, and switch the theme and density for every example at once.

Default

Show the code

Default, code

const Formatting = () => (
  <Toolbar aria-label="Text formatting">
    {/* Standalone toggles: a ToggleButtonGroup nested in a Toolbar gets aria-orientation on role=group (a React Aria quirk axe rejects). */}
    <ToggleButton icon={Bold} aria-label="Bold" />
    <ToggleButton icon={Italic} aria-label="Italic" />
    <ToggleButton icon={Underline} aria-label="Underline" />
    <ToolbarSeparator />
    <IconButton icon={Link} label="Add link" variant="ghost" showTooltip={false} />
    <Button variant="outline">Clear formatting</Button>
  </Toolbar>
);

<Formatting />

Vertical, stretch

Show the code

Vertical, stretch, code

const Vertical = ({ align }: { align: 'start' | 'stretch' }) => (
  <Toolbar aria-label="Clipboard" orientation="vertical" align={align} className="w-60">
    <Button variant="ghost" iconStart={Share}>Share</Button>
    <Button variant="ghost" iconStart={Copy}>Copy</Button>
    <ToolbarSeparator orientation="horizontal" />
    <Button variant="ghost">Paste as plain text</Button>
  </Toolbar>
);

<Vertical align="stretch" />

Vertical, start

Show the code

Vertical, start, code

const Vertical = ({ align }: { align: 'start' | 'stretch' }) => (
  <Toolbar aria-label="Clipboard" orientation="vertical" align={align} className="w-60">
    <Button variant="ghost" iconStart={Share}>Share</Button>
    <Button variant="ghost" iconStart={Copy}>Copy</Button>
    <ToolbarSeparator orientation="horizontal" />
    <Button variant="ghost">Paste as plain text</Button>
  </Toolbar>
);

<Vertical align="start" />

Tokens

The 2 design tokens Toolbar reads, with the value each has in the theme and density chosen above. Change a token and the component follows, in Figma and in code.

Show all 2 tokens
Tokens Toolbar reads
TokenValue nowCSS variable
color.border.default…--sd-color-border-default
spacing.gap.xs…--sd-spacing-gap-xs

Install

The npm package isn’t published yet. When it is, this is the install line; until then, this page runs the same build of the package (from commit fa3abf8).

Install

npm i @superduperui/react @superduperui/tokens

Import

import { Toolbar, ToolbarSeparator } from "@superduperui/react"

Props

Toolbar also takes the props of the React Aria component it’s built on.

Toolbar props
PropTypeWhat it does
aria-labelrequiredstringNames the toolbar (required).
align'start' | 'stretch'Default 'stretch'Vertical toolbars only: stretch (default) makes every control fill the toolbar's width; start keeps each control at its own width against the start edge. Horizontal toolbars centre their controls on the row.

When to use it

Use it for

  • Editor formatting bars
  • Table and canvas action bars with several controls

Use something else for

  • A page header with two or three buttons: just use Buttons
  • Navigation: use Navbar or Tabs

Accessibility

Screen readers announce "Text formatting, toolbar" then "Bold, toggle button, not pressed".

WCAG 2.2 AAA criteria the component meets in Comfortable density: 1.4.6, 1.4.9, 2.1.3, 2.3.2, 2.4.13, 2.5.5, 2.5.6.

Compact density meets AA (2.5.8, 24px targets), not AAA.

What your product still has to do

  • Name the toolbar (aria-label)
  • Keep every control reachable with the arrow keys

This release’s test results

Test results for Toolbar in this release
axe-core (WCAG A, AA, AAA and best practice)80 runs across every story, theme, density and width: 0 violations
Rendered text contrast85 text runs: 0 below 7:1, lowest 16.71:1
Target size72 targets: 0 under 44px in Comfortable
Focus appearance (2.4.13)24 focus stops in 3 browser engines: all pass
Keyboard scriptChromium 5 of 5, Firefox 5 of 5, WebKit 5 of 5

Manual passes with VoiceOver and NVDA haven’t been done yet.

Keyboard

Each step is scripted and run in Chromium, Firefox and WebKit.

Toolbar keyboard steps
KeyWhat happens
TabTab enters the toolbar on its first control
ArrowRightRight moves to the next control
ArrowRightRight moves on past the separator
ArrowRightRight reaches the last control
ArrowLeftLeft moves back

In Figma

The Figma component is Toolbar, with Orientation (Horizontal, Vertical); Align (Start, Stretch). The Figma library isn’t published yet.

Figma to code: Orientation → orientation (Horizontal = "horizontal", Vertical = "vertical"); Controls → children; Align → align (Start = "start", Stretch = "stretch").