feat(lint): make contrast check blocking + fix dark subtle-text AA
Per review on #7009: the contrast check was warn-only and opt-in, so it would never catch regressions. Enforce it here (the follow-up PR): - theme-lint.mjs `contrast` mode now exits non-zero on any sub-floor pair - wired into `task frontend:lint:colors` (runs in the blocking lint gate) - fixed the two failing pairs: --c-text-subtle on dark/portal-dark surfaces (3.36/3.67 → 4.74/5.18) by adding --p-zinc-250 and pointing dark subtle at it All text-on-surface / on-primary pairs now clear WCAG AA per theme.
This commit is contained in:
@@ -63,9 +63,9 @@ One file: `editor/scripts/lint/theme-lint.mjs` (no baseline). Run via `task fron
|
||||
- **Default (blocking):** enforces "literals only in `primitives.css`; everything else in `core/theme/` references tokens; no duplicate primitives." Scope: `core/theme/`.
|
||||
- **`css-colors` (blocking):** enforces **no hardcoded colour in any source `.css`** across `editor/src` — `primitives.css` (the literal home) and generated `output.css` are the only exemptions. The file list comes from `git ls-files` (not a directory walk), and comments/structural black-white-transparent are ignored.
|
||||
- **`code-colors` (blocking):** enforces **no hardcoded colour in TS/TSX DOM code**. TS/TSX can't be zeroed like CSS (canvas/PDF/pdfium rendering, colour maths, colour pickers, vendor brand and self-contained docs legitimately need numeric colour), so it's **default-deny with layered exemptions**: (1) structural black/white/transparent; (2) detected safe contexts on the line — `var(--x, …)` / `readColor(…)` fallbacks, canvas assignments (`fillStyle`/`ctx.`…), pdf-lib `rgb(0..1)`, and an explicit **`// theme-allow-color <reason>`** opt-out; (3) exempt **paths** for whole rendering/vendor/config/illustration areas (viewer/annotation, `*Thumbnail`/`*Overlay`, `*Pdf*`, colour pickers, `onboarding/`, `mantineTheme`/`theme.ts`, tests, stories, type decls, marketing banners). A raw colour anywhere else fails. Adding a new colour to a normal component → blocked; genuine exceptions get the marker.
|
||||
- **`node theme-lint.mjs contrast`** (task `frontend:contrast`, non-blocking): WCAG contrast report for text-on-surface / on-primary pairs per theme.
|
||||
- **`contrast` (blocking):** fails if any text-on-surface / on-primary pair misses its WCAG AA floor (4.5 normal, 3.0 on-primary) in any theme, resolved for the default accent. Custom accents are handled at runtime by the `customPrimary.ts` guardrails.
|
||||
|
||||
All three blocking modes run under `task frontend:lint:colors`. Source **CSS is at zero** hardcoded colour and **TS/TSX DOM code is clean** (only the exempt rendering/vendor/config areas hold literals). Keep it there — add the literal to `primitives.css` and reference `var(--p-…)`, or for an unavoidable TS/TSX literal add `// theme-allow-color <reason>`.
|
||||
All four blocking modes run under `task frontend:lint:colors`. Source **CSS is at zero** hardcoded colour and **TS/TSX DOM code is clean** (only the exempt rendering/vendor/config areas hold literals). Keep it there — add the literal to `primitives.css` and reference `var(--p-…)`, or for an unavoidable TS/TSX literal add `// theme-allow-color <reason>`.
|
||||
|
||||
## Gotchas
|
||||
|
||||
|
||||
@@ -72,7 +72,7 @@ html[data-app-theme="midnight"] {
|
||||
|
||||
--c-text: var(--p-zinc-100);
|
||||
--c-text-muted: var(--p-zinc-200);
|
||||
--c-text-subtle: var(--p-zinc-300);
|
||||
--c-text-subtle: var(--p-zinc-250);
|
||||
--c-text-on-primary: var(--p-white);
|
||||
|
||||
--c-border: var(--p-zinc-650);
|
||||
@@ -209,7 +209,7 @@ html[data-app-theme="custom"][data-mantine-color-scheme="dark"] {
|
||||
/* Neutral text / borders / overlay (not accent-tinted). */
|
||||
--c-text: var(--p-zinc-100);
|
||||
--c-text-muted: var(--p-zinc-200);
|
||||
--c-text-subtle: var(--p-zinc-300);
|
||||
--c-text-subtle: var(--p-zinc-250);
|
||||
--c-border-strong: var(--p-zinc-500);
|
||||
--c-overlay: rgba(0, 0, 0, 0.6);
|
||||
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
--p-zinc-500: #3f3f46;
|
||||
--p-zinc-400: #52525b;
|
||||
--p-zinc-300: #71717a;
|
||||
--p-zinc-250: #8a8a93;
|
||||
--p-zinc-200: #a1a1aa;
|
||||
--p-zinc-100: #f4f4f5;
|
||||
--p-blue-400: #60a5fa;
|
||||
|
||||
Reference in New Issue
Block a user