/* site.css — structure, layout and behaviour. No colour literals:
   everything resolves through the tokens in theme.css.
   Shared by every page. Edit once, lands everywhere. */
/* =========================================================================
   D24 — Peter's palette. No constellation, no ripple. Interactivity comes
   from the panels themselves. Three card states: rest, hover, read.
   ========================================================================= */

*{box-sizing:border-box}
/* NO scrollbar-gutter HERE, DELIBERATELY.
   It was added as insurance against pages of differing widths and it created
   the very fault it was meant to prevent. During a view transition the browser
   suppresses the scrollbar while it captures the page; `scrollbar-gutter:
   stable` then reserves that 15px and paints it with the html background, so an
   off-white strip was baked INTO the snapshot at the page's right edge and
   travelled with it. Peter: "the scroll bar is somehow imprinting a white
   vertical strip on the homepage, and it's staying there." It was, and this
   line is what told it to.

   The insurance was never needed: every page here is long enough to scroll, so
   they are all the same width anyway. If a short page is ever added, fix it on
   that page — do not reserve a gutter globally. */
html{-webkit-font-smoothing:antialiased}
body{margin:0;background:var(--c-page);color:var(--t-page);font-family:var(--sans);
  font-weight:400;font-size:16px;line-height:1.6;overflow-x:hidden}
a{color:inherit}
.mono{font-family:var(--mono);font-size:11px;letter-spacing:.1em;text-transform:uppercase}
.dot{display:inline-flex;align-items:center;gap:9px}
.dot::before{content:"";width:6px;height:6px;background:currentColor;flex:none}

.js .rv{opacity:0;transform:translateY(22px);}
.rv{transition:opacity .8s var(--ease),transform .8s var(--ease)}
/* The first pass reveals what is already on screen with no animation at all,
   so a page is never captured mid-fade by a transition. */
html.rv-instant .rv{transition:none}
.rv.in{opacity:1;transform:none}
@media (prefers-reduced-motion:reduce){.rv,.rv.in{opacity:1;transform:none;transition:none}}

/* ---------- masthead ---------- */
.mast{position:fixed;inset:0 0 auto 0;z-index:60;display:flex;justify-content:space-between;
  align-items:center;gap:16px;padding:11px var(--pad);background:var(--c-mast);color:var(--t-mast);
  transition:background .135s linear,color .135s linear}
.mast:hover{background:var(--c-masth);color:var(--t-masth)}
.mast a{text-decoration:none}
/* THE PERSONAL MASTHEAD. The professional title is not removed, it is struck
   through and pushed back — set aside rather than retracted — and a second
   descriptor follows in the serif, lowercase, at ease. Two voices in one line,
   which is the whole point of the page. */
.mast .desc.faded{opacity:.34}
.mast .desc s{text-decoration:line-through;text-decoration-thickness:1px}
/* NOT the accent. The masthead ground IS the accent (--c-mast is #FF4C33), so
   accent-on-accent was invisible until hover turned the bar black. The contrast
   here is typographic, not chromatic — struck mono at a third strength against
   serif italic at full — which is why it survives whatever colour the bar
   becomes. */
.mast .alt{font-family:var(--serif);font-style:italic;font-size:16px;line-height:1;
  text-transform:none;letter-spacing:0;margin-left:11px;color:inherit;opacity:1;
  position:relative;top:1px}
.mast .r{display:flex;gap:clamp(14px,2vw,30px)}
.mast .r a{opacity:.78;transition:opacity .2s ease}
.mast .r a:hover{opacity:1}

/* ---------- panels ---------- */
.panel{padding:clamp(72px,14vh,190px) var(--pad);position:relative}
.panel.flush{padding:0}
.p-paper{background:var(--paper)}
.p-bone{background:var(--c-beyond);color:var(--t-beyond);transition:background .135s linear,color .135s linear}
.p-bone:hover{background:var(--c-beyondh);color:var(--t-beyondh)}
.p-gold{background:var(--c-quote);color:var(--t-quote);transition:background .135s linear,color .135s linear}
.p-gold:hover{background:var(--c-quoteh);color:var(--t-quoteh)}
.p-black{background:var(--c-thesis);color:var(--t-thesis);transition:background .135s linear,color .135s linear}
.p-black:hover{background:var(--c-thesish);color:var(--t-thesish)}
.p-earth{background:var(--c-contact);color:var(--t-contact);transition:background .135s linear,color .135s linear}
.p-earth:hover{background:var(--c-contacth);color:var(--t-contacth)}
.phead{display:flex;justify-content:space-between;align-items:baseline;gap:20px;
  margin-bottom:clamp(40px,7vh,88px);opacity:.55}

/* ---------- hero: typographic, nothing behind it ---------- */
.hero{min-height:100svh;display:flex;flex-direction:column;justify-content:flex-end;
  padding:calc(42px + clamp(60px,12vh,140px)) var(--pad) clamp(44px,8vh,86px);background:var(--c-hero);color:var(--t-hero);
  transition:background .135s linear,color .135s linear}
.hero:hover{background:var(--c-heroh);color:var(--t-heroh)}
h1.rot{font-family:var(--serif);font-weight:400;font-size:clamp(46px,9vw,142px);line-height:.98;
  letter-spacing:-.024em;margin:0 0 clamp(30px,5vh,54px);max-width:16ch}
h1.rot .stem{display:block;font-family:var(--sans);font-size:.24em;letter-spacing:.02em;
  line-height:1.4;margin-bottom:1em;opacity:.5}
.swap{display:block;position:relative;min-height:1em}
.swap span{display:block;transition:opacity .55s var(--ease),transform .55s var(--ease)}
.swap span.out{position:absolute;inset:0;opacity:0;transform:translateY(-16px)}
.swap span.in{opacity:1;transform:none}
.swap span.pre{opacity:0;transform:translateY(16px)}
.acts{display:flex;flex-wrap:wrap;gap:clamp(14px,2vw,26px);align-items:center}
.cta{background:var(--t-hero);color:var(--c-hero);text-decoration:none;padding:14px 26px;
  font-size:14px;transition:background .135s linear}
.cta:hover{background:var(--c-accent)}
.quiet{text-decoration:none;border-bottom:1px solid currentColor;padding-bottom:2px;font-size:14px;
  opacity:.6;transition:opacity .2s ease,border-color .2s ease}
.quiet:hover{opacity:1;border-color:var(--black)}

/* =========================================================================
   WORK — three states.
   REST   a coloured ground with the drawing showing through
   HOVER  a solid panel wipes up and covers the drawing; content only
   READ   a light ground, dark text, generous measure
   ========================================================================= */
.band{display:flex;flex-direction:column}
@media(min-width:900px){.band{flex-direction:row;height:clamp(600px,86vh,900px);
  transition:height .68s var(--ease)}}
.case{border:0;text-align:left;font:inherit;cursor:pointer;position:relative;overflow:clip;
  display:flex;flex-direction:column;min-height:clamp(460px,66vh,600px);padding:var(--pad);
  transition:flex-grow .68s var(--ease)}
.case:nth-child(1){background:var(--c-case1);color:var(--t-case1)}
.case:nth-child(2){background:var(--c-case2);color:var(--t-case2)}
.case:nth-child(3){background:var(--c-case3);color:var(--t-case3)}
@media(min-width:900px){
  .case{flex:1 1 0;min-width:0;min-height:0;height:auto}
  .band.anyopen .case{flex-grow:.055}
  .band.anyopen .case.open{flex-grow:1}
}
/* the wipe */
.case::before{content:"";position:absolute;inset:0;z-index:1;opacity:0;transition:opacity .135s linear}
.case:nth-child(1)::before{background:var(--c-case1h)}
.case:nth-child(2)::before{background:var(--c-case2h)}
.case:nth-child(3)::before{background:var(--c-case3h)}
.case:not(.open):hover::before{opacity:1}
.case:nth-child(1):not(.open):hover{color:var(--t-case1h)}
.case:nth-child(2):not(.open):hover{color:var(--t-case2h)}
.case:nth-child(3):not(.open):hover{color:var(--t-case3h)}
.case.open::before,.band.anyopen .case:not(.open)::before{opacity:0}
.case .art{position:absolute;right:-14%;bottom:-10%;width:88%;z-index:0;pointer-events:none;
  opacity:.34;transition:opacity .5s var(--ease)}
.case:not(.open):hover .art{opacity:.12;transition:none}
.case .art svg{width:100%;height:auto;display:block}
.case > *:not(.art){position:relative;z-index:2}
.case .hd{display:contents}
.case .hd > *{position:relative;z-index:2}
@media(min-width:900px){.case.open .hd{display:block}}

.case .top{display:flex;justify-content:space-between;margin-bottom:auto;opacity:.7}
.case .top .n{opacity:1}
/* per-card ink — heading and accent, independent of the card's body colour */
.case:nth-child(1) h3{color:var(--h-case1)}
.case:nth-child(2) h3{color:var(--h-case2)}
.case:nth-child(3) h3{color:var(--h-case3)}
.case:nth-child(1) .top .n,.case:nth-child(1) .spine .sn{color:var(--a-case1)}
.case:nth-child(2) .top .n,.case:nth-child(2) .spine .sn{color:var(--a-case2)}
.case:nth-child(3) .top .n,.case:nth-child(3) .spine .sn{color:var(--a-case3)}
.case h3{font-family:var(--serif);font-weight:400;font-size:clamp(30px,2.9vw,48px);line-height:1.04;
  letter-spacing:-.018em;margin:0 0 18px;max-width:14ch;transition:font-size .5s var(--ease),max-width .5s var(--ease)}
.case .sub{font-size:15px;line-height:1.55;margin:0;max-width:34ch;opacity:.86}
.case .more{margin-top:22px;display:flex;align-items:center;gap:10px;opacity:.6}
.pm{width:12px;height:12px;position:relative;flex:none}
.pm::before,.pm::after{content:"";position:absolute;background:currentColor;transition:transform .35s var(--ease)}
.pm::before{left:0;top:5.5px;width:12px;height:1px}
.pm::after{left:5.5px;top:0;width:1px;height:12px}
.case.open .pm::after{transform:scaleY(0)}

/* spine */
.case .spine{display:none;position:sticky;bottom:var(--pad);margin-top:auto;align-self:flex-start;
  writing-mode:vertical-rl;text-orientation:mixed;align-items:center;justify-content:flex-end;
  gap:clamp(14px,2vh,26px);opacity:0;transition:opacity .4s var(--ease) .18s;z-index:3;
  white-space:nowrap;max-height:70vh}
@media(min-width:900px){
  /* collapsed slivers must not contribute height — opacity alone left a
     48px headline wrapping inside a 70px column and the band sized to that */
  .band.anyopen .case:not(.open) > *:not(.spine),
  .band.anyopen .case:not(.open) .hd > *{display:none}
  .band.anyopen .case:not(.open) .spine{display:flex;opacity:.85}
  .case .spine .sn{color:var(--c-accent);opacity:1}
}

/* --- READ state: the whole point is legibility --- */
.case.open{background:var(--c-read);color:var(--t-read)}
.case.open .art{opacity:.05}
.case.open .top{opacity:.5}
.case .body{opacity:0;height:0;overflow:hidden;pointer-events:none;transition:opacity .4s var(--ease)}
.case.open .body{opacity:1;height:auto;overflow:visible;pointer-events:auto;
  transition:opacity .5s var(--ease) .34s}
.case .body > div{padding-top:clamp(22px,3vh,36px)}
.case .body p{font-size:15.5px;line-height:1.72;margin:0 0 1.15em;max-width:60ch;opacity:.82}
.case .body p.lead{font-size:19px;line-height:1.5;opacity:1;margin-bottom:1.3em;max-width:52ch}
.case .body .reflect{border-left:2px solid var(--a-read);padding-left:20px;margin:.5em 0 1.4em;break-inside:avoid}
.case .body .reflect .lbl{display:block;font-family:var(--mono);font-size:10px;letter-spacing:.12em;
  text-transform:uppercase;color:var(--a-read);margin-bottom:9px}
/* the open card is its own colour context and must win over the per-card
   rules above — equal specificity, so this has to come later in the file */
.case.open h3{color:var(--h-read)}
.case.open .top .n{color:var(--a-read)}
.case .body .reflect p{font-family:var(--serif);font-size:21px;line-height:1.34;opacity:1;margin:0;max-width:40ch}
.case .body .ref{font-family:var(--mono);font-size:10px;letter-spacing:.1em;text-transform:uppercase;
  opacity:.45;margin:0}
@media(min-width:900px){
  /* header sits BESIDE the prose, not stacked above it — halves the height */
  .case.open{display:grid;grid-template-columns:minmax(0,.34fr) minmax(0,.66fr);
    grid-template-rows:auto 1fr;column-gap:clamp(40px,4.5vw,90px);align-content:start}
  .case.open .top{grid-column:1/-1;margin-bottom:clamp(24px,3.4vh,44px)}
  .case.open .hd{grid-column:1;grid-row:2}
  .case.open .body{grid-column:2;grid-row:2}
  .case.open .more{grid-column:1;grid-row:3;margin-top:26px}
  .case.open h3{font-size:clamp(28px,2.5vw,40px);max-width:none;margin-bottom:14px}
  .case.open .sub{font-size:16.5px;line-height:1.5;max-width:none;opacity:1}
  /* Peter ruled the two-column prose belongs to depth 3, on the case's
     own page. Depth 2 is a shorter written version and reads as one column. */
  .case.open .body > div{padding-top:0}
  /* the column IS the measure — capped paragraphs left a fifth of each column empty */
  .case.open .body p{max-width:none}
  .case.open .body p.lead{max-width:none;font-size:17px}
  .case.open .body .reflect{column-span:all;max-width:none;margin:1.4em 0}
  .case.open .body .reflect p{max-width:none;font-size:20px}
}

/* =========================================================================
   BUILT — personal / AI projects. Deliberately NOT the .case component.
   The three professional cases argue from decisions and are bound by what
   can be claimed; these argue from an artifact that exists and can be
   pointed at. Different evidence, so a different, lighter card: no expand,
   no read state, a spec list instead of prose.
   ========================================================================= */
.builtband{display:grid;grid-template-columns:1fr;background:var(--c-built);color:var(--t-built)}
@media(min-width:900px){.builtband{grid-template-columns:repeat(3,1fr)}}
.built{padding:var(--pad);padding-top:clamp(44px,6.5vh,78px);padding-bottom:clamp(44px,6.5vh,78px);
  display:flex;flex-direction:column;position:relative;overflow:clip;
  border-top:1px solid currentColor;text-decoration:none;color:inherit}
@media(min-width:900px){
  .built{border-top:0;border-left:1px solid currentColor}
  .built:first-child{border-left:0}
}
.built::before{content:"";position:absolute;inset:0;z-index:0;opacity:0;
  background:var(--c-builth);transition:opacity .135s linear;pointer-events:none}
.built > *{position:relative;z-index:1}
a.built:hover::before{opacity:1}
a.built:hover{color:var(--t-builth)}
.built .top{display:flex;justify-content:space-between;align-items:baseline;
  margin-bottom:clamp(30px,5vh,58px);opacity:.62}
.built .top .n{color:var(--a-built);opacity:1}
.built h3{font-family:var(--serif);font-weight:400;font-size:clamp(25px,2.3vw,36px);line-height:1.08;
  letter-spacing:-.016em;margin:0 0 14px;max-width:14ch;color:var(--h-built)}
.built .what{margin:0 0 auto;font-size:15px;line-height:1.62;max-width:34ch;opacity:.78}
/* the spec list is the evidence — plain, countable, checkable */
.built .spec{margin:clamp(26px,4vh,44px) 0 0;padding:0;list-style:none;
  font-family:var(--mono);font-size:10.5px;letter-spacing:.055em;line-height:1.9}
.built .spec li{display:flex;justify-content:space-between;gap:14px;
  border-top:1px solid currentColor;padding-top:6px;margin-top:6px;opacity:.62}
.built .spec li:first-child{border-top:0;margin-top:0}
.built .spec li b{font-weight:400;opacity:1}
.built .go{margin-top:24px;font-family:var(--mono);font-size:10.5px;letter-spacing:.1em;
  text-transform:uppercase;display:flex;align-items:center;gap:9px;opacity:.6}
/* A RESERVED SLOT IS NOT A DISABLED ONE. These carried opacity:.72 across the
   whole tile, which on a light ground reads as a white wash over everything —
   Peter: "there's some kind of white overlay across it... the orange colour is
   muted as well." It also dragged the accent number down with it, and it was
   left over from when these tiles went nowhere. They open a panel now, so they
   must not look switched off. The "In progress" label and the empty rows in the
   panel do the signalling; nothing needs dimming to say it. */
.built.soon .what{opacity:.66}

/* ---------- widows -------------------------------------------------------
   Peter: "we should never have a line with only one word on it at the end of a
   sentence." Two layers, because neither is sufficient alone.

   text-wrap:balance evens the lines of a short heading, which is what stops a
   single word being stranded in large type. text-wrap:pretty does the same job
   for running prose, where balancing would be wrong. Both are ignored by
   browsers that do not support them, which is why build.py ALSO binds the last
   two words of every headline with a non-breaking space — that fix works
   everywhere and does not depend on the browser agreeing with us.

   balance is capped by browsers at a handful of lines, so it is scoped to
   headings and never applied to body copy. */
h1,h2,h3,h4,.statement,.hero .line,.built h3,.lens h2,summary{text-wrap:balance}
p,li,.what,.ans,.sub-statement,.crumbs li{text-wrap:pretty}

/* ---------- statement ---------- */
.statement{font-family:var(--serif);font-weight:400;font-size:clamp(36px,6.4vw,104px);line-height:1.02;
  letter-spacing:-.024em;margin:0;max-width:15ch}
.statement em{font-style:italic;color:var(--c-accent)}
/* The closing panel is the last thing a recruiter reads. The statement makes
   the claim; this line answers the two practical questions that immediately
   follow it — what level, and can he actually take the job — without making
   anyone open the résumé to find out. */
.contact-meta{margin:clamp(26px,4vh,44px) 0 0;opacity:.62}
.sub-statement{font-size:clamp(18px,2vw,26px);line-height:1.44;max-width:42ch;
  margin:clamp(30px,5vh,56px) 0 0;opacity:.72}

/* ---------- lenses ---------- */
.lensband{display:grid;grid-template-columns:1fr}
@media(min-width:820px){.lensband{grid-template-columns:repeat(3,1fr)}}
/* Every lens also carries .rv, and .rv declares its own `transition`
   shorthand at equal specificity — so whichever rule comes last wins the
   WHOLE property and silently drops the other's. Declaring all four here
   ends that collision. Suspect in the reported hover lag; not yet proven. */
/* The lens hover was transitioning background-color on a large text block,
   which repaints the whole block every frame. The work cards never had this
   problem because they wipe with a pseudo-element and animate OPACITY, which
   the compositor handles without repainting. Same technique here. */
/* No `transition` declared here on purpose, for two reasons.
   1. The work cards transition ONLY flex-grow — their hover text colour
      snaps. That instant snap is what "fast" has felt like all along, so
      the lens matches it: the ground wipes, the ink changes at once.
   2. Declaring nothing lets .rv keep its own reveal transition instead of
      the two rules clobbering each other's shorthand. Naming transform in
      a transition list also promotes the element to its own compositing
      layer, which made every repaint more expensive, not less. */
.lens{padding:var(--pad);padding-top:clamp(52px,8vh,96px);padding-bottom:clamp(52px,8vh,96px);
  display:flex;flex-direction:column;position:relative;overflow:clip}
.lens::before{content:"";position:absolute;inset:0;z-index:0;opacity:0;
  transition:opacity .135s linear;pointer-events:none}
.lens > *{position:relative;z-index:1}
.lens:nth-child(1){background:var(--c-lens1);color:var(--t-lens1)}
.lens:nth-child(2){background:var(--c-lens2);color:var(--t-lens2)}
.lens:nth-child(3){background:var(--c-lens3);color:var(--t-lens3)}
.lens:nth-child(1)::before{background:var(--c-lens1h)}
.lens:nth-child(2)::before{background:var(--c-lens2h)}
.lens:nth-child(3)::before{background:var(--c-lens3h)}
.lens:hover::before{opacity:1}
.lens:nth-child(1):hover{color:var(--t-lens1h)}
.lens:nth-child(2):hover{color:var(--t-lens2h)}
.lens:nth-child(3):hover{color:var(--t-lens3h)}
.lens .n{color:var(--c-accent);margin-bottom:auto}
.lens h3{font-family:var(--serif);font-weight:400;font-size:clamp(25px,2.3vw,36px);line-height:1.08;
  letter-spacing:-.016em;margin:clamp(40px,6vh,74px) 0 16px;max-width:16ch}
.lens p{margin:0;font-size:15px;line-height:1.68;max-width:42ch;opacity:.72}

/* ---------- quote ---------- */
.quote{font-family:var(--serif);font-size:clamp(30px,4.6vw,74px);line-height:1.06;letter-spacing:-.02em;margin:0;
  text-indent:-.42em}
.quote em{font-style:normal;opacity:.5}
/* hanging quotation marks — the opening mark sits in the margin so the
   first character of the sentence still aligns to the panel edge */
.quote .qt::before{content:"\201C"}
.quote .qt::after{content:"\201D"}
.attr{display:block;font-family:var(--mono);font-size:11px;letter-spacing:.1em;text-transform:uppercase;
  margin-top:clamp(30px,5vh,52px);opacity:.55;line-height:1.7;text-indent:0}
.attr a{text-decoration:none;border-bottom:1px solid currentColor;padding-bottom:2px;
  transition:opacity .135s linear}
.attr a:hover{opacity:.6}
.attr a::after{content:"\2197";margin-left:.45em;font-size:.9em;vertical-align:.05em}

/* ---------- beyond ---------- */
.acc details{border-bottom:1px solid currentColor}
.acc details{--hair:currentColor}
.acc details:first-child{border-top:1px solid currentColor}
.acc summary{list-style:none;cursor:pointer;padding:clamp(22px,3vh,34px) 0;display:flex;
  justify-content:space-between;gap:24px;align-items:baseline;font-family:var(--serif);
  font-size:clamp(23px,2.4vw,36px);letter-spacing:-.014em;transition:color .2s ease}
.acc summary::-webkit-details-marker{display:none}
.acc summary:hover,.acc details[open] summary{color:var(--c-accent)}
.acc .ans{padding:0 0 clamp(28px,4vh,44px);max-width:64ch;font-size:16px;line-height:1.72;opacity:.75}

/* ---------- contact ---------- */
.linkband{display:grid;grid-template-columns:1fr}
@media(min-width:700px){.linkband{grid-template-columns:repeat(4,1fr)}}
.linkband a{padding:var(--pad);text-decoration:none;display:flex;flex-direction:column;gap:12px;transition:background .135s linear,color .135s linear;
  min-height:clamp(140px,20vh,220px);justify-content:flex-end;background:var(--c-links);color:var(--t-links);
  }
.linkband a:nth-child(2){background:var(--c-links2)}
.linkband a:nth-child(3){background:var(--c-links3)}
.linkband a:nth-child(4){background:var(--c-links4)}
.linkband a:hover{background:var(--c-linksh);color:var(--t-linksh)}
.linkband .k{opacity:.5}
.linkband .v{font-family:var(--serif);font-size:clamp(19px,1.8vw,27px)}
.foot{display:flex;justify-content:space-between;gap:16px;flex-wrap:wrap;padding:18px var(--pad);
  background:var(--c-links);color:var(--t-links);opacity:.45}

/* ---- colour panel (design tool; strip before launch) ---- */


