Skip to content
buttery

v1.0.0

Source on GitHub

Version 1.0.0

Colors

The color tokens every component draws with, by role, in light and dark.

A color token is a named role, such as --bt-text-secondary or --bt-bg-section, that holds one value for the light theme and one for the dark theme. Use a token for every color an app draws, and the app follows light and dark, a theme made with createTheme, and the contrast rules without any code of its own.

Use a token, never a value

Each token is a CSS variable that ButteryProvider sets on the page. Read it with var():

Do

css

.order-total {
  color: var(--bt-text-strong);
  background-color: var(--bt-bg-section);
}

The tokens change with the theme.

Don't

css

.order-total {
  color: #1a1a1a;
  background-color: #f7f7f7;
}

Hex values stay the same in dark mode, and buttery's stylelint config fails them.

In TypeScript and Tailwind

The same tokens are in TypeScript as colors from @butteryui/core, each with its light value, its dark value and what it's for. Use them in code that needs a value rather than a variable, such as a chart drawn on a canvas.

With Tailwind v4, import @butteryui/core/tailwind.css after Tailwind in your stylesheet:

css

@import "tailwindcss";
@import "@butteryui/core/tailwind.css";

Utilities such as bg-surface, text-fg-secondary and border-border then read the same tokens. Keep importing @butteryui/core/styles.css at your app's entry, because it defines the variables they read.

Surfaces

The backgrounds pages, panels and cards sit on. A surface's text and borders are chosen to read on it, so pair them as the components do.

SwatchTokenLightDarkUse
--bt-bg-app#f3f3f4#0f0f10Page and stage background behind everything.
--bt-bg-surface#ffffff#19191bHeader bar, inspector panel, inner cards, dialogs.
--bt-bg-raised#ffffff#2c2c30Elements raised above a surface or a control track: the active segment, secondary buttons.
--bt-bg-floating#ffffff#1f1f22Floating layers: menus, popovers, floating toolbars.
--bt-bg-section#f7f7f7#141416The well behind a section's card.
--bt-bg-inset#fefefe#161618Small recessed controls: tilt pad, anchor grid.
--bt-bg-control#f1f1f1#232326Segmented track, value badge, soft button, hover fill.
--bt-bg-control-subtle#f9f9f9#1e1e20Disabled soft button and chip.
--bt-bg-item-hover#f7f7f7#202023Highlighted menu item.
--bt-bg-control-active#ececec#2a2a2dGhost trigger while its menu is open.
--bt-bg-tint#fbf4da#2d1e14A tinted card or page band: the cream gradient's first stop in light, the espresso family at OKLCH L 0.25 in dark, so every text color holds 4.5:1 on it and every chart series 3:1.

Text and icons

text-strong is for titles and numbers that lead, text for labels and body text, text-secondary for descriptions and inactive items, and text-tertiary for the quietest hints.

Contrast. All four meet WCAG AA contrast on the surfaces above. Disabled text is exempt, as inactive UI is.

SwatchTokenLightDarkUse
--bt-text-strong#1a1a1a#f5f5f6Dialog titles and page headings.
--bt-text#303030#ececedLabels, primary text, the active segment.
--bt-text-secondary#616161#a0a0a6Section titles, body copy, value badges, icons, inactive segments.
--bt-text-tertiary#6b6b6b#93939aCaptions and hints.
--bt-text-disabled#acacac#55555bDisabled text. Exempt from contrast rules, like all inactive UI.
--bt-text-disabled-subtle#b8b8b8#4d4d53Disabled chip text, one step quieter than text-disabled.
--bt-icon-disabled#c0c0c0#4a4a50Disabled icons.

Borders

Edges and dividers. control-border marks the edge of a control where nothing else does, such as a text input's box or a switch's track, at 3:1 on every surface.

SwatchTokenLightDarkUse
--bt-border#ebebeb#2a2a2eRow dividers, section borders, separators.
--bt-border-strong#e3e3e3#333338Slider track, anchor grid, tilt pad, and the edge of a disabled input.
--bt-control-border#858585#75757cThe edge that marks a control where nothing else does: a text input's box, a checkbox's box, a switch's track. 3:1 on every surface.
--bt-divider-on-primaryrgba(255, 255, 255, 0.18)rgba(17, 17, 17, 0.18)The hairline between a split button's halves.

Primary and accent

primary fills the one main action on a screen. accent marks focus rings, selection and links; accent-text is the accent's shade for text, which meets contrast where accent itself wouldn't.

SwatchTokenLightDarkUse
--bt-primary#1a1a1a#f2f2f3Primary button and split button.
--bt-primary-hover#2b2b2b#ffffffPrimary hover. Lightens in light mode rather than darkening.
--bt-primary-disabled#a3a3a3#4a4a50Disabled primary background; the text keeps on-primary.
--bt-on-primary#ffffff#111111Text on primary.
--bt-accent#2862e0#4f89ffFocus ring, tilt arc, selection highlights.
--bt-accent-subtle#e9f0fd#16223bBackground of an info callout.
--bt-accent-text#2862e0#4f89ffThe accent as text: links and icons in an info callout. 4.5:1 on the surface and on accent-subtle, even when a theme's accent is lighter.
--bt-selectionrgba(40, 98, 224, 0.2)rgba(79, 137, 255, 0.3)Text selection highlight.
--bt-ring-selected#cacaca#4a4a50Selected swatch ring, crop handle border, drop-zone dashes.

Status

danger, success and warning are for text and icons that say how something went. Their -subtle shades are the backgrounds of callouts and badges that carry them.

