Ship your finish
A finish is finished when it works in every palette, in both canvases, and — the part no script can check — in the exported PDF. This page is that list.
What you touch
Section titled “What you touch”lib/core/resolve-finish.js ← one row in FINISH_REGISTERlib/base/base.finish.css ← the preset blockdocs/src/components/studio/finish-catalog.ts ← the Studio's picker entrydocs/src/components/studio/finish-library.ts ← the reserved-name listdesign/skills/finish.md ← the count of shipped finishesexamples/quarry.md + quarry.pdf ← the demo deckSix files. Only the second one is real work — the other four are a line each, and every one of them has a gate that fails until you write it.
The checklist
Section titled “The checklist”The preset
- One row added to
FINISH_REGISTER. - All four slot families declared. Unused background slots are
none; unused--fin-frameis0 0 transparent—noneis invalid in a shadow list and silently kills the tone rail. - Every full-bleed layer has a
-opaquetwin ending onvar(--fin-canvas). - The two faces have the same layer count.
-
--fin-size,--fin-positionand--fin-repeateach carry one entry per layer, in the same order the layers are listed: texture first, then wash. - Accent alpha stays in the 5–16% range wherever a layer covers the whole page. A narrow band — an edge strip, a mark bar — may go higher.
- Both mark slots declared:
--fin-mark: noneand--fin-mark-text: "". - A full frame uses
--fin-frame, not the section’s::after.
Palette-blind
- Every color is a
color-mix()ofvar(--accent),var(--fin-canvas)orvar(--text-heading). - No hex literals, no
url(), nomask-image, nomargin.
Around it
-
finish-catalog.tsentry added, all seven fields (natureandzoneare easy to miss and TypeScript will stop you). - The name added to
RESERVED_FINISH_NAMESinfinish-library.ts, so a saved user finish cannot shadow your preset. - The shipped-finish count in
design/skills/finish.mdbumped — the ownership guard checks it against the register. -
examples/quarry.mdwritten, six to ten slides, PDF committed. - A changelog fragment in
changelog.d/. -
npm run build:checkgreen. -
npm testgreen.
The sign-off no script can do
- Exported through both engines — the command-line PDF and the in-browser export — in both canvases, all four files opened and looked at.
That last one is a hard requirement. A finish changes the bytes of every exported file, and its failure mode — a gray cloud across a full-bleed fade, a title slide washed to near-blank — appears only in the export. Nothing on screen predicts it.
Six ways a finish goes wrong
Section titled “Six ways a finish goes wrong”- A fade ending on
transparentin the opaque face. A gray cloud in every PDF. - Accent alpha too high across the full page. The backdrop competes with the words.
--fin-frame: none. Invalid inside a shadow list, so the declaration dies and takes the tone rail with it. Use0 0 transparent.url(),mask-image, a hex, or amarginanywhere in the preset.- A monogram baked into a deck-wide finish.
- Mismatched layer counts between the two faces, which quietly corrupts the shared size and position lists.
Where to go next
Section titled “Where to go next”- Pick the colors it will wear: Theme anatomy.
- Arrange what sits on top of it: Component anatomy.
- Build one from dropdowns and sliders instead: the Studio has a finish workbench that writes this CSS for you.