/* =========================================================================
   MOBILE. The layout is already mobile-first — every structural rule is
   min-width — so this block only fixes the things that don't survive a
   narrow, touch-driven viewport.
   ========================================================================= */

/* 1. Touch devices have no hover. Without this, a tap latches the hover
   ground and it stays until you tap elsewhere. Rather than unpick every
   :hover rule, point each hover variable back at its own base colour so
   the hover state resolves to no visible change. */
@media (hover:none){
  :root{
    --c-masth:var(--c-mast);       --t-masth:var(--t-mast);
    --c-heroh:var(--c-hero);       --t-heroh:var(--t-hero);
    --c-case1h:var(--c-case1);     --t-case1h:var(--t-case1);
    --c-case2h:var(--c-case2);     --t-case2h:var(--t-case2);
    --c-case3h:var(--c-case3);     --t-case3h:var(--t-case3);
    --c-thesish:var(--c-thesis);   --t-thesish:var(--t-thesis);
    --c-lens1h:var(--c-lens1);     --t-lens1h:var(--t-lens1);
    --c-lens2h:var(--c-lens2);     --t-lens2h:var(--t-lens2);
    --c-lens3h:var(--c-lens3);     --t-lens3h:var(--t-lens3);
    --c-quoteh:var(--c-quote);     --t-quoteh:var(--t-quote);
    --c-beyondh:var(--c-beyond);   --t-beyondh:var(--t-beyond);
    --c-contacth:var(--c-contact); --t-contacth:var(--t-contact);
    --c-linksh:var(--c-links);     --t-linksh:var(--t-links);
    --c-builth:var(--c-built);     --t-builth:var(--t-built);
  }
  .case::before{display:none}
}

@media (max-width:899px){
  /* 2. Masthead: the descriptor doesn't fit next to four nav links. */
  .mast{padding:9px var(--pad);gap:10px}
  .mast .desc{display:none}
  .mast .alt{margin-left:0;font-size:14px}
  .mast .r{gap:13px}
  .mast,.mast .mono{font-size:10px;letter-spacing:.07em}

  /* 3. Cards stack, so they size to content — a fixed min-height leaves
     a dead band under short collapsed copy. */
  .case{min-height:0;padding:clamp(30px,9vw,46px) var(--pad)}
  .band{height:auto !important}

  /* 4. The colour panel is a desktop tool. Keep it reachable for testing
     mobile grounds, but out of the way: a collapsed bottom strip. */
  #cpanel{left:8px;right:8px;bottom:8px;width:auto;max-height:60vh}
  #cpanel .cp-body{max-height:44vh}

  /* 5. Give the display type room to breathe without overflowing. */
  h1.rot{max-width:none}
  .quote{text-indent:0}
  .quote .qt::before,.quote .qt::after{content:none}
}

@media (max-width:520px){
  .acts{gap:12px}
  .cta{width:100%;text-align:center}
}

/* =========================================================================
   DEPTH 3 — the case page. Two tracks: prose left, visual lane right.
   The lane is sticky-per-figure rather than one sticky block, so a figure
   holds while its paragraphs pass and then releases. Nothing reflows: the
   grid columns are fixed, so adding a figure never moves the text.
   ========================================================================= */
.casehero{padding:calc(42px + clamp(60px,12vh,140px)) var(--pad) clamp(40px,7vh,72px);
  background:var(--c-hero);color:var(--t-hero);display:flex;flex-direction:column}
.casehero .top{display:flex;justify-content:space-between;margin-bottom:clamp(40px,8vh,110px);opacity:.55}
.casehero .top .n{color:var(--c-accent);opacity:1}
.casehero h1{font-family:var(--serif);font-weight:400;font-size:clamp(34px,5.4vw,86px);
  line-height:1.02;letter-spacing:-.022em;margin:0 0 clamp(20px,3vh,34px);max-width:19ch}
.casehero .hook{margin:0;font-size:clamp(16px,1.8vw,22px);line-height:1.5;max-width:54ch;opacity:.72}

.casebody{background:var(--c-read);color:var(--t-read);padding:clamp(50px,9vh,120px) var(--pad)}
.track{display:grid;grid-template-columns:1fr;gap:clamp(28px,4vw,64px);align-items:start}
@media(min-width:900px){
  /* prose stays narrow and fixed; the lane never pushes it */
  .track{grid-template-columns:minmax(0,.56fr) minmax(0,.44fr)}
}
.prose p{font-size:16px;line-height:1.72;margin:0 0 1.2em;max-width:64ch}
.prose p.lead{font-size:21px;line-height:1.46;margin-bottom:1.4em;max-width:52ch}
.prose .reflect{border-left:2px solid var(--a-read);padding-left:20px;margin:1.6em 0}
.prose .reflect .lbl{display:block;font-family:var(--mono);font-size:10px;letter-spacing:.12em;
  text-transform:uppercase;color:var(--a-read);margin-bottom:9px}
/* was 42ch inside a 64ch column, so the reflection stopped three quarters
   of the way across and read as a mistake. It is a pull quote, not a
   narrower column: same measure, larger type. */
.prose .reflect p{font-family:var(--serif);font-size:22px;line-height:1.34;margin:0;max-width:none}
.prose .ref{font-family:var(--mono);font-size:10px;letter-spacing:.1em;text-transform:uppercase;opacity:.5}
.lane{display:flex;flex-direction:column;gap:clamp(30px,6vh,80px)}
.lane figure{margin:0;position:sticky;top:clamp(70px,12vh,120px)}
.lane figcaption{font-family:var(--mono);font-size:10px;letter-spacing:.09em;
  text-transform:uppercase;opacity:.5;margin-top:10px}
/* mobile: the lane stops being a lane and each figure sits after the
   paragraph it belongs to, in document order. No sticky, no sync. */
@media(max-width:899px){
  .lane figure{position:static}
  .lane{gap:clamp(22px,4vh,40px)}
}
.depth3{text-decoration:none;border-bottom:1px solid currentColor;padding-bottom:2px}

/* =========================================================================
   RÉSUMÉ PAGE. Real text in real headings — the point is that a crawler and
   an agent can both read it. Nothing here is an image or an embedded PDF.
   ========================================================================= */
.subhero.rz{padding-bottom:clamp(30px,5vh,54px)}
.subhero.rz h1{margin-bottom:10px}
.subhero.rz .headline{font-family:var(--mono);font-size:12px;letter-spacing:.1em;
  text-transform:uppercase;opacity:.75;margin:0 0 14px;max-width:none}
.subhero.rz .meta{font-size:14px;opacity:.6;margin:0 0 clamp(24px,4vh,40px);max-width:none}
.resume{background:var(--c-read);color:var(--t-read);padding:clamp(46px,8vh,110px) var(--pad)}
.resume section{margin-bottom:clamp(40px,6vh,78px);max-width:78ch}
.resume h2{font-family:var(--mono);font-size:10.5px;letter-spacing:.14em;text-transform:uppercase;
  font-weight:400;opacity:.5;margin:0 0 clamp(18px,3vh,30px);
  padding-bottom:9px;border-bottom:1px solid currentColor}
.resume h3{font-family:var(--serif);font-weight:400;font-size:clamp(21px,2vw,29px);
  line-height:1.14;letter-spacing:-.014em;margin:0 0 4px}
.resume .rmeta{font-family:var(--mono);font-size:10px;letter-spacing:.09em;text-transform:uppercase;
  opacity:.55;margin:0 0 12px}
.resume .ctx{font-size:15px;line-height:1.6;opacity:.78;margin:0 0 14px;max-width:70ch}
.resume ul{margin:0 0 26px;padding:0;list-style:none}
.resume li{position:relative;padding-left:20px;margin-bottom:11px;font-size:15px;line-height:1.66;
  max-width:74ch}
.resume li::before{content:"";position:absolute;left:0;top:.62em;width:9px;height:1px;
  background:currentColor;opacity:.45}
.resume .role{margin-bottom:clamp(30px,4.5vh,52px)}
.resume .sub{margin:0 0 6px;font-family:var(--mono);font-size:10px;letter-spacing:.09em;
  text-transform:uppercase;opacity:.7}
.resume .summary{font-size:18px;line-height:1.6;max-width:64ch;margin:0}

/* Depth 2 breadcrumbs. Milestones and decisions, scannable in one pass. The
   rule marks each one without turning the list into résumé bullets. */
.case .body .crumbs{margin:0 0 1.4em;padding:0;list-style:none}
.case .body .crumbs li{position:relative;padding-left:26px;margin-bottom:15px;
  font-size:16px;line-height:1.56;max-width:58ch}
.case .body .crumbs li::before{content:"";position:absolute;left:0;top:.66em;
  width:14px;height:1px;background:var(--a-read);opacity:.85}

/* =========================================================================
   LAYOUT PASS — 2026-09-06
   ========================================================================= */

/* The footer strip was a fixed 4-column grid. Case pages carry two tiles, so
   the strip stopped halfway across the page. Let it fill whatever it has. */
@media(min-width:700px){
  .linkband{grid-template-columns:repeat(auto-fit,minmax(min(260px,100%),1fr))}
}

/* "Read the full case" is the action the whole card is arguing for. It was
   wearing .ref — the same muted 10px mono as the credit line above it. */
.case .body .depth3{display:inline-flex;align-items:center;gap:11px;
  margin-top:clamp(26px,4vh,44px);text-decoration:none;
  font-family:var(--mono);font-size:12px;letter-spacing:.11em;text-transform:uppercase;
  color:var(--a-read);border-bottom:1px solid currentColor;padding-bottom:7px;
  transition:opacity .135s linear}
.case .body .depth3 .ar{font-size:14px;transition:transform .2s var(--ease)}
.case .body .depth3:hover .ar{transform:translateX(4px)}

/* Depth 3: until the visual lane has content, an empty 44% column just pushes
   the prose into the left half of the screen. Centre the measure instead, and
   only split the page once there is something to split it with. */
@media(min-width:900px){
  .track{grid-template-columns:minmax(0,1fr);justify-items:center}
  .track:has(.lane figure){grid-template-columns:minmax(0,.56fr) minmax(0,.44fr);
    justify-items:stretch}
  .prose{max-width:72ch}
  .track:has(.lane figure) .prose{max-width:none}
  .lane:empty{display:none}
}

/* Give every page hero room to breathe. They were all pinned to the top-left
   corner because .subhero and .casehero only had the masthead offset. */
/* THE PAGE GUTTER. Every full-bleed block inherits its left edge from --pad,
   which is what makes the hero copy, the card copy, the section labels and
   the footer all start on the same vertical line. .subhero had no base rule
   at all — only a padding-top — so the personal and résumé heroes were
   sitting flush against the window edge while everything below them was
   inset. There is now one rule that owns the gutter for every hero. */
.hero,.subhero,.casehero,.panel,.resume,.casebody{
  padding-left:var(--pad);padding-right:var(--pad)}
/* .panel.flush is declared earlier in this file, so the gutter rule above was
   silently winning against it and putting an inset back on the sections that
   are meant to run edge to edge. */
.panel.flush{padding-left:0;padding-right:0}
.subhero{display:flex;flex-direction:column;justify-content:flex-end}
.casehero,.subhero{padding-top:calc(42px + clamp(90px,17vh,190px));
  padding-bottom:clamp(40px,7vh,72px)}
.casehero{padding-bottom:clamp(56px,10vh,110px)}
.casehero h1{max-width:22ch}
.subhero h1{max-width:20ch}
/* The rule under each heading is only correct when it ends where the text
   ends. Cap the section, not the paragraphs, so the two always agree. */
.resume section{max-width:82ch}
.resume .role,.resume .summary,.resume li,.resume .ctx{max-width:none}

/* "What I learned" sits beside "What I'd change" but must not read as its
   twin. The concession gets the accent rule; the transferable lesson gets a
   quieter full rule above it, so the two are siblings, not echoes. */
.case .body .learned,.prose .learned{border-left:0;border-top:1px solid currentColor;
  padding:18px 0 0;margin:1.8em 0 1.4em;opacity:.92}
.case .body .learned .lbl,.prose .learned .lbl{display:block;font-family:var(--mono);
  font-size:10px;letter-spacing:.12em;text-transform:uppercase;opacity:.55;margin-bottom:10px}
.case .body .learned p,.prose .learned p{font-family:var(--serif);font-size:21px;
  line-height:1.36;margin:0;max-width:none}

/* The way back out of a case study. It is the last thing on the page and it
   was reading as part of the furniture; the accent makes it the exit sign.
   Sits in the token layer, so a palette change carries it. */
.linkband a.lead-tile{background:var(--c-accent);color:var(--t-mast)}
.linkband a.lead-tile:hover{background:var(--c-links);color:var(--t-links)}
.linkband a.lead-tile .k{opacity:.72}

/* "Who was involved" — depth 3 only. Same family as the other reflections,
   quieter still, because it is credit rather than argument. */
.prose .credits{border-top:1px solid currentColor;padding:18px 0 0;margin:1.8em 0 0}
.prose .credits .lbl{display:block;font-family:var(--mono);font-size:10px;letter-spacing:.12em;
  text-transform:uppercase;opacity:.55;margin-bottom:10px}
.prose .credits p{font-size:16px;line-height:1.7;margin:0;max-width:none;opacity:.85}

/* These borders were rgba(0,0,0,...) literals, so a dark ground would have
   erased them. They inherit ink now and are held back with opacity instead,
   which works on any palette. */
.quiet{border-bottom-color:currentColor}
.acc details{border-bottom-color:color-mix(in srgb,currentColor 18%,transparent)}
.acc details:first-child{border-top-color:color-mix(in srgb,currentColor 18%,transparent)}
/* a project tile with no destination */
.built.inert{cursor:default}
.built.inert::before{display:none}
.play.inert{cursor:default}
.play.inert::before{display:none}

/* =========================================================================
   PROJECT DETAIL PANEL. The band never moves — it stays as the index and the
   panel grows beneath it. Animating the tile itself meant animating a grid
   item's height while siblings left the grid and its column span changed,
   which flickered. One element animates now.
   ========================================================================= */
.built[role="button"]{cursor:pointer}
.built.on::before{opacity:1;background:var(--c-accent)}
.built.on{color:var(--t-mast)}
.built.on .top .n,.built.on .go{color:var(--t-mast)}
.pdetail{height:0;overflow:hidden;background:var(--c-read);color:var(--t-read);
  transition:height .5s var(--ease)}
.pdetail .inner{padding:clamp(34px,5vh,54px) var(--pad) clamp(40px,6vh,64px)}
.pdetail .dhead{display:flex;justify-content:space-between;align-items:baseline;gap:20px;
  font-family:var(--mono);font-size:10px;letter-spacing:.11em;text-transform:uppercase;
  opacity:.55;margin-bottom:22px}
.pclose{background:none;border:0;cursor:pointer;font:inherit;color:inherit;padding:0;opacity:.85}
.pclose:hover{color:var(--c-accent);opacity:1}
.pdetail h3{font-family:var(--serif);font-weight:400;font-size:clamp(25px,3vw,36px);
  line-height:1.1;letter-spacing:-.018em;margin:0 0 14px;max-width:24ch}
.pdetail .what{margin:0 0 30px;font-size:16px;line-height:1.66;max-width:60ch;opacity:.84}
.pdetail .model{display:grid;grid-template-columns:1fr;gap:22px;align-items:start}
@media(min-width:820px){.pdetail .model{grid-template-columns:minmax(0,1.1fr) minmax(0,.9fr)}}
.pdetail .stage{background:var(--c-beyond);padding:18px}
.pdetail .stage svg{width:100%;height:auto;display:block}
.pdetail .node{cursor:pointer}
.pdetail .node rect{fill:none;stroke:currentColor;stroke-width:1.1;transition:fill .18s linear}
.pdetail .node.on rect{fill:var(--gold)}
.pdetail .node text{font-family:var(--mono);font-size:7px;letter-spacing:.09em;fill:currentColor}
.pdetail .node .cnt{font-family:var(--serif);font-size:13px}
.pdetail .edge{stroke:currentColor;stroke-width:1;fill:none;opacity:.3}
.pdetail .pulse{fill:var(--c-accent)}
.pdetail .readout .lbl{font-family:var(--mono);font-size:9.5px;letter-spacing:.12em;
  text-transform:uppercase;opacity:.5;display:block;margin-bottom:8px}
.pdetail .readout h4{font-family:var(--serif);font-weight:400;font-size:21px;margin:0 0 8px;
  line-height:1.22}
.pdetail .readout p{margin:0;opacity:.82;max-width:44ch;line-height:1.62;font-size:14px}
.pdetail .legend{font-family:var(--mono);font-size:9px;letter-spacing:.1em;text-transform:uppercase;
  opacity:.45;margin-top:12px}
@media(prefers-reduced-motion:reduce){.pdetail{transition:none}}

/* The panel header sticks. Once the band scrolls away, the accent on the open
   tile can no longer say which project you are in — this carries that job,
   with the same accent mark, and keeps Close reachable without scrolling back. */
.pdetail .dhead{position:sticky;top:0;z-index:4;background:var(--c-read);
  padding:16px 0 14px;margin-bottom:20px;border-bottom:1px solid currentColor;opacity:1}
.pdetail .dhead .who{display:inline-flex;align-items:center;gap:10px;opacity:.75}
.pdetail .dhead .who i{width:9px;height:9px;background:var(--c-accent);flex:none;
  display:inline-block}
.pdetail .pclose{opacity:.75}

/* =========================================================================
   COMPACT BAND. Opening a project condenses every tile to a thumbnail —
   number and title only — which frees the vertical space the panel needs.

   EVERY property below uses --dur and --ease, with no delays. Earlier this
   had four transitions across three durations and two curves, plus the panel
   starting a frame late, and it read as several small animations tripping
   over each other rather than one movement.
   ========================================================================= */
.built,
.built h3,
.built .tbody,
.pdetail{transition-duration:var(--dur);transition-timing-function:var(--motion-ease)}
.built{transition-property:min-height,padding}
.built h3{transition-property:font-size,margin}
.built .tbody{transition-property:grid-template-rows,opacity,margin}
.pdetail{transition-property:height}

.built .tbody{display:grid;grid-template-rows:1fr}
.built .tbody>div{overflow:hidden;min-height:0}
.builtband.compact .built{min-height:0;padding:20px var(--pad)}
.builtband.compact .built .tbody{grid-template-rows:0fr;opacity:0;margin-top:0}
.builtband.compact .built h3{font-size:clamp(16px,1.5vw,19px);margin:8px 0 0;max-width:none}
.builtband.compact .built .top{margin-bottom:0}
/* a thumbnail that is not the open one still has to look clickable */
.builtband.compact .built:not(.on){opacity:.62}
.builtband.compact .built:not(.on):hover{opacity:1}
@media(prefers-reduced-motion:reduce){
  .built,.built h3,.built .tbody,.pdetail{transition:none}
}

/* =========================================================================
   PLAY. Justified rows, computed in JS from each image's true aspect ratio.

   Why not CSS grid: a grid forces every picture into a cell, so either the
   picture gets cropped or the cell gets empty. Why not CSS columns: they
   cannot reflow around a growing item. Justified rows are what a contact
   sheet actually is — every row exactly fills the width, every image keeps
   its own proportions, and there is no negative space anywhere.

   Sizes are written inline by site.js. Everything here is presentation only.
   ========================================================================= */
.playband{display:flex;flex-wrap:wrap;gap:var(--play-gap,2px);background:currentColor;
  align-content:flex-start}
.play{position:relative;display:block;padding:0;border:0;overflow:hidden;
  background:var(--c-beyond);color:var(--t-beyond);cursor:var(--cur-open);flex:0 0 auto}
.play img{display:block;width:100%;height:100%;object-fit:cover}
/* RESTORED. These were destroyed when the .play.big block was swapped out — the
   replacement matched from .play.big{ all the way to the reduced-motion rule and
   took the veil and the captions with it. That is why nothing dimmed. */
.play::after{content:"";position:absolute;inset:0;background:var(--t-page);opacity:0;
  transition:opacity var(--dur-fast) linear;pointer-events:none}
.play:hover::after{opacity:.26}
.play .cap,.play .t{position:absolute;left:14px;color:var(--c-read);opacity:0;
  transition:opacity var(--dur-fast) linear;text-shadow:0 1px 6px rgba(0,0,0,.6);
  pointer-events:none;z-index:2}
.play .cap{bottom:32px;font-family:var(--mono);font-size:9px;letter-spacing:.1em;
  text-transform:uppercase}
.play .t{bottom:14px;font-family:var(--serif);font-size:16px}
.play:hover .cap,.play:hover .t{opacity:1}

/* WHILE ONE IMAGE IS OPEN. The grid stays legible as a grid but stops
   competing: everything drops behind a black field, and hover is muted so the
   page does not light up under a wandering cursor. */
.playband.viewing .play::after{opacity:.74}
.playband.viewing .play:hover::after{opacity:.52}
.playband.viewing .play .cap,.playband.viewing .play .t{opacity:0}

/* THE SOURCE TILE. It goes furthest back, and it has NO hover state — hovering
   it was lifting the veil and lighting up the very thing that is meant to have
   been emptied out. The label it used to carry is gone; the cursor says it
   instead, which is quieter and only speaks when you are actually pointing. */
.playband.viewing .play.source::after,
.playband.viewing .play.source:hover::after{opacity:.93}
.playband.viewing .play.source{cursor:var(--cur-close)}
.playband.viewing .play.source:hover .cap,
.playband.viewing .play.source:hover .t{opacity:0}
/* and the same on the opened image itself, so there is a way out from the well */
.playview{cursor:var(--cur-close)}

/* THE VIEWING WELL. A full-width flex item, so inserting it forces a wrap:
   the rows above keep their exact positions and the rows below are pushed
   down. Its height is the only thing that animates. Peter: "you're getting to
   view the image without much visual noise, so you can really focus in on it." */
/* No height transition here: site.js drives the height frame by frame so it
   can move the scroll position by exactly the same amount at exactly the same
   time. That lockstep is what pins the clicked row while the rows above rise. */
.playview{flex:0 0 100%;height:0;overflow:hidden;background:var(--t-page)}
.playview .pv-inner{position:relative;height:100%;display:flex;align-items:center;
  justify-content:center;padding:clamp(26px,4vw,64px)}
.playview img{max-width:100%;max-height:100%;width:auto;height:auto;display:block;
  opacity:0;transform:scale(.99);
  transition:opacity var(--dur) var(--motion-ease),transform var(--dur) var(--motion-ease)}
.playview.in img{opacity:1;transform:none}
/* No counter, no close button. Peter: "I also don't think we need the numbering
   and the close button in the expanded view." The well is the picture and
   nothing else. */

/* Everything that is not the opened image drops back behind a black field, so
   the grid is still legible as a grid but stops competing with the picture.
   .play::after already exists for hover and is painted in --t-page. */
.playband.viewing .play::after{opacity:.68}
.playband.viewing .play:hover::after{opacity:.42}
.playband.viewing .play .cap,.playband.viewing .play .t{opacity:0}

@media(prefers-reduced-motion:reduce){
  .playview img{transition:none;opacity:1;transform:none}
}

/* The reserved-slot panel. Same component as the finished project, opened
   against the shape the write-up will take, so the open/switch/close
   behaviour can be judged on all three tiles rather than only on the one
   that happens to be written. */
.skeleton{list-style:none;margin:26px 0 0;padding:0;display:grid;gap:1px;
  background:currentColor;border-top:1px solid currentColor;
  border-bottom:1px solid currentColor}
.skeleton li{display:flex;align-items:center;gap:16px;padding:15px var(--pad) 15px 0;
  background:var(--c-built)}
.skeleton .mono{font-family:var(--mono);font-size:10px;letter-spacing:.12em;opacity:.5;
  min-width:2.4em}
