Refrain Recurna

This site follows your system settings for colour scheme and reduced motion on its own. The buttons let you see the other side without changing them.

Evidence

Token reference

170 tokens, 126 of which carry a light and a dark value. This table is generated by reading the package's own stylesheet during the build — no value on it was typed by hand, and a token added to the package appears here with no edit to this page.

Reading the table

Tokens are grouped by name, not by a curated list, which is what makes the previous sentence true. Where a token is an alias — one name standing for another so a surface can be renamed without touching every call site — the target is shown beneath it and the value resolved to the end of the chain.

Values marked same in the dark column are theme-invariant: the scales for radius, duration, easing and stacking order are declared once and do not vary between themes, because nothing about a viewer's colour preference should change how far a sheet travels.

Colour is authored in OKLCH

Lightness in OKLCH is perceptual, so 0.6 means the same apparent brightness at every hue. That is what makes a contrast budget tractable: a hue can be changed without silently changing how light it reads, and the measured ratios on this site follow from the values rather than from taste.

Geometry

One radius, six derived steps. Every corner in the products resolves to this scale.

Geometry tokens, with light and dark values
Token Light Dark
--radius 0.75rem same
--radius-sm calc(var(--radius) - 4px) same
--radius-md calc(var(--radius) - 2px) same
--radius-lg alias of --radius 0.75rem same
--radius-xl calc(var(--radius) + 4px) same
--radius-2xl calc(var(--radius) + 12px) same
--radius-3xl calc(var(--radius) + 20px) same

Shell layout

The fixed measurements the application shell is built on.

Shell layout tokens, with light and dark values
Token Light Dark
--sidebar-width 16rem same
--sidebar-width-collapsed 4rem same
--content-max 72rem same
--content-max-narrow 52rem same

Typography

Two stacks — one for display, one for body copy.

Typography tokens, with light and dark values
Token Light Dark
--font-display "Satoshi", sans-serif same
--font-body "Inter", sans-serif same

Duration scale

Every animated stop in the products picks from this scale. Raw millisecond values in component styles are a lint failure, not a preference.

Duration scale tokens, with light and dark values
Token Light Dark
--duration-instant 50ms same
--duration-press 80ms same
--duration-fast 150ms same
--duration-base 250ms same
--duration-medium 300ms same
--duration-slow 400ms same
--duration-slower 600ms same
--duration-sheet-open 380ms same
--duration-sheet-close 240ms same
--duration-hero 900ms same
--duration-settle 2200ms same
--duration-skeleton-settle 420ms same

Easing scale

Curves are named for the job they do, so a component cannot invent its own feel.

Easing scale tokens, with light and dark values
Token Light Dark
--ease-out-expo cubic-bezier(0.16, 1, 0.3, 1) same
--ease-linear linear same
--ease-out cubic-bezier(0, 0, 0.2, 1) same
--ease-spring cubic-bezier(0.34, 1.56, 0.64, 1) same
--ease-in-out cubic-bezier(0.65, 0, 0.35, 1) same
--ease-water cubic-bezier(0.22, 1, 0.36, 1) same

Z-index scale

Stacking order is enumerated, so nothing has to guess a number.

Z-index scale tokens, with light and dark values
Token Light Dark
--z-base 0 same
--z-dropdown 10 same
--z-sticky 20 same
--z-banner 30 same
--z-overlay 40 same
--z-modal 50 same
--z-popover 60 same
--z-toast 70 same
--z-tooltip 80 same

Interactive states

Hover, active and disabled are tokens, not opacity applied at the call site.

Interactive states tokens, with light and dark values
Token Light Dark
--text-disabled oklch(0.7 0.005 60) oklch(0.45 0.01 250)
--primary-hover oklch(0.7 0.13 220) oklch(0.58 0.13 218)
--primary-active oklch(0.45 0.13 230) oklch(0.46 0.13 225)
--primary-disabled oklch(0.5 0.13 230 / 40%) oklch(0.52 0.13 220 / 40%)
--destructive-hover oklch(0.5 0.24 27) oklch(0.66 0.19 22)
--destructive-active oklch(0.46 0.23 27) oklch(0.62 0.19 22)
--destructive-disabled oklch(0.55 0.245 27.325 / 40%) oklch(0.704 0.191 22.216 / 40%)
--secondary-hover oklch(0.88 0.005 60) oklch(0.25 0.01 250)
--secondary-active oklch(0.84 0.005 60) oklch(0.29 0.01 250)
--secondary-disabled oklch(0.92 0.005 60 / 50%) oklch(0.21 0.01 250 / 50%)

