/* ============================================================
   Route B9 — Pushed refinement
   Home = one composition stage; scroll and the arrow keys both
   drive interpolated travel between five state compositions.
   Elements TRAVEL — nothing repopulates. Subpages use a
   smoothed, lag-based plane engine (no budging).
   Dark tones = placeholder image-field values (neutral, not brown).
   ============================================================ */

/* The two faces, chosen 15 Oct 2026 and served with the site: Geist (Voice) and Geist Mono (System),
   variable, one file each, under the SIL Open Font License (assets/fonts/geist-ofl.txt). Preloaded in
   index.html; block, so the page never shows in a stand-in face first.
   Voice offers no medium: the pages were designed and approved in Arial, which has none, so a 500
   request falls to 400 as it always has (the two ranges leave 500 out; 600 and 700 stay). */
@font-face{font-family:"Geist";src:url("/assets/fonts/geist-variable.woff2") format("woff2");font-weight:100 400;font-style:normal;font-display:block;}
@font-face{font-family:"Geist";src:url("/assets/fonts/geist-variable.woff2") format("woff2");font-weight:600 900;font-style:normal;font-display:block;}
@font-face{font-family:"Geist Mono";src:url("/assets/fonts/geist-mono-variable.woff2") format("woff2");font-weight:100 900;font-style:normal;font-display:block;}
:root{
  /* RECORD — default mode: the instrument live */
  --ground:#131312;
  --ink:#ebe9e3;
  --mut:#94918a;
  --dim:#5f5c55;
  --accent:#d8472b;
  --line:#2c2b28;
  --line-strong:#3a3934;
  --hover:#ffffff;
  --mat:#1f1f1d;
  --mat-2:#272725;
  --paper:#f0ece1;
  --paper-ink:#221f18;
  --ground-2:#1b1b19;
  /* legacy aliases — existing rules keep working */
  --ph-1:var(--ground-2);
  --ph-2:var(--mat);
  --ph-3:var(--mat-2);
  --panel:var(--mat);
  --voice:"Geist", "Helvetica Neue", Helvetica, Arial, sans-serif;
  --system:"Geist Mono", "SF Mono", ui-monospace, "Cascadia Mono", Menlo, monospace;
  --s-giant:clamp(48px,7.4vw,122px);
  --s-display:clamp(28px,3vw,44px);
  --s-prose:clamp(17px,1.4vw,21px);
  --s-index:clamp(20px,2vw,30px);
  --s-meta:12px;
  --s-ui:10px;
  --top-h:56px;
  --bot-h:44px;
  --mx:6vw;
  /* text-column offset, floored clear of the rail: rail ink is fixed-size (10px) while
     the columns are vw, so below ~1890px 6vw no longer clears it. Keyed to the widest
     rail value in use — shorten that and this number can come down. */
  --colx:max(var(--mx), calc(var(--mx)*0.4 + 68px));
  /* system pages: 12 columns between --colx and --mx. The % resolves against the page width
     wherever these are used, so a positioned element can sit on a column line:
     left: calc(var(--colx) + 6 * (var(--sys-col) + var(--sys-gap)))  → the start of column 7 */
  --sys-gap:2vw;
  --sys-w:calc(100% - var(--colx) - var(--mx));
  --sys-col:calc((var(--sys-w) - 11 * var(--sys-gap)) / 12);
  /* one spacing scale for system sections: between sections · hairline to content · label to figure */
  --sys-section:14vh;
  --sys-rule:3.2vh;
  --sys-label:10px;
  --ease:cubic-bezier(.2,.7,.2,1);
}

*{margin:0;padding:0;box-sizing:border-box;}
html{scroll-behavior:auto;scrollbar-gutter:stable;}   /* views that scroll and views that don't keep one width — the frame never slides */
body{background:var(--ground);color:var(--ink);font-family:var(--voice);font-size:var(--s-prose);line-height:1.5;-webkit-font-smoothing:antialiased;}
a{color:inherit;text-decoration:none;}
ul{list-style:none;}
button{font:inherit;color:inherit;background:none;border:0;cursor:pointer;}

/* ============ FRAME ============ */
.frame-top{position:fixed;inset:0 0 auto 0;height:var(--top-h);z-index:50;display:flex;align-items:center;justify-content:flex-end;padding:0 var(--mx);}   /* the name lives in the arrival line and the domain; the frame carries the nav alone */
/* on a page the frame is a band of the ground, so text and figures pass under the nav, not through it; the home field stays open */
body:not(:has(.view[data-view="home"].active)) .frame-top{background:var(--ground);}
/* System face, meta size, dim until hovered or active */
.registers{display:flex;gap:1.7em;font-family:var(--system);font-size:var(--s-meta);letter-spacing:.03em;}
.registers a{color:var(--mut);position:relative;transition:color .15s var(--ease);}
.registers a:hover,.registers a.active{color:var(--ink);}
.registers{position:relative;}
.reg-line{position:absolute;left:0;bottom:-7px;height:1px;width:0;background:var(--accent);pointer-events:none;
  transition:transform .55s var(--ease),width .55s var(--ease);}
[data-mode="bone"] .reg-line{background:var(--ink);}
/* the marker is a hairline under the active word, exactly its width; it glides to the next word as the
   page or field state changes (placeRegLine in script.js) and takes no width, so the links never shift */
.rail{position:fixed;top:calc(var(--top-h) + 22px);left:0;z-index:40;display:flex;flex-direction:column;gap:.55em;padding-left:calc(var(--mx)*0.4);font-family:var(--system);font-size:var(--s-ui);color:var(--mut);letter-spacing:.03em;}
.rail-line{transition:opacity .15s var(--ease);font-variant-numeric:tabular-nums;}
.rail-line.swap{opacity:0;}