.skeleton b{font-weight:400;font-size:15px;opacity:.82}
.skeleton i{flex:1;height:1px;background:currentColor;opacity:.22}
.pdetail .ref{margin-top:14px;font-size:12px;opacity:.55}

/* A label strip should not out-weigh the work it labels. These were carrying
   up to 120px of top padding plus the .phead default margin, so between two
   dense bands they read as the largest element on the page. */
.phead.bandhead{padding:clamp(30px,4.5vh,54px) var(--pad) clamp(14px,1.8vh,20px);
  margin-bottom:0;opacity:.45}
.phead.bandhead h2{font-size:11px;margin:0}

/* =========================================================================
   PERSONAL HERO. Same architecture as the homepage hero — mono kicker over
   a large serif line — so the two read as one system. The differences are
   deliberate and small: a coloured ground rather than paper, and the kicker
   in the accent, because this is the side of the site that gets to be louder.
   ========================================================================= */
.subhero.personal{background:var(--c-built);color:var(--t-built);
  min-height:62svh;justify-content:flex-end}
.subhero.personal .stem{display:block;color:var(--c-accent);margin-bottom:clamp(18px,2.4vh,26px);
  font-size:11px;letter-spacing:.14em}
.subhero.personal h1{font-family:var(--serif);font-weight:400;
  font-size:clamp(38px,6.6vw,104px);line-height:1;letter-spacing:-.024em;
  margin:0 0 clamp(20px,3vh,34px);max-width:17ch}
.subhero.personal p{font-size:clamp(15px,1.6vw,19px);line-height:1.55;max-width:56ch;opacity:.78}



/* ---- SEAMLESS PAGE TRANSITIONS (same-origin only) -------------------------
   Peter: "I really wish there was a way to make it fluid, to make the page
   that's leaving and the page that's coming in connected... it really kills
   the flow to have this huge blank negative space."

   This is that, natively. Cross-document View Transitions keep BOTH documents
   on screen at once and animate between them, so the outgoing and incoming
   pages travel edge to edge with nothing between them. No void, because there
   is no moment when only one page exists.

   It requires a same-origin pair. file:// origins are opaque, so this is inert
   when the site is opened from the filesystem and the JavaScript fallback in
   site.js takes over instead. Run `python3 serve.py` and open localhost to see
   the real thing — that needs no hosting decision.

   THE MASTHEAD IS A SHARED ELEMENT. Naming it means the browser carries the
   same bar across both documents rather than animating it out and back in.
   It genuinely persists — the illusion Peter asked for is no longer an
   illusion. */
@view-transition{ navigation:auto }

.mast{view-transition-name:mast}

::view-transition-group(root){ animation-duration:var(--dur-nav-in) }
::view-transition-old(root),::view-transition-new(root){
  animation-duration:var(--dur-nav-in);
  animation-timing-function:var(--ease);
  mix-blend-mode:normal;                    /* no cross-fade: the pages TOUCH */

  /* THE PALE STRIP, AND WHAT IT ACTUALLY WAS.
     Peter: "the white strip sits at the join between the pages and travels
     with it." That one sentence identified it. The document paints
     clientWidth (1455px here) but each snapshot is sized to the viewport
     (1470px) — the difference is the scrollbar column. So every snapshot
     carried ~15px of transparency at one edge, and both pages travelled the
     full viewport width rather than the width they had actually painted. The
     two painted edges could never meet, and the shortfall rode along with the
     join.

     Forcing the snapshot to fill its box makes the painted content and the
     travelled distance the same measurement again. This is what four earlier
     attempts were working around rather than fixing: the canvas colour, the
     scrollbar gutter, and twice an overlap — which is what produced the
     parallax, because an overlap is a second plane. */
  width:100%; height:100%; object-fit:fill;
  /* Trim the unpainted scrollbar column off both snapshots so only real page
     content is ever on screen. This is the pale bar Peter chased all evening:
     not a gap between the pages, but a strip belonging to one of them, riding
     along its right edge and covering the other at the join. */
  clip-path:inset(0 var(--vt-gutter, 0px) 0 0)}

/* The two pages travel as ONE object: same distance, same duration, same
   curve, meeting at exactly one edge.

   An earlier version offset them by 44px to hide a seam. That was wrong, and
   Peter named it precisely: "it looks like the elements aren't actually
   connected as one big continuous piece. They're moving and sliding at
   different speeds, and so they're parallaxing behind each other." An overlap
   IS a second plane. It cannot help but read as one. Whatever the pale strip
   turns out to be, it is not fixed by breaking the thing the motion exists to
   express. */
@keyframes vt-out-left { to   { transform:translateX(calc(-1 * var(--vt-travel, 100%))) } }
@keyframes vt-in-right { from { transform:translateX(var(--vt-travel, 100%))             } }
@keyframes vt-out-right{ to   { transform:translateX(var(--vt-travel, 100%))             } }
@keyframes vt-in-left  { from { transform:translateX(calc(-1 * var(--vt-travel, 100%))) } }


html[data-nav="deeper"]::view-transition-old(root){ animation-name:vt-out-left }
html[data-nav="deeper"]::view-transition-new(root){ animation-name:vt-in-right }
html[data-nav="back"]::view-transition-old(root){   animation-name:vt-out-right }
html[data-nav="back"]::view-transition-new(root){   animation-name:vt-in-left }

@media(prefers-reduced-motion:reduce){
  @view-transition{ navigation:none }
}

/* ---- page transitions ----------------------------------------------------
   A page mid-slide is wider than the window, so the horizontal overflow has to
   be clipped for the duration or the browser offers a scrollbar into empty
   space. The class is added and removed by site.js and exists nowhere at rest,
   so nothing here can interfere with normal scrolling. */
html.nav-x{overflow-x:hidden}
html.nav-x,html.nav-x body{max-width:100%}
.pageflow{will-change:auto}
/* The way out, on case pages only. Full strength against the other nav items,
   which sit at .78, so it reads as the exit without needing a colour of its
   own — the masthead ground is already the accent. */