Chart colours

Data series only. Warm amber lives here and is never allowed to carry status meaning.

Chart colours tokens, with light and dark values
Token Light Dark
--chart-1 oklch(0.78 0.13 70) oklch(0.78 0.13 70)
--chart-2 oklch(0.6 0.118 184.704) oklch(0.696 0.17 162.48)
--chart-3 oklch(0.398 0.07 227.392) oklch(0.769 0.188 70.08)
--chart-4 oklch(0.828 0.189 84.429) oklch(0.627 0.265 303.9)
--chart-5 oklch(0.769 0.188 70.08) oklch(0.645 0.246 16.439)
--chart-forecast alias of --primary oklch(0.5 0.13 230) oklch(0.52 0.13 220)
--chart-actual oklch(0.6 0.13 70) oklch(0.78 0.13 70)
--chart-confidence oklch(0.5 0.13 230 / 8%) oklch(0.56 0.13 220 / 8%)
--chart-danger oklch(0.65 0.22 25 / 20%) oklch(0.65 0.22 25 / 25%)
--chart-forecast-fill-mid oklch(0.5 0.15 235 / 0.32) oklch(0.5 0.15 235 / 0.32)
--chart-tick oklch(0.5 0.01 250) oklch(0.63 0.01 250)
--chart-favorable oklch(0.55 0.16 160) oklch(0.65 0.17 160)
--chart-unfavorable oklch(0.6 0.18 30) oklch(0.65 0.2 30)

Sidebar

The navigation surface keeps its own set so it can diverge from card surfaces.

Sidebar tokens, with light and dark values
Token Light Dark
--sidebar oklch(0.94 0.008 60) oklch(0.16 0.01 250)
--sidebar-foreground alias of --card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--sidebar-primary alias of --primary oklch(0.5 0.13 230) oklch(0.52 0.13 220)
--sidebar-primary-foreground alias of --primary-foreground oklch(1 0 0) oklch(1 0 0)
--sidebar-accent oklch(0.9 0.01 240) oklch(0.24 0.01 250)
--sidebar-accent-foreground alias of --card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--sidebar-border alias of --border oklch(0.88 0.005 60) oklch(1 0 0 / 10%)
--sidebar-ring alias of --ring oklch(0.5 0.13 230 / 40%) oklch(0.56 0.13 220 / 50%)

Domain accents

Per-section wayfinding hues. Gradient stops are not representable in the typed lens, so these are CSS-only by design.

Domain accents tokens, with light and dark values
Token Light Dark
--domain-pantry oklch(0.74 0.16 75) oklch(0.8 0.16 80)
--domain-pantry-from oklch(0.54 0.16 85) oklch(0.54 0.16 85)
--domain-pantry-to oklch(0.46 0.16 60) oklch(0.46 0.16 60)
--domain-pantry-wash oklch(0.98 0.025 90) oklch(0.23 0.04 75)
--domain-pantry-foreground oklch(1 0 0) oklch(1 0 0)
--domain-list oklch(0.6 0.14 235) oklch(0.7 0.13 225)
--domain-list-from oklch(0.52 0.13 220) oklch(0.52 0.13 220)
--domain-list-to oklch(0.44 0.16 255) oklch(0.44 0.16 255)
--domain-list-wash oklch(0.975 0.02 240) oklch(0.21 0.04 250)
--domain-list-foreground oklch(1 0 0) oklch(1 0 0)
--domain-trips oklch(0.64 0.16 158) oklch(0.72 0.16 156)
--domain-trips-from oklch(0.52 0.17 150) oklch(0.52 0.17 150)
--domain-trips-to oklch(0.44 0.13 165) oklch(0.44 0.13 165)
--domain-trips-wash oklch(0.975 0.03 158) oklch(0.2 0.04 160)
--domain-trips-foreground oklch(1 0 0) oklch(1 0 0)
--domain-catalog oklch(0.58 0.14 290) oklch(0.7 0.14 292)
--domain-catalog-from oklch(0.56 0.15 295) oklch(0.56 0.15 295)
--domain-catalog-to oklch(0.47 0.16 285) oklch(0.47 0.16 285)
--domain-catalog-wash oklch(0.975 0.02 295) oklch(0.21 0.04 290)
--domain-catalog-foreground oklch(1 0 0) oklch(1 0 0)
--domain-more oklch(0.64 0.18 45) oklch(0.72 0.18 48)
--domain-more-from oklch(0.55 0.18 55) oklch(0.55 0.18 55)
--domain-more-to oklch(0.46 0.21 32) oklch(0.46 0.21 32)
--domain-more-wash oklch(0.975 0.025 50) oklch(0.22 0.05 45)
--domain-more-foreground oklch(1 0 0) oklch(1 0 0)
--fab-addtrip-from oklch(0.52 0.1 190) same
--fab-addtrip-to oklch(0.45 0.1 190) same
--fab-addtrip oklch(0.6 0.1 190) same
--fab-addtrip-foreground oklch(1 0 0) same