/* ============ CURSOR PREVIEW ============ */
.preview{position:fixed;z-index:45;width:320px;pointer-events:none;opacity:0;transition:opacity .18s var(--ease);}
.preview.on{opacity:1;}
/* loupe must not float over an open panorama */
body:has(.ph.pano-open) .preview{opacity:0!important;visibility:hidden;}
.preview .ph{border:1px solid var(--line);background:var(--ph-2);}
.preview .ph.pdoc{background:#fff;border-color:var(--line-strong);}   /* a document's first page: paper, held whole */
.preview .meta{margin-top:6px;color:var(--dim);font-size:var(--s-ui);font-variant-numeric:tabular-nums;}

/* ============ HOME — THE COMPOSITION STAGE ============ */
#field{padding:0 0 calc(var(--bot-h) + 4vh);}
.view{display:none;}
.view.active{display:block;animation:viewin .4s var(--ease);}
@keyframes viewin{from{opacity:0;}to{opacity:1;}}

.stagewrap{height:620vh;position:relative;}         /* five compositions + the 4→5 loop tail */
.stage{position:sticky;top:0;height:100vh;overflow:hidden;}

/* stage planes — positioned every frame by the field engine.
   No CSS position transitions: the engine interpolates, so
   motion is continuous, eased and never start-stop. */
.splane{position:absolute;left:0;top:0;will-change:transform,opacity;opacity:0;}
.splane[data-depth="bg"]{z-index:1;}
.splane[data-depth="mid"]{z-index:2;}
.splane[data-depth="fg"]{z-index:3;}
.splane[data-depth="text"]{z-index:5;}
.splane[data-depth="ui"]{z-index:6;}
.splane .elcap{margin-top:8px;white-space:nowrap;}   /* the field's labels are short (0N / name): one line, whatever the face */
.splane.card .ph,.splane.card .vid{border:1px solid var(--line);background:var(--panel);}

/* ============ ZONES (subpages) ============ */
.zone{position:relative;width:100%;}
.el{position:absolute;will-change:transform;}
.el .elcap{margin-top:8px;}
.el.bg{z-index:1;}
.el.mid{z-index:2;}
.el.fg{z-index:3;}
.card .ph,.card .vid{border:1px solid var(--line);background:var(--panel);}

.zone .el{opacity:0;transform:translateY(30px);}
.zone.zlive .el{opacity:1;transform:translateY(0);transition:opacity .55s var(--ease),transform .6s var(--ease);}

.z-studyhead{height:90vh;padding-top:var(--top-h);}
.z-seq{height:300vh;}
.z-grid{height:160vh;}
.z-loop{height:80vh;}
.z-statement{height:100vh;}
.z-notes{min-height:120vh;padding:4vh 0 12vh;}
.z-nea-head{height:72vh;}   /* Neandertal: title, intro and film fit one screen */
.z-seq.z-nea-seq{height:262vh;}   /* four frames, not Study 02's five */
/* Study 03 — frameless specimens: the renders share the page ground, so no plate behind them */
.ph.bare{background:transparent;}
.ph.p58{aspect-ratio:5/8;}
.ph.p-lib{aspect-ratio:3200/2952;}
.z-tw-head{height:70vh;}   /* the head ends with Pl. I, not a full screen */
.z-tw-fig1{height:96vh;}
.z-tw-pl2{height:calc(8vh + 60vw * 0.38 * 2 + 14vh);}
.tw-cells{display:grid;grid-template-columns:repeat(4,1fr);column-gap:2vw;row-gap:3vw;margin-top:4vh;}
.z-tw-turns{height:calc(42.5vw + 18vh);}
.z-tw-surface{height:calc(40.5vw + 34vh);}
.z-tw-pl3{height:calc(48vw + 16vh);}
.z-tw-end{height:138vh;}
.scrub-stage img,.scrub-stage video{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;}
.scrub-stage video{opacity:0;transition:opacity .3s var(--ease);}
/* decoded video lands a level or two off --ground (browsers round the YUV conversion
   differently), so the frame edge is feathered away rather than matched. The specimen
   stays at least 5% inside the frame, so the feather never reaches the type. */
.scrub-stage video{
  -webkit-mask-image:linear-gradient(to right, transparent, #000 4%, #000 96%, transparent), linear-gradient(to bottom, transparent, #000 4%, #000 96%, transparent);
  -webkit-mask-composite:source-in;
  mask-image:linear-gradient(to right, transparent, #000 4%, #000 96%, transparent), linear-gradient(to bottom, transparent, #000 4%, #000 96%, transparent);
  mask-composite:intersect;
}
.scrub-ready .scrub-stage video{opacity:1;}
.scrub-stage img{transition:opacity .3s var(--ease);}
.scrub-ready .scrub-stage img{opacity:0;}   /* the poster has a hard edge; once the feathered film is up, it goes */
.scrub-zone{touch-action:pan-y;}
.scrub-zone .scrub{cursor:ew-resize;}
/* the turned seahorse sits above the land shell; lighten drops its ground, so only the specimen overlaps the shell, never its frame */
.z-tw-end .scrub{z-index:4;mix-blend-mode:lighten;}
.tw-film .ph{background:transparent;}
.tw-film .vid{overflow:hidden;
  /* same reason as the scrub: Vimeo's decoded ground isn't exactly --ground, so feather the edge */
  -webkit-mask-image:linear-gradient(to right, transparent, #000 3%, #000 97%, transparent), linear-gradient(to bottom, transparent, #000 3%, #000 97%, transparent);
  -webkit-mask-composite:source-in;
  mask-image:linear-gradient(to right, transparent, #000 3%, #000 97%, transparent), linear-gradient(to bottom, transparent, #000 3%, #000 97%, transparent);
  mask-composite:intersect;
}
.tw-film .vid iframe{inset:auto;top:50%;left:50%;width:222%;height:100%;transform:translate(-50%,-50%);pointer-events:none;}
/* square crop (56% of the film's width) for specimens that spread wider as they turn —
   measured: meandrina 26–74%, crab claw 27–73%; a 4:5 crop (45%) would clip them */
.ph.p11{aspect-ratio:1/1;}
.ph.p11 .vid{position:absolute;inset:0;width:100%;height:100%;aspect-ratio:auto;background:transparent;}
.tw-film .ph.p11 .vid iframe{width:177.78%;}
.tw-app .ph.p169 .vid iframe,
.with-controls .ph.p169 .vid iframe{pointer-events:auto;}   /* films shown as players keep their controls */
/* every .el is its own layer (will-change) and paints in page order, so a later figure drifting
   up on parallax would cover earlier text; text always sits above the figures here */
.view[data-view="study-03"] .el:has(> .prose),
.view[data-view="study-02"] .el:has(> .prose){z-index:3;}
@media (max-width:900px){
  .tw-cells{grid-template-columns:repeat(2,1fr);}
  /* phones keep the desktop's contrast of scale: heroes wide, the rest at set
     fractions, alternating sides */
  .view[data-view="study-03"] .el.m-l{width:86% !important;}
  .view[data-view="study-03"] .el.m-m{width:70% !important;}
  .view[data-view="study-03"] .el.m-s{width:50% !important;}
  .view[data-view="study-03"] .el.m-xs{width:38% !important;}
  .view[data-view="study-03"] .el.m-r{margin-left:auto;}
}
.z-next{padding:4vh 0 16vh;}
.biglink.xl{transition:letter-spacing .3s var(--ease),color .2s var(--ease);}
.biglink.xl:hover{letter-spacing:.015em;color:var(--hover);}
/* studio — the contact page (layout E "ruler", chosen 15 Oct 2026 over field, stagger, aside and
   statement): the writing alone, at the site's prose size and measure, from column 4; the opening
   in ink and the rest in --mut. (A ruler beside the text — a hairline with ticks and numbers, then
   the hairline alone — was tried and taken off 15 Oct 2026.) The page's name is outlined behind the text, low on the left and
   off the edge; it travels at about half the text's speed and leans from the pointer (script:
   "contact"). --c is one column and its gutter, measured on the page's own width (a container unit:
   --sys-col's % would resolve against whichever box uses it, a paragraph included). */
.st{container-type:inline-size;--c:calc((100cqw - 11 * var(--sys-gap)) / 12 + var(--sys-gap));position:relative;padding:14vh var(--mx) 50vh var(--colx);overflow-x:clip;}   /* the room after the email lets the last paragraphs reach the ruler's reading line, so their marks spread */
.st-back{position:absolute;inset:0 0 auto 0;height:0;z-index:0;}
.st-wm{position:absolute;top:58vh;left:-6vw;margin:0;opacity:.9;pointer-events:none;will-change:translate;}   /* where and as the field draws its contact state's name */
.st-text{position:relative;z-index:1;margin-left:calc(3 * var(--c));}
.st-text p{max-width:46ch;line-height:1.55;margin:0 0 1.3em;}
.st-text p:not(:first-child):not(.st-mail){color:var(--mut);}   /* the opening in ink, the running text in --mut, as on the system pages */
.st-text .st-mail{margin-top:12vh;}
.st-cut :is(.el,.reveal,.ch){transition:none !important;}   /* handed over from the field: already in place, nothing moves */
.st-field{container-type:inline-size;--c:calc((100cqw - 11 * var(--sys-gap)) / 12 + var(--sys-gap));}   /* the field's contact state: the page's content box, so the same grid */
.st-text > .el{position:relative;}   /* the page is a zone: its first paragraphs rise into place in turn, but stay in the text's flow */
@media (max-width:900px){
  .st.zone{padding:calc(var(--top-h) + 26px + 4vh) var(--mx) 10vh !important;}   /* the system pages' phone frame, over the zone's */
  .st .el{width:auto !important;margin-bottom:1.3em;}   /* phones set every .el full width with a 6vh gap; here the text keeps its spacing */
  .st .st-back.el{margin:0;}
  .st-wm{top:52vh;}
  .st-text{margin-left:0;}
}

/* ============ TYPE ============ */
.giant{font-size:var(--s-giant);font-weight:500;line-height:1.02;letter-spacing:-.02em;}
.display{font-size:var(--s-display);font-weight:500;letter-spacing:-.015em;line-height:1.1;margin-bottom:.3em;}
.prose{max-width:46ch;}
.prose p{margin-bottom:1.3em;line-height:1.55;}
.nobr{white-space:nowrap;}   /* a value or range that must not break across lines */
.meta,.kicker{font-family:var(--system);font-size:var(--s-meta);color:var(--mut);letter-spacing:.03em;font-variant-numeric:tabular-nums;}
.meta.dim,.dim{color:var(--dim);}
.kicker{display:block;margin-bottom:1.6em;}
/* arrival positioning statement — Voice, ink, between prose and display; three lines under the hero */
.positioning{font-size:clamp(20px,1.6vw,28px);font-weight:500;line-height:1.35;letter-spacing:-.01em;color:var(--ink);max-width:60ch;text-wrap:pretty;}
.textlink{border-bottom:1px solid var(--line);}
.textlink:hover{border-color:var(--accent);}
.biglink{font-size:var(--s-index);border-bottom:1px solid var(--line);}
.biglink.xl{font-size:var(--s-display);font-weight:500;}

/* figure labels — one system across the studies, like a paper: [fig. n] for an image or film,
   [pl. n] (parts a, b, c) for a group, [doc. n] for a document. The number always shows; the
   short name sits beside it on the same line and shuffles in on hover/focus (space reserved,
   nothing wraps, nothing reflows). */
.procnote{line-height:1.6;white-space:nowrap;}
.procnote .pn-no{color:var(--dim);letter-spacing:.08em;margin-right:.9em;}
.procnote .pn-deg{color:var(--dim);margin-left:.9em;font-variant-numeric:tabular-nums;}
.procnote .pn-cap{opacity:0;transition:opacity .25s var(--ease);}
:is(figure,article,.el):is(:hover,:focus-visible,:focus-within) .procnote .pn-cap{opacity:1;}

/* zone note — short bridging prose introducing what a zone argues */
.zone-note{margin:1.2em 0 2.4em;}
.zone-note p{color:var(--mut);}

/* zone head — declared section boundary (Process): rule + display title + meta subline */
.zone-head{border-top:1px solid var(--line-strong);padding-top:22px;}
.zone-head .display{margin-bottom:.15em;}
.zone-head .meta{display:block;margin-bottom:1.6em;}

/* seq frame 01 caption travels to the clear right side — frame 02 advances over the left */
.z-seq [data-seq="1"] .elcap{margin-left:auto;}
.z-nea-seq [data-seq="1"] .elcap{width:fit-content;}   /* Neandertal: fig. 2's caption right-set, clear of fig. 3 below it (as wide as its text, so it can move) */

/* study statement — one held thought between the evidence and the method */
.z-statement .el{text-align:center;}
.statement-tag{display:block;margin-bottom:1.4em;color:var(--dim);letter-spacing:.08em;}
.statement{font-size:var(--s-display);font-weight:500;letter-spacing:-.01em;line-height:1.35;max-width:30ch;margin:0 auto;}
.study-system-bridge{border-top:1px solid var(--line);padding-top:1.4em;}
.study-system-bridge .prose{margin:0 auto;color:var(--mut);}

/* study residue — real system fragments stay subordinate to the authored images */
.process-card .spec-frag{min-height:100%;}
.process-card .spec-frag pre{color:var(--ink);}
.residue-card{max-width:22%;}
.z-statement .residue-card{text-align:left;}   /* beat .z-statement .el center — evidence stays left-set */
.residue-card .textlink{display:inline-block;margin-top:.6em;}
.residue-profile{position:absolute;right:0;top:0;width:34%;max-width:34%;min-width:340px;z-index:3;}   /* wider than other residue — the profile register is denser; floor keeps state 05 inside the fixed window */
.residue-verdicts{max-width:34%;min-width:320px;}   /* same denser register as the profile viewer */
/* every .el keeps a transform after its entrance, so each one is its own stacking
   context and the profile card's z-index can't reach past its wrapper. The grid
   group has to outrank the sequence frames it follows, or the last frame drifts
   over the card as the two planes travel. */
.z-grid > .el{z-index:5;}
.z-grid .zone-note{max-width:52%;}
.z-grid .vgrid-wrap{margin-top:18vh;}
.grid-search{margin:4vh 0 0 auto;width:calc((100% - 11 * var(--sys-gap)) / 3 + 3 * var(--sys-gap));}   /* the last four of the library's twelve columns */
/* notes zone — the prose runs in flow so it sets the zone height; the next-study
   row follows it. A vh offset can't clear a prose block measured in pixels. */
.studio-notes{position:relative;margin-left:var(--colx);width:46%;}
.studio-notes .prose{max-width:46ch;}
.notes-next{position:relative;margin-left:var(--colx);width:80%;margin-top:14vh;}
/* scan credits — one quiet line that opens to the list (Typewriter Scans) */
.credits{position:relative;margin-left:var(--colx);width:min(58%, 72ch);margin-top:8vh;}
.credits summary{cursor:pointer;color:var(--mut);list-style:none;width:max-content;}
.credits summary::-webkit-details-marker{display:none;}
.credits summary::after{content:" ↓";}
.credits[open] summary::after{content:" ↑";}
.credits summary:hover,.credits summary:focus-visible{color:var(--ink);}
.credits-body{color:var(--mut);margin-top:2.2em;line-height:1.7;}
.credits-body p{margin:0 0 1.6em;}
.credits-list{list-style:none;margin:0;padding:0;}
.credits-list li{display:grid;grid-template-columns:3em 1fr;margin-bottom:.9em;}
.credits-list .cr-no{color:var(--dim);}
.process-handoff{border-top:1px solid var(--line);padding-top:1.5em;}

/* specification viewer — one persistent document reorganises inside the
   existing foreground plane; dark evidence register, never app chrome */
.spec-viewer-frame{
  height:420px;
  overflow:hidden;
  background:var(--mat);
  border:1px solid var(--line);
  color:var(--ink);
}
.spec-viewer-head{
  min-height:58px;
  display:flex;flex-direction:column;justify-content:center;gap:.25em;
  padding:11px 13px;
  border-bottom:1px solid var(--line);
  font-family:var(--system);font-size:9px;line-height:1.35;
  letter-spacing:.025em;
}
.spec-viewer-slug{color:var(--ink);}
.spec-viewer-status{color:var(--dim);}
.spec-viewer-window{
  position:relative;display:block;
  width:calc(100% - 20px);height:326px;
  margin:10px 10px 0;padding:0;
  overflow:hidden;text-align:left;
  background:var(--mat-2);
  border:1px solid var(--line);
  cursor:pointer;
}
.spec-viewer-window:focus-visible{
  outline:1px solid var(--accent);
  outline-offset:-1px;
}
.spec-viewer-meta{
  display:flex;justify-content:space-between;gap:10px;
  padding:12px 13px 0;
  font-family:var(--system);font-size:9px;line-height:1.3;
  letter-spacing:.055em;color:var(--dim);
}
.spec-viewer-content{
  display:block;position:relative;
  min-height:270px;padding:22px 13px 14px;
}
.spec-viewer-title{
  display:block;margin-bottom:16px;
  font-family:var(--system);font-size:10px;font-weight:500;
  line-height:1.3;letter-spacing:.07em;text-transform:uppercase;
  color:var(--ink);
}
.spec-viewer-copy{
  display:block;
  font-family:var(--voice);font-size:13px;line-height:1.5;
  letter-spacing:-.005em;color:var(--mut);
}
.spec-viewer-rows{display:grid;gap:10px;}
.spec-viewer-row{
  display:grid;grid-template-columns:66px minmax(0,1fr);
  gap:8px;align-items:start;
  font-family:var(--system);line-height:1.4;
}
.spec-viewer-key{font-size:9px;color:var(--dim);}
.spec-viewer-value{font-size:10px;color:var(--ink);}
/* a struck row is a removed line, still readable — the edit is the record */
.spec-viewer-row-struck .spec-viewer-key,
.spec-viewer-row-struck .spec-viewer-value{color:var(--dim);text-decoration:line-through;}
.spec-viewer-line{
  opacity:0;transform:translateY(14px);filter:blur(2px);
  animation:specAssemble .46s cubic-bezier(.22,.75,.22,1) forwards;
  animation-delay:calc(var(--spec-i) * 48ms);
}
.spec-viewer-content.leaving .spec-viewer-line{
  animation:specDisassemble .22s var(--ease) forwards;
  animation-delay:calc(var(--spec-i) * 16ms);
}
.spec-viewer-scan{
  position:absolute;z-index:2;left:0;right:0;top:0;height:1px;
  opacity:0;pointer-events:none;
  background:linear-gradient(90deg,transparent,var(--mut),transparent);
}
.spec-viewer-window.scanning .spec-viewer-scan{animation:specScan .72s ease-out;}
.spec-viewer-progress{
  display:grid;grid-template-columns:repeat(6,1fr);gap:4px;
  padding:9px 10px 0;
}
.spec-viewer-mark{height:1px;background:var(--line);}
.spec-viewer-mark.active{background:var(--mut);}
@keyframes specAssemble{
  to{opacity:1;transform:translateY(0);filter:blur(0);}
}
@keyframes specDisassemble{
  to{opacity:0;transform:translateY(-10px);filter:blur(2px);}
}
/* aesthetic profile viewer — same instrument; wider key column for longer keys */
.residue-profile .spec-viewer-row{grid-template-columns:92px minmax(0,1fr);}

@keyframes specScan{
  0%{top:0;opacity:0;}
  18%{opacity:.22;}
  100%{top:100%;opacity:0;}
}

/* validator trace — same instrument shell as the document viewers;
   finite test event, not a cycling document */
.vt-frame{
  height:420px;
  overflow:hidden;
  background:var(--mat);
  border:1px solid var(--line);
  color:var(--ink);
  cursor:pointer;
}
.vt-frame:focus-visible{
  outline:1px solid var(--accent);
  outline-offset:-1px;
}
.vt-head{
  min-height:58px;
  display:flex;flex-direction:column;justify-content:center;gap:.25em;
  padding:11px 13px;
  border-bottom:1px solid var(--line);
  font-family:var(--system);font-size:9px;line-height:1.35;
  letter-spacing:.025em;
}
.vt-slug{color:var(--ink);}
.vt-status{color:var(--dim);}
.vt-window{
  position:relative;
  width:calc(100% - 20px);height:326px;
  margin:10px 10px 0;padding:0;
  overflow:hidden;text-align:left;
  background:var(--mat-2);
  border:1px solid var(--line);
}
.vt-scan{
  position:absolute;z-index:2;left:0;right:0;top:0;height:1px;
  opacity:0;pointer-events:none;
  background:linear-gradient(90deg,transparent,var(--mut),transparent);
}
.vt-window.scanning .vt-scan{animation:specScan .72s ease-out;}
.vt-batch,.vt-summary{
  position:absolute;inset:0;
  padding:12px 13px 14px;
  overflow:hidden;
}
.vt-batch.done{display:none;}
.vt-summary{
  display:none;
  align-content:start;gap:16px;
}
.vt-summary.active{display:grid;}
.vt-meta{
  display:flex;justify-content:space-between;gap:10px;
  margin:0 0 6px;
  font-family:var(--system);font-size:9px;line-height:1.3;
  letter-spacing:.055em;color:var(--dim);
}
.vt-rows{
  margin:0;padding:0;list-style:none;
  border-top:1px solid var(--line);
}
.vt-row{
  display:grid;grid-template-columns:minmax(0,1fr) auto;
  gap:8px;align-items:center;
  min-height:28px;padding:4px 0;
  border-bottom:1px solid var(--line);
  opacity:0;transform:translateY(10px);filter:blur(1.5px);
}
.vt-row.visible{
  opacity:1;transform:translateY(0);filter:blur(0);
  transition:
    opacity .48s cubic-bezier(.22,.75,.22,1),
    transform .48s cubic-bezier(.22,.75,.22,1),
    filter .48s cubic-bezier(.22,.75,.22,1);
}
.vt-batch.finding .vt-row.recede{display:none;}
.vt-batch.finding .vt-row.focused{
  min-height:auto;padding-bottom:2px;
  border-bottom:0;
}
.vt-row.recede{opacity:.28;transition:opacity .36s var(--ease);}
.vt-row.focused{opacity:1;}
.vt-name{
  font-family:var(--system);font-size:10px;line-height:1.35;
  letter-spacing:.01em;color:var(--ink);
}
.vt-verdict{
  min-width:4.6em;
  font-family:var(--system);font-size:9px;letter-spacing:.04em;
  text-align:right;color:var(--dim);
  opacity:0;transform:translateX(6px);
}
.vt-verdict.visible{
  opacity:1;transform:translateX(0);
  transition:opacity .34s var(--ease),transform .34s cubic-bezier(.22,.75,.22,1);
}
.vt-verdict.fixable{color:var(--ink);}
.vt-detail{
  display:none;
  margin-top:6px;padding-top:8px;
  border-top:1px solid var(--line);
}
.vt-detail.active{display:block;}
.vt-detail-head{
  display:flex;justify-content:space-between;gap:10px;
  margin:0 0 8px;
  font-family:var(--system);font-size:9px;letter-spacing:.04em;
}
.vt-detail-head strong{font-weight:600;color:var(--ink);}
.vt-detail-head span{color:var(--dim);}
.vt-finding{display:grid;gap:6px;}
.vt-block{
  display:grid;grid-template-columns:66px minmax(0,1fr);
  gap:8px;align-items:start;margin:0;
  opacity:0;transform:translateY(10px);filter:blur(1.5px);
}
.vt-block.visible{
  opacity:1;transform:translateY(0);filter:blur(0);
  transition:
    opacity .5s cubic-bezier(.22,.75,.22,1),
    transform .5s cubic-bezier(.22,.75,.22,1),
    filter .5s cubic-bezier(.22,.75,.22,1);
}
.vt-key{
  font-family:var(--system);font-size:9px;line-height:1.4;
  letter-spacing:.04em;text-transform:uppercase;color:var(--dim);
}
.vt-value{
  font-family:var(--system);font-size:10px;line-height:1.4;
  color:var(--ink);
}
.vt-quote{color:var(--mut);}
.vt-repair{padding-left:8px;border-left:1px solid var(--mut);}
.vt-summary-title{
  margin:0;
  font-family:var(--system);font-size:9px;letter-spacing:.04em;
  color:var(--dim);
}
.vt-summary-grid{
  display:grid;grid-template-columns:repeat(3,minmax(0,1fr));
  border-top:1px solid var(--line);border-bottom:1px solid var(--line);
}
.vt-summary-item{
  margin:0;padding:14px 8px;
  border-right:1px solid var(--line);
  opacity:0;transform:translateY(10px);
}
.vt-summary-item:last-child{border-right:0;}
.vt-summary-item.visible{
  opacity:1;transform:translateY(0);
  transition:opacity .48s var(--ease),transform .48s cubic-bezier(.22,.75,.22,1);
}
.vt-summary-item strong{
  display:block;margin-bottom:4px;
  font-family:var(--voice);font-size:18px;font-weight:500;
  letter-spacing:-.02em;color:var(--ink);
}
.vt-summary-item span{
  font-family:var(--system);font-size:9px;letter-spacing:.05em;
  color:var(--dim);
}
.vt-render-limit{
  margin:0;padding-top:2px;
  opacity:0;transform:translateY(10px);
}
.vt-render-limit.visible{
  opacity:1;transform:translateY(0);
  transition:opacity .48s var(--ease),transform .48s cubic-bezier(.22,.75,.22,1);
}
.vt-render-limit strong{
  font-family:var(--system);font-size:9px;font-weight:500;
  letter-spacing:.04em;color:var(--ink);
}
.vt-progress{
  display:grid;grid-template-columns:repeat(6,1fr);gap:4px;
  padding:9px 10px 0;
}
.vt-mark{height:1px;background:var(--line);}
.vt-mark.active{background:var(--mut);}

/* character cascade */
[data-chars] .ch{opacity:0;transition:opacity .26s var(--ease);}
[data-chars].chlive .ch{opacity:1;}

/* ============ IMAGE BLOCKS ============ */
.ph{position:relative;background:var(--ph-2);display:grid;place-items:center;overflow:hidden;min-height:60px;}
.ph::after{content:attr(data-label);font-family:var(--system);font-size:var(--s-ui);letter-spacing:.14em;color:var(--dim);text-align:center;padding:0 .8em;}
.ph.p43{aspect-ratio:4/3;background:var(--ph-1);}
.ph.p45{aspect-ratio:4/5;}
.ph.p32{aspect-ratio:3/2;background:var(--ph-3);}
.ph.p34{aspect-ratio:3/4;}
.ph.p169{aspect-ratio:16/9;}
.ph.p16087{aspect-ratio:160/87;}   /* ComfyUI workflow screenshot — 3840×2088 */
.ph.p219{aspect-ratio:21/9;width:100%;}
/* study loop — 16:9 Vimeo cover-cropped into 21:9 frame */
.ph.p219 .vid{position:absolute;inset:0;width:100%;height:100%;aspect-ratio:auto;background:transparent;overflow:hidden;}
.ph.p219 .vid iframe{inset:auto;top:50%;left:50%;width:100%;height:131.25%;transform:translate(-50%,-50%);pointer-events:none;}
/* study loop + any 16:9 ph — Vimeo fills the frame */
.ph.p169 .vid{position:absolute;inset:0;width:100%;height:100%;aspect-ratio:auto;background:transparent;}
.ph.p169 .vid iframe{pointer-events:none;}
/* sequence frame — 16:9 Vimeo cover-cropped into 3:2 (.p32) slot; still kept as poster/fallback */
.ph.has-seq-vid .seq-vid-still{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;transition:opacity .45s var(--ease);}
.ph.has-seq-vid.vid-ready .seq-vid-still{opacity:0;}
.ph.p32.has-seq-vid .vid{position:absolute;inset:0;width:100%;height:100%;aspect-ratio:auto;background:transparent;overflow:hidden;}
.ph.p32.has-seq-vid .vid iframe{inset:auto;top:50%;left:50%;width:118.52%;height:100%;transform:translate(-50%,-50%);pointer-events:none;}
.ph img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;}
/* p32 + 4:5 portrait — rotate 90°, min cover (fills frame, no stretch, no over-zoom) */
.ph.p32.rot-90{background:var(--ground);}
.ph.p32.rot-90 img{inset:auto;top:50%;left:50%;width:80%;height:auto;aspect-ratio:4/5;object-fit:cover;transform:translate(-50%,-50%) rotate(90deg);}
.ph.himg::after{display:none;}
.ph[data-xfade]{isolation:isolate;}
.ph .xfade-b{
  opacity:1;
  will-change:mask-image,-webkit-mask-image;
  -webkit-mask-image:linear-gradient(transparent,transparent);   /* hidden at rest: the record shows, the rig waits */
  mask-image:linear-gradient(transparent,transparent);
  -webkit-mask-size:100% 100%;
  mask-size:100% 100%;
  -webkit-mask-repeat:no-repeat;
  mask-repeat:no-repeat;
}
.vid{position:relative;aspect-ratio:16/9;background:var(--ph-1);}
.vid iframe{position:absolute;inset:0;width:100%;height:100%;border:0;}
/* archive #sp-a4 — a silent loop, 4:5 cover crop (#sp-a3 became a still, 16 Oct 2026) */
.ph.p45 .vid{position:absolute;inset:0;width:100%;height:100%;aspect-ratio:auto;background:transparent;}
#sp-a4 .vid{overflow:hidden;}
#sp-a4 .vid iframe{inset:auto;top:50%;left:50%;width:222%;height:100%;transform:translate(-50%,-50%);pointer-events:none;}
/* arrival film: native 16:9, no well — its own ground (19,19,19) is the page ground, so it sits under the headline and hero without an edge */
#sp-v1 .vid{background:transparent;}
#sp-wm{z-index:2;}   /* the watermark outline draws over the arrival film; the hero, later in the DOM at the same depth, still covers it */
/* hero re-render — the amber types in band by band; one clipped image (script.js) */
#sp-hero .hero-next{clip-path:polygon(0 0,0 0,0 100%,0 100%);pointer-events:none;}
#sp-c3,#sp-rest{mix-blend-mode:lighten;}   /* a frameless scan on the page ground: lighten drops its ground, so the atmosphere behind shows through instead of a dark box */
#sp-v1 .vid iframe{pointer-events:none;}

/* ============ INDEX ============ */
.index{border-top:1px solid var(--line);}
.index-row{display:grid;grid-template-columns:2.6em 1fr auto;align-items:baseline;gap:1.2em;padding:1.1em 0;border-bottom:1px solid var(--line);}
/* a title never wraps: where a row is tight (the studies list in Geist), its short description takes two lines instead */
@media (min-width:901px){ #home-index .index-row{grid-template-columns:2.6em max-content minmax(0,1fr);} #home-index .ix-meta{text-wrap:balance;} }
.ix-no{font-family:var(--system);font-size:var(--s-meta);color:var(--dim);}
.ix-title{font-size:var(--s-index);font-weight:500;transition:transform .22s var(--ease),color .15s var(--ease);display:inline-block;}
/* shuffle cells (shuffleTitle in script.js) — titles and row descriptions: words never break, each letter holds its kerned advance */
:is(.index-row,.procnote) .ix-word{white-space:nowrap;}
:is(.index-row,.procnote) .ix-ch{display:inline-block;white-space:pre;}
.ix-meta{font-family:var(--system);font-size:var(--s-meta);color:var(--mut);text-align:right;transition:opacity .15s var(--ease);}
.index-row:hover .ix-title,.index-row:focus-visible .ix-title{color:var(--hover);transform:translateX(6px);}
.index-row:focus-visible{outline:none;}
.tall-rows .index-row{padding:1.5em 0;}
/* five systems rows outgrow one screen on short windows — rows size with width, the frame
   with height. Both systems listings tighten together so the nav hand-off still settles. */
@media (max-height:860px){
  #systems-index .index-row,#home-sysindex .index-row{padding:1.2em 0;}
}
.index-row.disabled{opacity:.4;pointer-events:none;}
/* index rows swap their meta on hover — to a readout (data-alt) or, for a row without a real
   figure, to its subject. Invisible copies of every value the cell can hold keep the column at the widest,
   so the swap itself never rewraps the title — the index field reads row geometry. (The hover
   letter-spacing below can still tip a title that fits within a few px, in narrow width bands.) */
:is(#home-index,#home-sysindex) .index-row[data-subject]:not(.disabled):not(:has(.ix-meta[data-alt])) .ix-meta{grid-row:1;grid-column:3;}
:is(#home-index,#home-sysindex) .index-row[data-subject]:not(.disabled):not(:has(.ix-meta[data-alt]))::after{content:attr(data-subject);grid-row:1;grid-column:3;align-self:start;height:0;overflow:hidden;visibility:hidden;font-family:var(--system);font-size:var(--s-meta);}
:is(#home-index,#home-sysindex) .index-row:not(.disabled) .ix-meta[data-default]::after{content:attr(data-default) "\A" attr(data-alt);white-space:pre;display:block;height:0;overflow:hidden;visibility:hidden;}
/* systems descriptions (at rest) are longer than the status shown on hover. The meta column is fixed
   at the status's width ("self-initiated · 2026") and the description stays on one line, growing leftward into the
   gap before the title (an rtl cell with the text isolated as ltr) — nothing reflows, nothing moves */
@media (min-width:901px){   /* phones stack the meta under the title instead */
  #home-sysindex .index-row::after{display:none;}
  #home-sysindex .ix-meta{width:22ch;direction:rtl;white-space:nowrap;}   /* ch of the meta face, not the title's */
  #home-sysindex .ix-meta-t{direction:ltr;unicode-bidi:isolate;}
}

/* ============ WORK — piece hover (image zoom, title surface) ============ */
.workpiece .ph{cursor:pointer;}
.workpiece .ph img{transition:opacity .35s var(--ease),transform .7s var(--ease);}
/* the archive's installation pictures: the title shuffles in, holds, shuffles out (script.js) */
.worktag{position:absolute;left:18px;bottom:14px;z-index:2;pointer-events:none;
  font-size:var(--s-index);font-weight:500;color:#fff;
  text-shadow:0 1px 2px rgba(0,0,0,.55),0 2px 16px rgba(0,0,0,.32);
  opacity:0;transition:opacity .22s var(--ease);}
.worktag.on{opacity:1;}
.worktag .ix-word{white-space:nowrap;}
.worktag .ix-ch{display:inline-block;white-space:pre;}

/* ============ VARIATION GRID ============ */
.vgrid-wrap{position:relative;overflow-anchor:none;} /* FLIP transform must not trigger scroll anchoring */
.vgrid{display:grid;grid-template-columns:repeat(5,1fr);gap:3px;}
.vgrid .cell{aspect-ratio:4/5;background:var(--ph-2);display:grid;place-items:center;cursor:pointer;transition:opacity .45s var(--ease);font-family:var(--system);font-size:10px;color:var(--dim);letter-spacing:.06em;}
.vgrid .cell.has-img{padding:0;overflow:hidden;color:transparent;position:relative;}
.vgrid .cell.has-img img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;display:block;transition:opacity .15s var(--ease);}
.vgrid .cell.has-img:hover img{opacity:.82;}
.vgrid .cell.empty:hover{background:var(--ph-3);}
.vgrid-wrap.zoomed .vgrid .cell{opacity:.15;pointer-events:none;transition-delay:.08s;}
.vgrid-wrap.zoomed .vgrid .cell.empty{opacity:.08;cursor:default;}
.vgrid-readout{margin-top:12px;min-height:1.4em;}
.vgrid-zoom{position:absolute;inset:0;z-index:5;display:grid;place-items:center;align-content:center;}
.vgrid-zoom[hidden]{display:none;}
.vgrid-zoom .zoom-img{width:54%;background:var(--ph-3);will-change:transform;overflow:hidden;}
.vgrid-zoom .zoom-img img{z-index:1;display:block;}
.vgrid-zoom .zoom-img.loupe img{will-change:transform;transition:none;backface-visibility:hidden;}
.vgrid-zoom .zoom-cap{margin-top:12px;text-align:center;position:relative;z-index:2;transition:opacity .3s var(--ease);}
.vgrid-zoom.zcap-in .zoom-cap{opacity:0;}

/* ============================================================
   SYSTEMS — locked frame, live states.
   Stable spine (opening line, heading, stepper) on a 12-col grid;
   the evidence (SPEC→IMAGE, THE SCORE, the films) floats over it via
   z-index depth + parallax. Heights stay content-driven, so collisions
   are structurally impossible — overlap is depth, never coordinates.
   ============================================================ */
.syspage{
  /* The site's frame: system pages start at --colx and end at --mx like every other page.
     (The wider gutter that cleared the old text rail went when desktop moved to the ruler.) */
  padding:10vh var(--mx) 12vh var(--colx);   /* the head starts where the studies' heads start */
}
.syspage .elcap{margin-top:10px;}

/* depth layers — give floating evidence a stacking context over the spine */
.syspage .bg{position:relative;z-index:1;}
.syspage .mid{position:relative;z-index:2;}
.syspage .fg{position:relative;z-index:3;}
.syspage [data-plane]{will-change:transform;}

.sys-block{margin-bottom:14vh;}
.sys-pipeline{max-width:100%;}

/* a. opening pair — line is the anchor; SPEC card floats lower, right */
.sys-open{
  display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;
  align-items:start;margin-bottom:13vh;
}
.sys-lead{grid-column:1/7;max-width:42ch;margin-top:3vh;}
.sys-open-spec{grid-column:8/12;grid-row:1;margin-top:11vh;width:120%;justify-self:end;}
.sys-open-spec .reveal-slow{transition-delay:.1s;}

/* c. the case — film anchors left; THE SCORE drifts in from the right,
   crossing the film's right edge at fg depth (mirror of wp-a residue) */
.sys-case{
  display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;
  align-items:start;
}
.sys-film-main{grid-column:1/9;grid-row:1;}
.sys-score{grid-column:8/13;grid-row:1;margin-top:15vh;}
.sys-score .reveal-slow{transition-delay:.12s;}
.sys-prov{margin-top:1em;}

/* d. the work around it — tie-in (spine) then two films at different planes */
.sys-tie{max-width:46ch;margin-bottom:6vh;}
.sys-films{display:grid;grid-template-columns:1fr 1fr;column-gap:2vw;align-items:start;}
.sys-film:nth-child(2){margin-top:11vh;}
.sys-film:nth-child(2) .reveal,.sys-film:nth-child(2) .reveal-slow{transition-delay:.12s;}

/* next-system row — mirrors the study hand-off (.notes-next) */
.sys-next{margin-top:14vh;width:80%;}
/* desktop: every page's next row runs the full twelve columns, ending on the same edge as the section rules above it
   (both were 80% of different containers, so studies and systems ended on different lines) */
@media (min-width:901px){ .sys-next{width:100%;} .notes-next{width:var(--sys-w);} }

/* second system case — AI Material Generator */
.sys-product-open{
  display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;
  align-items:start;margin-bottom:11vh;
}
.sys-case-no{grid-column:1/6;margin-bottom:2vh;}
.sys-product-open .display{grid-column:1/10;grid-row:2;}
.sys-product-lead{grid-column:1/7;grid-row:3;margin-top:2vh;max-width:46ch;}
.sys-product-fact{
  grid-column:7/10;grid-row:3;margin-top:3vh;padding-top:1.2em;
  border-top:1px solid var(--line);line-height:1.8;
}
.sys-product-specimen{
  grid-column:10/13;grid-row:1/4;align-self:start;
  text-decoration:none;color:inherit;
}
.sys-product-specimen .reveal-slow{transition-delay:.1s;}
.sys-product-specimen:hover .elcap{color:var(--ink);}

.lle-layers{
  display:grid;grid-template-columns:repeat(3,1fr);
  border-top:1px solid var(--line);border-bottom:1px solid var(--line);
  margin-bottom:14vh;
}
.lle-layer{padding:2em 2vw 2.4em 0;}
.lle-layer + .lle-layer{border-left:1px solid var(--line);padding-left:2vw;}
.lle-layer h3{font-size:var(--s-index);font-weight:500;margin:.65em 0 .8em;}
.lle-layer p{font-size:var(--s-meta);line-height:1.7;color:var(--mut);max-width:38ch;}

.lle-workflow{margin-bottom:14vh;}
.lle-workflow .ph{
  width:100%;
  border:1px solid var(--line);
  background:var(--mat);
}
.lle-workflow.workpiece .ph{cursor:pointer;}
.lle-workflow.workpiece .ph img{transition:opacity .35s var(--ease),transform .7s var(--ease);}

.lle-pipeline{margin-bottom:14vh;}
.lle-flow{
  display:grid;grid-template-columns:repeat(4,minmax(0,1fr) auto) minmax(0,1fr);
  align-items:stretch;border:1px solid var(--line);background:var(--panel);
  padding:1px;min-height:150px;
}
.lle-flow span{
  position:relative;
  display:flex;flex-direction:column;justify-content:space-between;
  padding:1.2em;font-family:var(--system);font-size:var(--s-meta);
  color:var(--mut);border:1px solid transparent;
  cursor:pointer;
  transition:color .2s var(--ease),border-color .2s var(--ease),background .2s var(--ease);
}
.lle-flow span:hover{color:var(--ink);}
.lle-flow span:focus-visible{
  outline:1px solid var(--accent);
  outline-offset:-1px;
}
.lle-flow span b{font-size:var(--s-ui);font-weight:400;color:var(--dim);}
.lle-flow span small{font-size:var(--s-ui);color:var(--dim);margin-top:2em;}
.lle-flow i{align-self:center;color:var(--dim);font-family:var(--system);font-style:normal;pointer-events:none;}
.lle-flow span.on{color:var(--ink);border-color:var(--line-strong);background:var(--ground-2);}
.process-card .lle-flow{
  grid-template-columns:repeat(3,minmax(0,1fr) auto) minmax(0,1fr);
  min-height:190px;background:var(--paper);border-color:var(--line-strong);
}
.process-card .lle-flow span{color:var(--paper-ink);}
.process-card .lle-flow span b,.process-card .lle-flow span small,.process-card .lle-flow i{color:var(--paper-ink);opacity:.58;}

.lle-evidence{
  display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;
  align-items:start;margin-bottom:14vh;
}
.lle-evidence-card{
  background:var(--panel);border:1px solid var(--line);padding:1.6em;
}
.lle-evidence-card:nth-child(1){grid-column:1/7;}
.lle-evidence-card:nth-child(2){grid-column:7/13;margin-top:10vh;}
.lle-evidence-card:nth-child(3){grid-column:3/11;margin-top:8vh;}
.lle-evidence-card:nth-child(4){grid-column:5/13;margin-top:8vh;}
.lle-evidence-card header{
  display:flex;justify-content:space-between;gap:1em;
  padding-bottom:1em;border-bottom:1px solid var(--line);
}
.lle-evidence-card header strong{font-weight:400;color:var(--dim);}
.lle-evidence-card pre{
  white-space:pre-wrap;margin:2em 0;font-family:var(--system);
  font-size:var(--s-meta);line-height:1.8;color:var(--ink);
}
.lle-evidence-card .prose{font-size:var(--s-prose);color:var(--mut);}
.lle-spec-pair .lle-spec-body{
  display:grid;grid-template-columns:minmax(0,1fr) 40%;column-gap:2vw;
  align-items:start;margin-top:1.6em;
}
.lle-spec-pair .lle-spec-text pre{margin-top:0;}
.lle-spec-frame .ph{border:1px solid var(--line);background:var(--mat);}
.lle-spec-frame .elcap{margin-top:10px;}
.compile-order{list-style:none;counter-reset:compile;margin:2em 0;line-height:1.9;color:var(--ink);}
.compile-order li{counter-increment:compile;border-bottom:1px solid var(--line);padding:.35em 0;}
.compile-order li::before{content:"0" counter(compile);color:var(--dim);margin-right:1.4em;}

/* one row of five at the study grid's size: same left edge (--colx), same width, same 3px gap */
.lle-library{
  --sys-l:var(--colx);
  display:grid;grid-template-columns:repeat(5,1fr);gap:3px;align-items:start;margin-bottom:14vh;
  width:min(calc((100% + var(--sys-l) + var(--mx)) * .88), calc(100% + var(--sys-l) - var(--colx)));
  margin-left:calc(var(--colx) - var(--sys-l));
}
.lle-library .ph{aspect-ratio:4/5;}
.lle-library-cell{transition:opacity .3s var(--ease);}
.lle-library-cell.workpiece .ph{cursor:pointer;}
.lle-library-cell.workpiece .ph img{transition:opacity .35s var(--ease),transform .7s var(--ease);}
.lle-library-cap{
  grid-column:1/-1;margin-top:3vh;color:var(--mut);line-height:1.7;
}

.lle-provenance{padding:5vh 0;border-top:1px solid var(--line-strong);border-bottom:1px solid var(--line-strong);margin-bottom:14vh;}
.lle-provenance-open{max-width:58ch;color:var(--mut);margin-bottom:7vh;}
.lle-provenance-items{display:grid;grid-template-columns:repeat(3,1fr);}
.lle-provenance-item{padding:2em 2vw 2.4em 0;}
.lle-provenance-item + .lle-provenance-item{border-left:1px solid var(--line);padding-left:2vw;}
.lle-provenance-item .prose{font-size:var(--s-meta);line-height:1.7;color:var(--mut);margin-top:1.4em;}
.cert-score{
  display:block;font-family:var(--voice);font-size:clamp(64px,10vw,160px);
  font-weight:500;line-height:.9;letter-spacing:-.055em;margin:.12em 0;
}
.lle-provenance .cert-score{font-size:clamp(54px,7vw,112px);margin:.25em 0;}
.sys-direction{margin-bottom:14vh;padding-top:1.6em;border-top:1px solid var(--line);}
.sys-direction .prose{max-width:62ch;color:var(--mut);}

/* ============================================================
   WHISTLE — ticketing. A film-led case: the work is software, so the
   moving record carries it and the stills are evidence beneath.
   ============================================================ */
.sys-whistle{margin-bottom:14vh;}

.whl-film .vid{border:1px solid var(--line);}   /* keeps the base --ph-1 ground; --mat would flash pale */
.whl-film .elcap{margin-top:10px;}

/* four questions — one per column, numbered. Four fit because each answer
   is a sentence, not a paragraph. */
.whl-reveal{margin-bottom:14vh;}
.whl-grid{
  display:grid;grid-template-columns:repeat(4,1fr);
  column-gap:2vw;margin-top:4vh;
}
.whl-item{padding:1.3em 0 2em;border-top:1px solid var(--line);}
.whl-no{display:block;color:var(--dim);margin-bottom:.9em;}
.whl-item h4{font-size:var(--s-index);font-weight:500;margin:0 0 .7em;}
.whl-item p{
  margin:0;font-size:var(--s-meta);line-height:1.7;
  color:var(--mut);max-width:30ch;
}
.whl-note{margin-top:4vh;max-width:62ch;color:var(--mut);}


/* ============================================================
   THIRD SYSTEM CASE — SeedVR2 Restoration Engine.
   Evidence leads: the comparison pair sits before the explanation,
   because the claim is only checkable at magnification. Rows replace
   the stepper — eight nodes do not compress to five tabs honestly.
   ============================================================ */

/* SeedVR2 Restoration Engine — built from the agreed system parts (9 Oct 2026): sections open on a
   hairline and read across the grid, heading 1–3 · text 4–8 · figure 9–12; plates hold their images
   at one size; labels above; drawn, not filled. */
[data-view="systems/restoration"] .rst-lab{margin:0 0 var(--sys-label);white-space:normal;}
.rst-sec{border-top:1px solid var(--line);padding-top:var(--sys-rule);margin-bottom:var(--sys-section);}
.rst-sec > .display,.rst-side > .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;color:var(--ink);margin:0 0 .6em;}
.rst-lead{max-width:62ch;color:var(--mut);margin:0;}
.rst-pl{margin:0;}
.rst-part{margin:0 0 var(--sys-label);color:var(--dim);}
.rst-part b{font-weight:400;color:var(--ink);margin-right:1ch;}
.rst-cell .ph{border:1px solid var(--line);}
.rst-cell{transition:opacity .3s var(--ease);}
.rst-cell[data-rst-loupe] .ph{cursor:zoom-in;}
.rst-cell[data-rst-loupe] .ph img,
.rst-graph[data-rst-loupe] .ph img{transition:opacity .35s var(--ease);will-change:transform;backface-visibility:hidden;}
.rst-graph{margin:0;}
.rst-graph .ph{aspect-ratio:6608/1289;border:1px solid var(--line);background:none;}   /* the canvas grab, cropped to an even margin round the workflow */
.rst-graph[data-rst-loupe] .ph{cursor:zoom-in;}
/* the node list — a ruled row per node: number, name and what it reports, then its own evidence from
   a live run (a report as written, a map as rendered) */
.rst-steps{list-style:none;counter-reset:step;margin:0;padding:0;}
.rst-steps li{counter-increment:step;position:relative;padding:var(--sys-rule) 0;margin:0;border-bottom:1px solid var(--line);}
.rst-steps li:first-child{padding-top:0;}
.rst-steps li:last-child{border-bottom:0;padding-bottom:0;}
.rst-steps li:first-child::before{top:0;}
.rst-steps li::before{content:counter(step, decimal-leading-zero);position:absolute;left:0;top:var(--sys-rule);margin-top:.5em;font-family:var(--system);font-size:var(--s-meta);line-height:1;color:var(--dim);}
.rst-step{padding-left:3.2em;max-width:62ch;}
.rst-steps h3{font-size:var(--s-prose);font-weight:500;color:var(--ink);margin:0 0 .25em;}
.rst-step p{margin:0;color:var(--mut);line-height:1.55;}
.rst-step p + p{margin-top:.7em;}
.rst-ev{margin:1.6em 0 0 3.2em;}
.rst-ev .ph{border:1px solid var(--line);}
.rst-doc{margin:0;padding:1.1em 1.2em;border:1px solid var(--line);line-height:1.75;color:var(--mut);white-space:pre-wrap;}
.rst-flip .rst-part{min-height:1.4em;}
.rst-flip .sw-read{float:none;}
.rst-flip .sw-view{height:auto;aspect-ratio:4 / 5;}
.rst-flip .sw-frame{object-fit:cover;}
.rst-flip .sw-scale{grid-template-columns:repeat(3,1fr);}
.rst-side{margin-bottom:var(--sys-rule);}
/* the grain sweep — the frame (a) with the region boxed, the detail (b) at actual pixels, never scaled,
   and the nine values beneath, each under the ninth of the detail that selects it */
.rst-test{margin:1.4em 0 0;color:var(--dim);}
.rst-sweep,.rst-versus{margin-top:6vh;}
/* the comparison — pairs at actual pixels: the picture is never scaled, the frame shows what fits */
.rst-vs{display:grid;grid-template-columns:1fr;row-gap:4vh;}
.rst-px{position:relative;overflow:hidden;aspect-ratio:16 / 10;border:1px solid var(--line);}
.rst-px img{position:absolute;inset:0;width:100%;height:100%;object-fit:none;object-position:50% 50%;}
/* the reveal — both renders in one frame; the divider follows the pointer (--rv) and carries the two
   names above the frame, each on its own side of the line: plain to the left, the suite to the right */
.rv{position:relative;--rv:50%;}
.rv .rst-px{cursor:ew-resize;touch-action:pan-y;}
.rv-rail{position:relative;height:2.2em;margin:0;color:var(--ink);white-space:nowrap;}
.rv-rail span{position:absolute;top:0;transition:opacity .2s var(--ease);}
.rv-a{right:calc(100% - var(--rv) + 10px);}
.rv-b{left:calc(var(--rv) + 10px);}
.rv-rail span.off{opacity:0;}
.rv-top{z-index:1;clip-path:inset(0 0 0 var(--rv));}
.rv-line{position:absolute;z-index:2;top:0;bottom:0;left:var(--rv);width:1px;background:var(--ink);pointer-events:none;}
.rst-sweep + .rst-sweep{margin-top:var(--sys-section);}
.sw-face .ph{border:1px solid var(--line);}
.sw-box{position:absolute;border:1px solid var(--ink);pointer-events:none;}
.sw-detail{margin-top:4vh;}
.sw-view{position:relative;overflow:hidden;height:62vw;border:1px solid var(--line);cursor:ew-resize;}
.sw-frame{position:absolute;inset:0;width:100%;height:100%;object-fit:none;object-position:50% 50%;opacity:0;}
.sw-frame.on{opacity:1;}
.sw-frame.top{z-index:1;}
.sw-read{float:right;color:var(--ink);}
.sw-scale{display:grid;grid-template-columns:repeat(9,1fr);margin-top:var(--sys-label);}
.sw-tick{position:relative;background:none;border:0;padding:1em 0 .5em;font:inherit;letter-spacing:inherit;color:var(--dim);text-align:left;cursor:pointer;}
.sw-tick::before{content:"";position:absolute;left:0;top:0;width:1px;height:7px;background:var(--line-strong);}
.sw-tick.on{color:var(--ink);}
.sw-tick.on::before{background:var(--ink);height:11px;}
.sw-band{grid-row:2;margin-right:10px;padding-top:.6em;border-top:1px solid var(--line);color:var(--dim);}
.rst-heads{display:grid;grid-template-columns:1fr 1fr;column-gap:var(--sys-gap);align-items:start;}
.rst-heads figure{margin:0;}

/* ============================================================
   Portrait Performance System — on the system grid (12 Oct 2026),
   built from the system parts: sections open on a hairline with the
   heading in columns 1–3 and the text in 4–8; a figure sits beside
   the text or beneath it; labels above; drawn, not filled.
   ============================================================ */
.sys-pps{margin-bottom:14vh;}
[data-view="systems/portrait-performance"] .pps-lab{margin:0 0 var(--sys-label);white-space:normal;}
.pps-sec{border-top:1px solid var(--line);padding-top:var(--sys-rule);margin-bottom:var(--sys-section);}
.pps-sec > .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;color:var(--ink);margin:0 0 .6em;}
.pps-text{max-width:62ch;color:var(--mut);margin:0;}
.pps-text p:last-child{margin-bottom:0;}
.pps-meta{margin:0;color:var(--mut);}
.pps-sec figure{margin:0;}
.pps-sec > :is(.pps-pl,.pps-fig,.pps-doc,.pps-nodetable,.stepper){margin-top:6vh;}
.pps-cells{display:grid;grid-template-columns:1fr 1fr;column-gap:var(--sys-gap);align-items:start;}
.pps-pair .pps-cells{row-gap:4vh;}
.pps-part{margin:0 0 var(--sys-label);color:var(--dim);}
.pps-part b{font-weight:400;color:var(--ink);margin-right:1ch;}
.pps-readout{margin:12px 0 0;}   /* how a stepping plate is operated, as under the cast grid */
/* pl. ii is a sweep: the cursor's place across a portrait picks the expression; one scale names it for both */
.pps-directed .sw-scale{grid-template-columns:repeat(6,1fr);}
.pps-directed .ph[data-reel-scrub]{cursor:ew-resize;}
.pps-directed .pps-readout{margin-top:2.4vh;}
.pps-units{margin:1.6vh 0 0;color:var(--dim);}   /* the block both faces were given, in the notation of doc. 2 */
.pps-units .sw-read{float:none;margin-left:2ch;}
.pps-cell .ph,.pps-fig .ph,.pps-workflow .ph{border:1px solid var(--line);}
.pps-turn .pps-fig .ph{aspect-ratio:6/5;}   /* three 4:5 frames across, the maps over the renders */
.pps-cell .ph:not(.himg){background:none;}   /* an empty slot until its render exists: drawn, not filled */
/* documents and pipeline stages are drawn, not filled */
.pps-doc .spec-frag{border:1px solid var(--line);padding:20px 22px;}
[data-view="systems/portrait-performance"] .spec-viewer-frame{background:none;border:1px solid var(--line);}
[data-view="systems/portrait-performance"] .stepper{border-top:0;padding-top:0;}
[data-view="systems/portrait-performance"] .lle-flow{background:none;border:0;padding:0;}
[data-view="systems/portrait-performance"] .lle-flow span{border-color:var(--line);}
[data-view="systems/portrait-performance"] .lle-flow span.on{border-color:var(--ink);background:none;}
[data-view="systems/portrait-performance"] .lle-flow i{padding:0 .7em;}
/* ten nodes — one ruled table: number, name, one line, the canvas group it works in */
.pps-nodetable{width:100%;border-collapse:collapse;}
.pps-nodetable th,.pps-nodetable td{text-align:left;vertical-align:baseline;font-weight:400;padding:.72em 2.4em .72em 0;border-top:1px solid var(--line);}
.pps-nodetable thead th{border-top:0;padding-top:0;color:var(--dim);}
.pps-nodetable tbody th{color:var(--ink);font-size:calc(var(--s-prose) * .86);white-space:nowrap;}
.pps-nodetable td{color:var(--mut);font-size:calc(var(--s-prose) * .76);line-height:1.5;}
.pps-nodetable td.meta{color:var(--dim);font-size:var(--s-meta);white-space:nowrap;}
.pps-nodetable tr > :last-child{padding-right:0;text-align:right;}
.pps-workflow .ph{width:100%;aspect-ratio:4753/2621;background:none;}   /* the canvas grab, cropped to an even margin round the workflow */
@media (min-width:901px){
  [data-view="systems/portrait-performance"] .sys-product-open{margin-bottom:var(--sys-section);}
  [data-view="systems/portrait-performance"] .sys-product-open:has(.spec) .sys-product-fact{grid-column:1 / 10;grid-row:5;justify-self:start;width:max-content;white-space:nowrap;margin-top:1vh;}
  .pps-sec{display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);align-items:start;}
  .pps-sec > .display{grid-column:1 / 4;}
  .pps-sec > :is(.pps-text,.pps-meta){grid-column:4 / 9;}
  .pps-sec > :is(.stepper,.pps-workflow){grid-column:1 / -1;}
  .pps-sec > .pps-nodetable{grid-column:1 / -1;}   /* the full width, so each node reads on one line */
  .pps-sec > :is(.pps-pl,.pps-fig){grid-column:1 / 9;}
  .pps-pair > .pps-pl{grid-column:1 / -1;}   /* a strip of five across the full width, its document beneath */
  .pps-pair .pps-cells{grid-template-columns:repeat(5,1fr);}
  .pps-sec.pps-pair > .pps-doc{grid-column:1 / 5;}
  .pps-sec > .pps-doc{grid-column:9 / 13;}
  .pps-identity > figure:nth-of-type(1){grid-column:1 / 5;}   /* one row: the reference, the document it was read into, the result */
  .pps-identity > .pps-doc{grid-column:5 / 9;}
  .pps-identity > figure:nth-of-type(3){grid-column:9 / 13;}
}

/* Comfy Bridge — blocked out 14 Oct 2026 on the same grid as Portrait Performance: sections open on a
   hairline, heading 1–3 · text 4–8, figures beside or beneath, labels above, drawn not filled */
.sys-cb{margin-bottom:14vh;}
[data-view="systems/comfy-bridge"] .cb-lab{margin:0 0 var(--sys-label);white-space:normal;}
.cb-sec{border-top:1px solid var(--line);padding-top:var(--sys-rule);margin-bottom:var(--sys-section);}
.cb-sec > .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;color:var(--ink);margin:0 0 .6em;}
.cb-text{max-width:62ch;color:var(--mut);margin:0;}
.cb-text p:last-child{margin-bottom:0;}
.cb-uses-links{margin-top:1.6em;line-height:1.9;}
.cb-uses-links a{white-space:nowrap;}
.cb-meta{margin:0;color:var(--mut);}
/* [fig. 3] one brief, built autonomously: the film on a screen, the chain beneath as its index (script.js) */
.cbb{position:relative;margin-top:var(--sys-label);}
.cbb .diagram{max-width:none;}
.cbb .diagram .ag{stroke-dasharray:4 3;}
.cbb .diagram .lp{fill:none;stroke:var(--mut);stroke-width:1;}
.cbb .diagram :is(.lead,.ldr){fill:none;stroke:var(--dim);stroke-width:1;stroke-dasharray:2 3;}
.cbb .diagram .nd.on{fill:var(--ink);stroke:var(--ink);}
.cbb .hit{cursor:pointer;outline:none;}
.cbb .hit rect{transition:stroke .25s var(--ease),fill .25s var(--ease);}
.cbb .hit:is(:hover,:focus-visible) rect,.cbb .hit.on rect{stroke:var(--ink);}
.cbb .hit.on rect{fill:var(--mat);}
.cbb .pn{opacity:0;pointer-events:none;transition:opacity .3s var(--ease);}
.cbb .pn.on{opacity:1;}
.cbb .lead{transition:transform .35s var(--ease),opacity .25s var(--ease);}
.cbb.film .lead{opacity:0;}
.cbb .pn text{font-size:13px;}
.cbb .pn .cap{font-size:11.5px;}
.cbb .pn .hd{font-size:17px;}
.cbb .pn .pt{font-family:var(--voice);font-size:28px;fill:var(--ink);}
.cbb .pn .pl{font-family:var(--system);font-size:14px;fill:var(--mut);}
.cbb .pn .pb{font-family:var(--voice);font-size:16px;fill:var(--mut);}
.cbb-vid{position:absolute;left:var(--fx);top:var(--fy);width:var(--fw);aspect-ratio:16/9;background:#000;}
.cbb-vid iframe{position:absolute;inset:0;width:100%;height:100%;border:0;}
.cbb:not(.film) .cbb-vid{visibility:hidden;}
@media (prefers-reduced-motion:reduce){ .cbb :is(.pn,.lead,.hit rect){transition:none;} }
.cbb-m{display:none;}
@media (max-width:900px){
  /* phone: the film full width, the copy as text, the chain as a column; a part opens its own screen beneath it,
     drawn at 1000px and scrolled sideways inside its frame (the screens are diagrams, too dense to shrink) */
  .cb-brief.cb-arch{overflow:visible;}
  .cb-brief .cbb > svg{display:none;}
  .cbb-m{display:block;}
  .cbb-m .cbb-vid{position:relative;left:auto;top:auto;width:100%;visibility:visible;}
  .cbb-m-title{font-family:var(--voice);font-size:calc(var(--s-prose) * 1.15);line-height:1.3;color:var(--ink);margin:1.4em 0 .5em;}
  .cbb-m-body{font-size:var(--s-prose);line-height:1.5;color:var(--mut);margin:0;}
  .cbb-m-len{color:var(--dim);margin:1em 0 0;}
  .cbb-m-chain{list-style:none;margin:2.2em 0 0;padding:0;}
  .cbb-m-chain li + li{margin-top:22px;position:relative;}
  .cbb-m-chain li + li::before{content:"";position:absolute;left:24px;top:-22px;height:22px;border-left:1px solid var(--dim);}
  .cbb-m-row{display:grid;grid-template-columns:1fr auto;width:100%;text-align:left;background:none;border:1px solid var(--line);padding:.9em 1em 1em;cursor:pointer;color:inherit;font:inherit;}
  .cbb-m-row.ag{border-style:dashed;border-color:var(--mut);}
  .cbb-m-row.wt{border-style:dashed;}
  .cbb-m-row > span{grid-column:1;}
  .cbb-m-row .cap{font-family:var(--system);font-size:var(--s-ui);color:var(--dim);letter-spacing:.03em;}
  .cbb-m-row .nm{font-family:var(--voice);font-size:calc(var(--s-prose) * .95);color:var(--ink);margin:.25em 0 .35em;}
  .cbb-m-row .ln{font-family:var(--system);font-size:var(--s-meta);color:var(--mut);line-height:1.6;}
  .cbb-m-row .op{grid-column:2;grid-row:1 / span 5;align-self:center;font-family:var(--system);font-size:var(--s-ui);color:var(--dim);}
  .cbb-m-row[aria-expanded="true"]{border-color:var(--ink);background:var(--mat);}
  .cbb-m-row[aria-expanded="true"] .op{color:var(--ink);}
  .cbb-m-screen{overflow-x:auto;border:1px solid var(--line);border-top:0;}
  .cbb-m-screen svg{display:block;width:1000px;max-width:none;}
  .cbb-m-screen .pn{opacity:1;pointer-events:auto;}
}
.cb-sec figure{margin:0;}
.cb-sec > :is(figure,.stepper){margin-top:6vh;}
[data-view="systems/comfy-bridge"] .stepper{border-top:0;padding-top:0;}
[data-view="systems/comfy-bridge"] .lle-flow{background:none;border:0;padding:0;}
[data-view="systems/comfy-bridge"] .lle-flow span{border-color:var(--line);}
[data-view="systems/comfy-bridge"] .lle-flow span.on{border-color:var(--ink);background:none;}
[data-view="systems/comfy-bridge"] .lle-flow i{padding:0 .7em;}
/* the refusals — ruled rows in two columns: number, the name the code returns, what it means */
/* documents: drawn in a hairline, set in the system face */
.cb-graph .nd{fill:var(--ground);stroke:var(--line-strong);}
/* the library — one mark per template reading, grouped by kind; the reading of the mark in hand beside it */
/* the tools — one ruled table across the full width */
/* [fig. 2] one change: the drawing, the revision table, the checks. Refusals are dashed and marked in ink —
   no red (colour-system §3: red is never a graphic). data-rev on the svg: 0 as loaded · 1, 2 refused · 3 applied */
.diagram.cb-sheet{margin-top:var(--sys-label);max-width:none;}
.cb-sheet :is(rect,line,path){shape-rendering:geometricPrecision;}
.cb-sheet .grp{fill:none;stroke:var(--line);stroke-width:1;}
.cb-sheet .gt{font-size:9px;fill:var(--dim);letter-spacing:.04em;}
.cb-sheet .w{fill:none;stroke:var(--line-strong);stroke-width:.8;}
.cb-sheet .pt{fill:var(--ground);stroke:var(--line-strong);stroke-width:.8;}
.cb-sheet .n rect{fill:var(--ground);stroke:var(--line-strong);stroke-width:.8;}
.cb-sheet .n line{stroke:var(--line);stroke-width:.8;}
.cb-sheet .n.on rect{stroke:var(--ink);stroke-width:1;}
.cb-sheet .n.on line{stroke:var(--mut);}
.cb-sheet .w.on{stroke:var(--ink);stroke-width:1.2;}
.cb-sheet .pt.on{stroke:var(--ink);}
.cb-sheet .nid{font-size:9px;fill:var(--ink);}
.cb-sheet .baseline{stroke:var(--line);}
.cb-sheet .key{font-size:11px;fill:var(--mut);}
.cb-sheet .key .id{fill:var(--ink);}
.cb-sheet .verdict{font-size:11px;fill:var(--ink);display:none;}
/* which marks each revision shows: 0 as loaded · 1, 2 the refused proposal, dashed · 3 the change in ink */
.cb-sheet :is(.n.nw,.w.nw,.pt.nw,.nid.nw,.w.gh,.pt.gh){display:none;}
.cb-sheet[data-rev="0"] .nid{display:none;}
.cb-sheet[data-rev="0"] .n.on:not(.nw) rect{stroke:var(--line-strong);stroke-width:.8;}
.cb-sheet:is([data-rev="1"],[data-rev="2"]) :is(.n.gh,.w.gh,.pt.gh,.nid.gh){display:inline;}
.cb-sheet:is([data-rev="1"],[data-rev="2"]) .n.gh rect{stroke:var(--mut);stroke-dasharray:3 2;}
.cb-sheet:is([data-rev="1"],[data-rev="2"]) .n.gh line{display:none;}
.cb-sheet:is([data-rev="1"],[data-rev="2"]) .w.gh{stroke:var(--mut);stroke-dasharray:3 2;stroke-width:1;}
.cb-sheet:is([data-rev="1"],[data-rev="2"]) .nid.gh{fill:var(--mut);}
.cb-sheet[data-rev="1"] .v1,.cb-sheet[data-rev="2"] .v2,.cb-sheet[data-rev="3"] .v3{display:inline;}
.cb-sheet[data-rev="3"] :is(.n.nw,.w.nw,.pt.nw,.nid.nw){display:inline;}
.cb-revs{width:100%;border-collapse:collapse;margin-top:3vh;}
.cb-revs th,.cb-revs td{text-align:left;vertical-align:baseline;font-weight:400;padding:.62em 1.6em .62em 0;border-top:1px solid var(--line);}
.cb-revs thead th{border-top:0;padding-top:0;color:var(--dim);}
.cb-revs tbody th{color:var(--mut);font-family:var(--system);font-size:var(--s-meta);white-space:nowrap;}
.cb-revs td{color:var(--mut);font-size:calc(var(--s-prose) * .76);line-height:1.5;}
.cb-revs td.meta{color:var(--dim);font-size:var(--s-meta);line-height:1.7;}
.cb-revs tr > :last-child{padding-right:0;white-space:nowrap;}
.cb-revs tbody tr{cursor:pointer;}
.cb-revs tbody tr:is(:hover,.on) :is(th,td){color:var(--ink);}
.cb-revs tbody tr.r td.meta:nth-child(4){font-style:normal;}
.cb-revs tbody tr.on th::before{content:"■ ";color:var(--accent);}
/* the six stages under the lead, drawn like [fig. 8]: boxes in sequence, dashed = the agent, solid = code */
.cb-flow{white-space:normal!important;width:auto!important;max-width:none!important;border-top:0!important;padding-top:0!important;}
.cb-fl-row{display:grid;grid-template-columns:repeat(5,minmax(0,1fr) auto) minmax(0,1fr);align-items:stretch;column-gap:.9vw;}
.cb-fl-box{border:1px solid var(--line-strong);padding:.9em 1em 1em;transition:border-color .25s var(--ease);outline:none;}
.cb-fl-box.ag{border-style:dashed;}
.cb-fl-box:is(:hover,:focus-visible){border-color:var(--ink);}
.cb-fl-k{font-family:var(--system);font-size:var(--s-ui);color:var(--dim);margin:0 0 1em;letter-spacing:.03em;}
.cb-fl-w{font-family:var(--system);font-size:var(--s-meta);color:var(--ink);margin:0 0 .4em;}
.cb-fl-l{font-family:var(--system);font-size:var(--s-ui);color:var(--mut);margin:0;line-height:1.6;}
.cb-fl-to{align-self:center;font-family:var(--system);font-size:var(--s-meta);color:var(--dim);}
.cb-flow .cb-buildfig{margin-top:5vh;}
.cb-fl-box[data-step]{cursor:pointer;}
.cb-fl-box.on{border-color:var(--ink);background:var(--mat);}
.cb-fl-box.on .cb-fl-k{color:var(--ink);}
.cb-build-txt pre.v{white-space:pre-wrap;font-family:var(--system);margin:0 0 .8em;}

@media (min-width:901px){ [data-view="systems/comfy-bridge"] .sys-product-open:has(.spec) .sys-product-fact.cb-flow{grid-column:1 / -1;grid-row:6;margin-top:7vh;justify-self:stretch;width:auto;} }
@media (max-width:900px){ .cb-fl-row{grid-template-columns:1fr;row-gap:.5em;} .cb-fl-to{transform:rotate(90deg);justify-self:start;margin-left:1em;} }
/* [fig. 2]: the six stages as a vertical rail beside the display — one figure */
.cb-flow .cb-buildfig{margin-top:0;}
.cb-fig2{display:grid;grid-template-columns:minmax(0,3fr) minmax(0,9fr);column-gap:var(--sys-gap);margin-top:var(--sys-label);align-items:start;}
.cb-rail{list-style:none;margin:0;padding:0;position:relative;}
.cb-rail::before{content:"";position:absolute;left:4px;top:1.1em;bottom:1.1em;width:1px;background:var(--line-strong);}
.cb-rail .cb-fl-box{position:relative;display:grid;grid-template-columns:1fr;row-gap:.25em;padding:.62em 0 .62em 26px;border:0;background:none;cursor:pointer;outline:none;}
.cb-rail .cb-fl-box::before{content:"";position:absolute;left:0;top:.9em;width:9px;height:9px;border:1px solid var(--mut);background:var(--ground);box-sizing:border-box;}
.cb-rail .cb-fl-box.ag::before{border-style:dashed;}
.cb-rail .cb-fl-box.on::before{background:var(--ink);border-color:var(--ink);border-style:solid;}
.cb-rail .k{font-family:var(--system);font-size:var(--s-ui);color:var(--dim);letter-spacing:.03em;}
.cb-rail .w{font-family:var(--system);font-size:var(--s-meta);color:var(--mut);}
.cb-rail .l{font-size:calc(var(--s-prose) * .72);line-height:1.4;color:var(--dim);}
.cb-rail .cb-fl-box:is(:hover,:focus-visible) .w{color:var(--hover);}
.cb-rail .cb-fl-box.on .w{color:var(--ink);}
.cb-rail .cb-fl-box.on .l{color:var(--ink);}
.cb-rail .cb-fl-box.on .k{color:var(--mut);}
.cb-fig2-main{min-width:0;}
.cb-fig2-main .cb-build-stage{margin-top:0;}
@media (max-width:900px){ .cb-fig2{grid-template-columns:1fr;row-gap:3vh;} }
/* [fig. 2] one illustration per stage, inside the frame; the stage boxes above switch them */
.cb-build-frame{aspect-ratio:2.5 / 1;}
.cb-st{position:absolute;inset:0;overflow:hidden;padding:22px;opacity:0;visibility:hidden;transition:opacity .35s var(--ease);display:grid;gap:22px;min-height:0;grid-auto-rows:minmax(0,1fr);}
.cb-st.on{opacity:1;visibility:visible;}
.cb-st figure{margin:0;min-height:0;display:flex;flex-direction:column;}
.cb-st img{display:block;width:100%;flex:1;min-height:0;object-fit:contain;object-position:left top;}
.cb-st-cap{font-family:var(--system);font-size:var(--s-ui);color:var(--dim);margin:0 0 10px;letter-spacing:.03em;}
.cb-st-lines{font-family:var(--system);font-size:11px;line-height:1.75;color:var(--mut);margin:0;white-space:pre-wrap;}
.cb-st-lines .ln{display:block;}
.cb-st-lines b{font-weight:400;color:var(--ink);}
.cb-st-lines .gap{display:block;height:.8em;}
.cb-st-read{grid-template-columns:68% minmax(0,1fr);}
.cb-st-prop{grid-template-rows:auto 1fr;}
.cb-st-brief{display:grid;align-content:start;border-top:1px solid var(--line);}
.cb-st-brief .r{display:grid;grid-template-columns:minmax(0,1.6fr) minmax(0,1fr);column-gap:24px;padding:9px 0;border-bottom:1px solid var(--line);align-items:baseline;}
.cb-st-brief pre{font-family:var(--system);font-size:11px;line-height:1.6;color:var(--ink);margin:0;white-space:pre-wrap;}
.cb-st-brief p{font-size:15px;color:var(--mut);margin:0;}
.cb-st-check{grid-template-rows:1fr auto;}
.cb-st-checks{font-family:var(--system);font-size:11px;display:grid;align-content:start;}
.cb-st-checks .r{display:grid;grid-template-columns:2.6em minmax(0,1fr) 13em 3em;padding:1px 0;border-bottom:1px solid var(--line);color:var(--ink);align-items:baseline;}
.cb-st-checks .c{font-family:var(--voice);font-size:13.5px;line-height:1.55;}
.cb-st-checks .k{color:var(--dim);}
.cb-st-checks .r.h .c{font-family:var(--system);font-size:11px;color:var(--dim);}
.cb-st-checks .n{color:var(--dim);}
.cb-st-checks .a,.cb-st-checks .b{text-align:center;}
.cb-st-checks .r.off .c{color:var(--mut);}
.cb-st-checks .r.stop{background:var(--mat);}
.cb-st-checks .r.h,.cb-st-checks .r.f{color:var(--dim);border-bottom:0;}
.cb-st-checks .r.f{border-top:1px solid var(--line-strong);padding-top:8px;}
.cb-st-checks .r.f .a,.cb-st-checks .r.f .b{color:var(--ink);}
.cb-st-err{font-family:var(--system);font-size:var(--s-ui);color:var(--mut);margin:0;line-height:1.6;}
.cb-st-change{grid-template-columns:1fr;}
.cb-st-change .to{align-self:center;font-family:var(--system);color:var(--dim);}
.cb-st-run{grid-template-rows:auto auto;grid-template-columns:minmax(0,1fr);align-content:center;}
.cb-st-prog .bar{display:grid;grid-template-columns:repeat(25,1fr);gap:3px;margin:0 0 8px;}
.cb-st-prog .bar i{display:block;height:8px;border:1px solid var(--line-strong);transition:background .12s linear,border-color .12s linear;}
.cb-st-prog .bar i.on{background:var(--ink);border-color:var(--ink);}
@media (max-width:900px){ .cb-build-frame{aspect-ratio:auto;} .cb-st{position:static;display:none;} .cb-st.on{display:grid;} .cb-st-read,.cb-st-change,.cb-st-report{grid-template-columns:1fr;} .cb-st-checks .r{grid-template-columns:2.2em minmax(0,1fr) 2em;} .cb-st-checks .k{display:none;} .cb-st-brief .r{grid-template-columns:1fr;} }
/* read stage: numbered nodes on the canvas, the same numbers on the lines the agent receives */
.cb-rd-canvas{min-height:0;}
.cb-rd-img{position:relative;width:100%;aspect-ratio:1240 / 680;}
.cb-rd-img img,.cb-rd-img svg{position:absolute;inset:0;width:100%;height:100%;}
.cb-rd-img .nb{fill:none;stroke:transparent;stroke-width:2;vector-effect:non-scaling-stroke;transition:stroke .25s var(--ease);}
.cb-rd-img .nb.hl{stroke:var(--ink);}
.cb-rd-img .tg rect{fill:var(--ground);stroke:var(--ink);stroke-width:1;vector-effect:non-scaling-stroke;}
.cb-rd-img .tg text{font-family:var(--system);font-size:24px;fill:var(--ink);}
.cb-rd-img .tg.hl rect{fill:var(--ink);} .cb-rd-img .tg.hl text{fill:var(--ground);}
.cb-rd-text{min-width:0;}
.cb-rd-lines{list-style:none;margin:0;padding:0;border-top:1px solid var(--line);}
.cb-rd-lines li{font-family:var(--system);font-size:11px;display:grid;grid-template-columns:22px 17ch minmax(0,1fr);column-gap:8px;align-items:center;padding:9px 0;border-bottom:1px solid var(--line);cursor:default;transition:background .25s var(--ease);}
.cb-rd-lines .n{font-family:var(--system);font-size:11px;color:var(--ink);border:1px solid var(--line-strong);height:20px;display:grid;place-items:center;transition:background .25s var(--ease),color .25s var(--ease);}
.cb-rd-lines .t{font-family:var(--system);font-size:11px;color:var(--mut);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.cb-rd-lines .v{font-family:var(--system);font-size:11px;color:var(--dim);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.cb-rd-lines li.hl{background:var(--mat);}
.cb-rd-lines li.hl .n{background:var(--ink);color:var(--ground);border-color:var(--ink);}
.cb-rd-lines li.hl :is(.t,.v){color:var(--ink);}
@media (max-width:900px){ .cb-st-read{grid-template-columns:1fr;} }
/* propose stage: the canvas as it stands, the agent's proposed nodes drawn dashed where they will go */
.cb-st-prop{grid-template-rows:none;}
.cb-prop{position:relative;align-self:center;width:100%;aspect-ratio:2000 / 800;}
.cb-prop img,.cb-prop svg{position:absolute;inset:0;width:100%;height:100%;}
.cb-prop .gn{fill:rgba(0,0,0,.25);stroke:var(--ink);stroke-width:1.5;stroke-dasharray:6 5;vector-effect:non-scaling-stroke;}
.cb-prop .gw{fill:none;stroke:var(--ink);stroke-width:1.5;stroke-dasharray:6 5;vector-effect:non-scaling-stroke;opacity:.8;}
.cb-prop .gt{font-family:var(--system);font-size:17px;fill:var(--ink);}
.cb-prop-l{position:absolute;font-family:var(--system);font-size:10.5px;color:var(--mut);white-space:nowrap;}
/* check stage: sixteen checks in two columns of eight; the ticks run through in order when the stage opens */
.cb-st-check{grid-template-rows:none;}
.cb-st-check .cb-st-checks{display:grid;grid-auto-flow:column;grid-template-rows:repeat(8,1fr);grid-template-columns:minmax(0,1fr) minmax(0,1fr);column-gap:40px;align-content:stretch;height:100%;}
.cb-st-check .cb-st-checks .r{display:grid;grid-template-columns:2.4em minmax(0,1fr) 2em;grid-template-areas:"n c b" "n k b";align-content:center;padding:0;border-bottom:1px solid var(--line);}
.cb-st-check .cb-st-checks .n{grid-area:n;align-self:center;color:var(--dim);}
.cb-st-check .cb-st-checks .c{grid-area:c;font-family:var(--voice);font-size:16px;line-height:1.3;color:var(--ink);}
.cb-st-check .cb-st-checks .k{grid-area:k;font-family:var(--system);font-size:10.5px;color:var(--dim);display:block;min-width:0;overflow-wrap:anywhere;}   /* Firefox: a long value must not widen its column */
.cb-st-check .cb-st-checks .b{grid-area:b;align-self:center;text-align:right;font-family:var(--system);font-size:14px;color:var(--ink);}
.cb-st-check.on .cb-st-checks .b{opacity:0;animation:cb-in .2s linear forwards;animation-delay:calc(.3s + var(--i) * .13s);}
@media (prefers-reduced-motion:reduce){ .cb-st-check.on .cb-st-checks .b{animation:none;opacity:1;} }
@media (max-width:900px){ .cb-st-check .cb-st-checks{grid-auto-flow:row;grid-template-columns:1fr;grid-template-rows:none;} }
/* report stage: the image large, Bridge's report beside it, rows arriving in turn */
.cb-st-report{grid-template-columns:auto minmax(0,1fr);column-gap:32px;}
.cb-rep-img{height:100%;aspect-ratio:1;}
.cb-rep-img img{width:100%;height:100%;object-fit:cover;}
.cb-rep-text{align-self:center;min-width:0;}
.cb-rep{list-style:none;margin:0;padding:0;border-top:1px solid var(--line);}
.cb-rep li{display:grid;grid-template-columns:11ch minmax(0,1fr);column-gap:16px;padding:12px 0;border-bottom:1px solid var(--line);align-items:baseline;}
.cb-rep .k{font-family:var(--system);font-size:var(--s-ui);color:var(--dim);letter-spacing:.03em;}
.cb-rep .v{font-family:var(--system);font-size:12px;color:var(--ink);overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.cb-st-report.on .cb-rep li{opacity:0;animation:cb-in .3s var(--ease) forwards;animation-delay:calc(.3s + var(--i) * .25s);}
@media (prefers-reduced-motion:reduce){ .cb-st-report.on .cb-rep li{animation:none;opacity:1;} }
@media (max-width:900px){ .cb-st-report{grid-template-columns:1fr;} .cb-rep-img{height:auto;} }
/* run stage: the finished canvas; the Save preview stays dark until the steps finish */
.cb-st-run{grid-template-rows:auto auto;grid-template-columns:minmax(0,1fr);align-content:center;}
.cb-run-top{display:flex;gap:22px;width:100%;min-width:0;}
.cb-runimg{position:relative;width:calc((100% - 22px) * 2.5 / 3.5);aspect-ratio:2000 / 800;flex:none;}
.cb-run-out{margin:0;width:calc((100% - 22px) / 3.5);aspect-ratio:1;flex:none;opacity:0;transform:scale(.98);transition:opacity .6s var(--ease),transform .6s var(--ease);border:1px solid var(--line);}
.cb-run-out img{display:block;width:100%;height:100%;object-fit:cover;}
.cb-st-run.done .cb-run-out{opacity:1;transform:none;}
.cb-runimg img,.cb-runimg svg{position:absolute;inset:0;width:100%;height:100%;object-fit:fill;}
.cb-added .pv{fill:rgb(38,39,41);}
.cb-runimg .pv{fill:rgb(38,39,41);transition:opacity .5s var(--ease);}
.cb-st-run.done .pv{opacity:0;}
/* change stage: the canvas as it was, then the two added nodes land and are outlined (runs each time the stage opens) */
.cb-added{position:relative;align-self:center;width:100%;aspect-ratio:2000 / 800;}
.cb-added img,.cb-added svg{position:absolute;inset:0;width:100%;height:100%;}
.cb-added .aft,.cb-added svg,.cb-added-l{opacity:0;}
.cb-st-change.on .aft{animation:cb-in .7s var(--ease) .8s forwards;}
.cb-st-change.on svg,.cb-st-change.on .cb-added-l{animation:cb-in .5s var(--ease) 1.6s forwards;}
.cb-st-change.on .cb-added-b{animation:cb-out .4s var(--ease) .8s forwards;}
@keyframes cb-in{to{opacity:1;}}
@keyframes cb-out{to{opacity:0;}}
.cb-added .dim{fill:var(--ground);opacity:.45;}
.cb-added .ring{fill:none;stroke:var(--ink);stroke-width:2;vector-effect:non-scaling-stroke;}
.cb-added-l,.cb-added-b{position:absolute;font-family:var(--system);font-size:var(--s-ui);background:var(--ground);padding:2px 6px;color:var(--ink);}

.cb-added-b{left:1%;top:8px;}
@media (prefers-reduced-motion:reduce){ .cb-st-change.on :is(.aft,svg,.cb-added-l){animation:none;opacity:1;} .cb-st-change.on .cb-added-b{animation:none;opacity:0;} }
/* the line under the frame: that stage's real output, and next */
.cb-build-bar{display:flex;justify-content:space-between;align-items:baseline;gap:2em;margin-top:12px;color:var(--mut);}
.cb-out{display:none;} .cb-out.on{display:inline;}
.cb-next{background:none;border:0;padding:0;color:var(--mut);cursor:pointer;flex:none;}
.cb-next:hover{color:var(--hover);}
/* [fig. 1] what it does, for any model and any workflow: proposal → Bridge → canvas, the refusal looping back */
.cb-spec-wrap{background:var(--ground);}
.cb-spec-wrap::after{display:none;}
.cb-spec{position:absolute;inset:0;width:100%;height:100%;overflow:visible;}
.cb-spec text{font-family:var(--system);font-size:9px;fill:var(--mut);}
.cb-spec .hd{font-family:var(--voice);font-size:13px;fill:var(--ink);}
.cb-spec .mono{font-size:9px;fill:var(--dim);}
.cb-spec .ink{fill:var(--ink);}
.cb-spec .lb{font-size:9px;fill:var(--dim);letter-spacing:.04em;}
.cb-spec .lb .n{fill:var(--ink);}
.cb-spec .bx{fill:none;stroke:var(--line-strong);}
.cb-spec .gate{fill:none;stroke:var(--ink);stroke-width:1.5;}
.cb-spec .tk{fill:var(--ink);}
.cb-spec .ar{fill:none;stroke:var(--ink);stroke-width:1;}
.cb-spec .ah{fill:none;stroke:var(--ink);stroke-width:1;}
.cb-spec .ar.back,.cb-spec .ah.back{stroke-dasharray:3 2;}
.cb-spec .cv{fill:none;stroke:var(--line-strong);}
.cb-spec .cvg{fill:url(#cb-dots);}
.cb-spec .dt{fill:var(--line-strong);}
.cb-spec .nd rect{fill:var(--ground);stroke:var(--line-strong);}
.cb-spec .nd line{stroke:var(--line);}
.cb-spec .nd text{font-size:8.5px;fill:var(--mut);}
.cb-spec .nd circle{fill:var(--ground);stroke:var(--mut);}
.cb-spec .nd.new rect{stroke:var(--ink);stroke-width:1.5;}
.cb-spec .nd.new text{fill:var(--ink);}
.cb-spec .nd.new circle{stroke:var(--ink);}
.cb-spec .wr{fill:none;stroke:var(--mut);stroke-width:1;}
.cb-spec .wr.new{stroke:var(--ink);stroke-width:1.5;}
.cb-spec .fl{fill:none;stroke:var(--mut);}
.cb-spec .code{font-family:var(--system);font-size:10.5px;fill:var(--ink);}
.cb-spec .rule{stroke:var(--line);}
.cb-spec .bar{fill:var(--line);stroke:none;}
.cb-spec .nd.new .bar{fill:var(--line-strong);}
/* the home field's copy of fig. 1 is line work on the field: no panel, no filled nodes, so the field shows through */
/* the systems field's Comfy Bridge picture: the canvas alone, nodes and wires, the output filled */
.cb-nodes{position:absolute;inset:0;width:100%;height:100%;}
.cb-nodes .nd.on{fill:var(--ink);stroke:var(--ink);}
.cb-spec .nn{font-family:var(--system);font-size:8px;fill:var(--dim);}
.cb-spec .nn.new{fill:var(--ink);}
/* fig. 1 states: all (still) · read (graph → text: left lit, node 5 not yet there) · write (text → graph: right lit, node 5 draws in) */
.cb-ess :is(.rd,.wt,.old,.nw5){transition:opacity .35s var(--ease);}
.cb-ess .hit{fill:transparent;cursor:pointer;outline:none;}
.cb-ess[data-state="read"] .wt,.cb-ess[data-state="write"] .rd{opacity:.18;}
.cb-ess[data-state="read"] .nw5{opacity:0;}
.cb-ess[data-state="read"] .old :is(rect,circle){stroke:var(--ink);}
.cb-ess[data-state="read"] .old .wr{stroke:var(--ink);}
.cb-ess[data-state="read"] .old .nn{fill:var(--ink);}
.cb-ess[data-state="write"] .old{opacity:.45;}
.cb-ess[data-state="write"] .nw5 :is(.wr,rect){stroke-dasharray:420;stroke-dashoffset:420;animation:cb-draw .9s var(--ease) forwards;}
@keyframes cb-draw{to{stroke-dashoffset:0;}}
@media (prefers-reduced-motion:reduce){ .cb-ess *{transition:none!important;animation:none!important;} .cb-ess[data-state="write"] .nw5 :is(.wr,rect){stroke-dashoffset:0;} }
/* head figure: the real canvas with a drawn layer — step tags on the nodes, the last change outlined, and a card for
   what crossed the bridge. The card is annotation in the site's own type, never an imitation of ComfyUI. */
.cb-hero{margin:0 0 var(--sys-section);}
.cb-hero > .cb-lab{margin:0 0 var(--sys-label);}
.cb-hero-canvas{position:relative;border:1px solid var(--line);container-type:inline-size;}
.cb-hero-canvas img{display:block;width:100%;height:auto;}
.cb-hero-ov{position:absolute;inset:0;width:100%;height:100%;pointer-events:none;overflow:visible;}
.cb-hero-ov .hl{fill:none;stroke:var(--ink);stroke-width:2;vector-effect:non-scaling-stroke;}
.cb-hero-ov .lead{fill:none;stroke:var(--ink);stroke-width:1;vector-effect:non-scaling-stroke;}
.cb-hero-ov .dot{fill:var(--ink);}
.cb-hero-ov .tg rect{fill:var(--ground);stroke:var(--ink);stroke-width:1;vector-effect:non-scaling-stroke;}
.cb-hero-ov .tg text{font-family:var(--system);font-size:12px;fill:var(--ink);}
.cb-hero-card{position:absolute;left:44%;top:62%;width:18.6%;background:var(--ground);border:1px solid var(--ink);padding:.9cqw 1cqw .8cqw;}
.cb-hero-card .meta{font-size:clamp(8px,.68cqw,12px);}
.cb-hc-k{color:var(--dim);margin:0 0 .5em;}
.cb-hc-k b{font-weight:400;color:var(--ink);margin-right:.5em;}
.cb-hc-ask{font-size:clamp(11px,1.02cqw,17px);line-height:1.35;color:var(--ink);margin:0 0 .9em;}
.cb-hc-checks{display:grid;grid-template-columns:repeat(16,1fr);gap:.18cqw;margin:.2em 0 .8em;}
.cb-hc-checks i{display:block;aspect-ratio:1;border:1px solid var(--ink);background:var(--ink);}
.cb-hc-v{color:var(--ink);margin:0;}
.cb-hero-cap{color:var(--dim);margin-top:var(--sys-label);display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);}
.cb-hero-cap span{grid-column:1 / 8;line-height:1.7;}
@media (max-width:900px){ .cb-hero-card{position:static;width:auto;min-width:0;border:0;border-top:1px solid var(--line);} .cb-hero-ov .lead,.cb-hero-ov .dot{display:none;} .cb-hero-cap span{grid-column:1 / -1;} }
/* [fig. 1] one build: a frame per step, the step's proposal and verdict beside it, steps beneath */
.cb-build-stage{display:block;margin-top:var(--sys-label);}
.cb-build-frame{position:relative;aspect-ratio:1800 / 719;border:1px solid var(--line);background:var(--ground);}
.cb-build-img{position:absolute;inset:0;width:100%;height:100%;object-fit:contain;opacity:0;transition:opacity .35s var(--ease);}
.cb-build-img.on{opacity:1;}
.cb-build-txt{display:none;}
.cb-build-txt.on{display:block;}
.cb-build-txt .k{color:var(--dim);margin:0 0 1em;}
.cb-build-txt .prop{font-size:calc(var(--s-prose) * .8);line-height:1.5;color:var(--ink);margin:0 0 1em;}
.cb-build-txt .v{color:var(--mut);line-height:1.7;margin:0 0 .8em;word-break:break-word;}
.cb-build-txt.r .v{color:var(--ink);}
.cb-build-txt .rec{color:var(--dim);margin:0;}
.cb-build-steps{display:flex;flex-wrap:wrap;gap:.4em 1.8em;margin-top:2.4vh;border-top:1px solid var(--line);padding-top:1.2em;}
.cb-build-steps button{background:none;border:0;padding:0;font:inherit;color:var(--dim);cursor:pointer;}
.cb-build-steps button:hover{color:var(--hover);}
.cb-build-steps button.on{color:var(--ink);}
.cb-build-steps button.on::before{content:"■ ";color:var(--accent);}
@media (max-width:900px){ .cb-build-stage{grid-template-columns:1fr;row-gap:3vh;} }
.cb-grabs{display:grid;grid-template-columns:minmax(0,1.301fr) minmax(0,2.339fr);column-gap:var(--sys-gap);margin-top:6vh;align-items:start;}
.cb-grabs figure{margin:0;}
.cb-grabs img{display:block;width:100%;height:auto;border:1px solid var(--line);}
.cb-grabs figcaption{color:var(--dim);margin-top:var(--sys-label);}
@media (max-width:760px){ .cb-grabs{grid-template-columns:1fr;row-gap:4vh;} }
.cb-gates{margin-top:6vh;}
.cb-gates .pass{stroke:var(--mut);stroke-width:1;}
.cb-gates .tick{fill:var(--ground);stroke:var(--mut);}
.cb-gates .stop{fill:none;stroke:var(--ink);stroke-width:1.5;}
.cb-gates .col{transition:opacity .3s var(--ease);}
.cb-gates[data-rev] .col{opacity:.28;}
.cb-gates[data-rev="0"] .col,.cb-gates .col.on{opacity:1;}
.cb-gates .col.on .pass{stroke:var(--ink);} .cb-gates .col.on .tick{stroke:var(--ink);}
@media (min-width:901px){
  [data-view="systems/comfy-bridge"] .sys-product-open{margin-bottom:var(--sys-section);}
  [data-view="systems/comfy-bridge"] .sys-product-specimen{grid-column:8/13;grid-row:1/6;}
  [data-view="systems/comfy-bridge"] .sys-product-open:has(.spec) .sys-product-fact{grid-column:1 / 10;grid-row:5;justify-self:start;width:max-content;white-space:nowrap;margin-top:1vh;}
  .cb-sec{display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);align-items:start;}
  .cb-sec > .display{grid-column:1 / 4;}
  [data-view="systems/comfy-bridge"] .lle-flow{grid-template-columns:repeat(5,minmax(0,1fr) auto) minmax(0,1fr);}   /* six stages, not five */
  .cb-sec > :is(.cb-text,.cb-meta){grid-column:4 / 9;}
  .cb-sec > :is(.stepper,.cb-wide){grid-column:1 / -1;}
}

/* principles — tight name list (col 1) + evidence lane (col 2) */
.sys-principles{
  margin:3vh 0 0;padding-top:1.6em;
  border-top:1px solid var(--line);
}
.sys-principles-layout{
  display:grid;grid-template-columns:minmax(0,0.8fr) minmax(0,1.5fr);
  column-gap:3vw;align-items:start;
}

/* index — tight list in column 1 */
.sys-principles-index{list-style:none;margin:0;padding:0;grid-column:1;grid-row:1;}
.sys-principle-item{border-bottom:1px solid var(--line);}
.sys-principles-index .index-row{
  display:block;width:100%;text-align:left;
  background:none;border:0;
  grid-template-columns:none;gap:0;
  padding:.6em 0;cursor:pointer;font:inherit;color:inherit;
}
.sys-principles-index .ix-title{
  font-family:var(--system);font-size:var(--s-ui);font-weight:400;
  color:var(--dim);letter-spacing:.05em;line-height:1.2;
  transition:color .15s var(--ease),transform .22s var(--ease);
}
.sys-principles-index .index-row:hover .ix-title,
.sys-principles-index .index-row:focus-visible .ix-title{color:var(--hover);transform:translateX(6px);}
.sys-principles-index .index-row:focus-visible{outline:none;}
.sys-principles-index .index-row.row-on .ix-title{color:var(--ink);}
.sys-principles-index .index-row.row-on .ix-title::before{
  content:"";display:inline-block;width:6px;height:6px;
  background:var(--accent);margin-right:.6em;vertical-align:middle;
}

/* evidence lane — column 2; each block top-aligned to its name via JS */
.sys-principles-evidence{
  grid-column:2;grid-row:1;
  position:relative;align-self:stretch;
  min-height:0;
}
.sys-principle-cl{
  position:absolute;left:0;right:0;
  opacity:0;visibility:hidden;pointer-events:none;
  z-index:1;transform:none;
}
.sys-principle-cl.focus{
  opacity:1;visibility:visible;z-index:2;
}
.view.cluster-active .sys-principle-cl{transform:none;}
.sys-cl-name{display:none;}
.sys-principle-name{
  font-family:var(--system);font-size:var(--s-ui);font-weight:400;
  color:var(--mut);letter-spacing:.05em;margin-bottom:.55em;line-height:1.2;
}
.sys-principle-body{
  font-size:var(--s-prose);
  margin-bottom:0;max-width:60ch;line-height:1.55;color:var(--ink);
  min-height:calc(2 * 1.55em);text-wrap:balance;
}

/* ============ STEPPER ============ */
.stepper{margin-top:3vh;border-top:1px solid var(--line);padding-top:1.6em;}
.step-track{display:flex;gap:2em;flex-wrap:wrap;margin-bottom:2em;}
.step-track button{font-family:var(--system);font-size:var(--s-meta);color:var(--mut);letter-spacing:.04em;}
.step-track button:hover{color:var(--ink);}
.step-track button.on{color:var(--ink);}
.step-track button.on::before{content:"";display:inline-block;width:6px;height:6px;background:var(--accent);margin-right:.5em;}
.step-stage .step-img{width:100%;transition:opacity .25s var(--ease);}
.step-stage .step-img.swap{opacity:0;}
/* a drawn pipeline: the active stage's outline and name fade up in place, the last one's fade down */
[data-view="systems/material-generator"] .lle-flow span{transition:color .45s var(--ease),border-color .45s var(--ease);}
.step-text{max-width:52ch;margin-top:1.4em;min-height:3.2em;}
.step-next{margin-top:.8em;color:var(--mut);border-bottom:1px solid var(--line);}
.step-next:hover{color:var(--ink);border-color:var(--ink);}

/* ============ CASCADE + REVEALS ============ */
.cascade span{display:block;opacity:0;transform:translateY(8px);transition:opacity .3s var(--ease),transform .3s var(--ease);}
.cascade.landed span{opacity:1;transform:none;}
.cascade.landed span:nth-child(1){transition-delay:0s;}
.cascade.landed span:nth-child(2){transition-delay:.06s;}
.cascade.landed span:nth-child(3){transition-delay:.12s;}
.cascade.landed span:nth-child(4){transition-delay:.18s;}
.reveal{opacity:0;transform:translateY(10px);transition:opacity .4s var(--ease),transform .4s var(--ease);}
.reveal.landed{opacity:1;transform:none;}
.reveal-clip{clip-path:inset(100% 0 0 0);transition:clip-path .5s var(--ease);}
.reveal-clip.landed{clip-path:inset(0 0 0 0);}
.reveal-slow{opacity:0;transition:opacity .6s var(--ease);}
.reveal-slow.landed{opacity:1;}

@media (prefers-reduced-motion: reduce){
  *,*::before,*::after{transition:none!important;animation:none!important;}
  .zone .el,.reveal,.reveal-clip,.reveal-slow,.cascade span,[data-chars] .ch{opacity:1!important;transform:none!important;clip-path:none!important;}
  [data-plane]{transform:none!important;}
  .preview{display:none!important;}
  /* specification viewer becomes manually stepped and cuts between states */
  .spec-viewer-line{
    opacity:1!important;transform:none!important;filter:none!important;
    animation:none!important;
  }
  .spec-viewer-scan{display:none!important;}
  .vt-row,.vt-verdict,.vt-block,.vt-summary-item,.vt-render-limit{
    opacity:1!important;transform:none!important;filter:none!important;
    transition:none!important;
  }
  .vt-scan{display:none!important;}
  .procnote .pn-cap{opacity:1!important;}
  /* principles fall back to static stacked name + body blocks */
  .sys-principles-layout{display:block;}
  .sys-principles-index .index-row{display:none;}
  .sys-principles-evidence{position:static;min-height:0!important;}
  .sys-principle-cl{
    position:static;left:auto;right:auto;top:auto!important;
    opacity:1!important;visibility:visible!important;
    pointer-events:auto;margin-bottom:1.6em;
  }
  .sys-principle-body.reveal-clip{clip-path:none!important;}
  .sys-cl-name{display:block;}
  .ph.has-seq-vid .vid{display:none;}
}

@media (max-width:900px){
  .stagewrap{height:auto;}
  .stage{position:static;height:auto;overflow:visible;padding:calc(var(--top-h) + 30px) var(--mx) 8vh;}
  .splane{position:static !important;opacity:1 !important;transform:none !important;width:100% !important;margin-bottom:6vh;display:block;}
  .zone{height:auto !important;padding:4vh var(--mx) !important;}
  /* a page's first zone starts below the fixed header and the 26px rail bar, not under them */
  .view > .zone:first-child{padding-top:calc(var(--top-h) + 26px + 4vh) !important;}
  .el{position:static !important;width:100% !important;margin-bottom:6vh;transform:none !important;opacity:1 !important;}
  .giant{font-size:clamp(34px,10vw,54px);}
  .rail{flex-direction:row;top:var(--top-h);left:0;right:0;height:26px;align-items:center;padding:0 var(--mx);gap:1.4em;background:var(--ground);}
  .registers{gap:1em;font-size:var(--s-ui);}
  /* index rows: the meta column cannot wrap and reserves its widest readout, so on a phone
     it pushed the page wider than the screen — it drops under the title instead */
  .index-row{grid-template-columns:2.6em minmax(0,1fr);row-gap:.35em;}
  .ix-meta,
  :is(#home-index,#home-sysindex) .index-row[data-subject]:not(.disabled):not(:has(.ix-meta[data-alt])) .ix-meta{grid-row:2;grid-column:2;text-align:left;}
  :is(#home-index,#home-sysindex) .index-row[data-subject]:not(.disabled):not(:has(.ix-meta[data-alt]))::after,
  :is(#home-index,#home-sysindex) .index-row:not(.disabled) .ix-meta[data-default]::after{display:none;}
  .preview{display:none;}
  /* principles drop the index+stage mechanic — stacked name + body blocks */
  .sys-principles-layout{display:block;}
  .sys-principles-index .index-row{display:none;}
  .sys-principles-evidence{position:static;min-height:0!important;}
  .sys-principle-cl{
    position:static;left:auto;right:auto;top:auto!important;
    opacity:1!important;visibility:visible!important;
    pointer-events:auto;margin-bottom:1.6em;
  }
  .sys-principle-body.reveal-clip{clip-path:none!important;}
  .sys-cl-name{display:block;}
  .syspage{padding:calc(var(--top-h) + 26px + 4vh) var(--mx) 10vh;}   /* clears the rail bar like the zones */
  .sys-block{margin-bottom:9vh;}
  /* collapse every systems grid to a single column; evidence stops floating */
  .sys-open,.sys-case,.sys-films,.sys-product-open,.lle-evidence,.lle-library{grid-template-columns:1fr;}
  .sys-lead,.sys-open-spec,
  .sys-film-main,.sys-score,
  .sys-film,.sys-case-no,.sys-product-open .display,.sys-product-lead,.sys-product-fact,.sys-product-specimen,
  .lle-evidence-card:nth-child(1),.lle-evidence-card:nth-child(2),.lle-evidence-card:nth-child(3),.lle-evidence-card:nth-child(4){
    grid-column:1/-1;grid-row:auto;
  }
  .sys-open{margin-bottom:7vh;}
  .sys-open-spec{margin-top:6vh;width:100%;justify-self:stretch;}
  .sys-score{margin-top:6vh;}
  .sys-films{row-gap:6vh;}
  .sys-film:nth-child(2){margin-top:0;}
  .sys-product-fact{margin-top:4vh;}
  .sys-product-specimen{margin-bottom:4vh;}
  .lle-layers{grid-template-columns:1fr;margin-bottom:9vh;}
  .lle-layer{padding:1.6em 0;}
  .lle-layer + .lle-layer{border-left:0;border-top:1px solid var(--line);padding-left:0;}
  .lle-flow,.process-card .lle-flow{
    display:flex;flex-direction:column;min-height:0;
  }
  .lle-flow i{transform:rotate(90deg);padding:.2em 0;}
  .lle-flow span small{margin-top:.6em;}
  .lle-evidence{row-gap:4vh;}
  .lle-evidence-card:nth-child(2),.lle-evidence-card:nth-child(3),.lle-evidence-card:nth-child(4){margin-top:0;}
  .lle-spec-pair .lle-spec-body{grid-template-columns:1fr;}
  .lle-spec-frame{margin-top:1.6em;}
  .lle-library{grid-template-columns:repeat(3,1fr);column-gap:3vw;margin-bottom:9vh;width:auto;margin-left:0;}
  .lle-library-cell:nth-child(1),
  .lle-library-cell:nth-child(2),
  .lle-library-cell:nth-child(3){grid-column:auto;margin-top:0;}
  .lle-library-cap{grid-column:1/-1;}
  .lle-provenance-items{grid-template-columns:1fr;}
  .lle-provenance-item{padding:1.6em 0;}
  .lle-provenance-item + .lle-provenance-item{border-left:0;border-top:1px solid var(--line);padding-left:0;}
  .whl-grid{grid-template-columns:1fr 1fr;}
  .rst-sec{margin-bottom:9vh;}
  .rst-heads{order:9;margin:5vh 0 0;}
  .pps-sec{margin-bottom:9vh;}
  .pps-sec > :is(.pps-pl,.pps-fig,.pps-doc,.pps-nodetable,.stepper){margin-top:4vh;}
  .pps-nodetable tbody th{white-space:normal;}
  .pps-directed .sw-tick{white-space:nowrap;}
  .pps-directed .sw-tick:not(.on){color:transparent;}   /* six names do not fit a phone: the marks stay, the current name shows */
  .pps-nodetable th,.pps-nodetable td{padding-right:.9em;}
  .cb-sec{margin-bottom:9vh;}
  .cb-sec > :is(figure,.stepper){margin-top:4vh;}
  .residue-card{max-width:none;}
  .residue-profile{position:static;width:100%;max-width:none;min-width:0;margin:0 0 6vh;}
  .residue-verdicts{max-width:none;min-width:0;width:100%;}
  .z-notes{min-height:0;}
  .studio-notes,.notes-next{margin-left:0;margin-top:0;}
  .z-grid .zone-note{max-width:46ch;}
  .z-grid .vgrid-wrap{margin-top:0;}
  .grid-search{margin:0;width:100%;}
  /* specification viewer stays a single state; tap/keys advance */
  .spec-viewer-frame{height:468px;}
  .spec-viewer-head{min-height:58px;padding:12px 14px;font-size:9px;}
  .spec-viewer-window{height:368px;margin:10px 10px 0;}
  .spec-viewer-meta{padding:14px 14px 0;}
  .spec-viewer-content{min-height:310px;padding:24px 14px 16px;}
  .spec-viewer-copy{font-size:14px;}
  .spec-viewer-row{grid-template-columns:88px minmax(0,1fr);gap:10px;}
  .spec-viewer-key{font-size:9px;}
  .spec-viewer-value{font-size:10px;}
  /* validator trace — same shell as specification viewer */
  .vt-frame{height:468px;}
  .vt-head{min-height:58px;padding:12px 14px;font-size:9px;}
  .vt-window{height:368px;margin:10px 10px 0;}
  .vt-batch,.vt-summary{padding:14px 14px 16px;}
  .vt-block{grid-template-columns:1fr;gap:4px;}
  .vt-summary-grid{grid-template-columns:1fr;}
  .vt-summary-item{border-right:0;border-bottom:1px solid var(--line);}
  .vt-summary-item:last-child{border-bottom:0;}
  .procnote .pn-cap{opacity:1;}
  .procnote{white-space:normal;}   /* no hover on a phone: the names show, and may wrap */
  .syspage [data-plane]{transform:none!important;}
  .procnote .pn-no{white-space:nowrap;}   /* a label's number never splits: "[doc. 3]" stays whole */
  .credits{margin-left:0;}   /* its desktop inset pushed the page wider than the screen */
  .biglink.xl{font-size:clamp(20px,6.4vw,28px);}   /* the email address fits the screen */
  .grid-search{margin-top:4vh;}   /* clear of the grid's readout, which wraps to two lines here */
  #sp-sys3 .ph{min-height:0;}   /* the canvas strip is under 60px tall here; the minimum height widened it past its column */
  /* an enlarged grid frame takes the whole screen on a phone, sized to fit either way up; a tap closes it */
  .el:has(.vgrid-wrap){will-change:auto;}   /* nothing moves here, and the hint would pin the full-screen frame to its column */
  .vgrid-zoom{position:fixed;z-index:200;background:var(--ground);padding:0 var(--mx);transition:background-color .3s var(--ease);}
  .vgrid-wrap:not(.zoomed) .vgrid-zoom{background:transparent;}   /* closing: the page shows while the frame returns to its cell */
  .vgrid-zoom .zoom-img{width:min(100%, calc((100dvh - 150px) * .8));}
  /* a diagram is drawn for 1200px. On a phone it keeps a readable size and scrolls sideways in its frame;
     its label stays put */
  :is(.whl-arch,.bns-arch,.cb-arch){overflow-x:auto;}
  :is(.whl-arch,.bns-arch,.cb-arch) .diagram{width:1000px;max-width:none;}
  :is(.whl-arch,.bns-arch,.cb-arch) > .procnote{position:sticky;left:0;}
}

/* ============ B7 ADDITIONS ============ */
/* preview window: the image inside answers the cursor too */
.preview .ph img,.preview .ph::after{transition:transform .2s var(--ease);}
/* Work loupe — magnified crop tracks cursor (focal eased in script.js) */
.preview.loupe .ph img{inset:0 auto auto 0;max-width:none;object-fit:fill;transform-origin:0 0;will-change:transform;backface-visibility:hidden;transition:none;}
.preview.loupe .ph::after{transition:transform .2s var(--ease);}
.workpiece{transition:opacity .3s var(--ease);scroll-margin-top:14vh;}   /* /archive#work-0N lands where the script places it */

/* ============ B9 ADDITIONS ============ */
/* the state watermark — typographic field marker, barely there */
.watermark{
  font-family:var(--voice);font-weight:700;font-size:17vw;line-height:1;
  letter-spacing:.02em;text-transform:uppercase;white-space:nowrap;
  color:transparent;-webkit-text-stroke:1px color-mix(in srgb,var(--mut) 16%,transparent);   /* the mode's own grey (was a fixed grey that stayed Record's on Bone) */
  user-select:none;
}

/* index titles breathe on hover */
.index-row:hover .ix-title{letter-spacing:.012em;}

/* work: serial numerals surface on hover; stronger zoom */
.workno{
  position:absolute;right:3%;top:-0.34em;z-index:3;
  font-family:var(--system);font-weight:700;font-size:7vw;line-height:1;
  color:transparent;-webkit-text-stroke:1px color-mix(in srgb,var(--mut) 40%,transparent);
  opacity:0;transform:translateY(14px);
  transition:opacity .3s var(--ease),transform .35s var(--ease);
  pointer-events:none;
}
.workpiece:hover .workno{opacity:1;transform:translateY(0);}
.wn-frame{
  font-size:.30em;
  font-weight:inherit;
  color:transparent;
  -webkit-text-stroke:1px color-mix(in srgb,var(--mut) 40%,transparent);
  letter-spacing:.06em;
  vertical-align:baseline;
}
/* archive / work hover — fine pointer only; touch overrides below */
@media (hover:hover) and (pointer:fine){
  .workpiece .ph:hover img{opacity:.68;transform:scale(1.07) translateY(-1.8%);}   /* only the image under the cursor — a work can hold more than one */
  .docpage:has(.workpiece:hover) .workpiece:not(:hover){opacity:.55;transition:opacity .3s var(--ease);}
  .lle-library:has(.workpiece:hover) .lle-library-cell:not(:hover){opacity:.55;transition:opacity .3s var(--ease);}
}
@media (hover:none),(pointer:coarse){
  .workpiece .ph img{opacity:1!important;transform:none!important;}
  .workno{opacity:0!important;transform:translateY(14px)!important;}
  .workpiece:not(:hover){opacity:1!important;}
}

/* ============================================================
   BONE — the printed record (data-mode="bone" on <body>)
   Work + Studio render as paper; motion is gated in script.js.
   ============================================================ */
[data-mode="bone"]{
  --ground:#f5f2ea;
  --ground-2:#ece8de;
  --ink:#1d1b16;
  --mut:#6f6a5f;
  --dim:#a39b89;
  --accent:#c23a20;
  --line:#d9d3c6;
  --line-strong:#c5beac;
  --hover:#000000;
  --mat:#efebe1;
  --mat-2:#e8e2d4;
}
/* Bone is monochrome: markers and hovers return to ink (the red
   that remains is the china-pencil annotation, applied case by case) */
[data-mode="bone"] .textlink:hover{border-color:var(--ink);}
[data-mode="bone"] .ph::after{color:var(--dim);}

/* residue artefacts — the evidence register: dark mats, hairline rules.
   The home splane artefact prints keep their paper mats; study residue
   matches the Systems evidence boxes. */
.card .ph{background:var(--paper);border:1px solid var(--line-strong);outline:none;}
.card .ph::after{color:color-mix(in srgb,var(--paper-ink) 60%,var(--paper));}   /* a label on the paper mat, from the paper tokens */
.card .spec-frag{background:var(--mat);border:1px solid var(--line);padding:20px 22px;}
.spec-frag pre{white-space:pre-wrap;margin:8px 0 0;font-family:var(--system);font-size:11px;line-height:1.6;color:var(--mut);}

/* selecting text is a live act */
::selection{background:var(--accent);color:var(--ground);}
:focus-visible{outline:1px solid var(--accent);outline-offset:3px;}

/* ============================================================
   WORK — document flow (Bone register)
   Record pages are operated fields; Bone pages are printed
   documents. Documents stack: no absolute coordinates, heights
   come from content, text can grow without collisions.
   ============================================================ */
.docpage{padding:calc(var(--top-h) + 8vh) var(--mx) 12vh;}
.doc-head{margin-bottom:9vh;}

.docpage .workpiece{
  position:relative;
  display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;
  align-items:start;
  margin-bottom:17vh;
}
/* alternating asymmetry — composition without coordinates */
.wp-a .wp-img{grid-column:1/9;}
.wp-a .wp-text{grid-column:10/13;}
.wp-b .wp-img{grid-column:5/13;grid-row:1;}
.wp-b .wp-text{grid-column:1/4;grid-row:1;}
.wp-text{padding-top:5vh;}
.wp-cap{margin-top:10px;}
.wp-year{color:var(--dim);margin-bottom:1.1em;}
.wp-read{font-size:15px;line-height:1.65;color:var(--ink);max-width:36ch;}

/* serial numeral sits over the image corner, never over text */
.docpage .workno{right:auto;left:-.06em;top:-.42em;}
.wp-b .workno{left:auto;right:-.06em;}

@media (max-width:900px){
  .docpage .workpiece{grid-template-columns:1fr;}
  .wp-a .wp-img,.wp-b .wp-img,.wp-a .wp-text,.wp-b .wp-text{grid-column:1/-1;grid-row:auto;}
  .wp-text{padding-top:2vh;}
  .docpage .workpiece{margin-bottom:10vh;}
}

/* the record — the archive's chronology, one row away from the archive page (agreed 12 Oct 2026).
   One list by year on the archive's 12 columns: year · kind · entry · place. Years, kinds and
   marks in System; names in Voice. */
.chron-year{display:grid;grid-template-columns:repeat(12,minmax(0,1fr));column-gap:2vw;align-items:baseline;border-top:1px solid var(--line);padding:1.5em 0 1.1em;}
.chron-y{grid-column:1/2;font-family:var(--system);font-size:var(--s-meta);font-weight:400;letter-spacing:.03em;color:var(--ink);font-variant-numeric:tabular-nums;white-space:nowrap;}
.chron-year ul{grid-column:2/13;}
.chron-row{display:grid;grid-template-columns:repeat(11,minmax(0,1fr));column-gap:2vw;align-items:baseline;padding:.42em 0;font-size:15px;line-height:1.5;color:var(--mut);}
.chron-k{grid-column:1/3;font-family:var(--system);font-size:var(--s-meta);letter-spacing:.03em;color:var(--dim);}
.chron-e{grid-column:3/8;}
.chron-p{grid-column:8/11;}
.chron-j{grid-column:11/12;justify-self:end;font-family:var(--system);font-size:var(--s-meta);color:var(--dim);text-align:right;white-space:nowrap;}
/* ink opens (chosen 12 Oct 2026): a row that opens something — a work, a text, a document, an article —
   is in ink, with what it opens named at the right; a row that opens nothing is grey. No underlines. */
a.chron-row .chron-e,a.chron-row .chron-p,a.chron-row .chron-j{color:var(--ink);}
a.chron-row:hover .chron-k,a.chron-row:focus-visible .chron-k{color:var(--ink);}
.chron + .arch-row{margin-top:14vh;}
@media (max-width:900px){
  .chron-year{grid-template-columns:1fr;row-gap:.6em;}
  .chron-y,.chron-year ul{grid-column:1/-1;}
  .chron-row{grid-template-columns:1fr;padding:.6em 0;}
  .chron-k,.chron-e,.chron-p{grid-column:1/-1;}
  .chron-j{grid-column:1/-1;justify-self:start;text-align:left;}
}

/* ============ PANORAMA DOOR ============
   A still that opens, in place, into the live 360 — restrained until entered. */
.ph[data-reel]{cursor:pointer;}

/* hover cue — shown only when the next click steps into the panorama */
.ph .pano-enter{
  position:absolute; left:12px; bottom:12px; z-index:2;
  font-family:var(--system); font-size:var(--s-ui); letter-spacing:.14em;
  text-transform:uppercase; color:var(--ink); background:rgba(11,11,13,.5);
  padding:5px 9px; opacity:0; transform:translateY(4px); pointer-events:none;
  transition:opacity .3s var(--ease), transform .3s var(--ease);
}
.ph.next-pano:hover .pano-enter{opacity:1; transform:none;}
.ph.pano-open .pano-enter{opacity:0;}

/* the live viewer — fades in over the still, fills the frame in place */
.ph .pano-frame{
  position:absolute; inset:0; width:100%; height:100%; border:0; z-index:1;
  background:#0b0b0d; opacity:0; pointer-events:none;
  transition:opacity .5s var(--ease);
}
.ph.pano-open .pano-frame{opacity:1; pointer-events:auto;}
.ph.pano-open > img{opacity:0;}
/* a film in the reel (@film:) — the whole 16:9 frame across the photograph's width, black bands
   above and below as in a cinema (the reel's frame stays 3:2, so nothing on the page moves) */
.ph .film-frame{position:absolute;inset:0;z-index:2;display:grid;place-items:center;background:#000;opacity:0;pointer-events:none;transition:opacity .5s var(--ease);}
.ph .film-frame iframe{display:block;width:100%;aspect-ratio:16 / 9;height:auto;border:0;}
.ph.film-open .film-frame{opacity:1;pointer-events:auto;}

/* quiet close — always light on the dark pano field (Bone page ink is too dark here).
   Bottom right: the work's number and frame label sit over a top corner of the picture. */
.ph .pano-close{
  position:absolute; bottom:10px; right:10px; z-index:4;
  font-family:var(--system); font-size:var(--s-ui); letter-spacing:.12em;
  text-transform:uppercase; color:#e9e6df;
  background:rgba(11,11,13,.62); border:1px solid rgba(255,255,255,.22);
  padding:6px 10px; cursor:pointer; opacity:0; pointer-events:none;
  transition:opacity .3s var(--ease);
}
.ph.pano-open .pano-close{opacity:1; pointer-events:auto;}

/* the field recedes while you're inside — same language as the hover dim */
.docpage:has(.ph.pano-open) .workpiece:not(:has(.ph.pano-open)){
  opacity:.3; transition:opacity .4s var(--ease);
}

/* home archive — the way into the archive page, at listing scale */
.arch-row{display:flex;justify-content:space-between;align-items:baseline;padding:.9em 0;border-top:1px solid var(--line);border-bottom:1px solid var(--line);
  font-family:var(--voice);font-size:var(--s-index);font-weight:500;color:var(--ink);transition:color .15s var(--ease);}
.arch-row:hover{color:var(--hover);}
.arch-row .ar-go{transition:transform .22s var(--ease);}
.arch-row:hover .ar-go{transform:translateX(6px);}
/* archive images are doors: each opens its work on the archive page */
.splane[data-work]{cursor:pointer;}
/* archive works: registration marks settle just inside the image on hover — something to open
   (with the soft bring-forward in script.js) */
.splane[data-work] .ph::before{content:"";position:absolute;inset:12px;z-index:2;pointer-events:none;--c:var(--paper);
  background:
    linear-gradient(var(--c),var(--c)) top left/14px 1px,linear-gradient(var(--c),var(--c)) top left/1px 14px,
    linear-gradient(var(--c),var(--c)) top right/14px 1px,linear-gradient(var(--c),var(--c)) top right/1px 14px,
    linear-gradient(var(--c),var(--c)) bottom left/14px 1px,linear-gradient(var(--c),var(--c)) bottom left/1px 14px,
    linear-gradient(var(--c),var(--c)) bottom right/14px 1px,linear-gradient(var(--c),var(--c)) bottom right/1px 14px;
  background-repeat:no-repeat;opacity:0;transform:scale(1.06);transition:opacity .25s var(--ease),transform .45s var(--ease);}
.splane[data-work]:hover .ph::before,.splane[data-work] .ph:focus-visible::before{opacity:1;transform:scale(1);}


/* archive page — a series' portraits under the text, stepped through on click */
.wp-portraits{margin:3em 0 0;width:58%;}
.wp-portraits .ph{cursor:pointer;}
.wp-portraits .wp-cap{margin-top:.6em;}
@media (max-width:900px){ .wp-portraits{width:70%;} }

/* home archive: each work carries its year and venue above its title */
.splane[data-work] .elcap::before{content:attr(data-meta) "\A";white-space:pre-line;color:var(--mut);}

/* the rail — a measured scale in the frame's margin, tucked to the screen edge: the reading rides
   to the left of the line, the ticks run to its right, clear of the column. On every page on
   desktop it replaces the text rail; phones keep the text rail. */
.rail-ruler{position:fixed;left:8px;top:calc(var(--top-h) + 44px);   /* 18px lower since 15 Oct 2026, clear of the field arrows above it */ height:44vh;width:52px;z-index:40;
  font-family:var(--system);font-size:var(--s-ui);color:var(--mut);pointer-events:none;opacity:0;transition:opacity .3s var(--ease);}
.rr-axis{position:absolute;left:40px;top:0;bottom:0;width:1px;background:var(--line);}
.rr-tick{position:absolute;left:40px;width:4px;height:1px;background:var(--dim);}
.rr-tick.major{width:8px;background:var(--mut);}
.rail-ruler{--rp:0;}
/* the fill: a red line from the top of the scale down to the position; ticks passed turn red with it */
.rr-fill{position:absolute;left:40px;top:0;width:1px;height:calc(var(--rp) * 100%);background:var(--accent);}
.rr-tick.past{background:var(--accent);}
.rr-read{position:absolute;right:16px;top:-.62em;color:var(--ink);font-variant-numeric:tabular-nums;}   /* holds still, level with the head of the scale where the fill begins */
@media (min-width:901px){
  .rail-ruler{opacity:1;}
  .rail{opacity:0;}
}
[data-mode="bone"] :is(.rr-fill,.rr-tick.past){background:var(--ink);}   /* the printed record: markers return to ink */
.rr-ticks{position:absolute;inset:0;}
@media (max-width:900px){ .rail-ruler{display:none;} }

/* the study spec sheet — labels in a column, values beside them in ink */
.spec dt{color:var(--dim);}
.spec dd{margin:0;color:var(--ink);}
.spec div{display:grid;grid-template-columns:12ch 1fr;line-height:1.9;}
/* on a system page it takes the row under the title; the lead and the fact line step down one */
@media (min-width:901px){
  .sys-product-open .spec{grid-column:1/10;grid-row:3;margin:1vh 0 3vh;}
  .sys-product-open:has(.spec) .sys-product-lead,.sys-product-open:has(.spec) .sys-product-fact{grid-row:4;}
  .sys-product-open:has(.spec) .sys-product-specimen{grid-row:1/5;}
}

/* the arrival image is seen through the bands the system renders in — 40 rows, the same rows the
   amber types into on the way to studies — inside registration marks, so it reads as an output and
   the statement leads. --arr is 1 at arrival and 0 a third of the way to studies (written by the
   engine); the bands close on hover (--dev). The amber (.hero-next) is never banded. */
@property --dev{syntax:"<number>";inherits:true;initial-value:0;}
#sp-hero{--arr:1;--dev:0;transition:--dev .9s var(--ease);}
#sp-hero:hover{--dev:1;}
#sp-hero .ph{background:transparent;overflow:visible;}
#sp-hero .ph img:first-child{--k:calc(var(--arr) * (1 - var(--dev)));
  -webkit-mask-image:repeating-linear-gradient(to bottom,#000 0,#000 calc(2.5% * (1 - .62 * var(--k))),transparent calc(2.5% * (1 - .62 * var(--k))),transparent 2.5%);
          mask-image:repeating-linear-gradient(to bottom,#000 0,#000 calc(2.5% * (1 - .62 * var(--k))),transparent calc(2.5% * (1 - .62 * var(--k))),transparent 2.5%);}
#sp-hero .ph::before{content:"";position:absolute;inset:-10px;pointer-events:none;z-index:2;opacity:var(--arr);
  background:
    linear-gradient(var(--mut),var(--mut)) left top/14px 1px no-repeat,linear-gradient(var(--mut),var(--mut)) left top/1px 14px no-repeat,
    linear-gradient(var(--mut),var(--mut)) right top/14px 1px no-repeat,linear-gradient(var(--mut),var(--mut)) right top/1px 14px no-repeat,
    linear-gradient(var(--mut),var(--mut)) left bottom/14px 1px no-repeat,linear-gradient(var(--mut),var(--mut)) left bottom/1px 14px no-repeat,
    linear-gradient(var(--mut),var(--mut)) right bottom/14px 1px no-repeat,linear-gradient(var(--mut),var(--mut)) right bottom/1px 14px no-repeat;}

/* AI Material Generator — the study is the images and the eye; the apparatus lives on Systems.
   A shorter head, the sequence set as image + specification pairs, the library and the loop sized
   to stay crisp. Desktop only; phones stack the page in reading order. */
@media (min-width:901px){
  [data-view="study"] .z-studyhead{height:72vh;}
  [data-view="study"] .z-seq{height:318vh;margin-top:8vh;}
  [data-view="study"] .z-grid{height:auto;padding-bottom:10vh;}
  [data-view="study"] .z-grid > .el{position:relative;}
  [data-view="study"] .z-grid .vgrid-wrap{margin-top:30vh;}
  [data-view="study"] .z-loop{height:auto;padding:4vh 0 8vh;}
  [data-view="study"] .z-loop > .el{position:relative;margin-left:calc(var(--colx) + 4 * (var(--sys-col) + var(--sys-gap)));width:calc(8 * var(--sys-col) + 7 * var(--sys-gap));}   /* fig. 7 the last eight columns — smaller, so the web film stays crisp */
  [data-view="study"] .z-notes{min-height:0;padding:6vh 0 10vh;}
  [data-view="study"] .notes-next{margin-top:10vh;}
}
/* the printed specification — something to observe rather than read: the smallest
   type, a fixed hierarchy, dim throughout and fading out downward like a fragment of a longer record.
   Hovering lights it like a reading lamp: a soft band a few lines tall brightens around the cursor
   and follows it slowly (--my, eased by the script); the light rises and leaves slowly (--lamp). */
@property --lamp{syntax:"<number>";inherits:false;initial-value:0;}
.specplate{--my:-999px;--lamp:0;font-size:var(--s-ui);line-height:1.5;color:var(--mut);
  transition:--lamp 1.6s cubic-bezier(.25,.1,.25,1) .2s;
  -webkit-mask-image:linear-gradient(to bottom,#000 55%,transparent 100%),
    linear-gradient(to bottom,rgb(0 0 0/.4) calc(var(--my) - 90px),rgb(0 0 0/calc(.4 + .5 * var(--lamp))) var(--my),rgb(0 0 0/.4) calc(var(--my) + 90px));
          mask-image:linear-gradient(to bottom,#000 55%,transparent 100%),
    linear-gradient(to bottom,rgb(0 0 0/.4) calc(var(--my) - 90px),rgb(0 0 0/calc(.4 + .5 * var(--lamp))) var(--my),rgb(0 0 0/.4) calc(var(--my) + 90px));
  -webkit-mask-composite:source-in;mask-composite:intersect;}
.specplate:hover{--lamp:1;}
.specplate header{display:flex;flex-direction:column;gap:.3em;padding-bottom:1em;border-bottom:1px solid var(--line);}
.specplate header span:first-child{color:var(--ink);}
.specplate section{padding:.9em 0;border-bottom:1px solid var(--line);}
.specplate h5{font:inherit;color:var(--ink);margin:0 0 .5em;}
.specplate p{margin:0;}
.specplate dl{display:grid;grid-template-columns:16ch 1fr;gap:.25em 1em;margin:0;}
.specplate dd{margin:0;}

/* the aesthetic profile on the study — the box in the site's own language: one hairline, no fills,
   no window-in-window, no scan or progress bar, caption type throughout */
[data-view="study"] .residue-profile{width:24%;min-width:300px;}
[data-view="study"] .residue-profile .spec-viewer-frame{height:auto;background:none;border:1px solid var(--line);}
[data-view="study"] .residue-profile .spec-viewer-head{min-height:0;padding:12px 14px;}
[data-view="study"] .residue-profile .spec-viewer-window{width:100%;height:230px;margin:0;background:none;border:0;border-top:1px solid var(--line);}
[data-view="study"] .residue-profile :is(.spec-viewer-scan,.spec-viewer-progress){display:none;}
[data-view="study"] .residue-profile .spec-viewer-meta{padding:12px 14px 0;}
[data-view="study"] .residue-profile .spec-viewer-content{min-height:0;padding:16px 14px;}
[data-view="study"] .residue-profile .spec-viewer-title{font-weight:400;text-transform:none;letter-spacing:.03em;font-size:var(--s-ui);color:var(--ink);margin-bottom:12px;}
[data-view="study"] .residue-profile .spec-viewer-copy{font-family:var(--system);font-size:var(--s-ui);line-height:1.6;color:var(--mut);}
[data-view="study"] .residue-profile .spec-viewer-value{color:var(--mut);}

/* placed beside the library note: grid columns 4–5, top-aligned with the paragraph, held still so it
   stays in register with the grid below */
@media (min-width:901px){
  [data-view="study"] .residue-profile{top:calc(var(--s-meta) * 1.6 + 1.2em);width:calc(40% - 1.5px);max-width:none;min-width:0;transform:none!important;}
}

/* listing thumbnails — a small image trails the pointer past the title; the project's images type
   in over one another (the script draws the bands). No caption. Home field, desktop only. */
.rowthumb{position:fixed;z-index:45;width:clamp(110px, 7vw, 140px);pointer-events:none;opacity:0;transition:opacity .25s var(--ease);}
.rowthumb.on{opacity:1;}
.rowthumb-ph{position:relative;aspect-ratio:4/5;background:var(--ph-2);border:1px solid var(--line);overflow:hidden;}
.rowthumb-ph img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;opacity:0;}
.rowthumb-ph img.on{opacity:1;}
/* field steps — the neighbouring sections by name, bottom left, home field only */
/* field arrows — top left on the content's edge, level with the nav, with room around them: two
   outlined arrows in the state words' outline, a step back or on round the loop. They say nothing
   else — what they do is plain */
.fieldnav{display:none;position:absolute;left:var(--colx);top:0;height:var(--top-h);align-items:center;gap:22px;}
body:is(:has(.view[data-view="home"].active),:has(.view[data-view="studio"].active),:has(.view[data-view^="study"].active),:has(.view[data-view^="systems/"].active)) .fieldnav{display:flex;}   /* on a project page: back to its list, on to the next project */
.fieldnav button{all:unset;cursor:pointer;display:grid;place-items:center start;width:32px;height:var(--top-h);font-family:var(--voice);font-weight:700;font-size:36px;line-height:1;color:transparent;-webkit-text-stroke:1px var(--mut);transition:-webkit-text-stroke-color .2s var(--ease),color .2s var(--ease);}
.fieldnav button:hover,.fieldnav button:focus-visible{-webkit-text-stroke-color:var(--ink);}
.fieldnav button:active{color:var(--ink);}
.fieldnav button:focus-visible{outline:1px solid var(--accent);outline-offset:-6px;}
@media (max-width:900px){ .fieldnav,.rowthumb{display:none!important;} }


/* diagrams — inline SVG in the site's grammar: hairlines, no fills, square corners, the site's two
   voices, colour from the tokens (Record/Bone follow). Drawn at 1:1 up to 1200px wide. */
.diagram{display:block;width:100%;max-width:1200px;height:auto;overflow:visible;}
.diagram .bx{fill:none;stroke:var(--line);stroke-width:1;}
.diagram .gate{fill:none;stroke:var(--mut);stroke-width:1;}
.diagram .wt{fill:none;stroke:var(--line);stroke-width:1;stroke-dasharray:4 4;}
.diagram .ln{fill:none;stroke:var(--dim);stroke-width:1;}
.diagram .rule{fill:none;stroke:var(--line);stroke-width:1;}
.diagram .bar{fill:none;stroke:var(--ink);stroke-width:2;}
.diagram .nd{fill:var(--ground);stroke:var(--mut);stroke-width:1;}
.diagram .ah{fill:none;stroke:var(--dim);stroke-width:1;}
.diagram text{font-family:var(--system);font-size:12px;fill:var(--ink);}
.diagram .hd{font-family:var(--voice);font-size:16px;fill:var(--ink);}
.diagram .hdm{font-family:var(--system);font-size:13px;fill:var(--ink);}
.diagram .mut{fill:var(--mut);}
.diagram .cap{font-size:11px;fill:var(--dim);letter-spacing:.04em;}
.diagram .cap.ink{fill:var(--ink);}

/* Whistle: the film beside the lead in the head; then one section per idea, each with its figure.
   Sections run on the 12-column grid between the reading column and the right margin. */
.z-whl-head{height:87.5vh;}
.whl-sec{height:auto;padding:0 var(--mx) var(--sys-section) var(--colx);}
/* section headings read as the opening line of their section: body size, in ink against the muted text */
.whl-sec .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;color:var(--ink);margin-bottom:.6em;}
.whl-item h4{font-size:var(--s-prose);}
.whl-item .whl-ask{color:var(--ink);margin:0 0 .6em;}
.whl-lead{max-width:62ch;color:var(--mut);}
.whl-lead + .whl-shot,.whl-note + .whl-shot{margin-top:6vh;}
.whl-shot{margin:0;}
.whl-shot .ph{border:1px solid var(--line);}
/* labels above, as on every system page */
[data-view="systems/whistle"] figure > .procnote:first-child{margin:0 0 var(--sys-label);}
.whl-split{display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;align-items:start;}
.whl-kicker{margin-top:5vh;margin-bottom:0;}
.whl-kinds{margin:1.2em 0 0;border-top:1px solid var(--line);}
.whl-kinds div{display:grid;grid-template-columns:14ch 1fr;padding:.75em 0;border-bottom:1px solid var(--line);}
.whl-kinds dt{color:var(--ink);}
.whl-kinds dd{margin:0;color:var(--mut);}
.whl-steps{list-style:none;counter-reset:step;margin:0 0 1.6em;padding:0;max-width:62ch;color:var(--mut);border-top:1px solid var(--line);}
.whl-steps li{counter-increment:step;display:grid;grid-template-columns:3.2em 1fr;align-items:baseline;padding:.7em 0;margin:0;line-height:1.55;border-bottom:1px solid var(--line);}
.whl-steps li::before{content:counter(step, decimal-leading-zero);font-family:var(--system);font-size:var(--s-meta);color:var(--dim);}
.whl-arch{margin:6vh 0 0;}
/* screens at the studies' scale: beside their text, sides alternating, never wider than half the page */
@media (min-width:901px){
  .whl-g{display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;align-items:start;}
  .whl-g > .display,.whl-g > .whl-grid{grid-column:1 / -1;}
  /* the four answers lead; the heading follows them and introduces the note and its figure */
  .whl-g-four > .whl-grid{margin-top:0;}
  .whl-g-four > .display{margin-top:6vh;}
}
.whl-arch .diagram{max-width:none;}
.whl-arch .diagram :is(.bx,.gate,.wt,.ln){shape-rendering:crispEdges;}
.diagram .dim{fill:var(--dim);}
.whl-made{padding-bottom:12vh;}
/* from "what counts as done" down: each section opens on a hairline, equal spacing between them */
.whl-sec:not(.whl-g-four){padding-top:var(--sys-rule);padding-bottom:var(--sys-section);background:linear-gradient(var(--line), var(--line)) no-repeat var(--colx) 0 / calc(100% - var(--colx) - var(--mx)) 1px;}
/* the close holds only the next-system row: no reserved height */
[data-view="systems/whistle"] .z-notes{min-height:0;padding:0 0 16vh;}
[data-view="systems/whistle"] .notes-next{margin-top:0;}
@media (max-width:900px){
  .z-whl-head{height:auto;padding-bottom:6vh;}
  .whl-sec{padding:4vh var(--mx) 9vh;}
  .whl-split{display:block;}
  .whl-split .whl-shot{margin-top:6vh;}
  .whl-mirror .whl-text{padding-top:0;}
  .whl-mirror{display:flex;flex-direction:column;align-items:stretch;}
  .whl-mirror .whl-text{order:-1;}
  .whl-kinds div{grid-template-columns:1fr;row-gap:.2em;}
  .whl-grid{grid-template-columns:1fr;}
}

/* AI Material Generator — rebuilt from the agreed system parts: labels above, drawn not filled,
   a measure for the score, sections opening on a hairline. Scoped to this page. */
[data-view="systems/material-generator"] .mg-lab{margin:0 0 var(--sys-label);white-space:normal;}
[data-view="systems/material-generator"] .lle-library-lab{grid-column:1 / -1;}
[data-view="systems/material-generator"] .lle-layer h3{font-size:var(--s-prose);}
[data-view="systems/material-generator"] .lle-pipeline .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;margin-bottom:.4em;}
[data-view="systems/material-generator"] .lle-workflow .ph{background:none;}
[data-view="systems/material-generator"] .lle-pipeline .stepper{border-top:0;padding-top:0;margin-top:3.2vh;}
[data-view="systems/material-generator"] .lle-flow{background:none;border:0;padding:0;}
[data-view="systems/material-generator"] .lle-flow span{border-color:var(--line);}
[data-view="systems/material-generator"] .lle-flow span.on{border-color:var(--ink);background:none;}
[data-view="systems/material-generator"] .lle-flow i{padding:0 .7em;}
[data-view="systems/material-generator"] .lle-evidence-card{background:none;}
[data-view="systems/material-generator"] .lle-provenance{border-top-color:var(--line);border-bottom:0;}
.mg-measure{display:grid;grid-template-columns:auto 1fr auto;align-items:center;column-gap:1em;margin:1.2em 0 0;padding:.75em 0;border-top:1px solid var(--line);border-bottom:1px solid var(--line);font-family:var(--system);font-size:var(--s-meta);}
.mg-measure .lab{color:var(--dim);}
.mg-measure .val{color:var(--ink);}
.mg-measure .bar{position:relative;height:1px;background:var(--line-strong);}
.mg-measure .bar i{position:absolute;left:0;top:-1px;height:3px;background:var(--ink);}
@media (min-width:901px){
  [data-view="systems/material-generator"] .sys-product-open{margin-bottom:var(--sys-section);}
  [data-view="systems/material-generator"] .sys-product-open .sys-product-fact{grid-column:1 / 10;grid-row:5;justify-self:start;width:max-content;white-space:nowrap;margin-top:1vh;}
  [data-view="systems/material-generator"] :is(.lle-pipeline,.lle-evidence,.lle-library){border-top:1px solid var(--line);padding-top:var(--sys-rule);}
  [data-view="systems/material-generator"] .lle-evidence{align-items:stretch;row-gap:2vw;}
  [data-view="systems/material-generator"] .lle-evidence-card:nth-child(odd){grid-column:1 / 7;margin-top:0;}
  [data-view="systems/material-generator"] .lle-evidence-card:nth-child(even){grid-column:7 / 13;margin-top:0;}
  [data-view="systems/material-generator"] .lle-library{width:auto;margin-left:0;}
}

/* Whistle — who checks the work: the steps run down one hairline like the page's ruler, a tick and
   its number at each step, no row rules; the decision paragraph sits off the line, level with the steps' text */
[data-view="systems/whistle"] .whl-steps{position:relative;border-top:0;margin:0 0 1.6em;}
[data-view="systems/whistle"] .whl-steps::before{content:"";position:absolute;left:0;top:1.15em;bottom:1.15em;width:1px;background:var(--line-strong);}
[data-view="systems/whistle"] .whl-steps li{position:relative;border-bottom:0;padding:.45em 0;grid-template-columns:3.6em 1fr;}
[data-view="systems/whistle"] .whl-steps li::before{padding-left:18px;}
[data-view="systems/whistle"] .whl-steps li::after{content:"";position:absolute;left:0;top:1.2em;width:10px;height:1px;background:var(--mut);}
[data-view="systems/whistle"] .whl-steps + .whl-lead{padding-left:3.6em;font-size:var(--s-prose);}

/* Whistle as a ledger (chosen 9 Oct 2026): each section one ruled row read straight across —
   heading 1–3 · text 4–8 · screen 9–12. Every screen one width (four columns); the tall panels
   cropped to 4:5 on the part their text is about, the supervisor strip to its transcript. */
@media (min-width:901px){
  [data-view="systems/whistle"] .whl-shot{grid-column:9 / 13;width:100%;justify-self:stretch;}
  [data-view="systems/whistle"] .whl-split:not(.whl-mirror) .whl-shot .ph{aspect-ratio:4/5!important;}
  [data-view="systems/whistle"] .whl-split:not(.whl-mirror) .whl-shot img{object-position:50% 100%;}
  [data-view="systems/whistle"] .whl-mirror .whl-shot .ph{aspect-ratio:4/5!important;}
  [data-view="systems/whistle"] .whl-mirror .whl-shot img{object-position:50% 0%;}
  [data-view="systems/whistle"] .whl-g-sup .whl-shot .ph{aspect-ratio:16/10!important;}
  [data-view="systems/whistle"] .whl-g-sup .whl-shot img{object-position:0% 50%;}

  [data-view="systems/whistle"] .whl-sec:not(.whl-g-four){display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);grid-template-rows:auto auto auto 1fr;align-items:start;}
  [data-view="systems/whistle"] .whl-sec .whl-text{display:contents;}
  [data-view="systems/whistle"] .whl-sec:not(.whl-g-four) > .display,
  [data-view="systems/whistle"] .whl-sec .whl-text > .display{grid-column:1 / 4;grid-row:1 / 5;}
  [data-view="systems/whistle"] .whl-sec:not(.whl-g-four) :is(.whl-lead,.whl-kicker,.whl-kinds,.whl-steps){grid-column:4 / 9;}
  [data-view="systems/whistle"] .whl-sec:not(.whl-g-four) .whl-shot{grid-row:1 / 5;margin-top:0;}
  [data-view="systems/whistle"] .whl-g-four{grid-template-rows:auto auto 1fr;}
  [data-view="systems/whistle"] .whl-g-four > .display{grid-column:1 / 4;grid-row:2 / 4;}
  [data-view="systems/whistle"] .whl-g-four .whl-note{grid-column:4 / 9;grid-row:2;}
  [data-view="systems/whistle"] .whl-g-four .whl-shot{grid-row:2 / 4;margin-top:6vh;}
  [data-view="systems/whistle"] .whl-g-four .whl-note{margin-top:6vh;}
  [data-view="systems/whistle"] .whl-sec:not(.whl-g-four) .whl-arch{grid-column:1 / -1;grid-row:5;}
  [data-view="systems/whistle"] .whl-made > .kicker{grid-column:1 / 4;}
  [data-view="systems/whistle"] .whl-made .whl-lead{grid-column:4 / 9;}
}

/* SeedVR2 Restoration Engine on the system grid (desktop) */
@media (min-width:901px){
  [data-view="systems/restoration"] .sys-product-open{margin-bottom:var(--sys-section);}
  [data-view="systems/restoration"] .sys-product-open .rst-heads{grid-column:7 / 13;}
  [data-view="systems/restoration"] .sys-product-open :is(.display,.spec){grid-column:1 / 7;}
  [data-view="systems/restoration"] .sys-product-open .sys-product-fact{grid-column:1 / 7;grid-row:5;justify-self:start;width:max-content;white-space:nowrap;margin-top:1vh;}
  .rst-sec{display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);grid-template-rows:auto auto 1fr;align-items:start;}
  .rst-sec > :is(.display,.rst-side){grid-column:1 / 4;grid-row:1 / 3;}
  .rst-sec > .rst-lead{grid-column:4 / 9;grid-row:1;}
  .rst-sec > .rst-steps{grid-column:4 / 13;grid-row:1;display:grid;grid-template-columns:subgrid;}
  .rst-steps li{grid-column:1 / -1;display:grid;grid-template-columns:subgrid;align-items:start;}
  .rst-step{grid-column:1 / 6;max-width:none;}
  .rst-ev{grid-column:6 / 10;margin:0;}
  .rst-side{margin-bottom:0;}
  .rst-sec > .rst-test{grid-column:4 / 9;grid-row:2;}
  .rst-sec > :is(.rst-sweep,.rst-graph,.rst-versus){grid-column:1 / -1;}
  .rst-vs{grid-template-columns:1fr 1fr;column-gap:var(--sys-gap);}
  .rst-sweep{display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);align-items:start;}
  .rst-sweep > .rst-lab{grid-column:1 / -1;}
  .sw-face,.sw-detail{display:contents;}
  .sw-face .rst-part,.sw-face .ph{grid-column:1 / 5;}
  .sw-detail .rst-part,.sw-view,.sw-scale{grid-column:5 / 13;}
  .sw-face .rst-part,.sw-detail .rst-part{grid-row:2;}
  .sw-face .ph,.sw-view{grid-row:3;}
  .sw-view{height:auto;align-self:stretch;}
  .sw-scale{grid-row:4;}
}

/* Banana Stack — built from the system parts on the system grid: sections open on a hairline with the
   heading in columns 1–3 and the text in 4–8; figures and plates take the full width beneath; labels above;
   drawn, not filled. */
[data-view="systems/banana-stack"] .bns-lab{margin:0 0 var(--sys-label);white-space:normal;}
.bns-sec{border-top:1px solid var(--line);padding-top:var(--sys-rule);}
.bns-sec + .bns-sec{margin-top:var(--sys-section);}
.bns-sec > .display{font-size:var(--s-prose);font-weight:400;letter-spacing:0;line-height:1.55;color:var(--ink);margin:0 0 .6em;}
.bns-lead{max-width:62ch;color:var(--mut);margin:0;}
.bns-sec figure{margin:0;}
.bns-sec > :is(.bns-doc,.bns-result,.bns-pl,.bns-arch){margin-top:6vh;}
.bns-film .vid,.bns-cell .ph,.bns-result .ph{border:1px solid var(--line);}
.bns-beside{margin-top:6vh;}
/* the brief — a document, drawn: field names in ink, the text as written */
.bns-brief{margin:0;border:1px solid var(--line);padding:.4em 1.2em;}
.bns-brief div{display:grid;grid-template-columns:22ch 1fr;column-gap:2ch;padding:.85em 0;border-bottom:1px solid var(--line);line-height:1.75;}
.bns-brief div:last-child{border-bottom:0;}
.bns-brief dt{color:var(--ink);}
.bns-brief dd{margin:0;color:var(--mut);}
.bns-result{cursor:zoom-in;}
.bns-cells{display:grid;grid-template-columns:1fr 1fr;column-gap:var(--sys-gap);row-gap:4vh;align-items:start;}
.bns-part{margin:0 0 var(--sys-label);color:var(--dim);}
.bns-part b{font-weight:400;color:var(--ink);margin-right:1ch;}
.bns-slot .ph{display:flex;align-items:center;justify-content:center;background:none;}
.bns-slot .ph .meta{color:var(--dim);}
.bns-cell.workpiece .ph{cursor:pointer;}
.bns-cap{margin-top:var(--sys-label);color:var(--dim);}
.bns-arch .diagram :is(.bx,.gate,.wt,.ln){shape-rendering:crispEdges;}
.bns-canvas .ph{aspect-ratio:3967/1601;border:1px solid var(--line);background:none;}   /* the canvas grab, cropped to an even margin round the workflow */
@media (max-width:900px){
  .bns-brief div{grid-template-columns:1fr;row-gap:.2em;}
}
@media (min-width:901px){
  [data-view="systems/banana-stack"] .sys-product-open{margin-bottom:var(--sys-section);}
  [data-view="systems/banana-stack"] .sys-product-open .sys-product-fact{grid-column:1 / 10;grid-row:5;justify-self:start;width:max-content;white-space:nowrap;margin-top:1vh;}
  .bns-sec{display:grid;grid-template-columns:repeat(12,1fr);column-gap:var(--sys-gap);align-items:start;}
  .bns-sec > .display{grid-column:1 / 4;}
  .bns-sec > .bns-lead{grid-column:4 / 9;}
  .bns-sec > :is(.bns-pl,.bns-arch,.bns-canvas){grid-column:1 / -1;}
  .bns-film{grid-column:1 / 9;}
  .bns-sec > .bns-beside{grid-column:9 / 13;margin-top:calc(var(--sys-label) + 1.6em);}
  .bns-doc{grid-column:1 / 9;}
  .bns-result{grid-column:9 / 13;position:sticky;top:14vh;}
  .bns-cells-6{grid-template-columns:repeat(6,1fr);}
  .bns-cells-5{grid-template-columns:repeat(5,1fr);}
}

/* the record's reader (16 Oct 2026) — a document opened inside the site, on the archive's paper:
   a quiet bar (title · page · download · close) over the pages, one under another, each with a
   hairline edge like the site's other pictures; portrait pages 760 px wide, spreads 1180 px */
html.dr-lock{overflow:hidden;}
.doc-reader{position:fixed;inset:0;z-index:300;background:var(--ground);overflow-y:auto;overscroll-behavior:contain;opacity:0;transition:opacity .3s var(--ease);}
.doc-reader.on{opacity:1;}
.dr-bar{position:sticky;top:0;z-index:2;display:flex;justify-content:space-between;align-items:center;gap:2em;height:var(--top-h);padding:0 var(--mx) 0 var(--colx);background:var(--ground);border-bottom:1px solid var(--line);font-family:var(--system);font-size:var(--s-meta);letter-spacing:.03em;color:var(--mut);}
.dr-title{margin:0;color:var(--ink);min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.dr-tools{margin:0;display:flex;align-items:center;gap:2em;white-space:nowrap;font-variant-numeric:tabular-nums;}
:is(.dr-dl,.dr-src){color:var(--mut);border-bottom:1px solid transparent;transition:color .15s var(--ease),border-color .15s var(--ease);}
:is(.dr-dl,.dr-src):hover,:is(.dr-dl,.dr-src):focus-visible{color:var(--ink);border-color:var(--ink);}
.dr-src[hidden]{display:none;}
.dr-close{all:unset;cursor:pointer;color:var(--ink);font:inherit;letter-spacing:inherit;}
.dr-close:hover{color:var(--hover);}
.dr-close:focus-visible{outline:1px solid var(--ink);outline-offset:4px;}
.dr-pages{display:flex;flex-direction:column;align-items:center;gap:4vh;padding:7vh 16px 14vh;}
.dr-pages img{display:block;width:min(760px,100%);height:auto;background:var(--mat);border:1px solid var(--line);opacity:0;transform:translateY(12px);transition:opacity .45s var(--ease),transform .5s var(--ease);}
.dr-pages img.wide{width:min(1180px,100%);}
.dr-pages img.in{opacity:1;transform:none;}
/* a film in the reader — the player whole, as wide as a spread, on the paper (its own black inside) */
.dr-film{width:min(1180px,100%);background:#000;}
.dr-film iframe{display:block;width:100%;height:100%;border:0;}
:is(.doc-reader.is-film,.doc-reader.is-photo) .dr-pages{min-height:calc(100vh - var(--top-h));justify-content:center;padding-top:4vh;padding-bottom:6vh;}
/* photographs: an archive entry inside the reader — the archive's own grid, picture and text */
.dr-work{display:grid;grid-template-columns:repeat(12,1fr);column-gap:2vw;align-items:start;width:100%;}
.dr-work .wp-img{width:100%;}
.dr-photo{position:relative;overflow:hidden;background:var(--mat);}
/* in the reader the photograph is what is being looked at: it stays at full strength and still under the
   pointer (the archive's dim-and-lift marks a work in a list); the loupe does the magnifying */
.doc-reader .dr-work .ph:hover img{opacity:1;transform:none;}
html.dr-lock .preview{z-index:310;}   /* the loupe above the reader while it is open */
.dr-pages .dr-photo img{display:block;width:100%;height:100%;object-fit:cover;border:0;background:none;opacity:1;transform:none;}   /* swaps at once, as the archive's do */
.dr-photo.contain{background:none;}
.dr-pages .dr-photo.contain img{object-fit:contain;object-position:left top;}   /* an upright picture stands at the frame's left, on its caption's line */
.doc-reader.is-photo .dr-pages{align-items:stretch;padding-left:var(--mx);padding-right:var(--mx);}
@media (max-width:900px){ .dr-work{grid-template-columns:1fr;} }
@media (max-width:900px){
  .dr-bar{padding:0 16px;gap:1em;}
  .dr-tools{gap:1.1em;}
  .dr-count{display:none;}
  .dr-pages{gap:2.5vh;padding:4vh 12px 10vh;}
}
@media (prefers-reduced-motion:reduce){ .doc-reader,.dr-pages img{transition:none;transform:none;} }