.mast .r a.up{opacity:1}
/* home — normal declarations, then former priority declarations. */
/* removed 2026-09-22: body padding-bottom:48px existed only to clear the prototype's fixed #r2-tools diagnostic bar (round-two/round.css). The bar was stripped in the port; the padding left a blank strip below the footer. */
html.page-home .r2-status { margin-left: auto; font-size: 10px; }
html.page-home .r2-image,
html.page-home .r2-plate,
html.page-home .r2-cover,
html.page-home .r2-caseart { display: none; }
html.page-home .hero { position: relative; overflow: hidden; isolation: isolate; min-height: calc(-48px + 100svh); padding-top: clamp(120px, 20vh, 200px); padding-bottom: 38px; justify-content: flex-end; background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-home .hero:hover { background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-home .r2-image { display: block; position: absolute; inset: 12% 6% 19% 28%; z-index: 0; overflow: hidden; }
html.page-home .r2-image img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 50%; }
html.page-home .r2-plate { display: block; position: absolute; right: 2%; top: 56%; width: 26%; height: 24%; background: rgb(57, 44, 190); z-index: 1; }
html.page-home .hero h1.rot { font-family: var(--sans); font-weight: 400; letter-spacing: -0.066em; max-width: 15ch; position: relative; z-index: 2; color: rgb(28, 35, 29); line-height: 1.08; margin-bottom: clamp(32px, 6vh, 60px); }
html.page-home .hero .swap span { display: inline; background: rgb(220, 227, 194); box-decoration-break: clone; -webkit-box-decoration-break: clone; padding: 0px 0.035em; }
html.page-home .hero h1.rot .stem { width: max-content; background: rgb(220, 227, 194); padding: 3px 5px; }
html.page-home .hero h1.rot .stem { font-family: var(--mono); font-size: 0.105em; letter-spacing: 0.08em; text-transform: uppercase; opacity: 1; margin-bottom: 2em; }
html.page-home .hero .acts { position: relative; z-index: 3; width: 100%; background: rgb(220, 227, 194); padding-top: 15px; gap: 22px; }
html.page-home .hero .cta { background: none; border-bottom: 1px solid rgb(28, 35, 29); padding: 0px 0px 5px; color: rgb(28, 35, 29); font-size: 14px; }
html.page-home .hero .cta::after { content: " ↗"; margin-left: 20px; }
html.page-home .hero .quiet { opacity: 1; font-size: 12px; border-bottom: 0px; }
html.page-home .hero .quiet:hover { text-decoration: underline; }
html.page-home .mast { border-bottom: 1px solid rgba(28, 35, 29, 0.19); }
html.page-home .case .art { visibility: hidden; }
html.page-home .case > .r2-cover { display: block; position: absolute; left: 20%; right: 0px; top: 13%; height: 35%; z-index: 0; overflow: hidden; pointer-events: none; transition: opacity var(--dur) var(--motion-ease),transform var(--dur) var(--motion-ease); }
html.page-home .r2-cover img { width: 100%; height: 100%; object-fit: cover; object-position: 15% 25%; filter: saturate(0.7); }
html.page-home .case:nth-child(1) .r2-cover { clip-path: polygon(0px 0px, 100% 0px, 100% 75%, 60% 75%, 60% 100%, 0px 100%); }
html.page-home .case:nth-child(2) .r2-cover { left: 0px; right: 20%; top: 17%; height: 30%; clip-path: polygon(0px 0px, 60% 0px, 60% 25%, 100% 25%, 100% 100%, 0px 100%); }
html.page-home .case:nth-child(2) .r2-cover img { object-position: 78% 35%; filter: saturate(0.5) contrast(1.12); }
html.page-home .case:nth-child(3) .r2-cover { left: 20%; right: -20%; height: 34%; top: 12%; clip-path: polygon(0px 0px, 80% 0px, 80% 35%, 100% 35%, 100% 100%, 0px 100%); }
html.page-home .case:nth-child(3) .r2-cover img { object-position: 55% 90%; filter: saturate(0.9); }
html.page-home .case h3 { max-width: 15ch; }
html.page-home .case .top { opacity: 1; }
html.page-home .case:not(.open):is(:hover, :focus-visible) > .r2-cover { opacity: 0.2; transform: translateX(-10px); }
html.page-home .case.open > .r2-cover,
html.page-home .band.anyopen .case:not(.open) > .r2-cover { display: none; }
html.page-home .case.open .top { opacity: 0.7; }
html.page-home #approach { position: relative; overflow: hidden; padding-top: clamp(80px, 13vh, 145px); padding-bottom: clamp(90px, 16vh, 170px); }
html.page-home #approach .statement { max-width: 20ch; position: relative; z-index: 2; }
html.page-home #approach .statement em { color: rgb(57, 44, 190); }
html.page-home #approach .sub-statement { position: relative; z-index: 2; opacity: 1; max-width: 35ch; margin-left: 33.333%; }
html.page-home .lens { border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-home .lens p { opacity: 1; }
html.page-home .p-gold { padding-left: calc(var(--pad) + 8vw); padding-right: calc(var(--pad) + 8vw); }
html.page-home .quote { max-width: 22ch; }
html.page-home .quote em { opacity: 1; color: rgb(237, 195, 184); }
html.page-home .casehero { position: relative; overflow: hidden; isolation: isolate; background: rgb(38, 59, 54); color: rgb(244, 240, 231); min-height: 65vh; padding-top: clamp(120px, 20vh, 200px); padding-right: 35%; }
html.page-home .r2-caseart { display: block; position: absolute; inset: 0px 0px 0px 45%; z-index: -1; clip-path: polygon(20% 0px, 100% 0px, 100% 100%, 0px 100%, 0px 65%, 20% 65%); }
html.page-home .r2-caseart img { width: 100%; height: 100%; object-fit: cover; opacity: 0.32; }
html.page-home .casehero .hook { opacity: 1; }
html.page-home .casebody { padding-top: clamp(60px, 9vh, 110px); }
html.page-home .subhero.personal { background: rgb(237, 195, 184); }
html.page-home .subhero.personal h1 { max-width: 18ch; }
html.page-home .builtband .built { background: rgb(244, 240, 231); border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-home .builtband .built:hover { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-home .play { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-home.r2-grid body::after { content: ""; position: fixed; inset: 0 var(--pad) 48px; pointer-events: none; z-index: 99998; background: repeating-linear-gradient(90deg, rgba(240, 60, 83, 0.25) 0px, rgba(240, 60, 83, 0.25) 1px, transparent 1px, transparent calc(8.33333%)); }
@media (max-width: 899px) {
html.page-home .hero { min-height: calc(-64px + 100svh); padding-top: 210px; padding-bottom: 25px; }
}
@media (max-width: 899px) {
html.page-home .r2-image { inset: 12% 0px 26% 18%; }
}
@media (max-width: 899px) {
html.page-home .r2-plate { right: 0px; top: 49%; width: 33%; height: 23%; }
}
@media (max-width: 899px) {
html.page-home .hero h1.rot { max-width: 15ch; letter-spacing: -0.055em; }
}
@media (max-width: 899px) {
html.page-home .hero .acts { gap: 15px; flex-wrap: wrap; }
}
@media (max-width: 899px) {
html.page-home .case > .r2-cover { top: 14%; height: 30%; left: 40%; right: 0px; }
}
@media (max-width: 899px) {
html.page-home .case:nth-child(2) > .r2-cover { left: 25%; top: 13%; }
}
@media (max-width: 899px) {
html.page-home .case:nth-child(3) > .r2-cover { left: 40%; right: 0px; top: 13%; }
}
@media (max-width: 899px) {
html.page-home .casehero { padding-right: var(--pad); min-height: 55vh; }
}
@media (max-width: 899px) {
html.page-home .r2-caseart { left: 30%; opacity: 0.5; }
}
@media (max-width: 899px) {
html.page-home #approach .sub-statement { margin-left: 0px; }
}
@media (max-width: 899px) {
html.page-home .p-gold { padding-left: var(--pad); padding-right: var(--pad); }
}
@media (max-width: 899px) {
html.page-home .r2-status { display: none; }
}
@media (max-width: 600px) {
html.page-home .mast { display: grid; grid-template-columns: 1fr; gap: 7px; padding-top: 9px; padding-bottom: 9px; }
}
@media (max-width: 600px) {
html.page-home .mast .r { display: flex; width: 100%; justify-content: space-between; gap: 6px; }
}
@media (max-width: 600px) {
html.page-home .hero h1.rot .stem { font-size: 11px; }
}
@media (max-width: 600px) {
html.page-home .hero .acts .cta { width: 100%; margin-bottom: 5px; text-align: left; }
}
@media (max-width: 600px) {
html.page-home .casehero .top { margin-top: 15px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .r2-cover { transition: none; }
}
html.page-home .hero,
html.page-home .hero:hover { height: calc(-230px + 100svh); min-height: 380px; padding: clamp(84px,10vh,120px) var(--pad) 48px; justify-content: flex-start; background: rgb(240, 238, 230); }
html.page-home .hero .acts,
html.page-home .r2-plate { display: none; }
html.page-home .r2-image { inset: 0px 0px 0px 38%; overflow: hidden; }
html.page-home .r2-image img { filter: contrast(1.35) brightness(0.38); object-position: 25% 50%; }
html.page-home .hero h1.rot { color: white; mix-blend-mode: difference; max-width: 15ch; font-size: clamp(50px, 8.4vw, 128px); line-height: 0.99; margin: 0px; letter-spacing: -0.06em; }
html.page-home .hero .swap span { display: block; background: none; padding: 0px; }
html.page-home .hero h1.rot .stem { background: none; padding: 0px; font-size: 12px; margin-bottom: 28px; }
html.page-home .r3-next { display: none; }
html.page-home .r3-next { position: absolute; left: var(--pad); right: var(--pad); bottom: 20px; display: flex; justify-content: space-between; color: rgb(248, 231, 207); mix-blend-mode: normal; z-index: 3; font: 11px var(--mono); text-transform: uppercase; letter-spacing: 0.08em; text-decoration: none; }
html.page-home .r3-next span:last-child { font: 30px var(--sans); }
html.page-home .case { border-top: 1px solid; }
html.page-home .case > .r2-cover,
html.page-home .case:nth-child(2) > .r2-cover,
html.page-home .case:nth-child(3) > .r2-cover { inset: 105px 0px auto; height: 38%; clip-path: none; transform: none; opacity: 1; border-bottom: 1px solid; color: inherit; overflow: hidden; }
html.page-home .folio,
html.page-home .folio-echo { position: absolute; left: 8%; top: -0.19em; font: 400 clamp(200px,25vw,390px)/1 var(--serif); letter-spacing: -0.09em; }
html.page-home .folio-echo { left: 40%; color: transparent; -webkit-text-stroke: 1px currentcolor; opacity: 0.3; transform: translateX(25%); }
html.page-home .case:nth-child(2) .folio { transform: translateX(-16%); }
html.page-home .case:nth-child(3) .folio { left: 35%; }
html.page-home .case h3 { max-width: 16ch; }
html.page-home .band.anyopen .case:not(.open) > .r2-cover { display: block; inset: 0px; height: 100%; border: 0px; opacity: 0.8; background: repeating-linear-gradient(0deg, transparent 0px, transparent 45px, rgba(255, 255, 255, 0.094) 45px, rgba(255, 255, 255, 0.094) 46px); }
html.page-home .band.anyopen .case:not(.open) .folio { font-size: 400px; top: 10%; left: -65px; writing-mode: vertical-rl; }
html.page-home .band.anyopen .case:not(.open) .folio-echo { display: none; }
html.page-home .band.anyopen .case:not(.open) .spine { background: var(--c-case2); color: rgb(255, 255, 255); padding: 12px 7px; opacity: 1; }
html.page-home .band.anyopen .case:not(.open):hover > .r2-cover { transform: translateY(-15px); opacity: 1; }
html.page-home .case.open > .r2-cover { display: none; }
html.page-home #approach { border-top: 1px solid rgb(39, 59, 54); background: rgb(240, 238, 230); }
html.page-home #approach .statement em { color: rgb(39, 59, 54); }
html.page-home .casehero { padding-top: clamp(100px, 15vh, 160px); }
html.page-home .r2-caseart { clip-path: none; }
html.page-home .r2-caseart img { filter: grayscale(1); opacity: 0.2; }
@media (max-width: 899px) {
html.page-home .hero,
html.page-home .hero:hover { height: calc(-220px + 100svh); min-height: 340px; padding-top: 95px; }
}
@media (max-width: 899px) {
html.page-home .hero h1.rot { font-size: clamp(46px, 8.4vw, 76px); max-width: 15ch; }
}
@media (max-width: 899px) {
html.page-home .r2-image { left: 48%; }
}
@media (max-width: 899px) {
html.page-home .case { min-height: 560px; }
}
@media (max-width: 899px) {
html.page-home .case > .r2-cover,
html.page-home .case:nth-child(2) > .r2-cover,
html.page-home .case:nth-child(3) > .r2-cover { top: 60px; height: 210px; }
}
@media (max-width: 899px) {
html.page-home .folio,
html.page-home .folio-echo { font-size: 280px; }
}
@media (max-width: 899px) {
html.page-home .band.anyopen .case:not(.open) > .r2-cover { inset: 60px 0px auto; height: 210px; }
}
@media (max-width: 899px) {
html.page-home .band.anyopen .case:not(.open) .folio { font-size: 280px; writing-mode: horizontal-tb; top: -0.19em; left: 8%; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-home .hero,
html.page-home .hero:hover { min-height: 270px; height: calc(-165px + 100svh); padding-top: 65px; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-home .hero h1.rot { font-size: clamp(40px, 5vw, 70px); }
}
html.page-home body { padding: 0px; background: rgb(240, 238, 230); color: rgb(32, 40, 34); }
html.page-home .studyhead { padding: 28px var(--pad) 30px; }
html.page-home .studyhead p { font: 12px/1.5 var(--mono); margin: 0px 0px 16px; }
html.page-home .studyhead h1 { font: 400 clamp(32px,4vw,60px)/1.1 var(--serif); margin: 0px 0px 18px; }
html.page-home .studyhead nav { display: flex; gap: 10px; flex-wrap: wrap; }
html.page-home .studyhead button { font: 12px var(--mono); border: 1px solid rgb(32, 40, 34); background: none; color: inherit; padding: 12px 16px; cursor: pointer; }
html.page-home .studyhead button[aria-pressed="true"] { background: rgb(32, 40, 34); color: rgb(240, 238, 230); }
html.page-home .band.anyopen .case:not(.open) .spine { background: none; color: inherit; padding: 0px; opacity: 1; }
html.page-home .band.anyopen .case:not(.open) .spine .sn { color: inherit; }
html.page-home .case > .r2-cover,
html.page-home .case:nth-child(2) > .r2-cover,
html.page-home .case:nth-child(3) > .r2-cover { inset: 95px 0px auto; height: 36%; clip-path: none; background: none; border: 0px; opacity: 1; transform: none; }
html.page-home .number,
html.page-home .letter,
html.page-home .optics { display: none; position: absolute; }
html.page-home .number { display: block; font: 400 clamp(190px,23vw,350px)/.8 var(--serif); letter-spacing: -0.08em; left: 12%; top: 5%; }
html.page-home .case:not(.open):is(:hover, :focus-visible) > .r2-cover { opacity: 0.35; transform: none; }
html.page-home .band.anyopen .case:not(.open) > .r2-cover { display: block; inset: 0px 0px 170px; height: auto; opacity: 0.8; }
html.page-home .band.anyopen .case:not(.open) .number { font-size: 340px; writing-mode: vertical-rl; left: -50px; top: 30px; }
html.page-home .band.anyopen .case:not(.open) .letter { font-size: 480px; left: -100px; top: 40px; writing-mode: vertical-rl; }
html.page-home .band.anyopen .case:not(.open) .optics { inset: 0px -180px; }
html.page-home .case.open > .r2-cover { display: none; }
@media (max-width: 899px) {
html.page-home .case > .r2-cover,
html.page-home .case:nth-child(2) > .r2-cover,
html.page-home .case:nth-child(3) > .r2-cover { top: 65px; height: 200px; }
}
@media (max-width: 899px) {
html.page-home .studyhead { padding-top: 22px; }
}
@media (max-width: 899px) {
html.page-home .band.anyopen .case:not(.open) > .r2-cover { inset: 65px 0px auto; height: 200px; }
}
@media (max-width: 899px) {
html.page-home .band.anyopen .case:not(.open) .number,
html.page-home .band.anyopen .case:not(.open) .letter { writing-mode: horizontal-tb; left: 12%; top: 5%; }
}
@media (min-width: 900px) {
html.page-home .band:not(.anyopen) .case .sub { min-height: var(--shared-description-height,0px); }
}
html.page-home .band:not(.anyopen) .case { transition: background-color .135s linear,color .135s linear,flex-grow .68s var(--ease); }
html.page-home .band:not(.anyopen) .case::before { display: none; }
html.page-home .case > .r2-cover { opacity: 1; }
html.page-home .case:nth-child(1) > .r2-cover { color: var(--t-case1); }
html.page-home .case:nth-child(2) > .r2-cover { color: var(--t-case2); }
html.page-home .case:nth-child(3) > .r2-cover { color: var(--t-case3); }
html.page-home .band:not(.anyopen) .case:is(:hover, :focus-visible, .demo-hover) { background: rgb(25, 28, 32); color: rgb(244, 240, 231); }
html.page-home .band:not(.anyopen) .case h3,
html.page-home .band:not(.anyopen) .case .top .n { color: inherit; }
html.page-home .band.anyopen .case:not(.open) .spine { background: none; color: inherit; }
html.page-home .band.anyopen .case:not(.open) { transition: background-color .135s linear,color .135s linear,flex-grow .68s var(--ease); }
html.page-home .band.anyopen .case:not(.open)::before { display: none; }
html.page-home .band.anyopen .case:not(.open) > .r2-cover { color: inherit; }
html.page-home .band.anyopen .case:not(.open):is(:hover, :focus-visible, .demo-hover) { background: rgb(25, 28, 32); color: rgb(244, 240, 231); }
html.page-home .band.anyopen .case:nth-child(2):not(.open):is(:hover, :focus-visible, .demo-hover) { background: rgb(244, 240, 231); color: rgb(25, 28, 32); }
html.page-home .band.anyopen .case:not(.open) .spine .sn { color: inherit; }
@media (prefers-reduced-motion: reduce) {
html.page-home .band.anyopen .case:not(.open) { transition: none; }
}
html.page-home .r3-next span:last-child { display: none; }
html.page-home .mast .r { position: relative; }
html.page-home .reading-rail { position: absolute; left: 0px; top: 0px; overflow: visible; pointer-events: none; fill: none; stroke: currentcolor; stroke-width: 1; }
html.page-home .mast .r a[aria-current="location"] { opacity: 1; }
@media (max-width: 700px) {
html.page-home .mast .r { isolation: isolate; }
}
html.page-home #reading { background: rgb(198, 189, 104); color: rgb(32, 40, 34); position: relative; }
html.page-home #reading .hold { padding: 5vh 6vw; display: flex; flex-direction: column; justify-content: space-between; min-height: 85svh; }
html.page-home #reading .label,
html.page-home #reading button { font: 11px / 1.6 "Roboto Mono", monospace; letter-spacing: 0.06em; }
html.page-home #reading blockquote { margin: 4vh 0px; }
html.page-home #reading blockquote p { font: 400 clamp(35px, 4.8vw, 78px) / 1.07 "Instrument Serif", serif; letter-spacing: -0.018em; max-width: 1400px; margin: 0px; }
html.page-home #reading blockquote footer { font: 12px / 1.6 Inter, sans-serif; margin-top: 30px; opacity: 0; }
html.page-home #reading .word { display: inline-block; opacity: 0; padding-bottom: 0.22em; margin-bottom: -0.22em; overflow: visible; }
html.page-home #reading .foot { display: flex; align-items: center; gap: 24px; flex-wrap: wrap; background: transparent; color: inherit; padding: 0px; border: 0px; opacity: 1; }
html.page-home #reading button { color: inherit; background: none; border: 0px; padding: 12px 0px; text-decoration: underline; cursor: pointer; }
html.page-home #reading .quote-dots { display: flex; gap: 2px; margin-left: auto; }
html.page-home #reading .quote-dots button { width: 36px; height: 36px; padding: 0px; display: grid; place-items: center; text-decoration: none; }
html.page-home #reading .quote-dots button::after { content: ""; width: 6px; height: 6px; border: 1px solid; border-radius: 50%; }
html.page-home #reading .quote-dots button[aria-pressed="true"]::after { background: currentcolor; }
html.page-home #reading button:focus-visible { outline: currentcolor solid 2px; outline-offset: 2px; }
html.page-home #reading #place { visibility: hidden; }
html.page-home.rhythm-on #work .case:not(.entered) .number,
html.page-home.rhythm-on #work .case:not(.copy-entered) h3,
html.page-home.rhythm-on #work .case:not(.copy-entered) .sub,
html.page-home.rhythm-on #work .case:not(.copy-entered) .toggle { visibility: hidden; }
/* 2026-09-22: these five selectors read "html.page-home .rhythm-on" — a descendant
   space — but rhythm-on is set ON <html>, so they matched nothing. The work-card
   numerals therefore sat visible until their entrance animation blanked them and
   played them back in (Peter, incognito). From page-rhythm/rhythm.css line 28. */
@media (max-width: 600px) {
html.page-home #reading blockquote p { font-size: clamp(32px, 7.7vw, 45px); }
}
@media (max-width: 600px) {
html.page-home #reading .hold { padding: 4vh 6vw; }
}
html.page-home .fm-wait { opacity: 0; }
html.page-home #about .ans:not(.answer-ready) { visibility: hidden; }
html.page-home #approach .statement,
html.page-home #approach .statement em,
html.page-home #approach .sub-statement { opacity: 1; }
html.page-home #approach .fm-wait { opacity: 0; }
html.page-home .mast:hover { background: var(--c-mast); color: var(--t-mast); }
html.page-home .mast:has(> a:is(:hover, :focus-visible)) { background: var(--mast-home-hover,var(--c-masth)); color: var(--mast-home-ink,var(--t-masth)); }
html.page-home #about .acc details[open] summary::after { display: none; }
html.page-home #about .acc { transition: min-height 850ms cubic-bezier(0.22, 0.7, 0.2, 1); }
html.page-home .row-number { display: none; }
html.page-home .row-question { display: inline; }
html.page-home #contact .statement > span,
html.page-home #contact .statement > em { display: inline-block; }
html.page-home #about .acc { position: relative; }
html.page-home #about details[open] summary { opacity: 1; }
html.page-home #about details .ans { animation: auto ease 0s 1 normal none running none; }
html.page-home #about details { width: 42%; }
html.page-home #about .ans { position: absolute; left: 49%; top: 0px; width: 51%; padding: 24px 0px 24px 32px; border-left: 1px solid; margin: 0px; box-sizing: border-box; }
html.page-home #about .ans p { max-width: 48ch; margin: 0px; }
@media (max-width: 760px) {
html.page-home #about details { width: 100%; }
}
@media (max-width: 760px) {
html.page-home #about .ans { position: static; width: auto; margin-left: 20px; padding: 16px 0px 16px 20px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .fm-wait { opacity: 1; }
}
html.page-home #about .acc summary { font-size: clamp(21px, 2.1vw, 30px); line-height: 1.18; padding: 20px 24px 20px 42px; position: relative; letter-spacing: -0.025em; }
html.page-home #about .acc summary::before { content: attr(data-index); position: absolute; left: 0px; }
html.page-home #about .acc details::before { content: attr(data-index); position: absolute; margin-top: 24px; font: 10px var(--mono); opacity: 0.55; pointer-events: none; }
html.page-home #about .acc .pm { display: none; }
html.page-home #about .acc details { border-width: 1px 0px 0px; border-style: solid none none; border-color: color-mix(in srgb, currentcolor 20%, transparent) currentcolor currentcolor; border-image: none; }
html.page-home #about .acc details[open] summary { color: inherit; }
html.page-home #about .acc details[open] summary::after { content: ""; position: absolute; left: 0px; top: 47px; width: 18px; height: 1px; background: currentcolor; }
html.page-home #about .answer-caption { font: 10px var(--mono); text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 24px; opacity: 0.6; }
html.page-home #about .acc .ans p { font-size: clamp(17px, 1.45vw, 21px); line-height: 1.65; max-width: 47ch; }
html.page-home #about details { width: 34%; }
html.page-home #about .ans { left: 43%; width: 57%; padding: 20px 0px 24px; border: 0px; }
@media (max-width: 760px) {
html.page-home #about details { width: 100%; }
}
@media (max-width: 760px) {
html.page-home #about .ans { position: static; width: auto; padding: 16px 0px 24px 42px; margin: 0px; }
}
html.page-home #reading { background: var(--finish-quote,#c6bd68); color: var(--finish-quote-ink,#202822); }
html.page-home .palette-source { width: 100%; height: 110px; object-fit: contain; background: rgb(221, 221, 221); }
html.page-home .palette-swatches { display: flex; gap: 6px; margin-top: 10px; }
html.page-home .palette-swatches span { flex: 1 1 0%; }
html.page-home .palette-swatches i { display: block; height: 30px; }
html.page-home .palette-swatches small { font: 9px monospace; }
html.page-home #about .acc details::before { display: none; }
html.page-home #about .row-number { display: block; font: 11px var(--mono); opacity: 0.65; margin-bottom: 14px; }
html.page-home #about .row-question { display: block; }
html.page-home #about .acc summary { display: grid; grid-template-columns: 32px 1fr; gap: 20px; align-items: baseline; padding: 30px 20px 32px 0px; font-size: clamp(27px, 2.55vw, 37px); line-height: 1.2; }
html.page-home #about details { width: 39%; }
html.page-home #about .ans { left: 49%; width: 51%; padding-top: 30px; }
html.page-home #about .acc .ans p { font-size: clamp(20px, 1.75vw, 25px); line-height: 1.65; max-width: 43ch; }
html.page-home #about .acc details[open] summary::after { top: 38px; left: 30px; width: 24px; }
html.page-home #about .acc details:not([data-fanned]) .row-number,
html.page-home #about .acc details:not([data-fanned]) .row-question { opacity: 0; }
@media (max-width: 760px) {
html.page-home #about details { width: 100%; }
}
@media (max-width: 760px) {
html.page-home #about .ans { width: auto; padding: 8px 0px 32px 28px; }
}
@media (max-width: 760px) {
html.page-home #about .acc summary { font-size: 28px; }
}
html.page-home #about .acc summary { color: color-mix(in srgb,var(--t-beyond) 62%,var(--c-beyond)); transition: color 180ms, background-color 180ms, box-shadow 180ms; padding-left: 16px; padding-right: 16px; }
html.page-home #about .acc details[open] summary { color: var(--t-beyond); }
html.page-home #about .acc .row-number { opacity: 1; }
html.page-home #about .acc details summary:is(:hover, :focus-visible) { background: var(--about-hover-bg,var(--t-beyond)); color: var(--c-beyond); box-shadow: inset 0 1px 0 color-mix(in srgb,var(--c-beyond) 55%,transparent); }
html.page-home #about .row-word { display: inline-block; }
html.page-home #about .acc summary:focus-visible { outline: currentcolor solid 2px; outline-offset: 3px; }
html.page-home #about .acc summary .row-number { position: relative; }
html.page-home #about .acc summary .row-number::after { content: ""; position: absolute; left: 0px; top: calc(100% + 9px); width: 6px; height: 6px; border-radius: 50%; background: currentcolor; opacity: 0; transform: scale(0.5); transition: opacity 180ms, transform 180ms; }
html.page-home #about .acc details[open] .row-number::after { opacity: 1; transform: scale(1); }
html.page-home #about .acc summary .row-number { display: flex; align-items: center; justify-content: center; width: 32px; height: 30px; margin: 0px; box-sizing: border-box; transition: background-color 180ms, color 180ms; }
html.page-home #about .acc summary .row-number::after { display: none; }
html.page-home #about .acc details[open] .row-number { background: var(--about-hover-bg,var(--t-beyond)); color: var(--c-beyond); }
html.page-home #about .acc details[open] summary:is(:hover, :focus-visible) .row-number { background: var(--c-beyond); color: var(--about-hover-bg,var(--t-beyond)); }
html.page-home #about .acc details[open] summary .row-number { background: transparent; color: inherit; }
html.page-home #about .acc details[open] summary:is(:hover, :focus-visible) .row-number { background: transparent; color: inherit; }
html.page-home body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { text-transform: uppercase; -webkit-text-stroke: 0px; }
html.page-home body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .ind-project-label):not(.fm-wait) { opacity: 1; }
html.page-home body .linkband .k { opacity: 0.5; }
html.page-home body .contact-meta:not(.fm-wait) { opacity: 0.62; }
html.page-home #approach .sub-statement { max-width: 44ch; margin: 36px 0px 0px auto; font-family: var(--sans,Arial); font-size: clamp(18px, 1.6vw, 23px); font-weight: 400; letter-spacing: 0px; line-height: 1.55; text-wrap: pretty; }
html.page-home .lensband .lens:nth-child(n) { --ink: #102b55; --rule-accent: #f8e7cf; transition: background-color 350ms, color 350ms; }
html.page-home .lensband .lens:nth-child(n) { --ink: #f8e7cf; }
html.page-home #reading { --finish-quote-ink: #244d50; }
html.page-home #about .acc details { --about-hover-bg: #082a73; }
html.page-home #about .acc details:nth-child(2) { --about-hover-bg: #056a91; }
html.page-home #about .acc details:nth-child(3) { --about-hover-bg: #087865; }
html.page-home #about .acc details:nth-child(4) { --about-hover-bg: #056a2f; }
html.page-home #about .acc details:nth-child(5) { --about-hover-bg: #66592a; }
html.page-home #about .ans { font-weight: 400; letter-spacing: 0px; max-width: 52ch; padding-top: 20px; }
html.page-home #about .ans p { font: inherit; max-width: 52ch; }
@supports (background-clip:text) {
html.page-home #reading #words { position: relative; }
}
@supports (background-clip:text) {
html.page-home #reading #words .word { background-image: url("/static/art/independent-prism.webp"); background-size: var(--quote-art-size,auto 100vh); background-position: var(--word-crop,center); background-clip: text; -webkit-text-fill-color: transparent; text-shadow: none; -webkit-text-stroke: 0px; }
}
@media (max-width: 700px) {
html.page-home #approach .sub-statement { margin-left: 0px; }
}
html.page-home .lensband .lens { padding: 40px var(--pad) 64px; overflow: visible; transition: background-color 240ms, color 240ms; }
html.page-home .lensband .lens::before { display: none; }
html.page-home .lensband .lens h2 { font: 400 clamp(30px,3vw,46px)/1.08 var(--serif); letter-spacing: -0.025em; margin: 30px 0px; max-width: 17ch; }
html.page-home .lensband .lens p { font: 400 17px / 1.65 Inter, sans-serif; max-width: 48ch; margin: 0px; opacity: 1; }
html.page-home .lensband .lens .n { display: flex; align-items: center; gap: 22px; margin: 0px; font: 11px var(--mono); }
html.page-home .argument-rule { display: block; flex: 1 1 0%; height: 1px; background: currentcolor; opacity: 0.4; transform-origin: left center; }
html.page-home .lensband { background: var(--c-lens1); }
html.page-home .lensband .lens { background: transparent; color: var(--t-lens1); border-right: 1px solid color-mix(in srgb,var(--t-lens1) 16%,transparent); }
html.page-home .lensband .lens:last-child { border-right: 0px; }
@media (min-width: 820px) {
html.page-home .lensband { grid-template-rows: auto auto auto; }
}
@media (min-width: 820px) {
html.page-home .lensband .lens { display: grid; grid-row: span 3; grid-template-rows: subgrid; row-gap: 0px; }
}
@media (min-width: 820px) {
html.page-home .lensband .lens h2 { align-self: end; max-width: none; width: 100%; box-sizing: border-box; }
}
@media (min-width: 820px) {
html.page-home .lensband .lens p { align-self: start; }
}
html.page-home .lensband .lens:is(:hover, :focus-visible) { background: var(--c-lens2); color: var(--t-lens2); }
html.page-home .lensband .lens:focus-visible { outline: currentcolor solid 2px; outline-offset: -8px; }
html.page-home .lensband .lens:not([data-approach-seen]) > h2,
html.page-home .lensband .lens:not([data-approach-seen]) > p { opacity: 0; }
@media (max-width: 819px) {
html.page-home .lensband .lens { padding: 32px var(--pad) 40px; border-width: 1px 0px 0px; border-style: solid none none; border-color: currentcolor; border-image: none; }
}
@media (max-width: 819px) {
html.page-home .lensband .lens h2 { font-size: 34px; max-width: 22ch; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .lensband .lens { transition: none; }
}
@media (min-width: 1100px) {
html.page-home .lensband .lens { padding-left: 16px; padding-right: 16px; }
}
@media (min-width: 1100px) {
html.page-home .lensband .lens h2 { font-size: clamp(28px, 2.65vw, 42px); max-width: 11.4em; text-wrap: balance; }
}
@media (min-width: 820px) and (max-width: 1099px) {
html.page-home .lensband { grid-template-columns: 1fr; grid-template-rows: auto; }
}
@media (min-width: 820px) and (max-width: 1099px) {
html.page-home .lensband .lens { display: flex; grid-row: auto; }
}
@media (min-width: 820px) and (max-width: 1099px) {
html.page-home .lensband .lens h2 { align-self: start; max-width: 22ch; }
}
@media (min-width: 1100px) {
html.page-home .lensband .lens:nth-child(3) h2 { max-width: 9.8em; }
}
html.page-home .lensband .lens:nth-child(1) { --panel: var(--c-lens1); --ink: var(--t-lens1); --hover-panel: var(--c-lens2); --hover-ink: var(--t-lens2); --rule-accent: var(--approach-accent1,var(--t-lens2)); }
html.page-home .lensband .lens:nth-child(2) { --panel: var(--c-lens2); --ink: var(--t-lens2); --hover-panel: var(--c-lens3); --hover-ink: var(--t-lens3); --rule-accent: var(--approach-accent2,var(--t-lens3)); }
html.page-home .lensband .lens:nth-child(3) { --panel: var(--c-lens3); --ink: var(--t-lens3); --hover-panel: var(--c-lens1); --hover-ink: var(--t-lens1); --rule-accent: var(--approach-accent3,var(--t-lens1)); }
html.page-home .lensband .lens { background: var(--panel); color: var(--ink); transition: background-color 450ms, color 450ms; }
html.page-home .lensband .lens:is(:hover, :focus-visible) { background: var(--hover-panel); color: var(--hover-ink); }
html.page-home .lensband .lens .n { color: inherit; transition: color 600ms; }
html.page-home .lensband .lens:is(:hover, :focus-visible) .n { color: var(--rule-accent); }
html.page-home .argument-rule { position: relative; opacity: 1; background: color-mix(in srgb,var(--ink,currentColor) 35%,transparent); }
html.page-home .argument-rule::after { content: ""; position: absolute; inset: 0px; background: var(--rule-accent,currentColor); transform: scaleX(0); transform-origin: left center; transition: transform 750ms cubic-bezier(0.35, 0, 0.2, 1); }
html.page-home .lens:is(:hover, :focus-visible) .argument-rule::after { transform: scaleX(1); }
@media (prefers-reduced-motion: reduce) {
html.page-home .lensband .lens,
html.page-home .lensband .lens .n,
html.page-home .argument-rule::after { transition: none; }
}
html.page-home .hero { isolation: isolate; overflow: hidden; }
html.page-home .art-window { position: absolute; inset: 0px; width: 100%; height: 100%; pointer-events: none; z-index: -1; }
html.page-home .hero .art-window { z-index: 0; }
html.page-home .hero h1 { position: relative; z-index: 2; }
html.page-home .hero-cutout { position: absolute; inset: 0px; width: 100%; height: 100%; pointer-events: none; z-index: 3; opacity: 0; transition: opacity 350ms; }
@media (hover: hover) {
html.page-home .hero:hover .hero-cutout { opacity: 1; }
}
html.page-home .hero::after { content: ""; position: absolute; inset: 0px; background: var(--c-hero); opacity: 0; transition: opacity 350ms; z-index: 1; pointer-events: none; }
@media (hover: hover) {
html.page-home .hero:hover::after { opacity: 1; }
}
html.page-home #independent-study { position: relative; isolation: isolate; background: transparent; }
html.page-home #independent-study { min-height: 60svh; display: flex; flex-direction: column; justify-content: center; padding-top: clamp(72px, 10vh, 140px); padding-bottom: clamp(72px, 10vh, 140px); overflow: hidden; }
html.page-home #independent-study .ind-heading { position: relative; isolation: isolate; }
html.page-home #independent-study .ind-heading h2 { display: inline-block; width: fit-content; padding: 0px; background: none; color: rgb(255, 255, 255); }
html.page-home #reading { background: var(--finish-quote,var(--c-quote)); color: var(--finish-quote-ink,var(--t-quote)); }
html.page-home #reading .hold { margin-right: 0px; background: transparent; color: inherit; }
html.page-home #reading blockquote,
html.page-home #reading blockquote p,
html.page-home #reading blockquote p .word { color: inherit; mix-blend-mode: normal; -webkit-text-stroke: 0px; text-shadow: none; }
html.page-home #reading blockquote footer { max-width: 46ch; font-size: 12px; line-height: 1.5; color: inherit; background: none; padding: 0px; }
html.page-home .linkband > a { position: relative; isolation: isolate; overflow: hidden; }
html.page-home .linkband > a .art-window { z-index: 0; opacity: 0; transition: opacity 300ms; }
html.page-home .linkband > a:is(:hover, :focus-visible) .art-window { opacity: 1; }
html.page-home .linkband > a > span { position: relative; z-index: 1; }
html.page-home .linkband > a:is(:hover, :focus-visible) > span { background: var(--c-links); color: var(--t-links); box-shadow: 5px 0 var(--c-links),-5px 0 var(--c-links); }
html.page-home .hero h1.rot { font-optical-sizing: auto; }
html.page-home #approach { display: flex; flex-direction: column; align-items: flex-end; text-align: right; }
html.page-home #approach .statement { width: 85%; text-wrap: balance; }
html.page-home #approach .sub-statement { width: min(100%, 44ch); }
@media (max-width: 760px) {
html.page-home #approach .statement { width: 100%; }
}
html.page-home #about .acc summary { isolation: isolate; overflow: hidden; }
html.page-home #about .acc summary .about-crop { position: absolute; inset: 0px; z-index: -1; pointer-events: none; background-image: url("/static/art/hero-prism.webp"); background-size: var(--about-art-size); background-position: var(--crop-position); background-repeat: no-repeat; opacity: 0; transition: opacity 380ms; }
html.page-home #about .acc summary:is(:hover, :focus-visible) { text-shadow: none; -webkit-text-stroke: 0px; }
html.page-home #about .acc summary:is(:hover, :focus-visible) .about-crop { opacity: 1; }
html.page-home #independent-study { background: var(--c-beyond); color: var(--t-beyond); padding: 28px var(--pad) 64px; }
html.page-home .ind-heading { display: flex; justify-content: space-between; gap: 20px; border-top: 1px solid; padding-top: 16px; margin-bottom: 40px; font: 11px var(--mono); text-transform: uppercase; letter-spacing: 0.06em; }
html.page-home .ind-heading h2 { font: inherit; margin: 0px; }
html.page-home .ind-layout { display: grid; grid-template-columns: 1fr 1fr; gap: 64px; align-items: center; }
html.page-home .ind-copy h3 { font: 400 clamp(34px,4vw,62px)/1.05 var(--serif); letter-spacing: -0.025em; max-width: 17ch; margin: 0px 0px 24px; }
html.page-home .ind-copy p { font: 17px / 1.65 Inter, sans-serif; max-width: 49ch; margin: 0px 0px 28px; }
html.page-home .ind-copy a { display: inline-flex; gap: 36px; align-items: center; font: 12px var(--mono); color: inherit; text-decoration: none; border-bottom: 1px solid; padding-bottom: 10px; }
html.page-home .ind-copy a:hover span { transform: translate(3px, -3px); }
html.page-home .ind-copy a span { transition: transform 180ms; }
html.page-home .ind-layout figure { margin: 0px; background: var(--about-hover-bg,var(--t-beyond)); color: var(--c-beyond); padding: 28px; }
html.page-home .ind-layout figcaption { font: 10px/1.5 var(--mono); margin-bottom: 24px; }
html.page-home .ind-model svg { width: 100%; height: auto; display: block; }
html.page-home .ind-model svg text { fill: currentcolor; font: 10px monospace; }
html.page-home .ind-model svg rect,
html.page-home .ind-model svg circle { fill: transparent; stroke: currentcolor; stroke-width: 1; }
html.page-home .ind-model svg path,
html.page-home .ind-model svg line,
html.page-home .ind-model svg polyline { stroke: currentcolor; fill: none; stroke-width: 1; }
html.page-home #independent-study .ind-layout { grid-template-columns: 1.7fr 1fr; gap: 48px; }
html.page-home #independent-study .ind-copy { display: grid; grid-template-columns: 1fr 1fr; gap: 20px 36px; }
html.page-home #independent-study .ind-copy h3 { font-size: clamp(28px, 2.8vw, 42px); grid-row: span 2; margin: 0px; }
html.page-home #independent-study .ind-copy p { font-size: 15px; margin: 0px; }
html.page-home #independent-study .ind-copy a { justify-self: start; }
html.page-home #independent-study .ind-heading { margin-bottom: 24px; }
@media (max-width: 900px) {
html.page-home .ind-layout,
html.page-home #independent-study .ind-layout { grid-template-columns: 1fr; gap: 32px; }
}
@media (max-width: 900px) {
html.page-home #independent-study .ind-copy { display: block; }
}
@media (max-width: 900px) {
html.page-home #independent-study .ind-copy h3,
html.page-home #independent-study .ind-copy p { margin-bottom: 24px; }
}
@media (max-width: 900px) {
html.page-home .ind-heading { flex-wrap: wrap; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .ind-copy a span { transition: none; }
}
html.page-home #independent-study { padding-top: 48px; padding-bottom: 48px; }
html.page-home #independent-study .ind-heading { border: 0px; padding: 0px; margin: 0px 0px 20px; }
html.page-home .ind-disclosure { background: var(--c-lens2); color: var(--t-lens2); border-top: 1px solid; }
html.page-home .ind-disclosure > summary { list-style: none; display: grid; grid-template-columns: 160px 1fr auto; align-items: center; gap: 32px; padding: 30px; cursor: pointer; }
html.page-home .ind-disclosure > summary::-webkit-details-marker { display: none; }
html.page-home .ind-disclosure > summary h3 { font: 400 clamp(28px,2.8vw,42px)/1.1 var(--serif); letter-spacing: -0.02em; margin: 0px; max-width: 25ch; }
html.page-home .ind-project-label,
html.page-home .ind-open-cue { font: 11px/1.5 var(--mono); }
html.page-home .ind-disclosure > summary:hover,
html.page-home .ind-disclosure > summary:focus-visible { background: var(--about-hover-bg,var(--t-beyond)); color: var(--c-beyond); }
html.page-home .ind-disclosure > summary:focus-visible { outline: currentcolor solid 2px; outline-offset: -6px; }
html.page-home .ind-disclosure .ind-layout { padding: 8px 30px 32px; }
html.page-home #independent-study .ind-copy { display: block; }
html.page-home #independent-study .ind-copy p { font-size: 17px; margin-bottom: 24px; }
html.page-home .ind-open-cue .open-label,
html.page-home .ind-disclosure[open] .closed-label { display: none; }
html.page-home .ind-disclosure[open] .open-label { display: inline; }
@media (max-width: 760px) {
html.page-home .ind-disclosure > summary { grid-template-columns: 1fr; gap: 16px; padding: 24px; }
}
@media (max-width: 760px) {
html.page-home .ind-disclosure .ind-layout { padding: 0px 24px 24px; }
}
@media (max-width: 899px) {
html.page-home .number { font-size: 240px; }
}
@media (max-width: 899px) {
html.page-home .letter { font-size: 300px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .letter,
html.page-home .optics { transition: none; }
}
html.page-home .case { transition-delay: 0s !important; } /* !important restored from tile-studies/hover.css — without it the reveal's inline 140/210ms stagger wins and the card colour lags behind the numeral fade (2026-09-22) */
html.page-home .case > .r2-cover { z-index: 2; clip-path: inset(0px); transform: none; transition: opacity 0.135s linear; }
html.page-home .band:not(.anyopen) .case:is(:hover, :focus-visible, .demo-hover) > .r2-cover { opacity: 0; }
html.page-home .band.anyopen .case:not(.open) > .r2-cover { opacity: 0.8; transform: none; background: none; }
html.page-home .band.anyopen .case:not(.open) > .r2-cover { transition: opacity 0.135s linear, color 0.135s linear, transform 0.35s cubic-bezier(0.2, 0.7, 0.2, 1); }
html.page-home .band.anyopen .case:not(.open):is(:hover, :focus-visible, .demo-hover) > .r2-cover { transform: translateY(6%); opacity: 1; }
@media (prefers-reduced-motion: reduce) {
html.page-home .band:not(.anyopen) .case,
html.page-home .case > .r2-cover { transition: none; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .band.anyopen .case:not(.open):is(:hover, :focus-visible, .demo-hover) > .r2-cover { transform: none; }
}
html.page-home.rhythm-on #work .case { opacity: 1; transform: none; }
html.page-home.rhythm-on #work .band:not(.anyopen) .case.entrance-pending:not(:focus-visible):nth-child(1) { background: var(--c-case1); color: var(--t-case1); }
html.page-home.rhythm-on #work .band:not(.anyopen) .case.entrance-pending:not(:focus-visible):nth-child(2) { background: var(--c-case2); color: var(--t-case2); }
html.page-home.rhythm-on #work .band:not(.anyopen) .case.entrance-pending:not(:focus-visible):nth-child(3) { background: var(--c-case3); color: var(--t-case3); }
html.page-home.rhythm-on #work .band:not(.anyopen) .case.entrance-pending:not(:focus-visible) > .r2-cover { opacity: 1; }
@media (prefers-reduced-motion: reduce) {
html.page-home #about .ans { visibility: visible; }
}
html.page-home #contact .statement,
html.page-home #contact .statement em { color: var(--t-contact); }
html.page-home #approach,
html.page-home #approach:hover { background: var(--c-thesis); color: var(--t-thesis); }
html.page-home #approach .statement,
html.page-home #approach .statement em,
html.page-home #approach .sub-statement { color: var(--t-thesis); }
html.page-home #approach .statement em { color: var(--em-thesis,var(--approach-accent1,var(--t-thesis))); }
html.page-home #contact .statement em { color: var(--em-contact,var(--t-contact)); }
html.page-home .mast .r a:is(:hover, :focus-visible) { opacity: 1; }
@media (prefers-reduced-motion: reduce) {
html.page-home #about .acc { transition: none; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home #about .acc details .row-number,
html.page-home #about .acc details .row-question { opacity: 1; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home #about .acc summary,
html.page-home #about .acc .row-number::after { transition: none; }
}
html.page-home body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { font-family: var(--mono,monospace); font-size: var(--label-size); font-weight: 400; font-style: normal; line-height: 1.5; letter-spacing: var(--label-tracking); mix-blend-mode: normal; text-shadow: none; }
html.page-home body .r3-next,
html.page-home body .ind-heading h2,
html.page-home body .ind-heading > span,
html.page-home body #projects .phead > *,
html.page-home body .contact-meta { color: var(--label-light); }
html.page-home body #about .phead > *,
html.page-home body #reading .eyebrow,
html.page-home body #reading .foot .label { color: var(--label-dark); }
html.page-home body .linkband .k { color: inherit; }
html.page-home body .phead .dot::before { display: none; }
html.page-home body .phead h2 { font-weight: 400; }
html.page-home body .contact-meta:not(.fm-wait) { color: var(--t-contact); }
@media (forced-colors: active) {
html.page-home body :is(.r3-next, .ind-heading h2, .phead > *, .contact-meta, .linkband .k) { color: canvastext; }
}
html.page-home :is(.case, .ind-disclosure, .lensband .lens, #approach, #reading, #about, #contact, .acc details, .linkband > a, .built, .play, .resume, .subhero) { border-width: 0px; border-style: none; border-color: currentcolor; box-shadow: none; }
html.page-home #about .acc summary { box-shadow: none; }
html.page-home #about .ans { border: 0px; }
html.page-home .hero::after { background: var(--prism-veil,#c3d6d1); }
html.page-home .case.open { background: rgb(240, 238, 230); color: rgb(16, 43, 85); }
html.page-home .band.anyopen .case:not(.open):is(:hover, :focus-visible) { background: rgb(195, 214, 209); color: rgb(16, 43, 85); }
html.page-home .band.anyopen .case:not(.open):is(:hover, :focus-visible) .number { color: rgb(16, 43, 85); }
html.page-home #approach .statement { color: rgb(180, 217, 207); }
html.page-home #approach .statement em { color: rgb(255, 180, 127); }
html.page-home #approach .sub-statement { color: rgb(217, 182, 155); }
html.page-home .lensband .lens:nth-child(n) { background: rgb(160, 206, 195); color: rgb(16, 43, 85); }
html.page-home .lensband .lens:nth-child(n) { color: rgb(248, 231, 207); }
html.page-home .lensband .lens:nth-child(1) { background: rgb(5, 106, 145); }
html.page-home .lensband .lens:nth-child(2) { background: rgb(8, 120, 101); }
html.page-home .lensband .lens:nth-child(3) { background: rgb(5, 106, 47); }
html.page-home .lensband .lens:nth-child(n):is(:hover, :focus-visible) { background: rgb(16, 59, 66); color: rgb(248, 231, 207); }
html.page-home .lens:hover :is(h2, p, .n) { color: inherit; }
html.page-home #reading { color: rgb(36, 77, 80); }
html.page-home #about .acc summary:is(:hover, :focus-visible) { background: var(--about-hover-bg); color: rgb(248, 231, 207); }
html.page-home #contact,
html.page-home #contact:hover { background: rgb(16, 59, 66); color: rgb(180, 217, 207); }
html.page-home #contact .statement { color: rgb(180, 217, 207); }
html.page-home #contact .statement em { color: rgb(255, 180, 127); }
html.page-home #about .ans { font-family: var(--sans,Arial); font-size: clamp(18px, 1.5vw, 22px); line-height: 1.6; }
html.page-home #about .phead .dot::before { display: none; }
@supports (background-clip:text) {
html.page-home #reading #words { background: none; }
}
@supports (background-clip:text) {
html.page-home #reading #words .word { color: transparent; }
}
@media (prefers-reduced-motion: reduce) {
html.page-home .lensband .lens > h2,
html.page-home .lensband .lens > p { opacity: 1; }
}
html.page-home .hero .r2-image { display: none; }
@media (hover: hover) {
html.page-home .hero:hover h1 { opacity: 0; }
}
html.page-home #reading > .art-window,
html.page-home .quote-cutout { display: none; }
@media (prefers-reduced-motion: reduce) {
html.page-home .hero::after,
html.page-home .linkband .art-window { transition: none; }
}
html.page-home .hero h1.rot .stem { font-family: var(--mono,monospace); font-size: var(--label-size,11px); font-weight: 400; letter-spacing: var(--label-tracking,.08em); line-height: 1.5; text-transform: uppercase; margin-bottom: 24px; }
html.page-home .hero h1.rot { font-family: "Bricolage Grotesque", sans-serif; font-weight: 500; font-size: clamp(48px, 8.25vw, 124px); letter-spacing: -0.045em; line-height: 1.04; max-width: 19ch; }
html.page-home #approach .statement { margin: 0px; max-width: none; }
html.page-home #approach .sub-statement { margin: 32px 0px 0px; max-width: 44ch; }
html.page-home #about .acc summary:is(:hover, :focus-visible) { background: transparent; color: rgb(248, 231, 207); }
@media (prefers-reduced-motion: reduce) {
html.page-home .about-crop { transition: none; }
}
/* personal — normal declarations, then former priority declarations. */
/* removed 2026-09-22: body padding-bottom:48px existed only to clear the prototype's fixed #r2-tools diagnostic bar (round-two/round.css). The bar was stripped in the port; the padding left a blank strip below the footer. */
html.page-personal .r2-status { margin-left: auto; font-size: 10px; }
html.page-personal .r2-image,
html.page-personal .r2-plate,
html.page-personal .r2-cover,
html.page-personal .r2-caseart { display: none; }
html.page-personal .hero { position: relative; overflow: hidden; isolation: isolate; min-height: calc(-48px + 100svh); padding-top: clamp(120px, 20vh, 200px); padding-bottom: 38px; justify-content: flex-end; background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-personal .hero:hover { background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-personal .r2-image { display: block; position: absolute; inset: 12% 6% 19% 28%; z-index: 0; overflow: hidden; }
html.page-personal .r2-image img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 50%; }
html.page-personal .r2-plate { display: block; position: absolute; right: 2%; top: 56%; width: 26%; height: 24%; background: rgb(57, 44, 190); z-index: 1; }
html.page-personal .hero h1.rot { font-family: var(--sans); font-weight: 400; letter-spacing: -0.066em; max-width: 15ch; position: relative; z-index: 2; color: rgb(28, 35, 29); line-height: 1.08; margin-bottom: clamp(32px, 6vh, 60px); }
html.page-personal .hero .swap span { display: inline; background: rgb(220, 227, 194); box-decoration-break: clone; -webkit-box-decoration-break: clone; padding: 0px 0.035em; }
html.page-personal .hero h1.rot .stem { width: max-content; background: rgb(220, 227, 194); padding: 3px 5px; }
html.page-personal .hero h1.rot .stem { font-family: var(--mono); font-size: 0.105em; letter-spacing: 0.08em; text-transform: uppercase; opacity: 1; margin-bottom: 2em; }
html.page-personal .hero .acts { position: relative; z-index: 3; width: 100%; background: rgb(220, 227, 194); padding-top: 15px; gap: 22px; }
html.page-personal .hero .cta { background: none; border-bottom: 1px solid rgb(28, 35, 29); padding: 0px 0px 5px; color: rgb(28, 35, 29); font-size: 14px; }
html.page-personal .hero .cta::after { content: " ↗"; margin-left: 20px; }
html.page-personal .hero .quiet { opacity: 1; font-size: 12px; border-bottom: 0px; }
html.page-personal .hero .quiet:hover { text-decoration: underline; }
html.page-personal .mast { border-bottom: 1px solid rgba(28, 35, 29, 0.19); }
html.page-personal .case .art { visibility: hidden; }
html.page-personal .case > .r2-cover { display: block; position: absolute; left: 20%; right: 0px; top: 13%; height: 35%; z-index: 0; overflow: hidden; pointer-events: none; transition: opacity var(--dur) var(--motion-ease),transform var(--dur) var(--motion-ease); }
html.page-personal .r2-cover img { width: 100%; height: 100%; object-fit: cover; object-position: 15% 25%; filter: saturate(0.7); }
html.page-personal .case:nth-child(1) .r2-cover { clip-path: polygon(0px 0px, 100% 0px, 100% 75%, 60% 75%, 60% 100%, 0px 100%); }
html.page-personal .case:nth-child(2) .r2-cover { left: 0px; right: 20%; top: 17%; height: 30%; clip-path: polygon(0px 0px, 60% 0px, 60% 25%, 100% 25%, 100% 100%, 0px 100%); }
html.page-personal .case:nth-child(2) .r2-cover img { object-position: 78% 35%; filter: saturate(0.5) contrast(1.12); }
html.page-personal .case:nth-child(3) .r2-cover { left: 20%; right: -20%; height: 34%; top: 12%; clip-path: polygon(0px 0px, 80% 0px, 80% 35%, 100% 35%, 100% 100%, 0px 100%); }
html.page-personal .case:nth-child(3) .r2-cover img { object-position: 55% 90%; filter: saturate(0.9); }
html.page-personal .case h3 { max-width: 15ch; }
html.page-personal .case .top { opacity: 1; }
html.page-personal .case:not(.open):is(:hover, :focus-visible) > .r2-cover { opacity: 0.2; transform: translateX(-10px); }
html.page-personal .case.open > .r2-cover,
html.page-personal .band.anyopen .case:not(.open) > .r2-cover { display: none; }
html.page-personal .case.open .top { opacity: 0.7; }
html.page-personal #approach { position: relative; overflow: hidden; padding-top: clamp(80px, 13vh, 145px); padding-bottom: clamp(90px, 16vh, 170px); }
html.page-personal #approach .statement { max-width: 20ch; position: relative; z-index: 2; }
html.page-personal #approach .statement em { color: rgb(57, 44, 190); }
html.page-personal #approach .sub-statement { position: relative; z-index: 2; opacity: 1; max-width: 35ch; margin-left: 33.333%; }
html.page-personal .lens { border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-personal .lens p { opacity: 1; }
html.page-personal .p-gold { padding-left: calc(var(--pad) + 8vw); padding-right: calc(var(--pad) + 8vw); }
html.page-personal .quote { max-width: 22ch; }
html.page-personal .quote em { opacity: 1; color: rgb(237, 195, 184); }
html.page-personal .casehero { position: relative; overflow: hidden; isolation: isolate; background: rgb(38, 59, 54); color: rgb(244, 240, 231); min-height: 65vh; padding-top: clamp(120px, 20vh, 200px); padding-right: 35%; }
html.page-personal .r2-caseart { display: block; position: absolute; inset: 0px 0px 0px 45%; z-index: -1; clip-path: polygon(20% 0px, 100% 0px, 100% 100%, 0px 100%, 0px 65%, 20% 65%); }
html.page-personal .r2-caseart img { width: 100%; height: 100%; object-fit: cover; opacity: 0.32; }
html.page-personal .casehero .hook { opacity: 1; }
html.page-personal .casebody { padding-top: clamp(60px, 9vh, 110px); }
html.page-personal .subhero.personal { background: rgb(237, 195, 184); }
html.page-personal .subhero.personal h1 { max-width: 18ch; }
html.page-personal .builtband .built { background: rgb(244, 240, 231); border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-personal .builtband .built:hover { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-personal .play { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-personal.r2-grid body::after { content: ""; position: fixed; inset: 0 var(--pad) 48px; pointer-events: none; z-index: 99998; background: repeating-linear-gradient(90deg, rgba(240, 60, 83, 0.25) 0px, rgba(240, 60, 83, 0.25) 1px, transparent 1px, transparent calc(8.33333%)); }
@media (max-width: 899px) {
html.page-personal .hero { min-height: calc(-64px + 100svh); padding-top: 210px; padding-bottom: 25px; }
}
@media (max-width: 899px) {
html.page-personal .r2-image { inset: 12% 0px 26% 18%; }
}
@media (max-width: 899px) {
html.page-personal .r2-plate { right: 0px; top: 49%; width: 33%; height: 23%; }
}
@media (max-width: 899px) {
html.page-personal .hero h1.rot { max-width: 15ch; letter-spacing: -0.055em; }
}
@media (max-width: 899px) {
html.page-personal .hero .acts { gap: 15px; flex-wrap: wrap; }
}
@media (max-width: 899px) {
html.page-personal .case > .r2-cover { top: 14%; height: 30%; left: 40%; right: 0px; }
}
@media (max-width: 899px) {
html.page-personal .case:nth-child(2) > .r2-cover { left: 25%; top: 13%; }
}
@media (max-width: 899px) {
html.page-personal .case:nth-child(3) > .r2-cover { left: 40%; right: 0px; top: 13%; }
}
@media (max-width: 899px) {
html.page-personal .casehero { padding-right: var(--pad); min-height: 55vh; }
}
@media (max-width: 899px) {
html.page-personal .r2-caseart { left: 30%; opacity: 0.5; }
}
@media (max-width: 899px) {
html.page-personal #approach .sub-statement { margin-left: 0px; }
}
@media (max-width: 899px) {
html.page-personal .p-gold { padding-left: var(--pad); padding-right: var(--pad); }
}
@media (max-width: 899px) {
html.page-personal .r2-status { display: none; }
}
@media (max-width: 600px) {
html.page-personal .mast { display: grid; grid-template-columns: 1fr; gap: 7px; padding-top: 9px; padding-bottom: 9px; }
}
@media (max-width: 600px) {
html.page-personal .mast .r { display: flex; width: 100%; justify-content: space-between; gap: 6px; }
}
@media (max-width: 600px) {
html.page-personal .hero h1.rot .stem { font-size: 11px; }
}
@media (max-width: 600px) {
html.page-personal .hero .acts .cta { width: 100%; margin-bottom: 5px; text-align: left; }
}
@media (max-width: 600px) {
html.page-personal .casehero .top { margin-top: 15px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-personal .r2-cover { transition: none; }
}
html.page-personal .hero,
html.page-personal .hero:hover { height: calc(-230px + 100svh); min-height: 380px; padding: clamp(84px,10vh,120px) var(--pad) 48px; justify-content: flex-start; background: rgb(240, 238, 230); }
html.page-personal .hero .acts,
html.page-personal .r2-plate { display: none; }
html.page-personal .r2-image { inset: 0px 0px 0px 38%; overflow: hidden; }
html.page-personal .r2-image img { filter: contrast(1.35) brightness(0.38); object-position: 25% 50%; }
html.page-personal .hero h1.rot { color: white; mix-blend-mode: difference; max-width: 15ch; font-size: clamp(50px, 8.4vw, 128px); line-height: 0.99; margin: 0px; letter-spacing: -0.06em; }
html.page-personal .hero .swap span { display: block; background: none; padding: 0px; }
html.page-personal .hero h1.rot .stem { background: none; padding: 0px; font-size: 12px; margin-bottom: 28px; }
html.page-personal .r3-next { display: none; }
html.page-personal .r3-next { position: absolute; left: var(--pad); right: var(--pad); bottom: 20px; display: flex; justify-content: space-between; color: rgb(248, 231, 207); mix-blend-mode: normal; z-index: 3; font: 11px var(--mono); text-transform: uppercase; letter-spacing: 0.08em; text-decoration: none; }
html.page-personal .r3-next span:last-child { font: 30px var(--sans); }
html.page-personal .case { border-top: 1px solid; }
html.page-personal .case > .r2-cover,
html.page-personal .case:nth-child(2) > .r2-cover,
html.page-personal .case:nth-child(3) > .r2-cover { inset: 105px 0px auto; height: 38%; clip-path: none; transform: none; opacity: 1; border-bottom: 1px solid; color: inherit; overflow: hidden; }
html.page-personal .folio,
html.page-personal .folio-echo { position: absolute; left: 8%; top: -0.19em; font: 400 clamp(200px,25vw,390px)/1 var(--serif); letter-spacing: -0.09em; }
html.page-personal .folio-echo { left: 40%; color: transparent; -webkit-text-stroke: 1px currentcolor; opacity: 0.3; transform: translateX(25%); }
html.page-personal .case:nth-child(2) .folio { transform: translateX(-16%); }
html.page-personal .case:nth-child(3) .folio { left: 35%; }
html.page-personal .case h3 { max-width: 16ch; }
html.page-personal .band.anyopen .case:not(.open) > .r2-cover { display: block; inset: 0px; height: 100%; border: 0px; opacity: 0.8; background: repeating-linear-gradient(0deg, transparent 0px, transparent 45px, rgba(255, 255, 255, 0.094) 45px, rgba(255, 255, 255, 0.094) 46px); }
html.page-personal .band.anyopen .case:not(.open) .folio { font-size: 400px; top: 10%; left: -65px; writing-mode: vertical-rl; }
html.page-personal .band.anyopen .case:not(.open) .folio-echo { display: none; }
html.page-personal .band.anyopen .case:not(.open) .spine { background: var(--c-case2); color: rgb(255, 255, 255); padding: 12px 7px; opacity: 1; }
html.page-personal .band.anyopen .case:not(.open):hover > .r2-cover { transform: translateY(-15px); opacity: 1; }
html.page-personal .case.open > .r2-cover { display: none; }
html.page-personal #approach { border-top: 1px solid rgb(39, 59, 54); background: rgb(240, 238, 230); }
html.page-personal #approach .statement em { color: rgb(39, 59, 54); }
html.page-personal .casehero { padding-top: clamp(100px, 15vh, 160px); }
html.page-personal .r2-caseart { clip-path: none; }
html.page-personal .r2-caseart img { filter: grayscale(1); opacity: 0.2; }
@media (max-width: 899px) {
html.page-personal .hero,
html.page-personal .hero:hover { height: calc(-220px + 100svh); min-height: 340px; padding-top: 95px; }
}
@media (max-width: 899px) {
html.page-personal .hero h1.rot { font-size: clamp(46px, 8.4vw, 76px); max-width: 15ch; }
}
@media (max-width: 899px) {
html.page-personal .r2-image { left: 48%; }
}
@media (max-width: 899px) {
html.page-personal .case { min-height: 560px; }
}
@media (max-width: 899px) {
html.page-personal .case > .r2-cover,
html.page-personal .case:nth-child(2) > .r2-cover,
html.page-personal .case:nth-child(3) > .r2-cover { top: 60px; height: 210px; }
}
@media (max-width: 899px) {
html.page-personal .folio,
html.page-personal .folio-echo { font-size: 280px; }
}
@media (max-width: 899px) {
html.page-personal .band.anyopen .case:not(.open) > .r2-cover { inset: 60px 0px auto; height: 210px; }
}
@media (max-width: 899px) {
html.page-personal .band.anyopen .case:not(.open) .folio { font-size: 280px; writing-mode: horizontal-tb; top: -0.19em; left: 8%; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-personal .hero,
html.page-personal .hero:hover { min-height: 270px; height: calc(-165px + 100svh); padding-top: 65px; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-personal .hero h1.rot { font-size: clamp(40px, 5vw, 70px); }
}
html.page-personal body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { text-transform: uppercase; -webkit-text-stroke: 0px; }
html.page-personal body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .ind-project-label):not(.fm-wait) { opacity: 1; }
html.page-personal body .linkband .k { opacity: 0.5; }
html.page-personal body .contact-meta:not(.fm-wait) { opacity: 0.62; }
html.page-personal .mast .r a { position: relative; transition: color 260ms, opacity 260ms; }
html.page-personal .mast .r a.return-home { opacity: 1; }
html.page-personal .mast .r a.return-home .return-label { opacity: 0.55; transition: opacity 260ms; }
html.page-personal .mast .r a.return-home:is(:hover, :focus-visible) .return-label { opacity: 1; }
html.page-personal .mast .r a.return-home::after { content: ""; position: absolute; left: calc(-1 * var(--return-gap)); right: 0px; top: 50%; height: 1px; background: currentcolor; transform-origin: left center; transition: transform 320ms cubic-bezier(0.22, 0.7, 0.2, 1); }
html.page-personal .mast .r a.return-home:first-child::after { left: -46px; }
html.page-personal .mast .r a.return-home:nth-child(4)::after { right: -22px; }
html.page-personal .mast .r { --return-gap: clamp(14px,2vw,30px); }
html.page-personal .mast .r a.return-home::before { content: "↖"; position: absolute; left: -0.95em; opacity: 0; transform: translate(3px, 3px); transition: opacity 320ms, transform 320ms; }
html.page-personal .mast .r a.return-home:is(:hover, :focus-visible) { opacity: 1; }
html.page-personal .mast .r a.return-home:is(:hover, :focus-visible)::after { transform: none; right: calc(100% + 14px); }
html.page-personal .mast .r a.return-home::after { opacity: 0.34; transition: right 320ms cubic-bezier(0.22, 0.7, 0.2, 1); }
html.page-personal .mast .r a.return-home:is(:hover, :focus-visible)::before { opacity: 1; transform: translate(0px, 0px); }
html.page-personal .mast .r a[aria-current="page"] { opacity: 1; }
html.page-personal .mast:has(> a:is(:hover, :focus-visible)) { background: var(--c-hero); color: var(--t-hero); }
@media (prefers-reduced-motion: reduce) {
html.page-personal .mast .r a,
html.page-personal .mast .r a::before,
html.page-personal .mast .r a::after { transition: none; }
}
html.page-personal #approach .sub-statement { max-width: 44ch; margin: 36px 0px 0px auto; font-family: var(--sans,Arial); font-size: clamp(18px, 1.6vw, 23px); font-weight: 400; letter-spacing: 0px; line-height: 1.55; text-wrap: pretty; }
html.page-personal .lensband .lens:nth-child(n) { --ink: #102b55; --rule-accent: #f8e7cf; transition: background-color 350ms, color 350ms; }
html.page-personal .lensband .lens:nth-child(n) { --ink: #f8e7cf; }
html.page-personal #reading { --finish-quote-ink: #244d50; }
html.page-personal #about .acc details { --about-hover-bg: #082a73; }
html.page-personal #about .acc details:nth-child(2) { --about-hover-bg: #056a91; }
html.page-personal #about .acc details:nth-child(3) { --about-hover-bg: #087865; }
html.page-personal #about .acc details:nth-child(4) { --about-hover-bg: #056a2f; }
html.page-personal #about .acc details:nth-child(5) { --about-hover-bg: #66592a; }
html.page-personal #about .ans { font-weight: 400; letter-spacing: 0px; max-width: 52ch; padding-top: 20px; }
html.page-personal #about .ans p { font: inherit; max-width: 52ch; }
@supports (background-clip:text) {
html.page-personal #reading #words { position: relative; }
}
@supports (background-clip:text) {
html.page-personal #reading #words .word { background-image: url("/static/art/independent-prism.webp"); background-size: var(--quote-art-size,auto 100vh); background-position: var(--word-crop,center); background-clip: text; -webkit-text-fill-color: transparent; text-shadow: none; -webkit-text-stroke: 0px; }
}
@media (max-width: 700px) {
html.page-personal #approach .sub-statement { margin-left: 0px; }
}
html.page-personal #projects .phead { opacity: 1; }
html.page-personal .personal-project-intro { position: relative; isolation: isolate; display: flex; align-items: flex-end; }
html.page-personal .personal-project-intro > .secondary-art { inset: 0px; height: 100%; background-size: max(1672px, 100vw) auto; background-position: 50% 60%; pointer-events: none; }
html.page-personal .personal-project-intro > .phead { width: 100%; box-sizing: border-box; margin: 0px; }
html.page-personal #play > .phead { box-sizing: border-box; align-items: flex-end; margin: 0px; padding-top: 28px; padding-bottom: 28px; background-size: auto max(100vh, 700px); background-position: 60% 5%; background-repeat: no-repeat; color: rgb(240, 238, 230); }
html.page-personal .subhero { background: rgb(240, 238, 230); color: rgb(16, 43, 85); }
html.page-personal .subhero:is(:hover, :focus-within) { background: rgb(195, 214, 209); color: rgb(16, 43, 85); }
html.page-personal #projects .phead > * { font: 400 11px/1.5 var(--mono); letter-spacing: 0.08em; text-transform: uppercase; opacity: 1; }
html.page-personal .built { transition: background-color 350ms, color 350ms; }
html.page-personal .built:nth-child(1) { --project-surface: #056a91; }
html.page-personal .built:nth-child(2) { --project-surface: #087865; }
html.page-personal .built:nth-child(3) { --project-surface: #056a2f; }
html.page-personal .built:nth-child(4) { --project-surface: #1f4e79; } /* 2026-10-07: the 4th tile had no colour and read white-on-white */
html.page-personal .built :is(h3, .what, .go, .top, .spec) { color: inherit; }
html.page-personal .built .top { opacity: 0.65; }
html.page-personal .built h3 { font-family: var(--sans); font-weight: 500; line-height: 1.12; letter-spacing: -0.025em; }
html.page-personal .pdetail { background: rgb(240, 238, 230); color: rgb(16, 43, 85); }
@media (prefers-reduced-motion: reduce) {
html.page-personal .built { transition: none; }
}
html.page-personal .subhero { position: relative; isolation: isolate; overflow: hidden; background: var(--c-read); color: var(--t-read); padding-bottom: clamp(64px, 8vw, 120px); }
html.page-personal .subhero > h1,
html.page-personal .subhero > p,
html.page-personal .subhero > .stem,
html.page-personal .subhero > .acts { position: relative; z-index: 1; max-width: 65%; }
html.page-personal .secondary-art { position: absolute; inset: 0px 0px 0px 72%; z-index: -1; background-repeat: no-repeat; background-size: auto max(100vh, 700px); background-position: 65% center; }
html.page-personal .subhero h1 { font-family: var(--serif); font-weight: 400; font-size: clamp(44px, 6vw, 88px); line-height: 1.04; letter-spacing: -0.025em; }
html.page-personal .phead h2 { font-size: 11px; letter-spacing: 0.1em; font-weight: 400; }
html.page-personal .resume { background: var(--c-read); color: var(--t-read); }
html.page-personal .resume h2 { font-family: var(--mono); font-size: 11px; letter-spacing: 0.1em; text-transform: uppercase; }
html.page-personal .resume h3 { font-family: var(--serif); font-weight: 400; font-size: clamp(25px, 3vw, 38px); line-height: 1.12; }
html.page-personal .resume .role { padding-top: 24px; padding-bottom: 28px; }
html.page-personal .resume p,
html.page-personal .resume li { line-height: 1.65; }
@media (max-width: 700px) {
html.page-personal .subhero > h1,
html.page-personal .subhero > p,
html.page-personal .subhero > .stem,
html.page-personal .subhero > .acts { max-width: 100%; }
}
@media (max-width: 700px) {
html.page-personal .subhero { padding-bottom: 180px; }
}
@media (max-width: 700px) {
html.page-personal .secondary-art { inset: auto 0px 0px; height: 130px; background-size: auto max(100vh, 700px); }
}
@media print {
html.page-personal .secondary-art { display: none; }
}
@media print {
html.page-personal .subhero { padding-bottom: 20px; }
}
@media print {
html.page-personal .subhero > h1,
html.page-personal .subhero > p { max-width: 100%; }
}
html.page-personal .linkband > a { position: relative; isolation: isolate; overflow: hidden; }
html.page-personal .footer-art { position: absolute; inset: 0px; z-index: 0; background-size: auto max(100vh, 700px); background-repeat: no-repeat; opacity: 0; transition: opacity 300ms; pointer-events: none; }
html.page-personal .linkband > a > span { position: relative; z-index: 1; }
html.page-personal .linkband > a:is(:hover, :focus-visible) .footer-art { opacity: 1; }
html.page-personal .linkband > a:is(:hover, :focus-visible) > span { background: none; color: var(--t-links); box-shadow: none; }
html.page-personal .resume-layout { position: relative; isolation: isolate; }
html.page-personal .resume-layout > .secondary-art { inset: 0px 0px 0px 78%; z-index: 2; background-attachment: fixed; background-position: right center; background-size: auto 100vh; pointer-events: none; }
html.page-personal .resume-layout > .resume { padding-right: 27%; }
html.page-personal .subhero { padding-bottom: 210px; }
html.page-personal .subhero > h1 { max-width: min(100%, 1000px); }
html.page-personal .subhero > p { max-width: min(100%, 65ch); }
html.page-personal .secondary-art { inset: auto 0px 0px; height: 140px; background-position: center 60%; }
@media (max-width: 700px) {
html.page-personal .resume-layout > .secondary-art { left: 94%; background-attachment: scroll; background-repeat: repeat-y; }
}
@media (max-width: 700px) {
html.page-personal .resume-layout > .resume { padding-right: 11%; }
}
@media (max-width: 700px) {
html.page-personal .resume-layout > .subhero { padding-bottom: 60px; padding-right: 11%; }
}
@media (max-width: 700px) {
html.page-personal .resume-layout > .subhero > h1,
html.page-personal .resume-layout > .subhero > p { max-width: 100%; }
}
@media (prefers-reduced-motion: reduce) {
html.page-personal .footer-art { transition: none; }
}
@media print {
html.page-personal .resume-layout > .secondary-art,
html.page-personal .footer-art { display: none; }
}
@media print {
html.page-personal .resume-layout > .resume { padding-right: 0px; }
}
html.page-personal .linkband a.lead-tile { background: var(--c-links); color: var(--t-links); }
html.page-personal .subhero { padding-top: clamp(60px, 10vh, 110px); padding-bottom: 290px; }
html.page-personal .secondary-art { height: 240px; transition: opacity 450ms; }
html.page-personal .subhero:has(> h1:hover, > p:hover, > .stem:hover) { background: var(--c-links); color: var(--t-links); }
html.page-personal .subhero { transition: background-color 400ms, color 400ms; overflow: visible; }
html.page-personal #projects .phead { position: relative; isolation: isolate; background: transparent; }
html.page-personal #projects .phead > * { position: relative; background: none; color: rgb(255, 255, 255); padding: 0px; }
html.page-personal .play-cursor-label { position: fixed; z-index: 10000; pointer-events: none; font: 400 10px/1.4 var(--mono); letter-spacing: 0.1em; color: var(--t-links); text-shadow: 0 1px 3px var(--c-links); }
html.page-personal .play-cursor-label[hidden] { display: none; }
html.page-personal .play-cursor-label { transform: translate(-50%, -50%); }
html.page-personal .resume-layout > .secondary-art { background-size: auto 115vh; }
@media (max-width: 700px) {
html.page-personal .subhero { padding-top: 55px; padding-bottom: 240px; }
}
@media (max-width: 700px) {
html.page-personal .secondary-art { height: 200px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-personal .secondary-art { transition: none; }
}
html.page-personal body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { font-family: var(--mono,monospace); font-size: var(--label-size); font-weight: 400; font-style: normal; line-height: 1.5; letter-spacing: var(--label-tracking); mix-blend-mode: normal; text-shadow: none; }
html.page-personal body .r3-next,
html.page-personal body .ind-heading h2,
html.page-personal body .ind-heading > span,
html.page-personal body #projects .phead > *,
html.page-personal body .contact-meta { color: var(--label-light); }
html.page-personal body #about .phead > *,
html.page-personal body #reading .eyebrow,
html.page-personal body #reading .foot .label { color: var(--label-dark); }
html.page-personal body .linkband .k { color: inherit; }
html.page-personal body .phead .dot::before { display: none; }
html.page-personal body .phead h2 { font-weight: 400; }
html.page-personal body .contact-meta:not(.fm-wait) { color: var(--t-contact); }
@media (forced-colors: active) {
html.page-personal body :is(.r3-next, .ind-heading h2, .phead > *, .contact-meta, .linkband .k) { color: canvastext; }
}
html.page-personal :is(.case, .ind-disclosure, .lensband .lens, #approach, #reading, #about, #contact, .acc details, .linkband > a, .built, .play, .resume, .subhero) { border-width: 0px; border-style: none; border-color: currentcolor; box-shadow: none; }
html.page-personal #about .acc summary { box-shadow: none; }
html.page-personal #about .ans { border: 0px; }
html.page-personal .hero::after { background: var(--prism-veil,#c3d6d1); }
html.page-personal .case.open { background: rgb(240, 238, 230); color: rgb(16, 43, 85); }
html.page-personal .band.anyopen .case:not(.open):is(:hover, :focus-visible) { background: rgb(195, 214, 209); color: rgb(16, 43, 85); }
html.page-personal .band.anyopen .case:not(.open):is(:hover, :focus-visible) .number { color: rgb(16, 43, 85); }
html.page-personal #approach .statement { color: rgb(180, 217, 207); }
html.page-personal #approach .statement em { color: rgb(255, 180, 127); }
html.page-personal #approach .sub-statement { color: rgb(217, 182, 155); }
html.page-personal .lensband .lens:nth-child(n) { background: rgb(160, 206, 195); color: rgb(16, 43, 85); }
html.page-personal .lensband .lens:nth-child(n) { color: rgb(248, 231, 207); }
html.page-personal .lensband .lens:nth-child(1) { background: rgb(5, 106, 145); }
html.page-personal .lensband .lens:nth-child(2) { background: rgb(8, 120, 101); }
html.page-personal .lensband .lens:nth-child(3) { background: rgb(5, 106, 47); }
html.page-personal .lensband .lens:nth-child(n):is(:hover, :focus-visible) { background: rgb(16, 59, 66); color: rgb(248, 231, 207); }
html.page-personal .lens:hover :is(h2, p, .n) { color: inherit; }
html.page-personal #reading { color: rgb(36, 77, 80); }
html.page-personal #about .acc summary:is(:hover, :focus-visible) { background: var(--about-hover-bg); color: rgb(248, 231, 207); }
html.page-personal #contact,
html.page-personal #contact:hover { background: rgb(16, 59, 66); color: rgb(180, 217, 207); }
html.page-personal #contact .statement { color: rgb(180, 217, 207); }
html.page-personal #contact .statement em { color: rgb(255, 180, 127); }
html.page-personal #about .ans { font-family: var(--sans,Arial); font-size: clamp(18px, 1.5vw, 22px); line-height: 1.6; }
html.page-personal #about .phead .dot::before { display: none; }
@supports (background-clip:text) {
html.page-personal #reading #words { background: none; }
}
@supports (background-clip:text) {
html.page-personal #reading #words .word { color: transparent; }
}
html.page-personal #play > .phead { opacity: 1; }
html.page-personal #projects .phead > h2 { color: rgb(240, 238, 230); }
html.page-personal .subhero { padding-bottom: 50px; overflow: hidden; }
html.page-personal #play > .phead { background-size: max(1672px, 100vw) auto; }
html.page-personal #projects .phead > * { color: rgb(16, 43, 85); background: none; box-shadow: none; text-shadow: none; }
html.page-personal .built { background: var(--project-surface); color: rgb(240, 238, 230); }
html.page-personal .built:is(:hover, :focus-visible) { background: rgb(16, 59, 66); color: rgb(240, 238, 230); }
html.page-personal.play-text-cursor .play,
html.page-personal.play-text-cursor .play *,
html.page-personal.play-text-cursor .playview,
html.page-personal.play-text-cursor .playview * { cursor: none !important; }
/* resume — normal declarations, then former priority declarations. */
/* removed 2026-09-22: body padding-bottom:48px existed only to clear the prototype's fixed #r2-tools diagnostic bar (round-two/round.css). The bar was stripped in the port; the padding left a blank strip below the footer. */
html.page-resume .r2-status { margin-left: auto; font-size: 10px; }
html.page-resume .r2-image,
html.page-resume .r2-plate,
html.page-resume .r2-cover,
html.page-resume .r2-caseart { display: none; }
html.page-resume .hero { position: relative; overflow: hidden; isolation: isolate; min-height: calc(-48px + 100svh); padding-top: clamp(120px, 20vh, 200px); padding-bottom: 38px; justify-content: flex-end; background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-resume .hero:hover { background: linear-gradient(90deg, rgb(220, 227, 194) 0px, rgb(220, 227, 194) 56%, rgb(237, 195, 184) 56%); }
html.page-resume .r2-image { display: block; position: absolute; inset: 12% 6% 19% 28%; z-index: 0; overflow: hidden; }
html.page-resume .r2-image img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 50%; }
html.page-resume .r2-plate { display: block; position: absolute; right: 2%; top: 56%; width: 26%; height: 24%; background: rgb(57, 44, 190); z-index: 1; }
html.page-resume .hero h1.rot { font-family: var(--sans); font-weight: 400; letter-spacing: -0.066em; max-width: 15ch; position: relative; z-index: 2; color: rgb(28, 35, 29); line-height: 1.08; margin-bottom: clamp(32px, 6vh, 60px); }
html.page-resume .hero .swap span { display: inline; background: rgb(220, 227, 194); box-decoration-break: clone; -webkit-box-decoration-break: clone; padding: 0px 0.035em; }
html.page-resume .hero h1.rot .stem { width: max-content; background: rgb(220, 227, 194); padding: 3px 5px; }
html.page-resume .hero h1.rot .stem { font-family: var(--mono); font-size: 0.105em; letter-spacing: 0.08em; text-transform: uppercase; opacity: 1; margin-bottom: 2em; }
html.page-resume .hero .acts { position: relative; z-index: 3; width: 100%; background: rgb(220, 227, 194); padding-top: 15px; gap: 22px; }
html.page-resume .hero .cta { background: none; border-bottom: 1px solid rgb(28, 35, 29); padding: 0px 0px 5px; color: rgb(28, 35, 29); font-size: 14px; }
html.page-resume .hero .cta::after { content: " ↗"; margin-left: 20px; }
html.page-resume .hero .quiet { opacity: 1; font-size: 12px; border-bottom: 0px; }
html.page-resume .hero .quiet:hover { text-decoration: underline; }
html.page-resume .mast { border-bottom: 1px solid rgba(28, 35, 29, 0.19); }
html.page-resume .case .art { visibility: hidden; }
html.page-resume .case > .r2-cover { display: block; position: absolute; left: 20%; right: 0px; top: 13%; height: 35%; z-index: 0; overflow: hidden; pointer-events: none; transition: opacity var(--dur) var(--motion-ease),transform var(--dur) var(--motion-ease); }
html.page-resume .r2-cover img { width: 100%; height: 100%; object-fit: cover; object-position: 15% 25%; filter: saturate(0.7); }
html.page-resume .case:nth-child(1) .r2-cover { clip-path: polygon(0px 0px, 100% 0px, 100% 75%, 60% 75%, 60% 100%, 0px 100%); }
html.page-resume .case:nth-child(2) .r2-cover { left: 0px; right: 20%; top: 17%; height: 30%; clip-path: polygon(0px 0px, 60% 0px, 60% 25%, 100% 25%, 100% 100%, 0px 100%); }
html.page-resume .case:nth-child(2) .r2-cover img { object-position: 78% 35%; filter: saturate(0.5) contrast(1.12); }
html.page-resume .case:nth-child(3) .r2-cover { left: 20%; right: -20%; height: 34%; top: 12%; clip-path: polygon(0px 0px, 80% 0px, 80% 35%, 100% 35%, 100% 100%, 0px 100%); }
html.page-resume .case:nth-child(3) .r2-cover img { object-position: 55% 90%; filter: saturate(0.9); }
html.page-resume .case h3 { max-width: 15ch; }
html.page-resume .case .top { opacity: 1; }
html.page-resume .case:not(.open):is(:hover, :focus-visible) > .r2-cover { opacity: 0.2; transform: translateX(-10px); }
html.page-resume .case.open > .r2-cover,
html.page-resume .band.anyopen .case:not(.open) > .r2-cover { display: none; }
html.page-resume .case.open .top { opacity: 0.7; }
html.page-resume #approach { position: relative; overflow: hidden; padding-top: clamp(80px, 13vh, 145px); padding-bottom: clamp(90px, 16vh, 170px); }
html.page-resume #approach .statement { max-width: 20ch; position: relative; z-index: 2; }
html.page-resume #approach .statement em { color: rgb(57, 44, 190); }
html.page-resume #approach .sub-statement { position: relative; z-index: 2; opacity: 1; max-width: 35ch; margin-left: 33.333%; }
html.page-resume .lens { border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-resume .lens p { opacity: 1; }
html.page-resume .p-gold { padding-left: calc(var(--pad) + 8vw); padding-right: calc(var(--pad) + 8vw); }
html.page-resume .quote { max-width: 22ch; }
html.page-resume .quote em { opacity: 1; color: rgb(237, 195, 184); }
html.page-resume .casehero { position: relative; overflow: hidden; isolation: isolate; background: rgb(38, 59, 54); color: rgb(244, 240, 231); min-height: 65vh; padding-top: clamp(120px, 20vh, 200px); padding-right: 35%; }
html.page-resume .r2-caseart { display: block; position: absolute; inset: 0px 0px 0px 45%; z-index: -1; clip-path: polygon(20% 0px, 100% 0px, 100% 100%, 0px 100%, 0px 65%, 20% 65%); }
html.page-resume .r2-caseart img { width: 100%; height: 100%; object-fit: cover; opacity: 0.32; }
html.page-resume .casehero .hook { opacity: 1; }
html.page-resume .casebody { padding-top: clamp(60px, 9vh, 110px); }
html.page-resume .subhero.personal { background: rgb(237, 195, 184); }
html.page-resume .subhero.personal h1 { max-width: 18ch; }
html.page-resume .builtband .built { background: rgb(244, 240, 231); border-top: 1px solid rgb(28, 35, 29); border-right: 1px solid rgba(28, 35, 29, 0.19); }
html.page-resume .builtband .built:hover { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-resume .play { background: rgb(38, 59, 54); color: rgb(244, 240, 231); }
html.page-resume.r2-grid body::after { content: ""; position: fixed; inset: 0 var(--pad) 48px; pointer-events: none; z-index: 99998; background: repeating-linear-gradient(90deg, rgba(240, 60, 83, 0.25) 0px, rgba(240, 60, 83, 0.25) 1px, transparent 1px, transparent calc(8.33333%)); }
@media (max-width: 899px) {
html.page-resume .hero { min-height: calc(-64px + 100svh); padding-top: 210px; padding-bottom: 25px; }
}
@media (max-width: 899px) {
html.page-resume .r2-image { inset: 12% 0px 26% 18%; }
}
@media (max-width: 899px) {
html.page-resume .r2-plate { right: 0px; top: 49%; width: 33%; height: 23%; }
}
@media (max-width: 899px) {
html.page-resume .hero h1.rot { max-width: 15ch; letter-spacing: -0.055em; }
}
@media (max-width: 899px) {
html.page-resume .hero .acts { gap: 15px; flex-wrap: wrap; }
}
@media (max-width: 899px) {
html.page-resume .case > .r2-cover { top: 14%; height: 30%; left: 40%; right: 0px; }
}
@media (max-width: 899px) {
html.page-resume .case:nth-child(2) > .r2-cover { left: 25%; top: 13%; }
}
@media (max-width: 899px) {
html.page-resume .case:nth-child(3) > .r2-cover { left: 40%; right: 0px; top: 13%; }
}
@media (max-width: 899px) {
html.page-resume .casehero { padding-right: var(--pad); min-height: 55vh; }
}
@media (max-width: 899px) {
html.page-resume .r2-caseart { left: 30%; opacity: 0.5; }
}
@media (max-width: 899px) {
html.page-resume #approach .sub-statement { margin-left: 0px; }
}
@media (max-width: 899px) {
html.page-resume .p-gold { padding-left: var(--pad); padding-right: var(--pad); }
}
@media (max-width: 899px) {
html.page-resume .r2-status { display: none; }
}
@media (max-width: 600px) {
html.page-resume .mast { display: grid; grid-template-columns: 1fr; gap: 7px; padding-top: 9px; padding-bottom: 9px; }
}
@media (max-width: 600px) {
html.page-resume .mast .r { display: flex; width: 100%; justify-content: space-between; gap: 6px; }
}
@media (max-width: 600px) {
html.page-resume .hero h1.rot .stem { font-size: 11px; }
}
@media (max-width: 600px) {
html.page-resume .hero .acts .cta { width: 100%; margin-bottom: 5px; text-align: left; }
}
@media (max-width: 600px) {
html.page-resume .casehero .top { margin-top: 15px; }
}
@media (prefers-reduced-motion: reduce) {
html.page-resume .r2-cover { transition: none; }
}
html.page-resume .hero,
html.page-resume .hero:hover { height: calc(-230px + 100svh); min-height: 380px; padding: clamp(84px,10vh,120px) var(--pad) 48px; justify-content: flex-start; background: rgb(240, 238, 230); }
html.page-resume .hero .acts,
html.page-resume .r2-plate { display: none; }
html.page-resume .r2-image { inset: 0px 0px 0px 38%; overflow: hidden; }
html.page-resume .r2-image img { filter: contrast(1.35) brightness(0.38); object-position: 25% 50%; }
html.page-resume .hero h1.rot { color: white; mix-blend-mode: difference; max-width: 15ch; font-size: clamp(50px, 8.4vw, 128px); line-height: 0.99; margin: 0px; letter-spacing: -0.06em; }
html.page-resume .hero .swap span { display: block; background: none; padding: 0px; }
html.page-resume .hero h1.rot .stem { background: none; padding: 0px; font-size: 12px; margin-bottom: 28px; }
html.page-resume .r3-next { display: none; }
html.page-resume .r3-next { position: absolute; left: var(--pad); right: var(--pad); bottom: 20px; display: flex; justify-content: space-between; color: rgb(248, 231, 207); mix-blend-mode: normal; z-index: 3; font: 11px var(--mono); text-transform: uppercase; letter-spacing: 0.08em; text-decoration: none; }
html.page-resume .r3-next span:last-child { font: 30px var(--sans); }
html.page-resume .case { border-top: 1px solid; }
html.page-resume .case > .r2-cover,
html.page-resume .case:nth-child(2) > .r2-cover,
html.page-resume .case:nth-child(3) > .r2-cover { inset: 105px 0px auto; height: 38%; clip-path: none; transform: none; opacity: 1; border-bottom: 1px solid; color: inherit; overflow: hidden; }
html.page-resume .folio,
html.page-resume .folio-echo { position: absolute; left: 8%; top: -0.19em; font: 400 clamp(200px,25vw,390px)/1 var(--serif); letter-spacing: -0.09em; }
html.page-resume .folio-echo { left: 40%; color: transparent; -webkit-text-stroke: 1px currentcolor; opacity: 0.3; transform: translateX(25%); }
html.page-resume .case:nth-child(2) .folio { transform: translateX(-16%); }
html.page-resume .case:nth-child(3) .folio { left: 35%; }
html.page-resume .case h3 { max-width: 16ch; }
html.page-resume .band.anyopen .case:not(.open) > .r2-cover { display: block; inset: 0px; height: 100%; border: 0px; opacity: 0.8; background: repeating-linear-gradient(0deg, transparent 0px, transparent 45px, rgba(255, 255, 255, 0.094) 45px, rgba(255, 255, 255, 0.094) 46px); }
html.page-resume .band.anyopen .case:not(.open) .folio { font-size: 400px; top: 10%; left: -65px; writing-mode: vertical-rl; }
html.page-resume .band.anyopen .case:not(.open) .folio-echo { display: none; }
html.page-resume .band.anyopen .case:not(.open) .spine { background: var(--c-case2); color: rgb(255, 255, 255); padding: 12px 7px; opacity: 1; }
html.page-resume .band.anyopen .case:not(.open):hover > .r2-cover { transform: translateY(-15px); opacity: 1; }
html.page-resume .case.open > .r2-cover { display: none; }
html.page-resume #approach { border-top: 1px solid rgb(39, 59, 54); background: rgb(240, 238, 230); }
html.page-resume #approach .statement em { color: rgb(39, 59, 54); }
html.page-resume .casehero { padding-top: clamp(100px, 15vh, 160px); }
html.page-resume .r2-caseart { clip-path: none; }
html.page-resume .r2-caseart img { filter: grayscale(1); opacity: 0.2; }
@media (max-width: 899px) {
html.page-resume .hero,
html.page-resume .hero:hover { height: calc(-220px + 100svh); min-height: 340px; padding-top: 95px; }
}
@media (max-width: 899px) {
html.page-resume .hero h1.rot { font-size: clamp(46px, 8.4vw, 76px); max-width: 15ch; }
}
@media (max-width: 899px) {
html.page-resume .r2-image { left: 48%; }
}
@media (max-width: 899px) {
html.page-resume .case { min-height: 560px; }
}
@media (max-width: 899px) {
html.page-resume .case > .r2-cover,
html.page-resume .case:nth-child(2) > .r2-cover,
html.page-resume .case:nth-child(3) > .r2-cover { top: 60px; height: 210px; }
}
@media (max-width: 899px) {
html.page-resume .folio,
html.page-resume .folio-echo { font-size: 280px; }
}
@media (max-width: 899px) {
html.page-resume .band.anyopen .case:not(.open) > .r2-cover { inset: 60px 0px auto; height: 210px; }
}
@media (max-width: 899px) {
html.page-resume .band.anyopen .case:not(.open) .folio { font-size: 280px; writing-mode: horizontal-tb; top: -0.19em; left: 8%; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-resume .hero,
html.page-resume .hero:hover { min-height: 270px; height: calc(-165px + 100svh); padding-top: 65px; }
}
@media (max-height: 600px) and (min-width: 900px) {
html.page-resume .hero h1.rot { font-size: clamp(40px, 5vw, 70px); }
}
html.page-resume body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { text-transform: uppercase; -webkit-text-stroke: 0px; }
html.page-resume body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .ind-project-label):not(.fm-wait) { opacity: 1; }
html.page-resume body .linkband .k { opacity: 0.5; }
html.page-resume body .contact-meta:not(.fm-wait) { opacity: 0.62; }
html.page-resume .mast .r a { position: relative; transition: color 260ms, opacity 260ms; }
html.page-resume .mast .r a.return-home { opacity: 1; }
html.page-resume .mast .r a.return-home .return-label { opacity: 0.55; transition: opacity 260ms; }
html.page-resume .mast .r a.return-home:is(:hover, :focus-visible) .return-label { opacity: 1; }
html.page-resume .mast .r a.return-home::after { content: ""; position: absolute; left: calc(-1 * var(--return-gap)); right: 0px; top: 50%; height: 1px; background: currentcolor; transform-origin: left center; transition: transform 320ms cubic-bezier(0.22, 0.7, 0.2, 1); }
html.page-resume .mast .r a.return-home:first-child::after { left: -46px; }
html.page-resume .mast .r a.return-home:nth-child(4)::after { right: -22px; }
html.page-resume .mast .r { --return-gap: clamp(14px,2vw,30px); }
html.page-resume .mast .r a.return-home::before { content: "↖"; position: absolute; left: -0.95em; opacity: 0; transform: translate(3px, 3px); transition: opacity 320ms, transform 320ms; }
html.page-resume .mast .r a.return-home:is(:hover, :focus-visible) { opacity: 1; }
html.page-resume .mast .r a.return-home:is(:hover, :focus-visible)::after { transform: none; right: calc(100% + 14px); }
html.page-resume .mast .r a.return-home::after { opacity: 0.34; transition: right 320ms cubic-bezier(0.22, 0.7, 0.2, 1); }
html.page-resume .mast .r a.return-home:is(:hover, :focus-visible)::before { opacity: 1; transform: translate(0px, 0px); }
html.page-resume .mast .r a[aria-current="page"] { opacity: 1; }
html.page-resume .mast:has(> a:is(:hover, :focus-visible)) { background: var(--c-hero); color: var(--t-hero); }
@media (prefers-reduced-motion: reduce) {
html.page-resume .mast .r a,
html.page-resume .mast .r a::before,
html.page-resume .mast .r a::after { transition: none; }
}
html.page-resume #approach .sub-statement { max-width: 44ch; margin: 36px 0px 0px auto; font-family: var(--sans,Arial); font-size: clamp(18px, 1.6vw, 23px); font-weight: 400; letter-spacing: 0px; line-height: 1.55; text-wrap: pretty; }
html.page-resume .lensband .lens:nth-child(n) { --ink: #102b55; --rule-accent: #f8e7cf; transition: background-color 350ms, color 350ms; }
html.page-resume .lensband .lens:nth-child(n) { --ink: #f8e7cf; }
html.page-resume #reading { --finish-quote-ink: #244d50; }
html.page-resume #about .acc details { --about-hover-bg: #082a73; }
html.page-resume #about .acc details:nth-child(2) { --about-hover-bg: #056a91; }
html.page-resume #about .acc details:nth-child(3) { --about-hover-bg: #087865; }
html.page-resume #about .acc details:nth-child(4) { --about-hover-bg: #056a2f; }
html.page-resume #about .acc details:nth-child(5) { --about-hover-bg: #66592a; }
html.page-resume #about .ans { font-weight: 400; letter-spacing: 0px; max-width: 52ch; padding-top: 20px; }
html.page-resume #about .ans p { font: inherit; max-width: 52ch; }
@supports (background-clip:text) {
html.page-resume #reading #words { position: relative; }
}
@supports (background-clip:text) {
html.page-resume #reading #words .word { background-image: url("/static/art/independent-prism.webp"); background-size: var(--quote-art-size,auto 100vh); background-position: var(--word-crop,center); background-clip: text; -webkit-text-fill-color: transparent; text-shadow: none; -webkit-text-stroke: 0px; }
}
@media (max-width: 700px) {
html.page-resume #approach .sub-statement { margin-left: 0px; }
}
html.page-resume .mast:has(> a:is(:hover, :focus-visible)) { background: rgb(8, 120, 101); color: rgb(240, 238, 230); }
html.page-resume .subhero { position: relative; isolation: isolate; overflow: hidden; background: var(--c-read); color: var(--t-read); padding-bottom: clamp(64px, 8vw, 120px); }
html.page-resume .subhero > h1,
html.page-resume .subhero > p,
html.page-resume .subhero > .stem,
html.page-resume .subhero > .acts { position: relative; z-index: 1; max-width: 65%; }
html.page-resume .secondary-art { position: absolute; inset: 0px 0px 0px 72%; z-index: -1; background-repeat: no-repeat; background-size: auto max(100vh, 700px); background-position: 65% center; }
html.page-resume .subhero h1 { font-family: var(--serif); font-weight: 400; font-size: clamp(44px, 6vw, 88px); line-height: 1.04; letter-spacing: -0.025em; }
html.page-resume .phead h2 { font-size: 11px; letter-spacing: 0.1em; font-weight: 400; }
html.page-resume .resume { background: var(--c-read); color: var(--t-read); }
html.page-resume .resume h2 { font-family: var(--mono); font-size: 11px; letter-spacing: 0.1em; text-transform: uppercase; }
html.page-resume .resume h3 { font-family: var(--serif); font-weight: 400; font-size: clamp(25px, 3vw, 38px); line-height: 1.12; }
html.page-resume .resume .role { padding-top: 24px; padding-bottom: 28px; }
html.page-resume .resume p,
html.page-resume .resume li { line-height: 1.65; }
@media (max-width: 700px) {
html.page-resume .subhero > h1,
html.page-resume .subhero > p,
html.page-resume .subhero > .stem,
html.page-resume .subhero > .acts { max-width: 100%; }
}
@media (max-width: 700px) {
html.page-resume .subhero { padding-bottom: 180px; }
}
@media (max-width: 700px) {
html.page-resume .secondary-art { inset: auto 0px 0px; height: 130px; background-size: auto max(100vh, 700px); }
}
@media print {
html.page-resume .secondary-art { display: none; }
}
@media print {
html.page-resume .subhero { padding-bottom: 20px; }
}
@media print {
html.page-resume .subhero > h1,
html.page-resume .subhero > p { max-width: 100%; }
}
html.page-resume .linkband > a { position: relative; isolation: isolate; overflow: hidden; }
html.page-resume .footer-art { position: absolute; inset: 0px; z-index: 0; background-size: auto max(100vh, 700px); background-repeat: no-repeat; opacity: 0; transition: opacity 300ms; pointer-events: none; }
html.page-resume .linkband > a > span { position: relative; z-index: 1; }
html.page-resume .linkband > a:is(:hover, :focus-visible) .footer-art { opacity: 1; }
html.page-resume .linkband > a:is(:hover, :focus-visible) > span { background: none; color: var(--t-links); box-shadow: none; }
html.page-resume .resume-layout { position: relative; isolation: isolate; }
html.page-resume .resume-layout > .secondary-art { inset: 0px 0px 0px 78%; z-index: 2; background-attachment: fixed; background-position: right center; background-size: auto 100vh; pointer-events: none; }
html.page-resume .resume-layout > .resume { padding-right: 27%; }
@media (max-width: 700px) {
html.page-resume .resume-layout > .secondary-art { left: 94%; background-attachment: scroll; background-repeat: repeat-y; }
}
@media (max-width: 700px) {
html.page-resume .resume-layout > .resume { padding-right: 11%; }
}
@media (max-width: 700px) {
html.page-resume .resume-layout > .subhero { padding-bottom: 60px; padding-right: 11%; }
}
@media (max-width: 700px) {
html.page-resume .resume-layout > .subhero > h1,
html.page-resume .resume-layout > .subhero > p { max-width: 100%; }
}
@media (prefers-reduced-motion: reduce) {
html.page-resume .footer-art { transition: none; }
}
@media print {
html.page-resume .resume-layout > .secondary-art,
html.page-resume .footer-art { display: none; }
}
@media print {
html.page-resume .resume-layout > .resume { padding-right: 0px; }
}
html.page-resume .linkband a.lead-tile { background: var(--c-links); color: var(--t-links); }
html.page-resume .play-cursor-label { position: fixed; z-index: 10000; pointer-events: none; font: 400 10px/1.4 var(--mono); letter-spacing: 0.1em; color: var(--t-links); text-shadow: 0 1px 3px var(--c-links); }
html.page-resume .play-cursor-label[hidden] { display: none; }
html.page-resume .play-cursor-label { transform: translate(-50%, -50%); }
html.page-resume .resume-layout > .secondary-art { background-size: auto 115vh; }
html.page-resume body :is(.r3-next, .ind-heading h2, .ind-heading > span, .phead h2, .phead > span, #reading .eyebrow, #reading .foot .label, .contact-meta, .linkband .k, .ind-project-label) { font-family: var(--mono,monospace); font-size: var(--label-size); font-weight: 400; font-style: normal; line-height: 1.5; letter-spacing: var(--label-tracking); mix-blend-mode: normal; text-shadow: none; }
html.page-resume body .r3-next,
html.page-resume body .ind-heading h2,
html.page-resume body .ind-heading > span,
html.page-resume body #projects .phead > *,
html.page-resume body .contact-meta { color: var(--label-light); }
html.page-resume body #about .phead > *,
html.page-resume body #reading .eyebrow,
html.page-resume body #reading .foot .label { color: var(--label-dark); }
html.page-resume body .linkband .k { color: inherit; }
html.page-resume body .phead .dot::before { display: none; }
html.page-resume body .phead h2 { font-weight: 400; }
html.page-resume body .contact-meta:not(.fm-wait) { color: var(--t-contact); }
@media (forced-colors: active) {
html.page-resume body :is(.r3-next, .ind-heading h2, .phead > *, .contact-meta, .linkband .k) { color: canvastext; }
}
html.page-resume :is(.case, .ind-disclosure, .lensband .lens, #approach, #reading, #about, #contact, .acc details, .linkband > a, .built, .play, .resume, .subhero) { border-width: 0px; border-style: none; border-color: currentcolor; box-shadow: none; }
html.page-resume #about .acc summary { box-shadow: none; }
html.page-resume #about .ans { border: 0px; }
html.page-resume .hero::after { background: var(--prism-veil,#c3d6d1); }
html.page-resume .case.open { background: rgb(240, 238, 230); color: rgb(16, 43, 85); }
html.page-resume .band.anyopen .case:not(.open):is(:hover, :focus-visible) { background: rgb(195, 214, 209); color: rgb(16, 43, 85); }
html.page-resume .band.anyopen .case:not(.open):is(:hover, :focus-visible) .number { color: rgb(16, 43, 85); }
html.page-resume #approach .statement { color: rgb(180, 217, 207); }
html.page-resume #approach .statement em { color: rgb(255, 180, 127); }
html.page-resume #approach .sub-statement { color: rgb(217, 182, 155); }
html.page-resume .lensband .lens:nth-child(n) { background: rgb(160, 206, 195); color: rgb(16, 43, 85); }
html.page-resume .lensband .lens:nth-child(n) { color: rgb(248, 231, 207); }
html.page-resume .lensband .lens:nth-child(1) { background: rgb(5, 106, 145); }
html.page-resume .lensband .lens:nth-child(2) { background: rgb(8, 120, 101); }
html.page-resume .lensband .lens:nth-child(3) { background: rgb(5, 106, 47); }
html.page-resume .lensband .lens:nth-child(n):is(:hover, :focus-visible) { background: rgb(16, 59, 66); color: rgb(248, 231, 207); }
html.page-resume .lens:hover :is(h2, p, .n) { color: inherit; }
html.page-resume #reading { color: rgb(36, 77, 80); }
html.page-resume #about .acc summary:is(:hover, :focus-visible) { background: var(--about-hover-bg); color: rgb(248, 231, 207); }
html.page-resume #contact,
html.page-resume #contact:hover { background: rgb(16, 59, 66); color: rgb(180, 217, 207); }
html.page-resume #contact .statement { color: rgb(180, 217, 207); }
html.page-resume #contact .statement em { color: rgb(255, 180, 127); }
html.page-resume #about .ans { font-family: var(--sans,Arial); font-size: clamp(18px, 1.5vw, 22px); line-height: 1.6; }
html.page-resume #about .phead .dot::before { display: none; }
@supports (background-clip:text) {
html.page-resume #reading #words { background: none; }
}
@supports (background-clip:text) {
html.page-resume #reading #words .word { color: transparent; }
}
html.page-resume.play-text-cursor .play,
html.page-resume.play-text-cursor .play *,
html.page-resume.play-text-cursor .playview,
html.page-resume.play-text-cursor .playview * { cursor: none !important; }
/* Semantic page scoping avoids applying secondary-page geometry on Home.
   These rules also resolve geometry formerly supplied through inline styles. */
html.page-home .hero{background-image:url('/static/art/hero-prism.webp');background-size:cover;background-position:center}
.footer-art{background-image:url('/static/art/hero-prism.webp');position:absolute;inset:0;pointer-events:none;opacity:0;transition:opacity 300ms ease;background-size:var(--about-art-size,max(1672px,100vw) auto);background-repeat:no-repeat;z-index:0}
.linkband>a:is(:hover,:focus-visible) .footer-art{opacity:1}
html.page-home .linkband>a:is(:hover,:focus-visible)>span{background:none;box-shadow:none}
.secondary-art{background-image:url('/static/art/hero-prism.webp')}
html.page-personal #play>.phead{background-image:url('/static/art/hero-prism.webp');background-position:60% 5%;background-size:max(1672px,100vw) auto}
html.page-personal #projects .phead>h2{color:#f0eee6}
html.page-personal .subhero.personal{background-color:#f0eee6}
html.page-personal .subhero.personal:is(:hover,:focus-within){background-color:#c3d6d1}
html.page-personal .builtband .built:nth-child(1){background-color:#056a91}
html.page-personal .builtband .built:nth-child(2){background-color:#087865}
html.page-personal .builtband .built:nth-child(3){background-color:#056a2f}
html.page-personal .builtband .built:nth-child(4){background-color:#1f4e79}
html.page-personal .builtband .built:is(:hover,:focus-visible){background-color:#103b42}
html.page-home #independent-study{background-image:url('/static/art/independent-prism.webp');background-size:cover;background-position:center top}
html.page-home #approach{padding-inline:var(--pad)}
html.page-home #about .acc{transition:min-height 850ms cubic-bezier(.22,.7,.2,1)}
html.page-home #about .ans .row-word{display:inline-block}
html.page-home #about .acc summary .about-crop{background-position:var(--crop-position)}
html.page-home #reading #words .word{background-position:var(--word-crop,center)}
.port-cursor{position:fixed;inset:0;pointer-events:none;z-index:99999;mix-blend-mode:difference;color:#eee8dd}
.port-cursor i{position:absolute;left:0;top:0;background:currentColor;will-change:transform}
.cursor-head{width:24px;height:24px}.cursor-tail{width:14px;height:14px}
.cursor-head{transition:background-color .18s ease,box-shadow .18s ease}.cursor-tail{transition:opacity .18s ease}
/* Clickable state (Peter, 2026-10-05, cursor lab option C): over a link or button the diamond turns upright into a square, tightens to about 72%, and the trailing dot goes away. The rotation is eased in site.js. */
html.cursor-link .cursor-tail{opacity:0}
/* Only exception: native cursor declarations include inline/SVG cursor rules.
   Cursor hiding must win throughout a composite interactive subtree. */
html.custom-pointer,html.custom-pointer *{cursor:none!important}
html.play-text-cursor .port-cursor{visibility:hidden}
@media(prefers-reduced-motion:reduce){.port-cursor{display:none}.footer-art{transition:none}html.page-home #about .acc{transition:none}}


/* ---- POR-28 labels ------------------------------------------------------
   Depth 2: three groups, each with a mono label. The label is the smallest
   thing in the card on purpose — it orients a scanning reader without
   competing with the breadcrumb it introduces.
   Depth 3: section headings as wayfinding, not as chunking. Same mono
   treatment so the two depths read as one system. */
.crumb-group{margin:0 0 clamp(16px,2.4vh,26px)}
.crumb-label{display:block;opacity:.5;margin:0 0 8px}
.crumb-group .crumbs{margin:0}
.csec{font-size:10px;letter-spacing:.14em;text-transform:uppercase;opacity:.5;
  font-weight:400;margin:clamp(38px,6vh,66px) 0 clamp(14px,2vh,20px);
  padding-top:clamp(14px,2vh,20px);border-top:1px solid currentColor}
.csec:first-child{margin-top:0;border-top:0;padding-top:0}


/* ==========================================================================
   prism-refine.css — carried verbatim from the approved prototype
   work/approved-source-handoff/site/page-rhythm/prism-refine.css

   This is the final layer of Peter's visual pass and it must stay LAST in the
   cascade. Every rule is gated on html[data-hero-family="prism"], which
   templates/base.html now sets statically. Nothing below has been reformatted,
   re-scoped, or stripped of !important — the priorities are load-bearing.
   ========================================================================== */
/* Codex 2026-09-09. Opt-in 0327 refinement; original remains available. */
html[data-hero-family=prism]{--c-case3:#ff9866!important;--t-case3:#102b55!important;--c-case1h:#103b42!important;--c-case2h:#103b42!important;--c-case3h:#103b42!important;--t-case1h:#f8e7cf!important;--t-case2h:#f8e7cf!important;--t-case3h:#f8e7cf!important}
html[data-hero-family=prism] .hero::after{background:var(--prism-veil,#c3d6d1)!important}
/* Softer foregrounds and one paper/navy interaction family. */
html[data-hero-family=prism]{--t-case1:#d9e3d7!important;--t-case2:#d7e0e9!important;--c-case1h:#c3d6d1!important;--c-case2h:#c3d6d1!important;--c-case3h:#c3d6d1!important;--t-case1h:#102b55!important;--t-case2h:#102b55!important;--t-case3h:#102b55!important;--c-read:#f0eee6!important;--t-read:#102b55!important}
html[data-hero-family=prism] .case.open{background:#f0eee6!important;color:#102b55!important}
html[data-hero-family=prism] .band.anyopen .case:not(.open):is(:hover,:focus-visible){background:#c3d6d1!important;color:#102b55!important}
html[data-hero-family=prism] .band.anyopen .case:not(.open):is(:hover,:focus-visible) .number{color:#102b55!important}
html[data-hero-family=prism] #approach .statement{color:#b4d9cf!important}
html[data-hero-family=prism] #approach .statement em{color:#ffb47f!important}
html[data-hero-family=prism] #approach .sub-statement{color:#d9b69b!important;max-width:44ch;margin:36px 0 0 auto;font-family:var(--sans,Arial);font-size:clamp(18px,1.6vw,23px);font-weight:400;letter-spacing:0;line-height:1.55;text-wrap:pretty}
html[data-hero-family=prism] .lensband .lens:nth-child(n){background:#a0cec3!important;color:#102b55!important;--ink:#102b55;--rule-accent:#f8e7cf;transition:background-color 350ms,color 350ms}
html[data-hero-family=prism] .lensband .lens:nth-child(n){color:#f8e7cf!important;--ink:#f8e7cf}
html[data-hero-family=prism] .lensband .lens:nth-child(1){background:#056a91!important}
html[data-hero-family=prism] .lensband .lens:nth-child(2){background:#087865!important}
html[data-hero-family=prism] .lensband .lens:nth-child(3){background:#056a2f!important}
html[data-hero-family=prism] .lensband .lens:nth-child(n):is(:hover,:focus-visible){background:#103b42!important;color:#f8e7cf!important}
html[data-hero-family=prism] .lens:hover :is(h2,p,.n){color:inherit!important}
html[data-hero-family=prism] #reading{color:#244d50!important;--finish-quote-ink:#244d50}
html[data-hero-family=prism] #about .acc details{--about-hover-bg:#082a73}
html[data-hero-family=prism] #about .acc details:nth-child(2){--about-hover-bg:#056a91}
html[data-hero-family=prism] #about .acc details:nth-child(3){--about-hover-bg:#087865}
html[data-hero-family=prism] #about .acc details:nth-child(4){--about-hover-bg:#056a2f}
html[data-hero-family=prism] #about .acc details:nth-child(5){--about-hover-bg:#66592a}
html[data-hero-family=prism] #about .acc summary:is(:hover,:focus-visible){background:var(--about-hover-bg)!important;color:#f8e7cf!important}
html[data-hero-family=prism] #contact,html[data-hero-family=prism] #contact:hover{background:#103b42!important;color:#b4d9cf!important}
html[data-hero-family=prism] #contact .statement{color:#b4d9cf!important}
html[data-hero-family=prism] #contact .statement em{color:#ffb47f!important}
html[data-hero-family=prism] #about .ans{font-family:var(--sans,Arial)!important;font-size:clamp(18px,1.5vw,22px)!important;font-weight:400;line-height:1.6!important;letter-spacing:0;max-width:52ch;padding-top:20px}
html[data-hero-family=prism] #about .ans p{font:inherit;max-width:52ch}
html[data-hero-family=prism] #about .phead .dot::before{display:none!important}
/* Image stays inside the quote's glyphs; no image takeover, shadow or outline. */
@supports (background-clip:text){
html[data-hero-family=prism] #reading #words{position:relative;background:none!important}
html[data-hero-family=prism] #reading #words .word{background-image:url('/static/art/independent-prism.webp');background-size:var(--quote-art-size,auto 100vh);background-position:var(--word-crop,center);background-clip:text;-webkit-background-clip:text;color:transparent!important;-webkit-text-fill-color:transparent;text-shadow:none;-webkit-text-stroke:0}
}
@media(max-width:700px){html[data-hero-family=prism] #approach .sub-statement{margin-left:0}}


/* ---- Book a call (2026-09-22) -------------------------------------------
   The site's action idiom, not a new one: underlined text, no filled button,
   as the hero's "See the work". Set in the Contact accent — the same coral as
   the italic half of the closing line — because this is the line it answers. */
#contact .contact-book{margin:clamp(22px,3.2vh,36px) 0 0}
#contact .contact-book a{font-family:var(--sans);font-size:15px;letter-spacing:0;
  color:#ffb47f;text-decoration:none;border-bottom:1px solid currentColor;padding-bottom:5px;
  transition:opacity 200ms}
#contact .contact-book a:is(:hover,:focus-visible){opacity:.72}
#contact .contact-book a span{display:inline-block;transition:transform 260ms cubic-bezier(.22,.7,.2,1)}
#contact .contact-book a:is(:hover,:focus-visible) span{transform:translateX(4px)}
@media(prefers-reduced-motion:reduce){#contact .contact-book a span{transition:none}}

/* Case wayfinding — option B, accepted 2026-09-23. The current case's
   existing underline carries reading progress; no extra chapter navigation. */
.case-nav{display:flex;align-items:center;gap:clamp(14px,2vw,28px)}
.case-nav a{position:relative;display:inline-block;text-decoration:none;white-space:nowrap;padding-block:8px}
/* Keep the 8px tap area without growing the masthead: case pages had a 57px bar against 41px elsewhere (Peter, 2026-10-05). */
.mast .case-nav a{margin-block:-8px}
.mast .case-nav .case-nav-item{opacity:.55}
.mast .case-nav .case-nav-item:is(:hover,:focus-visible,[aria-current="page"]){opacity:1}
.case-reading-line{position:absolute;bottom:3px;left:0;right:0;height:1px;background:currentColor;transform:scaleX(var(--case-progress,0));transform-origin:left;pointer-events:none}
.case-nav a:focus-visible{outline:1px solid currentColor;outline-offset:5px}
.case-nav-bottom{padding:clamp(30px,5vh,60px) var(--pad);background:var(--c-read);color:var(--t-read);justify-content:space-between;flex-wrap:wrap}
.case-nav-bottom .case-nav-item{opacity:.62;transition:opacity 200ms}
.case-nav-bottom .case-nav-item:is(:hover,:focus-visible,[aria-current="page"]){opacity:1}
.case-nav-bottom [aria-current="page"]{text-decoration:underline;text-underline-offset:6px}
/* Case footers use the same image windows as Personal and Résumé. */
html.page-case .linkband>a{position:relative;isolation:isolate;overflow:hidden;border:0;box-shadow:none;background:var(--c-links);color:var(--t-links)}
html.page-case .linkband>a>span{position:relative;z-index:1}
html.page-case .footer-art{background-size:auto max(100vh,700px)}
html.page-case .linkband>a:is(:hover,:focus-visible)>span{background:none;color:var(--t-links);box-shadow:none}
html.page-case .linkband .k{font:400 var(--label-size)/1.5 var(--mono);letter-spacing:var(--label-tracking);opacity:.5}
@media(prefers-reduced-motion:reduce){html.page-case .footer-art{transition:none}}
@media print{html.page-case .footer-art{display:none}}
@media(max-width:899px){
  .page-case .mast{flex-wrap:wrap}
  .page-case .mast .r{width:100%}
  .page-case .mast .case-nav{width:100%;justify-content:space-between;gap:10px}
  .page-case .case-nav{font-size:10px;letter-spacing:.02em}
  .case-nav-bottom{display:grid;grid-template-columns:1fr 1fr;gap:18px}
}

/* ---- Homepage hero: the directory of places (POR-59, 2026-09-24) ----
   Replaces the rotating headline. First pass from the lab (work/hero-lab-2026-09-24,
   option B2); Peter will refine scannability, legibility and hover states. */
html.page-home .hero .places-stem{position:relative;z-index:2;margin:0 0 .35em;color:#fff;mix-blend-mode:difference;
  font-family:"Bricolage Grotesque",var(--sans);font-weight:500;font-size:clamp(56px,8.4vw,128px);line-height:.95;letter-spacing:-.06em}
html.page-home .hero .hero-places{position:relative;z-index:2;list-style:none;margin:0 0 clamp(32px,6vh,60px);padding:0;
  display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:18px 36px;max-width:1200px;counter-reset:place;
  color:#fff;mix-blend-mode:difference}
html.page-home .hero .hero-places li{counter-increment:place;border-top:1px solid currentColor;padding-top:10px}
html.page-home .hero .hero-places li::before{content:counter(place,decimal-leading-zero);display:block;font-family:var(--mono);font-size:11px;letter-spacing:.08em;margin-bottom:6px}
html.page-home .hero .hero-places a{display:block;color:inherit;text-decoration:none;background:none}
html.page-home .hero .hero-places .txt{display:block;font-family:"Bricolage Grotesque",var(--sans);font-weight:500;font-size:clamp(17px,1.5vw,24px);line-height:1.2;letter-spacing:-.03em}
html.page-home .hero .hero-places .go{display:block;margin-top:8px;font-size:11px;letter-spacing:.08em;text-transform:uppercase;opacity:.7;transition:opacity .2s}
html.page-home .hero .hero-places a:hover .go,html.page-home .hero .hero-places a:focus-visible .go{opacity:1}
html.page-home .hero .hero-places a:hover .txt,html.page-home .hero .hero-places a:focus-visible .txt{text-decoration:underline;text-underline-offset:.18em;text-decoration-thickness:1px}
@media(max-width:850px){html.page-home .hero .hero-places{grid-template-columns:1fr 1fr;gap:16px 20px}}
@media(max-width:480px){html.page-home .hero .hero-places{grid-template-columns:1fr}}
/* The directory is taller than one rotating line, so the hero may grow: the old fixed
   height becomes the minimum, and the work band still peeks whenever the places fit. */
html.page-home .hero,html.page-home .hero:hover{height:auto;min-height:max(380px,calc(100svh - 230px))}
@media(max-width:899px){html.page-home .hero,html.page-home .hero:hover{min-height:max(340px,calc(100svh - 220px))}}
@media(max-height:600px) and (min-width:900px){html.page-home .hero,html.page-home .hero:hover{min-height:max(270px,calc(100svh - 165px))}}

/* ---- Homepage hero, 2026-10-05 (Peter) ----
   No hero-wide hover: the veil and the cutout headline are gone, so the image stays
   visible. The places are plain text, each with its own hover: a frosted panel over
   the moving image (the image swells beneath it, site.js). "Selected work" sits on
   the top edge of the cards. */
html.page-home .hero::after,html.page-home .hero:hover::after{opacity:0!important}
html.page-home .hero .hero-cutout{display:none}
html.page-home .hero:hover h1{opacity:1}
/* The blend moves from the list to its text, so a panel can sit behind each place. */
html.page-home .hero .hero-places{z-index:auto;mix-blend-mode:normal;color:inherit}
html.page-home .hero .hero-places li{position:relative;color:#fff;border-top:0;padding-top:11px}
html.page-home .hero .hero-places li>*,html.page-home .hero .hero-places li::before{mix-blend-mode:difference}
html.page-home .hero .hero-places li>.txt{position:relative;z-index:1}
html.page-home .hero .hero-places li::before{position:relative;z-index:1}
html.page-home .hero .hero-places li::after{content:"";position:absolute;inset:0 -14px -14px;border-top:1px solid rgba(255,255,255,.9);
  mix-blend-mode:difference;transition:background-color .35s ease,backdrop-filter .35s ease,-webkit-backdrop-filter .35s ease,border-color .35s ease;pointer-events:none}
html.page-home .hero .hero-places li::after{left:0;right:0}
@media(hover:hover){
  html.page-home .hero .hero-places li::after{inset:0 -14px -14px;border-image:linear-gradient(90deg,transparent 14px,rgba(255,255,255,.9) 14px,rgba(255,255,255,.9) calc(100% - 14px),transparent calc(100% - 14px)) 1}
  html.page-home .hero .hero-places li:hover::after{mix-blend-mode:normal;background:rgba(255,255,255,.18);
    -webkit-backdrop-filter:blur(16px) saturate(1.25);backdrop-filter:blur(16px) saturate(1.25);border-image:none;border-top-color:rgba(255,255,255,.55)}
}
html.page-home .hero .r3-next{position:absolute;left:var(--pad);right:var(--pad);bottom:16px;margin:0;z-index:2}
@media(prefers-reduced-motion:reduce){html.page-home .hero .hero-places li::after{transition:none}}

/* ---- Depth-2 fact rail (Peter, 2026-10-05) ----
   Role, scope, team and industry under the meta line, shown only when a card is open. */
.case .card-facts{display:none;margin:0 0 26px;padding:0;max-width:34ch}
.case.open .card-facts{display:grid;gap:12px}
.case .card-facts div{display:grid;gap:2px}
.case .card-facts dt{font-size:12px;letter-spacing:.08em;text-transform:uppercase;opacity:.72}
.case .card-facts dd{margin:0;font-size:14px;line-height:1.4}

/* ---- Legibility pass (Peter approved, 2026-10-05; POR-80) ----
   Labels people need to read: at least 12px (13px for depth-2 section labels) and at
   least 4.5:1 contrast. Measured before and after in work/legibility-lab-2026-10-05. */
.crumb-label{opacity:.72!important;font-size:13px!important}
.case .body .ref{opacity:.72!important;font-size:12px!important}
.case .more{opacity:.78!important;font-size:12px!important}
.case .body .reflect .lbl{font-size:12px!important}
.case a.depth3{font-size:13px!important}
html.page-resume .resume h2{opacity:.72!important;font-size:12px!important}
.resume .rmeta{opacity:.72!important;font-size:12px!important}
.subhero.rz .meta{opacity:.72!important}
.subhero.rz .quiet{opacity:.72!important}

/* Peter, 2026-10-05 (revised same evening): title and tagline lead, then the fact rail
   directly beneath them after generous space. The bottom-anchored version felt awkward. */
.case .card-facts{order:3}
.case.open .hd{display:flex;flex-direction:column}
.case.open .card-facts{margin:48px 0 0;padding-top:20px;border-top:1px solid rgba(16,43,85,.16)}

/* ---- Homepage hero: "Bad decisions scale, too." (Peter, 2026-10-05, POR-81) ----
   Big and punchy (Peter: "it's just kind of tucked away in the top-left corner"): the line
   spans the width of the hero, heavier, and sits low over the image; one supporting
   sentence under it. */
/* Hover must not move anything: an older rule re-aligned the hero to the top on :hover. */
html.page-home .hero,html.page-home .hero:hover{justify-content:center}
html.page-home .hero .hero-line{position:relative;z-index:2;margin:0 0 .28em;color:#fff;mix-blend-mode:difference;max-width:none;
  font-family:"Bricolage Grotesque",var(--sans);font-weight:700;font-variation-settings:"opsz" 96;
  font-size:clamp(56px,16.4vw,300px);line-height:.88;letter-spacing:-.055em;margin-left:-.04em}
html.page-home .hero .hero-line .l,html.page-home .hero .hero-support .l{display:block}
html.page-home .hero .hero-line .l{white-space:nowrap}
html.page-home .hero .hero-support{position:relative;z-index:2;margin:0;color:#fff;mix-blend-mode:difference;max-width:none;
  font-family:var(--sans);font-size:clamp(18px,1.8vw,26px);line-height:1.4}

/* Card outcome (UXfolio 2026 report 3.1: 40% pick a case partly on a clear outcome
   in the preview). One of the case's own hero stats, visible on the closed card. */
.case .card-outcome{display:flex;align-items:baseline;gap:10px;margin:16px 0 0;padding-top:12px;
  border-top:1px solid currentColor;border-top-color:color-mix(in srgb,currentColor 28%,transparent);max-width:34ch}
.case .card-outcome b{font-family:"Bricolage Grotesque",var(--sans,Arial),sans-serif;font-weight:700;
  font-size:clamp(22px,1.9vw,30px);line-height:1;letter-spacing:-.02em;flex:none}
.case .card-outcome span{font-size:14px;line-height:1.35;opacity:.86}
.case:nth-child(1) .card-outcome b{color:var(--h-case1)}
.case:nth-child(2) .card-outcome b{color:var(--h-case2)}
.case:nth-child(3) .card-outcome b{color:var(--h-case3)}
.case.open .card-outcome{display:none}
@media(max-width:899px){
  /* Phone pass 2026-10-06: the outcome line pushed the card title up into the 240px
     numeral. Give closed cards room for title, hook and outcome below it. */
  html.page-home .case:not(.open){min-height:640px}
}
@media(max-width:520px){
  /* Phone pass 2026-10-06: Peter's line break after "organizations" holds on desktop. On a
     phone the first line already wraps, which left "organizations" stranded, so let it flow. */
  html.page-home .hero .hero-support .l{display:inline}
}

/* Career arc (Peter, 2026-10-06): one organism, dividing. A slider drives it (static/arc.js);
   nothing is tied to scroll. All cells one colour; size carries focus. */
#path{padding-top:clamp(64px,10vh,120px);padding-bottom:clamp(56px,9vh,104px);color:var(--ink,#102b55)}
#path .arc-wrap{max-width:1120px;margin:0 auto;display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1.7fr);gap:clamp(24px,4vw,64px);align-items:center}
#path .arc-h{font-family:"Bricolage Grotesque",var(--sans,Arial),sans-serif;font-weight:700;font-size:clamp(34px,4vw,56px);line-height:1;letter-spacing:-.025em;margin:0 0 16px}
#path .arc-lede{font-size:17px;line-height:1.5;max-width:30ch;margin:0 0 clamp(24px,4vh,40px)}
#path .arc-stage{font-size:12px;letter-spacing:.1em;text-transform:uppercase;opacity:.72;margin:0}
#path .arc-era{font-family:"Bricolage Grotesque",var(--sans,Arial),sans-serif;font-weight:600;font-size:clamp(22px,2vw,28px);line-height:1.1;letter-spacing:-.015em;margin:6px 0 0;min-height:2.3em}
#path .arc-svg{width:100%;height:auto;display:block;overflow:visible}
#path .arc-rimc{fill:#cbd3e2}
#path .arc-bodyc{fill:#e3e7ef}
#path .arc-cell{fill:#102b55}
#path .arc-lb{font-family:"Bricolage Grotesque",var(--sans,Arial),sans-serif;font-weight:600;fill:#fff;text-anchor:middle;letter-spacing:-.005em;pointer-events:none;stroke:#102b55;stroke-width:4px;stroke-linejoin:round;paint-order:stroke}
#path .arc-tl{grid-column:1/-1;margin-top:clamp(20px,3vh,36px)}
#path .arc-slider{-webkit-appearance:none;appearance:none;width:100%;height:28px;background:transparent;cursor:pointer;margin:0}
#path .arc-slider::-webkit-slider-runnable-track{height:2px;background:#102b55}
#path .arc-slider::-moz-range-track{height:2px;background:#102b55}
#path .arc-slider::-webkit-slider-thumb{-webkit-appearance:none;width:22px;height:22px;margin-top:-10px;border-radius:50%;background:#102b55;border:5px solid var(--paper,#fefdf9);box-shadow:0 0 0 1.5px #102b55}
#path .arc-slider::-moz-range-thumb{width:12px;height:12px;border-radius:50%;background:#102b55;border:5px solid var(--paper,#fefdf9);box-shadow:0 0 0 1.5px #102b55}
#path .arc-slider:focus-visible{outline:2px solid #102b55;outline-offset:4px}
#path .arc-stops{position:relative;height:36px;margin-top:6px}
#path .arc-stops button{all:unset;position:absolute;top:0;transform:translateX(-50%);white-space:nowrap;cursor:pointer;font-family:var(--mono,monospace);font-size:12px;letter-spacing:.08em;text-transform:uppercase;opacity:.62;padding:6px 2px}
#path .arc-stops button:first-child{transform:none}#path .arc-stops button:last-child{transform:translateX(-100%)}
#path .arc-stops button.on{opacity:1}
#path .arc-stops button:focus-visible{outline:2px solid #102b55;outline-offset:2px}
@media(max-width:820px){#path .arc-wrap{grid-template-columns:1fr}#path .arc-lede{max-width:none}
  #path .arc-stops button{font-size:10px;letter-spacing:.04em;white-space:normal;width:20%;text-align:center}
  #path .arc-stops button:first-child{text-align:left}#path .arc-stops button:last-child{text-align:right}}

/* Phone hero (Peter, 2026-10-06): one word per line, so "Bad decisions scale, too." can run larger. */
@media(max-width:600px){
  html.page-home .hero .hero-line{font-size:23vw;line-height:.86}
  html.page-home .hero .hero-line .l{display:contents}
  html.page-home .hero .hero-line .w{display:block;white-space:nowrap}
}
@media (max-width:899px){
  /* Legibility floor (POR-80): phone nav labels at 12px, not 10px. Tighter tracking and gap keep
     the links on one line at 360px+. */
  .mast,.mast .mono{font-size:12px;letter-spacing:.04em}
  .mast .r{gap:11px}
}

/* Keyboard focus, everywhere (launch check 2026-10-07): a visible ring on anything you can Tab to.
   :where() keeps specificity at zero, so components with their own focus style keep it. */
:where(a[href],button,summary,input,select,textarea,[tabindex]:not([tabindex="-1"])):focus-visible{outline:2px solid currentColor;outline-offset:3px}