Status colour

Calm by intent. Each status carries an `-on-tint` variant for text sitting on its own wash, because the tint moves the background toward the text and drops the plain token below AA.

Status colour tokens, with light and dark values
Token Light Dark
--destructive oklch(0.55 0.245 27.325) oklch(0.704 0.191 22.216)
--destructive-foreground oklch(0.98 0 0) oklch(0.98 0 0)
--destructive-on-tint oklch(0.46 0.245 27.325) oklch(0.704 0.191 22.216)
--success-chip color-mix(in srgb, var(--success) 10%, var(--card)) color-mix(in srgb, var(--success) 10%, var(--card))
--warning-chip color-mix(in srgb, var(--warning) 10%, var(--card)) color-mix(in srgb, var(--warning) 10%, var(--card))
--destructive-chip color-mix(in srgb, var(--destructive) 10%, var(--card)) color-mix(in srgb, var(--destructive) 10%, var(--card))
--success oklch(0.45 0.15 155) oklch(0.72 0.17 155)
--success-foreground oklch(1 0 0) oklch(0.1 0.03 155)
--warning oklch(0.5 0.16 75) oklch(0.83 0.17 84)
--warning-foreground oklch(1 0 0) oklch(0.15 0.05 84)
--warning-on-tint oklch(0.46 0.16 75) oklch(0.7 0.17 84)
--transfer oklch(0.58 0.165 254.624) oklch(0.77 0.165 254.624)
--credit oklch(0.54 0.18 293) oklch(0.66 0.18 293)
--credit-on-tint oklch(0.48 0.18 293) oklch(0.68 0.18 293)
--destructive-surface oklch(0.55 0.245 27.325) oklch(0.44 0.2 22.216)

Surfaces, glass and glow

Elevation expressed as tokens rather than as ad-hoc shadow and blur values.

Surfaces, glass and glow tokens, with light and dark values
Token Light Dark
--goal-liquid-foreground oklch(0.43 0.01 40) oklch(0.9 0.01 250)
--surface-glass oklch(0 0 0 / 8%) oklch(1 0 0 / 7%)
--surface-glass-top oklch(0 0 0 / 5%) oklch(1 0 0 / 8%)
--glass-border oklch(0 0 0 / 8%) oklch(1 0 0 / 10%)
--hero-number-gradient-from oklch(0.32 0.13 230) oklch(0.92 0.06 220)
--hero-number-gradient-to oklch(0.44 0.13 230 / 85%) oklch(0.66 0.13 220)
--hero-number-gradient-critical-from oklch(0.36 0.2 27) oklch(0.86 0.09 30)
--hero-number-gradient-critical-to oklch(0.44 0.21 25 / 85%) oklch(0.68 0.19 25)
--glow-color alias of --primary-glow oklch(0.7 0.13 220) oklch(0.62 0.13 218)
--surface-base alias of --background oklch(0.97 0.008 60) oklch(0.14 0.03 265)
--surface-raised alias of --card oklch(1 0 0) oklch(0.19 0.03 262)
--surface-sunken oklch(0.98 0.005 60) oklch(0.11 0.01 250)
--surface-overlay alias of --popover oklch(1 0 0) oklch(0.19 0.03 262)

Shadows

Composite values, so elevation stays consistent across products.

