Skip to content
buttery

v1.0.0

Source on GitHub

Version 1.0.0

Checkbox

A box to tick for one yes-or-no choice, with its label beside it.

import { Checkbox } from "@butteryui/react";

Demo

When to use it

Use it for

  • Remember me, agree to the terms, email me tips: one choice in a form
  • A choice that waits for Save, or one of several that can each be on
  • A dense list or a filter menu, with size="sm"

Not for

  • A setting that takes effect at once: use Switch
  • One choice out of a few: use SegmentedControl

Examples

Agree to terms

An error on a box that has to be ticked, cleared once it is, beside a box that's disabled on this plan.

Available on the Roaster plan.

Email tips

An uncontrolled box with a hint, read by its form on Save: a ticked box submits its name with "on".

About once a month.

Remember me

A sign-in form's keep-me-signed-in box, its ticked state kept in the form's own state.

You'll stay signed in on this device

Select all

A select-all box over a list of cafés that shows mixed while only some are picked.

1 of 3 cafés picked

Two sizes

A checkbox at md over small ones for what goes in the box, which wait for the order to be packed.

1 extra in the box

Variants and states

States

Unticked, ticked, mixed, with a hint, with an error, and disabled.

About once a month.

I agree to the terms: Agree to the terms to make an account.

Agree to the terms to make an account.

Sizes

md, the default, is an 18px box beside a label-role label; sm is a 14px box beside 13px words, for a dense list. Both keep a 24px target.

On the slip, under the order.

Print customs forms: Add a customs number in Shipping first.

Add a customs number in Shipping first.

Props

Checkbox

PropTypeDefaultDescription
label

required

ReactNodeWhat ticking it means, beside the box. Pressing it ticks the box too.
hideLabelbooleanfalseKeeps the label for screen readers without showing it, as for a table row's checkbox. Defaults to false.
hintReactNodeA hint under the label.
errorReactNodeWhat's wrong, under the label and read with it, such as a box that has to be ticked.
checkedCheckboxStateWhether it's ticked. Pair with onCheckedChange to control it.
defaultCheckedCheckboxStatefalseWhether it starts ticked when uncontrolled. Defaults to false.
onCheckedChange((checked: CheckboxState) => void)Called when it's ticked or unticked.
valuestring"on"What it submits in a form while ticked. Defaults to "on".
size"sm" | "md""md""md" (the default), an 18px box beside a label-role label, or "sm", a 14px box beside 13px words, for dense lists and tables. Its target stays 24px either way.
announceErrorbooleantrueWhether a new error is read out as it appears. Defaults to true; turn it off when an error summary that takes focus reads the errors instead.

It also takes Omit<ComponentPropsWithRef<"button">, "value" | "defaultValue" | "defaultChecked" | "onChange" | "children" | "type">.

Accessibility

A real checkbox (role checkbox) named by its label, which takes presses too; Space ticks it. Its box has a 3:1 edge and a 24px target. Indeterminate reads as mixed. An error sets aria-invalid and is read with it.

KeysWhat they do
SpaceTicks or unticks it

Motion

It doesn't move.

With reduced motion: Nothing changes.

Layout

An 18px box with a 24px target, its label 8px beside it on the same row, or at size="sm" a 14px box with 5px corners and its 13px label 6px beside it, the target still 24px; a long label wraps onto more lines, and a hint or an error sits under the row. The field takes the width it's given, and the label takes presses as well as the box.

See it in the roastery demo's customers.