SwatchTokenLightDarkUse
--bt-danger#c72a1c#ff7a6eErrors: a field's border and message, error icons.
--bt-danger-subtle#fdeceb#3a1916Background of an error callout.
--bt-success#177245#4cc38aSuccess text and icons, a met requirement.
--bt-success-subtle#e7f5ed#132c20Background of a success callout.
--bt-warning#9a4d00#f2a33aWarning text and icons.
--bt-warning-subtle#fdf1e2#33230fBackground of a warning callout.

Inverse

For the few things drawn dark on a light page and light on a dark one, such as a toast.

SwatchTokenLightDarkUse
--bt-inverse-bg#1a1a1a#f2f2f3Tooltip and toast background.
--bt-inverse-text#ffffff#111111Tooltip and toast text.
--bt-inverse-text-secondary#a3a3a3#6b6b6bSecondary text and actions in tooltips and toasts.
--bt-inverse-success#4cc38a#177245Success on the inverse surface: a success toast's icon. Each theme takes the other theme's success, which reads on its inverse surface.
--bt-inverse-warning#f2a33a#9a4d00Warning on the inverse surface: a warning toast's icon.
--bt-inverse-danger#ff7a6e#c72a1cDanger on the inverse surface: a danger toast's icon.
--bt-inverse-success-bg#26342c#d5e0d9A success toast: the inverse surface mixed toward inverse-success in OKLab, 18% (14% in dark).
--bt-inverse-warning-bg#3b3024#e7dad3A warning toast: the inverse surface mixed toward inverse-warning, 18% (14% in dark).
--bt-inverse-danger-bg#3e2b28#f0d9d5A danger toast: the inverse surface mixed toward inverse-danger, 18% (14% in dark).

Charts

The colors of a chart's series. chart-1 is the accent, the next four are other hue families at the accent's lightness, and chart-muted is for a series to compare against, such as the previous period.

SwatchTokenLightDarkUse
--bt-chart-1#2862e0#4f89ffA chart's first series: the accent.
--bt-chart-2#008254#1ea971A chart's second series: the mint family at the accent's OKLCH lightness, chroma 0.14 or the most sRGB allows.
--bt-chart-3#a65400#cf752dA chart's third series: the apricot family at the accent's OKLCH lightness, chroma 0.14 or the most sRGB allows.
--bt-chart-4#7b57b2#9d7ad7A chart's fourth series: the lilac family at the accent's OKLCH lightness, chroma 0.14.
--bt-chart-5#ae445b#d6677cA chart's fifth series: the rose family at the accent's OKLCH lightness, chroma 0.14.
--bt-chart-muted#8b8b8b#6e6e74A comparison series, such as the previous period: the lightest gray still 3:1 on every chart background.

Scrims and marks

The scrim behind a dialog, the wash behind a menu, page dots, and a Skeleton's fills.

SwatchTokenLightDarkUse
--bt-overlayrgba(0, 0, 0, 0.32)rgba(0, 0, 0, 0.55)Dialog scrim, with no blur.
--bt-washrgba(255, 255, 255, 0.55)rgba(15, 15, 16, 0.55)Wash over the blurred page behind a menu.
--bt-dot#e8e8e8#2e2e32Page dots and idle anchor dots.
--bt-dot-active#303030#ececedThe active page dot.
--bt-skeleton#f2f2f4#232326A Skeleton's fill, and skeleton blocks in illustrations.
--bt-skeleton-strong#ececee#2a2a2dThe band that sweeps across a Skeleton, and skeleton lines in illustrations.

Decorative

Colors for illustrations, buttery's own mark and the knobs of sliders and other controls. They're never used for UI that has to be read.

SwatchTokenLightDarkUse
--bt-knob-top#535353#535353Top of the slider thumb's vertical gradient.
--bt-knob-bottom#2e2e2e#2e2e2eBottom of the slider thumb's vertical gradient.
--bt-knob-center#5c5c5c#5c5c5cLit point of the radial knob gradient (tilt knob, active anchor dot), 30% down from the top.
--bt-knob-edge#262626#262626Where the radial knob gradient ends: the bottom edge, the side farthest from the lit point.
--bt-knob-border#1c1c1c#000000Knob border.
--bt-knob-highlight#7a7a7a#7a7a7aOne-pixel inset highlight along the top of a knob.
--bt-knob-grip#b2b2b2#b2b2b2The two grip lines on the slider thumb.
--bt-knob-ring#ffffff#ffffffThe ring around a thumb drawn over picked colors (the color picker's), the same in both themes so it shows on any color.
--bt-traffic-red#ed6c61#ed6c61Window-chrome dot in illustrations.
--bt-traffic-yellow#f5c05c#f5c05cWindow-chrome dot in illustrations.
--bt-traffic-green#5ac55e#5ac55eWindow-chrome dot in illustrations.
--bt-brand-butter#f5d06f#f5d06fbuttery's brand color. Decorative only: the mark, docs, marketing.
--bt-brand-butter-deep#e8b64a#e8b64aThe brand mark's side and shadow.
--bt-brand-cream#fff4d6#fff4d6The brand mark's top face.
--bt-brand-gloss#ffffff#ffffffThe brand mark's highlight, white on any background.
--bt-brand-shadow#8a5a12#8a5a12The brand mark's contact shadow, drawn faint and blurred.
  • Theming

    Light and dark, compact density, and your own accent, grays and corners with createTheme.

  • Elevation

    Surface levels, from the app's background to dialogs, and the shadows that set them apart.