Accessibility
A floor we measure, never a matter of taste.
Contrast is computed (WCAG and APCA), motion is optional, and meaning never rests on color alone.
Contrast (computed)
Body text ≥ 4.5:1, UI and large text ≥ 3:1, in both Day and Night. Colored text uses a darker
-text variant; the bright token is reserved for fills and dots. The /design-system-review skill's
contrast.py audits every WCAG pairing; lumen/system/scripts/apca.py (self-tested against the apca-w3
reference values) covers the saturated mid-tones WCAG underrates.
APCA on the saturated fills (computed 2026-10-23, the v2 values):
| Label on fill | WCAG | APCA Lc | Read |
|---|---|---|---|
white on --primary #241917 (the action, in ink; gradient start) | 17.12 | 106.3 | ✅ body-size labels |
white on the gradient end (color-mix ≈ #412B12) | 13.30 | 102.8 | ✅ |
white on --brand #EA580C (Solar, the mark) | 3.56 | 67.6 | ⚠️ Solar is Halo's mark, never a label's ground |
white on --destructive #D42A2A | 5.04 | 78.5 | ✅ |
#18120F on Night --primary #EFE8DF | 15.26 | 92.0 | ✅ |
Edges (WCAG 1.4.11, 3:1 for the edge that identifies a control):
| Edge | On | WCAG | Read |
|---|---|---|---|
--border-strong #968476 (= --input) | Day card #FFFDFA | 3.53 | ✅ every control's edge |
--border-strong #857467 | Night card #221A16 | 3.82 | ✅ |
--border #E6DCD0 | Day card | 1.33 | decorative only: dividers inside a card, never a control |
lumen/system/scripts/check_truth.py enforces both tables: the action label at 4.5:1, every control edge at
3:1 on each surface a control can sit on, and every brand, status and data mark at 3:1 on a card.
Bright is for fills, not text
--brand (#EA580C) is a fill/dot color. For small colored text use --primary-text (#A8430A), which clears
AA on the light ground, the card and the muted fill. Every saturated hue ships a matching -text step — including --data-4-text.
Never use --glow under a light text label.
Beyond color
Status never depends on hue alone — it pairs color with an icon and a label, so it survives the grayscale test and works for color-vision deficiencies.
| State | Color | Icon | Survives grayscale? |
|---|---|---|---|
| On track | success | check | ✓ |
| Watch | warning | triangle | ✓ |
| Critical | danger | octagon | ✓ |
Motion
Every animation respects prefers-reduced-motion. Energy is earned — tied to a real signal — never
ambient noise. Under reduced-motion, transitions collapse to near-instant and looping animation stops.