Shadows tokens, with light and dark values
Token Light Dark
--shadow-elevated 0 8px 32px oklch(0 0 0 / 12%) 0 8px 32px oklch(0 0 0 / 40%)
--shadow-card 0 4px 16px oklch(0 0 0 / 8%) 0 4px 16px oklch(0 0 0 / 12%)
--shadow-glow-primary 0 0 16px oklch(0.7 0.13 220 / 30%) 0 0 16px oklch(0.62 0.13 220 / 30%)
--shadow-glow alias of --shadow-glow-primary 0 0 16px oklch(0.7 0.13 220 / 30%) 0 0 16px oklch(0.62 0.13 220 / 30%)

Borders

Weight tokens for standard edges, plus the separate borders the glass surfaces need.

Borders tokens, with light and dark values
Token Light Dark
--border oklch(0.88 0.005 60) oklch(1 0 0 / 10%)
--border-glass oklch(0 0 0 / 10%) oklch(1 0 0 / 10%)
--border-glass-critical oklch(0.55 0.245 27.325 / 35%) oklch(0.704 0.191 22.216 / 35%)
--border-subtle oklch(0.94 0.005 60) oklch(1 0 0 / 6%)
--border-default alias of --border oklch(0.88 0.005 60) oklch(1 0 0 / 10%)
--border-strong oklch(0.82 0.005 60) oklch(1 0 0 / 18%)

Semantic text

Text colour by role rather than by hue.

Semantic text tokens, with light and dark values
Token Light Dark
--text-primary alias of --foreground oklch(0.12 0.01 30) oklch(1 0 0)
--text-secondary alias of --muted-foreground oklch(0.5 0.01 40) oklch(0.63 0.01 250)
--text-tertiary alias of --foreground-muted oklch(0.5 0.01 30) oklch(0.65 0.01 250)

Base colours

The foundation both products build on.

Base colours tokens, with light and dark values
Token Light Dark
--background oklch(0.97 0.008 60) oklch(0.14 0.03 265)
--foreground oklch(0.12 0.01 30) oklch(1 0 0)
--card oklch(1 0 0) oklch(0.19 0.03 262)
--card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--popover alias of --card oklch(1 0 0) oklch(0.19 0.03 262)
--popover-foreground alias of --card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--primary oklch(0.5 0.13 230) oklch(0.52 0.13 220)
--primary-foreground oklch(1 0 0) oklch(1 0 0)
--primary-text alias of --primary oklch(0.5 0.13 230) oklch(0.6 0.13 220)
--primary-on-tint oklch(0.42 0.13 230) oklch(0.66 0.13 220)
--secondary oklch(0.92 0.005 60) oklch(0.2 0.03 260)
--secondary-foreground alias of --card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--muted alias of --secondary oklch(0.92 0.005 60) oklch(0.2 0.03 260)
--muted-foreground oklch(0.5 0.01 40) oklch(0.63 0.01 250)
--muted-foreground-subtle oklch(0.54 0.01 40) oklch(0.6 0.01 250)
--accent oklch(0.92 0.01 40) oklch(0.24 0.01 250)
--accent-foreground alias of --card-foreground oklch(0.12 0.01 30) oklch(1 0 0)
--input alias of --border oklch(0.88 0.005 60) oklch(1 0 0 / 12%)
--ring oklch(0.5 0.13 230 / 40%) oklch(0.56 0.13 220 / 50%)
--highlight-edge oklch(0 0 0 / 8%) oklch(1 0 0 / 15%)
--accent-glow oklch(0.5 0.13 230 / 12%) oklch(0.56 0.13 220 / 18%)
--blob-primary oklch(0.5 0.13 230 / 8%) oklch(0.56 0.13 220 / 12%)
--blob-secondary oklch(0.6 0.1 240 / 5%) oklch(0.7 0.1 240 / 7%)
--primary-glow oklch(0.7 0.13 220) oklch(0.62 0.13 218)
--foreground-muted oklch(0.5 0.01 30) oklch(0.65 0.01 250)
--modal-surface oklch(0.94 0.005 60) oklch(0.22 0.03 262)
--backdrop oklch(0 0 0 / 50%) oklch(0 0 0 / 70%)
--focus-ring alias of --ring oklch(0.5 0.13 230 / 40%) oklch(0.56 0.13 220 / 50%)
--focus-ring-offset alias of --background oklch(0.97 0.008 60) oklch(0.14 0.03 265)