diff --git a/spacecraft-accessibility-support.skill b/spacecraft-accessibility-support.skill index 45a0656..49fbbc5 100644 Binary files a/spacecraft-accessibility-support.skill and b/spacecraft-accessibility-support.skill differ diff --git a/spacecraft-accessibility-support.zip b/spacecraft-accessibility-support.zip index 869a4ba..84ffd29 100644 Binary files a/spacecraft-accessibility-support.zip and b/spacecraft-accessibility-support.zip differ diff --git a/spacecraft-accessibility-support/references/audit.md b/spacecraft-accessibility-support/references/audit.md index e1f9df3..618e98f 100644 --- a/spacecraft-accessibility-support/references/audit.md +++ b/spacecraft-accessibility-support/references/audit.md @@ -198,13 +198,13 @@ M0: [████████████████████] 100% M1: [████████████████████] 100% M2: [██████████████░░░░░░] 70% M3: [░░░░░░░░░░░░░░░░░░░░] 0% -MVP: [ ▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▱▱ ] 90% +MVP: [██████████████████░░] 90% PRD: [██████████████░░░░░░] 70% ``` One row per track, each with its own 20-cell bar: milestone rows first, then `MVP`, then whichever of `TODO`/`PLAN`/`PRD` the audit is driven by. Emit only the rows that apply — never pad the block with 0% rows for -tracks that do not exist. `MVP` uses `▰`/`▱` with a space inside each -bracket; every other row uses `█`/`░` with tight brackets, and the -padding is what keeps the columns aligned. +tracks that do not exist. Every row uses `█`/`░` with tight brackets: +label in a six-character field, bar in columns 8–27, percentage +right-aligned in a five-character field after the closing bracket. diff --git a/spacecraft-standard-constitution.skill b/spacecraft-standard-constitution.skill index c27edb2..2977471 100644 Binary files a/spacecraft-standard-constitution.skill and b/spacecraft-standard-constitution.skill differ diff --git a/spacecraft-standard-constitution.zip b/spacecraft-standard-constitution.zip index 367b80a..5d6a8f0 100644 Binary files a/spacecraft-standard-constitution.zip and b/spacecraft-standard-constitution.zip differ diff --git a/spacecraft-standard-constitution/SKILL.md b/spacecraft-standard-constitution/SKILL.md index 8ceebf4..b7921f6 100644 --- a/spacecraft-standard-constitution/SKILL.md +++ b/spacecraft-standard-constitution/SKILL.md @@ -8,7 +8,7 @@ description: > Spacecraft Software-umbrella project — even if the user doesn't explicitly mention the Standard. If the user mentions "Spacecraft Software", a Spacecraft Software subproject name, or asks you to work on anything in the Spacecraft Software ecosystem, consult this skill immediately. It encodes - The Steelbore Standard v1.47 (§13 design systems; §3.1.1 TypeScript; §5.7 AGENTS.md; §6.4 contribution targets; §5.6 skill packaging; §11 palettes + §11.6 system theme; §18 accessibility; §17 progress reporting; §3.2 compiler flags; concurrency; §3.3 security-by-design) so + The Steelbore Standard v1.48 (§13 design systems; §3.1.1 TypeScript; §5.7 AGENTS.md; §6.4 contribution targets; §5.6 skill packaging; §11 palettes + §11.6 system theme; §18 accessibility; §17 progress reporting; §3.2 compiler flags; concurrency; §3.3 security-by-design) so you never need to ask for it or have it attached to a prompt again. license: GPL-3.0-or-later maintainer: Mohamed Hammad @@ -17,7 +17,7 @@ website: https://Construct.SpacecraftSoftware.org/ # The Steelbore Standard — Compliance Reference -**Version:** 1.47 | **Date:** 2026-08-09 | **Author:** Mohamed Hammad +**Version:** 1.48 | **Date:** 2026-08-16 | **Author:** Mohamed Hammad **Maintainer:** Mohamed Hammad | **Contact:** [Mohamed.Hammad@SpacecraftSoftware.org](mailto:Mohamed.Hammad@SpacecraftSoftware.org) **Copyright:** Copyright (C) 2026 Mohamed Hammad & Spacecraft Software | **License:** GPL-3.0-or-later **Website:** [https://Construct.SpacecraftSoftware.org/](https://Construct.SpacecraftSoftware.org/) @@ -1495,7 +1495,7 @@ M1: [████████████░░░░░░░░] 60% M2: [████████████░░░░░░░░] 60% M3: [████████████░░░░░░░░] 60% M4: [████████████░░░░░░░░] 60% -MVP: [ ▰▰▰▰▰▰▰▰▰▰▰▰▰▰▱▱▱▱▱▱ ] 70% +MVP: [██████████████░░░░░░] 70% TODO: [████████████░░░░░░░░] 60% PLAN: [████████████░░░░░░░░] 60% PRD: [████████████░░░░░░░░] 60% @@ -1509,22 +1509,13 @@ PRD: [████████████░░░░░░░░] 60% Every bar is a static, 20-cell, high-visibility Unicode bar. Legacy ASCII characters — `#`, `-`, `=` — are forbidden in any bar. -Two cell styles are in use, and the distinction is normative: +A single cell style applies to every row — milestones, `MVP`, `TODO`, `PLAN`, and `PRD` alike: filled cells are `█` (U+2588), empty cells are `░` (U+2591), and the brackets are tight, with no space inside either bracket. -| Rows | Filled | Empty | Brackets | -|------|--------|-------|----------| -| Milestones, `TODO`, `PLAN`, `PRD` | `█` (U+2588) | `░` (U+2591) | Tight — no space inside either bracket | -| `MVP` | `▰` (U+25B0) | `▱` (U+25B1) | Padded — exactly one space inside each bracket | +**Column alignment is normative.** With one style shared by every row, alignment follows from three rules: -The MVP row is deliberately set apart: it is the headline figure, and the tracks above and below it are the inputs that feed it. Its distinct glyph pair makes it findable at a glance in a stack of otherwise identical bars. - -**Column alignment is normative.** The MVP row's bracket padding exists to preserve it — the row is one character narrower in its label field and one character wider inside each bracket, so every bar cell and every percentage digit lands in the same column across the whole block. - -- On every row other than `MVP`, the label and its colon are left-aligned in a six-character field, followed immediately by `[`. -- On the `MVP` row, `MVP:` is left-aligned in a five-character field, followed by `[` and one space. -- Both place the first bar cell in column 8, so every bar occupies columns 8 through 27. -- The percentage is right-aligned so its `%` sign lands in the same column on every row — two spaces after the closing bracket on the tight-bracket rows, one on the `MVP` row. That difference is exactly what the padded brackets buy. -- The separator never drops below one space. At 100% the `MVP` row keeps its single space and its percentage therefore sits one column right — the only value at which the two row types do not align, and preferable to a bracket abutting a digit. +- On every row, the label and its colon are left-aligned in a six-character field, followed immediately by `[`. +- That places the first bar cell in column 8, so every bar occupies columns 8 through 27 and the closing bracket lands in column 28. +- The percentage is right-aligned in a five-character field immediately after the closing bracket, so its `%` sign lands in column 33 whether the value is one, two, or three digits. The separator never drops below one space — at exactly 100% the number consumes one of the two separator spaces — and the block stays aligned at every value. **Cell count.** The number of filled cells is the percentage scaled to twenty cells and rounded to the nearest cell. Two saturation rules override the rounding: a bar shows twenty filled cells **only** at exactly 100%, and zero filled cells **only** at exactly 0%. Rounding 99% up to a visually complete bar reports work as finished that is not, which is the drift this chapter exists to catch. @@ -1750,7 +1741,7 @@ Before finalising **any** Spacecraft Software artifact, mentally verify: - [ ] **§14** ISO 8601 dates; 24h time; UTC Z is the default primary timestamp (companion local time with UTC offset permitted, never a replacement) — unless the project filed the §14.2.1 domain exception for inherently local-time-bound data; ISO 8601 durations; metric units - [ ] **§15** Attribution present: maintainer name (`Mohamed Hammad`), contact (`Mohamed.Hammad@SpacecraftSoftware.org`), and project URL in `--version` / README / About - [ ] **§15.3** Third-party work credited in `CREDITS.md` at project/skill root when triggers apply; deeper `references/ATTRIBUTION.md` present where reference content is adapted from external sources -- [ ] **§17** Development progress tracked and reported continuously as the §17.1 labelled-row block — one 20-cell bar per track, milestone rows then MVP then TODO/PLAN/PRD, only the rows that apply; MVP set in `▰`/`▱` with padded brackets and every other row in `█`/`░`, columns aligned, no ASCII bars +- [ ] **§17** Development progress tracked and reported continuously as the §17.1 labelled-row block — one 20-cell bar per track, milestone rows then MVP then TODO/PLAN/PRD, only the rows that apply; every row set in `█`/`░` with tight brackets, columns aligned, no ASCII bars - [ ] **§18** Accessible mode implemented and off by default; §18.1 toggle honored with correct precedence; status never color-only; no animation or decorative art in accessible mode; TUI ships a linear mode and a non-interactive CLI path; GUI publishes accessible names and roles (AccessKit for Rust); verified with a real screen reader; existing projects carry a dated remediation entry in `PROJECTS.md` until they conform — N/A for projects registered as games (§18.5), which are exempt in full - [ ] **§6.3** All commits to Spacecraft Software Git remotes cryptographically signed with the `Mohamed.Hammad@SpacecraftSoftware.org` key and showing "Verified" on the hosting platform; rewrites preserve signatures; programmatic and assistant-driven commits signed too - [ ] **§6.4** No commit, pull request, patch, issue, or package publication sent to a namespace outside `Spacecraft-Software` / `UnbreakableMJ` without explicit per-contribution maintainer authorization; automation, CI, and assistant-driven work never initiate an outbound contribution diff --git a/spacecraft-standard-constitution/references/CHANGELOG.md b/spacecraft-standard-constitution/references/CHANGELOG.md index 2cc7ebc..6baa071 100644 --- a/spacecraft-standard-constitution/references/CHANGELOG.md +++ b/spacecraft-standard-constitution/references/CHANGELOG.md @@ -12,6 +12,7 @@ activation. The canonical record is the published Standard's own `standard/CHANGELOG.md` (extracted from §1 of the document itself in v1.37); this file mirrors it and must be synced to the same version and date. +- **v1.48 (2026-08-16):** **§17.2 simplified — the MVP row joins the single cell style.** v1.47 set the `MVP` row apart in `▰` (U+25B0) / `▱` (U+25B1) with one space inside each bracket, on the argument that the headline figure should be findable at a glance in a stack of otherwise identical bars. In practice the distinction bought less than it cost: the padded row needed its own label-field width (five characters where every other row uses six), its own bracket geometry, its own percentage-separator rule (one space where the others use two), and a documented edge case in which the two row types stop aligning at exactly 100% — four special cases carried by every emitter and checker of the format, to distinguish a row that its fixed position (always immediately after the last milestone) and its label already distinguish. **§17.2 now defines one cell style for every row** — milestones, `MVP`, `TODO`, `PLAN`, and `PRD` alike: `█` (U+2588) filled, `░` (U+2591) empty, tight brackets with no space inside either. The `▰`/`▱` pair, the whole of §17.2 from v1.32 until v1.47 narrowed it to the MVP row alone, is now retired entirely. The alignment rules collapse from five bullets to three, all universal: label and colon left-aligned in a six-character field followed by `[`; first bar cell in column 8, bars occupying columns 8–27, `]` in column 28; percentage right-aligned in a five-character field so `%` lands in column 33 whether the value is one, two, or three digits. The v1.47 misalignment-at-100% carve-out disappears rather than being restated — with tight brackets and a two-space separator, a 100% value consumes one separator space and the block stays aligned at every value. Unchanged: §17.1's row set, fixed order, and only-applicable-rows rule; the cell-count rounding and its two saturation rules; the prohibition on ASCII bars. §16's §17 bullet drops the two-style clause. `spacecraft-accessibility-support`'s `references/audit.md` reporting example is updated to the single style in the same pass. This skill's own frontmatter `description` measures 988 characters under the §5.6 cap, unchanged — only the version number moved. - **v1.47 (2026-08-09):** **§17.1 and §17.2 rewritten — progress reports become a labelled-row block.** The format §17.1 has carried since the section was written packed every figure into three dense lines: a single unlabelled bar, then all milestones pipe-separated on one line, then MVP and PRD sharing a third. Only one of those numbers — the PRD total — ever got a bar, so the milestones and the MVP were reported as bare percentages while the least granular figure got the only visual. Reading it meant parsing a run-on line to find the milestone you cared about, and comparing two milestones meant comparing two integers rather than two bars. The replacement gives **every track its own row, its own 20-cell bar, and its own percentage**, in a fixed order: milestone rows `M0`…`Mn` ascending, then `MVP`, then `TODO`, then `PLAN`, then `PRD`. **`TODO` and `PLAN` are new tracks** — the old format had no way to report against a plan document or a task list at all, so work driven by either was reported against a PRD that did not exist. **Only applicable rows are emitted**, and this is a rule rather than a convenience: the milestone rows match the milestones the plan actually defines (`M0`–`M4` in the template is an illustration, not a required set), `TODO`/`PLAN`/`PRD` appear only when the task is driven by such an artifact, and `MVP` is always present. Padding the block out with fabricated 0% rows is forbidden — a track that does not exist reports progress against nothing, and a reader cannot tell a genuine zero from a placeholder. **§17.2 now defines two cell styles, and the distinction is normative.** Milestone, `TODO`, `PLAN` and `PRD` rows use `█` (U+2588) filled and `░` (U+2591) empty with tight brackets; the `MVP` row uses `▰` (U+25B0) and `▱` (U+25B1) with one space inside each bracket. MVP is the headline figure and the rows around it are the inputs that feed it, so it is set in a different glyph pair to stay findable at a glance in a stack of otherwise identical bars — the `▰`/`▱` pair that was the whole of §17.2 before this version is retained for exactly that one row rather than retired. **Column alignment is normative, and the bracket padding is what preserves it**: the MVP row is one character narrower in its label field and one character wider inside each bracket, so every bar cell and every percentage digit lands in the same column across the whole block. Stated as rules — label-plus-colon left-aligned in a six-character field on every row but MVP, five on MVP followed by `[` and a space; every bar in columns 8 through 27 on both; percentage right-aligned so its `%` lands in the same column on every row, which means two spaces after the closing bracket on the tight rows and one on `MVP`, with the separator never dropping below one space (so at 100% the `MVP` percentage sits one column right — the only value at which the two row types do not align, and preferable to a bracket abutting a digit). **Cell count is specified for the first time.** The old text said "20-character" and left the mapping from percentage to cells entirely unstated, so 43% could legitimately render as 8 cells or 9. It is now the percentage scaled to twenty cells and rounded to the nearest cell, with two saturation rules overriding the rounding: twenty filled cells **only** at exactly 100%, zero filled **only** at exactly 0%. Rounding 99% up to a visually complete bar reports work as finished that is not — precisely the drift §17 exists to catch. Unchanged: **§17.3's cadence** (baseline at task start, at each milestone completion, and in the end-of-turn summary), and the prohibition on legacy ASCII bars, now stated for `#`, `-` and `=` and binding on every row rather than on "the progress bar" singular. §16's §17 checklist bullet is rewritten from the old three-figure summary to the row-block form. `spacecraft-accessibility-support`'s `references/audit.md` reporting example is updated to the new block in the same pass. This skill's own frontmatter `description` measures 988 characters under the §5.6 cap, unchanged — only the version number moved. - **v1.46 (2026-08-08):** **§5.7 added — Agent Context Files.** §5.2 has enumerated the required root files since the standard's early versions and never named the one file every coding agent actually reads. That silence was not neutral: in its absence each project invented its own arrangement, and a survey of the umbrella found five incompatible conventions running simultaneously across ~39 repositories — byte-identical twins, a symlink, a declared superset, a thin pointer in one direction, and genuinely divergent files each holding facts the other lacked. The failure mode is specific and silent. `AGENTS.md` is the cross-vendor convention (Codex CLI, Cursor, Aider, OpenCode, Goose); Claude Code reads `CLAUDE.md`. When both exist as parallel prose they are edited in different sessions and drift, and **the agent reading the stale copy is never told it is stale** — it proceeds confidently on a build command that changed six weeks ago. Several files had already noticed and responded with the wrong remedy, carrying explicit "whenever you update CLAUDE.md, update AGENTS.md in the same pass" instructions: a maintenance tax paid manually, forever, that the drift proves was not being paid. §5.7 makes **`AGENTS.md` the single authority** — required at every project root alongside the §5.2 files, harness-neutral, carrying build/test/lint commands, architectural invariants, forbidden patterns, layout, and every fact an agent cannot infer from the code. `CLAUDE.md`, where a project ships one, becomes an **`@AGENTS.md` import plus only what is meaningless to a non-Claude harness** — Skill-tool invocations, `.claude/` paths, slash commands, Claude-client MCP configuration — and MUST NOT restate, summarize, or mirror it. Five rules attach. **Write to `AGENTS.md`**: new project knowledge goes there by default, and "update the context file" always means `AGENTS.md`; this is the rule that keeps the overlay from re-growing into a second copy one session at a time. **No duplication**, with the corollary that a "keep these in sync" instruction is evidence the split is wrong and MUST be removed rather than honored. **Both tracked** — a `.gitignore` entry for either breaks the `@AGENTS.md` import on a fresh clone and hides project knowledge from every contributor who did not author it; 15 of the surveyed repositories were ignoring one or both. **No secrets**, which is the clause that makes the tracking rule safe rather than merely tidy: context files become published artifacts, so credentials, tokens, keys, private hostnames or network topology, and personal filesystem paths are out, and a file that was previously ignored MUST be reviewed for sensitive content *before* it is un-ignored — a file that was safe as a local scratchpad has not thereby been cleared for publication, and un-ignoring is effectively irreversible once pushed. **Generated blocks target `AGENTS.md` only**: tooling that renders managed regions into context files — rule synchronizers, task systems — reintroduces exactly the duplication the import removes if it writes both, so the obligation is placed on the tooling rather than left for a human to notice. Other harness files (`GEMINI.md`, `.cursorrules`) follow the `CLAUDE.md` pattern rather than earning clauses of their own. This section **inverts the guidance previously carried only in the `spacecraft-agentic-cli` skill**, which instructed authors to make `CLAUDE.md` a strict superset of `AGENTS.md` and to start by symlinking or copying it — a rule that produced the duplication by construction and that every new scaffold reproduced; that skill's `references/agents-md-authoring.md` §1 and §3 and both `assets/` templates are rewritten to match in the same pass. The Skill Cross-References table gains a `spacecraft-agentic-cli` row for context-file authoring, which had never appeared there despite the skill being the implementation layer for it. §16 gains a §5.7 checklist bullet. Nothing in §5.2 changes: `AGENTS.md` is added to the required set, and no existing required file is relaxed or removed. This skill's own frontmatter `description` measures 988 characters under the §5.6 cap (the §3.1.1 highlight shortened to "§3.1.1 TypeScript" to make room for §5.7). - **v1.45 (2026-08-06):** **§11.6 added — System Theme Declaration & Resolution.** §11 has been a palette *family* since v1.35 and §11.1 has required every palette reference to go through a named theme since v1.34, yet nothing said what an application does when the *machine* has an opinion. The gap was invisible from both ends: §11.1 answers "how do I reference a color", §11.4 answers "which palette is mine", and neither question is "which member of the family renders on this system, right now" — so an application could satisfy every clause in §11 while shipping one hard-wired theme, deaf to the desktop it runs on. Steelbore OS has had a theme declaration for months (Bravais's `theme.nix` is a single word that re-themes every terminal, both bars, the TTY and greetd), which made the omission look like it did not exist; it ends at a rebuild, because that machinery resolves at build time and exports per-role hex but never the slug, so a *running* application can see individual colors and still not learn which theme is active. **Applications register the family, not a theme.** §11.6.1 separates two obligations §11.4 had conflated: a project *authors* against one palette and *registers* thirteen — the six conforming palettes (`steelbore`, `steelbore-blue`, `steelbore-blackpinkpanther`, `steelbore-matrixgreen`, `steelbore-navywhite`, `tokyonight`), each with its `-high-contrast` sibling, plus `steelbore-mono`. Three were already required by §11.4 and §11.1.1, so this adds ten, all already written out in `steelbore.toml`; every one binds the same eleven role tokens, so a theme layer that reads that file registers them in a loop. `steelbore-classic` is deliberately **not** in the mandatory set: it keeps the legacy six-role contract (§11.2), defines no surface class, and carries an `info` token that is not one of §11.1's eleven roles at all. **Resolution is two-stage, and that is the load-bearing decision.** Stage 1 picks a base palette from five sources — in-app selection, `SPACECRAFT_THEME`, the system declaration, the platform's light/dark preference, then the project's §11.4 default. Stage 2 picks a *variant of that palette* — a pinned `-high-contrast`/`-mono` slug, then `NO_COLOR` ⇒ `steelbore-mono`, then §18.1 accessible mode, then the platform's high-contrast preference under §18.3's existing precedent. Keeping the stages apart is what makes the section composable: an accessibility signal chooses a *sibling*, never a palette, so it can never silently change the brand — exactly the promise §11.1.1 has made since v1.33. §18.1's four-source precedence is consumed, not restated and not modified. An unknown or unregistered slug **falls through and is never fatal**, so a typo in `/etc` cannot leave a machine without a working interface (§3.1), and the resolved theme plus the deciding source are reported under `--verbose`. **Light and dark needed §11.4 read precisely.** `steelbore-navywhite` is the family's only light-canvas member, so a platform light preference can only be answered by rendering a different palette. §11.6.2 states that §11.4 forbids *combining* tokens from two palettes and that a switch combines nothing: the entire token set is replaced at once, the new canvas comes with it unaltered, and no frame ever carries a token from two palettes. **Switching is compliant; mixing remains forbidden** — the switch must be atomic and whole-surface (an application that cannot re-theme atomically resolves once at startup and holds), and the canvas travels with the palette. The family pair is `steelbore` ⇄ `steelbore-navywhite`; a project may declare its own or declare `light = none` with a stated reason on the §14.2.1 footing, which buys it nothing under §18. Solarized Dark and Light are a natural pair upstream and §11.5 bars both from adoption, so neither is ever a source-4 target. **The declaration is a file, deliberately** — `/etc/steelbore/theme.toml`, overridden per user by `$XDG_CONFIG_HOME/steelbore/theme.toml`, carrying `active` (required), an optional `light`/`dark` pair, `follow-color-scheme`, and `high-contrast`. A file, not a bus: the contract has to work for a CLI in a text console, where there is no session bus, no portal, and no portable way to ask the terminal what color its background is — which is why the platform color-scheme source is graphical-only. Absence of the file is *no declaration*; a file saying `active = "steelbore"` is a declaration *of Modern*, and the distinction matters because a system may need to pin Modern rather than inherit whatever the default later becomes. **The declaration carries slugs and never colors** — the same division §13 draws for component systems; an OS-installed registry is advisory and the application's own `steelbore.toml` governs, so per-role color environment variables are explicitly *not* a Standard interface. The variable is **`SPACECRAFT_THEME`**, in the `SPACECRAFT_` namespace §18.1 established with `SPACECRAFT_A11Y`; `STEELBORE_THEME` is named as **not** a Standard interface, because it is already a boolean shell flag and giving it slug semantics would make `STEELBORE_THEME=true` resolve to a nonexistent theme and fall through in silence. **§11.6.5** puts the symmetrical obligation on Steelbore OS in every flavor: render the declaration from its own selection rather than maintain it by hand, export the slug so it reaches graphical sessions and system services rather than login shells alone, keep the platform color-scheme preference in agreement with the declared polarity, and validate the slug at evaluation time so an unknown theme fails the build rather than the boot. **Scope is both §6.4 namespaces** and all three interface classes: a CLI is not exempt, because it already honors `NO_COLOR` and already emits ANSI. Artifacts with no user-facing output record §11.6 as N/A. Registered games are **not** exempt — §18.5 carves out §18 and §10, never §11 — but a game satisfies it in its menus, HUD and settings chrome, not in the world it simulates. Three things are unchanged: **`steelbore` is still the sole default** (§11.6 changes what an application *can* render, never what it renders when nothing is declared); **§11.4's mixing prohibition is unchanged** and is now precise enough to be enforceable; and **§18 is unchanged** — a declaration's `high-contrast` key selects a theme sibling and is explicitly barred from being read as enabling accessible mode. §11.4 gains two bullets and three amended ones; §16 gains a §11.6 bullet rather than lengthening the §11 one; the Skill Cross-References table gains a `steelbore-color-palette` row, closing a smaller gap — the skill has been the normatively cited canonical source in §11.4 since v1.39 and had never appeared in the table that tells a reader which skill to load. Recorded as a factual correction in the same entry: the §11 chapter-head palette-family table listed six slugs where `[meta] palette-family` and §11.4.1 both list seven — **`tokyonight` was missing** from the one table a reader consults first. It is added, and the table gains a canvas-polarity column, which §11.6.2 makes normative content. `assets/steelbore.toml` → v3.2.0: `[meta]` gains `default-dark-theme`, `default-light-theme`, `mono-theme`, and `registered-set` (the §11.6.1 thirteen), plus new `[resolution]`, `[resolution.polarity]`, and `[resolution.pair]` tables — slugs only, no color value, with every polarity value verified against the WCAG relative luminance of its own canvas. `spacecraft-theme-factory` now emits the registered set rather than one palette and its variants; `spacecraft-accessibility-support` gains the §11.6.3 stage-2 composition rules. This skill's own frontmatter `description` measures 980 characters under the §5.6 cap (the §11.5 fidelity highlight rotated out to make room for §11.6).