You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
svelte-kit-vice/docs/building-a-component.md

63 lines
5.4 KiB

feat(eidos): recipe contract R-4.x + motion-channel migration 15/15 + theme-builder fixes + inventory decisions Fable audit follow-through (fable_audit.md + fable-eidos-audit.md): - RECIPE_CONTRACT.md (E2 canon): the transversal systems every recipe must consume, enforced by component-audit R-4.1-4.6 (all at error; escape valves /* literal */ + /* functional */; WIP tracks excluded). Stale audit rules fixed against the current architecture (E-2.2 wrapper imports, D-1.2 v2 9-tab union, D-3.1 single snippet, TabsVariant mirror) - verdicts went 0/117/15 -> 75/50/5. - Motion migration 15/15: recipes off local @keyframes onto the channel - preset stamps (dropdown/context/select/combobox/tooltip/link-preview/ clipboard), new expand/collapse + value-flash signatures, shared-axis reverse pair, delayed-open open-alias in the preset trigger (PRESET_STATE_ALIASES), materials pattern for irreducible triggers (card/timeline/tabs/nav-menu/metrics). Duration/scale hooks keep every recipe's tuned values. - buildScheme (fase C): full a1..a12 alpha ramp per role (was a2/a3 - stale alphas after applyColorScheme), intentSeeds so temper starts from the ACTIVE theme's intent mapping (risk stays orange), alpha background self-derived from the scheme's own neutral step 1 (was hardcoded #fff/#111); mode now forces the donor variant. - Inventory decisions (fase D): semanticTracking axis removed (all-zero), border-hover slot dropped (0 consumers), separator slot adopted across line dividers (step 6, Radix divider tone), size-bundle consumption pilot on toggle (canonical coordinates consumed, deliberate deviations kept visible). - Docs: building-a-component.md (the one door, 9-phase route + known traps), PLAN-docs-reconciliation.md (fase 6 kickoff for a fresh session), THEMING wiring updates. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
3 months ago
---
title: Building a Component — the one door
type: guide
audience: human + agent
authority: navigational — THE entry point for building a new component; content lives in the linked docs
status: current
related:
acceptance: src/uix/COMPONENT_COMPLETION_CHECKLIST.md (when is it done — machine-audited)
soma: src/uix/soma/COMPONENT_GUIDE.md (the deepest phase doc)
---
# Building a Component — the one door
Read **this file first and only this file**. Building a component crosses the four
layers and the theming system; the knowledge lives in eight documents that each own
one phase. Nobody should have to discover that chain by archaeology — this doc IS
the chain. Each phase names **the one document to read**, what you produce, and the
guard that verifies it.
Role note (authoring rule 4 — one source per concern): this doc contains **no
content**, only sequencing. If a phase doc and this table disagree about order,
this doc wins on *order*; the phase doc wins on *content*.
---
## The route
| Phase | You produce | Read THIS | Verified by |
| --- | --- | --- | --- |
| **0 · Decide** | comparison table vs ark/bits/radix (+ react-aria), membership call (soma or eidos-native), compose-first check | [`soma/COMPONENT_GUIDE.md`](../src/uix/soma/COMPONENT_GUIDE.md) §Before You Start (1–4) · membership: [`soma/README.md`](../src/uix/soma/README.md) §2 | reviewer — the table goes in the component README (phase 7) |
| **1 · Morfo** | `src/uix/morfo/components/{kebab}.ts` — parts, data/aria, keyboard, events (family/verb/intent/sequence), `texts`, `expression` | [`morfo/README.md`](../src/uix/morfo/README.md) §Authoring a new morfo · vocabulary: [`CANON.md`](./CANON.md) | `validateMorfo` + `npm run morfo:vocabulary` + audit `A-*` |
| **2 · Soma** | `{kebab}-provider.svelte.ts` + thin wrappers + `types.ts` + provider test | [`soma/COMPONENT_GUIDE.md`](../src/uix/soma/COMPONENT_GUIDE.md) (patterns + rules A1–A37) | provider test + `npm run check` |
| **3 · Sema** | pack `src/uix/sema/components/{kebab}.ts` (or explicit `expression: 'family-default'`) — selectors via `semaSelector` ONLY | [`sema/README.md`](../src/uix/sema/README.md) §packs + §typed builder · pack-vs-default criteria: [`LIBRO_VARIACIONES`](../src/docs/LIBRO_VARIACIONES_Y_EXTENSIONES.md) D.4 | `npm run morfo:vocabulary` (expression coverage) |
| **4 · Eidos wrapper** | `eidos/components/{kebab}/` — root + attached parts (option C), visual props | [`eidos/components/README.md`](../src/uix/eidos/components/README.md) (the 7 hard rules) | `component-api-contract` test + audit `E-*` |
| **5 · Recipe + theming** | recipe tokens in `lib/recipes/base.ts` + `{kebab}.css` | [`eidos/THEMING_GUIDE.md`](../src/uix/eidos/THEMING_GUIDE.md) pasos 1–6 · **mandatory contract**: [`eidos/RECIPE_CONTRACT.md`](../src/uix/eidos/RECIPE_CONTRACT.md) · scope (if `data-color`): [`eidos/TSC.md`](../src/uix/eidos/TSC.md) | `npm run generate:eidos-css` + `recipe-css-contract` test + audit `R-*` (R-4.x = the contract) |
| **6 · Demo** | `web/routes/uix/components/{kebab}/+page.svelte` — v2 9-tab layout | [`DEMO_AUTHORING_GUIDE.md`](../web/routes/uix/lib/DEMO_AUTHORING_GUIDE.md) | audit `D-*` + `npm run smoke` |
| **7 · Component README** | Baseline · Comparativa (≥3 refs) · Decisiones · Gaps-with-disposition · Sema events table | template = any recent PASS component's README; sections audited | audit `F-*` |
| **8 · Acceptance** | nothing new — the component passes | [`COMPONENT_COMPLETION_CHECKLIST.md`](../src/uix/COMPONENT_COMPLETION_CHECKLIST.md) | `npm run component:audit --only {kebab}` + `npm run morfo:check` + `eidos-lint` |
Cross-phase invariants you will hit in every phase: the layer boundaries
([`active_architecture.md`](../src/uix/active_architecture.md) §7 hard rules) and the
2-of-3 rule for extending morfo ([`morfo/README.md`](../src/uix/morfo/README.md)).
---
## Known traps — sections that LOOK authoritative but are superseded
The corpus still carries superseded material inline. Until the cleanup pass lands,
do **not** follow these:
| If you read… | The truth is… |
| --- | --- |
| `translations:` field in morfo examples (morfo/README, SOMA_ARCHITECTURE §7) | The field is **`texts:`** (idlangrefs). `translations:` does not compile — audit rule A-1.3 flags it. |
| THEMING.md §13 (`event:*` TSC scope) + §14's `data-motion-ref` | Superseded — the motion model is [`eidos-motion.md`](../src/uix/eidos/eidos-motion.md) (two moments, signatures in `EidosConfig.motion`). |
| GUIA_IMPLEMENTACION §5.3 (`defaultSemantic`) | The implemented shape is additive `allowedFamilies` ([`LIBRO_VARIACIONES`](../src/docs/LIBRO_VARIACIONES_Y_EXTENSIONES.md) D.11). |
| GUIA_IMPLEMENTACION §6.2 holds table / §4.1 dialog=shift | Code + [`CANON.md`](./CANON.md) win: holds live in `SEMA_MAP` / `holds.ts`; Dialog's events are `emerge` in its morfo. |
| soma/README §3 deps (`@floating-ui`, `clsx`) | Positioning is the in-house engine (`soma/layers/floating` + `$ethereal`); those deps are gone/dev-only. |
| A 6-tab demo `type Tab` union in older demos | The canonical layout is the v2 **9-tab** union (DEMO_AUTHORING_GUIDE); v1 is accepted only pending migration. |
| "24 archetypes" (active_architecture §6, morfo/README) | `ARCHETYPE_VOCABULARY` in `morfo/types.ts` is the source (26 today — the const wins over any count in prose). |
Golden rule when a doc contradicts code: **code + CANON.md win** — and open an
issue/fix for the doc (THEMING.md's own footer says the same).

Powered by TurnKey Linux.