fix(design): the lab draws with the primitives' own classes, not a height-ladder copy; DESIGN no longer claims accent-color tints the colour well (E28)

This commit is contained in:
2026-09-25 17:15:03 +02:00
parent e13d93a3ed
commit 29abf609f3
4 changed files with 22 additions and 27 deletions
+2 -1
View File
@@ -143,7 +143,8 @@ The chosen rendering of each rule is in the lab under "Decided". The primitives
choice"), r8 and full width in a form, where it wears the field's frame (see-through, the ≥ 3:1 edge) and
lines up with the inputs. Open is the accent edge and the chevron turned over.
- **Checkbox, switch, slider (A6):** the browser's own controls tinted with `accent-color` (`Checkbox`,
`CheckRow`, `Slider`, `ColorInput`); the whole labelled row is the 44px target. Keyboard, screen reader and
`CheckRow`, `Slider`); `ColorInput` is the browser's colour well, which `accent-color` does not reach (it
tints only checkboxes, radios, ranges and progress bars). The whole labelled row is the 44px target. Keyboard, screen reader and
forced-colours support come from the browser. The switch stays `form`'s `Switch`: no browser has a native
one yet. A raw `<input>` or `<textarea>` outside those primitives is a lint error (a hidden file picker
passes).
+13 -9
View File
@@ -23,8 +23,13 @@ import {
import { Btn } from "./batchA";
import { C1 } from "./batchCActions";
import { Reference, Sample } from "./labKit";
import { FADE_ABOVE_PANEL, FADE_BELOW_PANEL, H, LAYER, STRONG } from "./labTokens";
import { FADE_ABOVE_PANEL, FADE_BELOW_PANEL, LAYER } from "./labTokens";
import { SURFACE } from "../components/ui/surfaces";
import { iconButtonClass } from "../components/ui/buttonStyles";
import { fieldClass } from "../components/ui/fieldStyles";
// The ui/ primitives' own classes on static spans: the lab draws what the app ships, not a copy.
const ICON = iconButtonClass({ variant: "ghost", size: "sm" });
// E28 S2 · Batch C — behaviour on touch and on a narrow window, DECIDED (owner, 2026-09-24): C1–C4 as
// proposed; C5 is the owner's reworked Plex control set (found by the live player pass, E28 S2d: the
@@ -61,10 +66,10 @@ function FilterPanel() {
<div className="flex items-center justify-between">
<span className="font-semibold">Filters</span>
<span className="flex gap-0.5">
<span className={clsx("grid place-items-center rounded-lg text-muted", H.iconSm, LAYER)}>
<span className={ICON}>
<Pin className="h-3.5 w-3.5" />
</span>
<span className={clsx("grid place-items-center rounded-lg text-muted", H.iconSm, LAYER)}>
<span className={ICON}>
<X className="h-3.5 w-3.5" />
</span>
</span>
@@ -144,12 +149,11 @@ function Field({ label, value, focused }: { label: string; value: string; focuse
<span className="font-medium">{label}</span>
<span
className={clsx(
// eslint-disable-next-line no-restricted-syntax -- a drawing of a field, not a label
"flex items-center rounded-lg border px-3 text-sm",
H.field,
focused && "ring-2 ring-accent",
fieldClass({ size: "md" }),
"flex items-center",
// The primitive's focus-within look, drawn: a mock span can hold no focus.
focused && "border-accent ring-1 ring-accent",
)}
style={{ borderColor: STRONG }}
>
{value}
</span>
@@ -173,7 +177,7 @@ function C4() {
)}
>
Edit details
<span className={clsx("grid place-items-center rounded-lg text-muted", H.iconSm)}>
<span className={ICON}>
<X className={ico} />
</span>
</div>
+5 -5
View File
@@ -1,7 +1,8 @@
import clsx from "clsx";
import { Bookmark, Check, ListPlus, MoreHorizontal, Play } from "lucide-react";
import { Reference, Sample } from "./labKit";
import { H, LAYER } from "./labTokens";
import { LAYER } from "./labTokens";
import { iconButtonClass } from "../components/ui/buttonStyles";
import { SURFACE } from "../components/ui/surfaces";
// E28 S2 · Batch C, part 1 — action placement: the classification table (object × action → where it
@@ -312,10 +313,9 @@ function Table() {
}
function Card({ touch }: { touch: boolean }) {
const act = clsx(
"grid place-items-center rounded-lg bg-black/55 text-white",
touch ? "h-11 w-11" : H.iconSm,
);
// The IconButton `media` face (a dark button on a picture); the touch rendering shows the 44 box
// that a coarse pointer gives it (A3).
const act = clsx(iconButtonClass({ variant: "media", size: "sm" }), touch && "size-11");
return (
<div className={`${SURFACE.card} group flex w-60 flex-col gap-1.5 p-1.5`}>
<div className="relative aspect-video overflow-hidden rounded-lg bg-linear-to-br from-accent/50 to-card">
+2 -12
View File
@@ -1,17 +1,7 @@
// The decided values the lab's reference renderings share (batches A and B, 2026-09-24). The colour
// rules are real now (E28 S3a): each constant below names the index.css utility or token that holds
// it, so the lab renders what the app ships. The height ladder moves into ui/Button in S3b.
/** B1 compact ladder: explicit heights, so one toolbar row lines up at 28. */
export const H = {
md: "h-8 px-3 text-sm gap-1.5",
sm: "h-7 px-2.5 text-sm gap-1.5",
xs: "h-6 px-2 text-xs gap-1",
iconSm: "w-7 h-7",
icon: "w-8 h-8",
field: "h-8",
bar: "h-7",
} as const;
// it, so the lab renders what the app ships. The height ladder lives in the primitives (ui/buttonStyles,
// ui/fieldStyles), and a lab drawing takes their classes (F31).
/** A4: the input edge, ≥ 3:1 against the page in every scheme and mode (index.css --edge-strong). */
export const STRONG = "var(--edge-strong)";