VI Controls

Star on GitHubFeedback
VI ControlsNative HTMLot-btn-group

Button group

A set of actions, drawn three ways: one pair of parentheses with hairlines between, a narrow column with a dash hung in the margin, or a list written into the sentence around it.

Report an issue with Button group

Example

Halden is ready to share. You can .

Rest
Pointed at
Disabled
Column
Pointed at
Disabled
SentenceThen .
Pointed atThen .
DisabledThen .

Install

Run it in a project that has the shadcn CLI set up. It brings the 0nlyType base and button along.

npx shadcn@latest add https://thedirectors.agency/ui/r/button-group.json

Usage

button-group-example.tsx
import { Button } from "@/components/ui/button"import { ButtonGroup } from "@/components/ui/button-group"export default function Example() {return (<div className="grid justify-items-start gap-(--ot-space-8)"><ButtonGroup aria-label="Share Halden"><Button>Copy link</Button><Button>Email</Button><Button>Export PDF</Button></ButtonGroup><ButtonGroup variant="column" aria-label="Halden"><Button>Open</Button><Button>Rename</Button><Button>Duplicate</Button><Button>Move to archive</Button></ButtonGroup><p className="ot-mp max-w-[34ch] text-(--ot-graphite)">Halden is ready to share. You can{" "}<ButtonGroup variant="sentence" aria-label="Share Halden"><Button>copy the link</Button><Button>email it</Button><Button>export a PDF</Button></ButtonGroup>.</p></div>)}

Contract

  • Underneath: native.
  • Anatomy: <div class="ot-btn-group" role="group" data-variant="parentheses | column | sentence" aria-label="Name"> of ot-btn buttons (no variant). The sentence is a <span>, since it sits inside a paragraph, and writes .ot-btn-group-sep (aria-hidden) between its buttons.
  • Parentheses: one pair holds the set, after 20(25), and hairlines stand between the actions. Pointing draws a line under one; it passes through.
  • Column: after "Less is more." and Healthy habits, the actions stacked as a narrow ragged column at tight leading, with no rules between. Pointing hangs the poster's short heavy dash in the margin beside the action; it grows out from the word and goes back into it, and a press lengthens it. It hangs into the inline-start margin, mirrored right to left.
  • Sentence: the actions written into running text as a list, the way prose names choices: "copy the link, email it, or export a PDF". The group takes the text's size; each action is ink on a pencil hairline, and pointing passes an ink line through it. conjunction sets the last word between ("or" by default).
  • Keyboard: Tab between buttons.

Props

Props of Button group
PropTypeDefaultWhat it does
aria-labelstringNames the set for a screen reader, such as Share Halden. The group is role=group.
variant"parentheses" | "column" | "sentence""parentheses"Parentheses hold the set and hairlines stand between. Column stacks the actions as a narrow ragged column; pointing hangs a short heavy dash in the margin beside one. Sentence writes them into running text as a list (copy the link, email it, or export a PDF), each on a pencil hairline that the ink passes through.
conjunctionstring"or"In a sentence, the word before the last action. Use and, or the page's own language.
childrenButton[]The actions. Each Button gives up its own brackets inside the group.

Craft

Where its move comes from

Where its move comes from
ComponentReferenceMove
Button group20(25)Parentheses hold the set; hairlines stand between
Column group"Less is more." corner column; Healthy habitsA ragged column; a heavy dash hung in the margin
Sentence groupHealthy habits → (one line of thought); the written listThe actions written into the sentence

How it moves

How it moves
ComponentArticulationWhat moves
Button groupPass-throughThe line under an action leaves the way it was heading
Column groupHangThe dash grows out of the word into the margin and goes back into it