/* Söhne (Klim Type Foundry), trial cuts: replace with licensed files before launch */
@font-face { font-family: "Sohne"; src: url("../fonts/test-soehne-buch.woff2") format("woff2"); font-weight: 400; font-display: swap; }
@font-face { font-family: "Sohne"; src: url("../fonts/test-soehne-leicht.woff2") format("woff2"); font-weight: 300; font-display: swap; }
@font-face { font-family: "Sohne"; src: url("../fonts/test-soehne-extraleicht.woff2") format("woff2"); font-weight: 200; font-display: swap; }
@font-face { font-family: "Sohne"; src: url("../fonts/test-soehne-kraftig.woff2") format("woff2"); font-weight: 500; font-display: swap; }

/* Colour is written in OKLCH. L is perceived lightness, so equal steps in L
   read as equal steps on screen, and the same numbers hold in both themes:
   a hover is a fixed move in L, the neutrals share one warm hue in light mode.
   Every value below renders exactly the hex it replaced (noted alongside). */
:root {
  color-scheme: dark;
  --bg: oklch(0 0 0);                  /* #000 */
  --fg: oklch(1 0 0);                  /* #fff */
  --chip: oklch(.297 0 0);             /* #2d2d2d */
  --chip-fg: oklch(1 0 0);
  --cta: oklch(1 0 0);
  --cta-hover: oklch(.92 0 0);         /* L −.08 */
  --cta-fg: oklch(.206 .004 286);      /* #171719 */
  --cta-press: brightness(95%);        /* a light button presses darker, toward the page */
  --index-bg: oklch(.943 0 0);         /* #ececec */
  --panel: oklch(.215 0 0);            /* the "About the project" panel, quotes */
  --link: oklch(.78 .09 245);          /* links inside writing */
  --index-fg: oklch(.164 0 0);         /* #0e0e0e */

  /* motion: long, decisive curves */
  --ease-slow: cubic-bezier(.73, 0, 0, 1);      /* big moves: slow start, hard stop */
  --ease-fast: cubic-bezier(.17, .67, .1, .99);  /* reveals: quick launch, long settle */
  --ease-faster: cubic-bezier(.19, 1, .22, 1);   /* hovers: expo out */
  /* presses: a damped spring (ζ ≈ .69, 5% overshoot), sampled for linear() */
  --spring: linear(0, .0778, .2508, .4513, .6386, .7921, .9054, .9807, 1.0247, 1.0452, 1.05, 1.0456, 1.0367, 1.0267, 1.0174, 1.0099, 1.0044, 1.0007, .9986, .9977, .9975, .9977, .9982, .9987, .9992, .9995, .9998, 1);
  --spring-dur: 400ms;

  /* layout, proportional to the 1728 × 1117 design frame */
  --edge-left: 3.18vw;
  --edge-right: 2.9vw;
  --logo-top: clamp(22px, 4.48svh, 50px);
  --logo-mid: calc(var(--logo-top) + clamp(17px, 1.45vw, 25px));
  --plate: clamp(260px, min(26.04vw, 40.29svh), 640px);
  --plate-y: calc(50svh - 4.25svh);
  --label: clamp(12px, 1.157vw, 20px);
  --headline: clamp(28px, 3.627vw, 64px);
}

[data-theme="light"] {
  color-scheme: light;
  --bg: oklch(.961 .005 95);           /* #f3f2ee, warm paper */
  --fg: oklch(.164 0 0);               /* #0e0e0e */
  --chip: oklch(.909 .007 97);         /* #e2e1dc */
  --chip-fg: oklch(.178 0 0);          /* #111 */
  --cta: oklch(.178 0 0);
  --cta-hover: oklch(.25 .003 95);     /* L +.07 */
  --cta-fg: oklch(.961 .005 95);
  --cta-press: brightness(110%) contrast(95%); /* a dark one presses lighter */
  --panel: oklch(.925 .006 95);
  --link: oklch(.5 .13 250);
}

*, *::before, *::after { box-sizing: border-box; }

html, body { margin: 0; height: 100%; }

html { background: var(--bg); color: var(--fg); }

body {
  overflow: hidden;
  font-family: "Sohne", "Helvetica Neue", Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-rendering: optimizeLegibility;
}

a, button { color: inherit; font: inherit; text-decoration: none; }
button { appearance: none; background: none; border: 0; padding: 0; margin: 0; cursor: pointer; }
:focus-visible { outline: 1px solid currentColor; outline-offset: 6px; border-radius: 2px; }

.sr-only {
  position: absolute; width: 1px; height: 1px; overflow: hidden;
  clip: rect(0 0 0 0); clip-path: inset(50%); white-space: nowrap;
}

/* -------------------------------------------------------------------- deck */
/* Every page is a full-screen view. In the index they shrink into cards that
   sit side by side; deck.js drives their transforms. */

.deck { position: fixed; inset: 0; overflow: clip; }

.index-backdrop {
  position: absolute;
  inset: 0;
  background: var(--index-bg);
  opacity: 0;
  /* on the way back in, stay white until the page has filled the screen */
  transition: opacity .25s linear .95s;
}
.is-index .index-backdrop { opacity: 1; transition: opacity .9s var(--ease-slow); }

.view {
  position: absolute;
  left: 0;
  top: 0;
  width: 100vw;
  height: 100svh;
  overflow: hidden;
  background: var(--bg);
  color: var(--fg);
  transform-origin: 0 0;
  visibility: hidden;
  transition: background-color 1s var(--ease-faster), color 1s var(--ease-faster);
}
.view.is-active { visibility: visible; z-index: 1; }
/* every page keeps its own layer, so a transition never starts or ends by
   creating or dropping one (that is a hitch, and a re-raster pop) */
.view { will-change: transform; }
.is-index .view > * { pointer-events: none; }

/* ------------------------------------------------------------------ chrome */

.top { position: absolute; inset: 0 0 auto; z-index: 6; pointer-events: none; }

.mark {
  position: absolute;
  left: 50%;
  top: var(--logo-top);
  width: clamp(62px, 5.16vw, 89.1915px);
  translate: -50% 0;
  pointer-events: auto;
  clip-path: inset(0 0 0 0);
  transition:
    clip-path 1.9s var(--ease-slow) .1s,
    opacity 1.4s var(--ease-fast) .1s,
    filter 1.6s var(--ease-fast) .1s,
    scale var(--spring-dur) var(--spring);
}
.mark img { display: block; width: 100%; height: auto; transition: filter 1s var(--ease-faster); }
[data-theme="light"] .mark img { filter: invert(1); }
.mark:hover { scale: 1.04; }

.theme-toggle {
  position: absolute;
  top: calc(var(--logo-mid) - 9px);
  right: var(--edge-right);
  width: 18px;
  height: 18px;
  pointer-events: auto;
  display: grid;
  place-items: center;
  --press-scale: .86; /* a 14px disc needs a deeper press to be felt */
  transition: opacity 1.2s var(--ease-fast) 1.4s, scale var(--spring-dur) var(--spring);
}
.theme-toggle::after { content: ""; position: absolute; inset: -12px; } /* comfortable hit area */
.theme-toggle__disc {
  position: relative;
  width: 14px;
  height: 14px;
  border-radius: 50%;
  border: 1px solid currentColor;
  overflow: hidden;
  transition: rotate 1.1s var(--ease-slow);
}
.theme-toggle__disc::after { content: ""; position: absolute; inset: 0 50% 0 0; background: currentColor; }
.theme-toggle:hover .theme-toggle__disc { rotate: 180deg; }
[data-theme="light"] .theme-toggle__disc { rotate: 180deg; }
[data-theme="light"] .theme-toggle:hover .theme-toggle__disc { rotate: 360deg; }

.side {
  position: absolute;
  top: var(--plate-y);
  translate: 0 -50%;
  z-index: 5;
  font-size: var(--label);
  font-weight: 400;
  line-height: 1;
  letter-spacing: .12em;
  text-transform: uppercase;
  white-space: nowrap;
  transition: scale var(--spring-dur) var(--spring);
}
.side--left { left: var(--edge-left); }
.side--right { right: var(--edge-right); }

/* letters that roll to a copy of themselves on hover */
.roll { display: inline-flex; }
.ch { position: relative; display: inline-block; overflow: hidden; padding-block: .12em; margin-block: -.12em; }
.ch__a, .ch__b { display: block; transition: transform .85s var(--ease-faster) calc(var(--i) * 18ms); }
.ch__b { position: absolute; left: 0; top: 100%; padding-block: .12em; margin-top: -.12em; }
.side:hover .ch__a, .side:hover .ch__b,
.svc__cta:hover .ch__a, .svc__cta:hover .ch__b { transform: translateY(-100%); }

/* ----------------------------------------------------------------- buttons */
/* After devouringdetails.com/system/button. Colour comes from role tokens and
   the shape from the design. Colours change quickly (125ms ease-out); the
   size moves on a spring. A press springs down to .97, or to .94 on a Force
   Touch press (press.js), and the fill moves toward the page: a light button
   presses darker, a dark one lighter. A loading button keeps its colour. */

[data-press] { -webkit-tap-highlight-color: transparent; }
[data-press]:active, [data-press][data-active] { scale: var(--press-scale, .97); }
[data-press][data-force] { scale: calc(var(--press-scale, .97) - .03); }

.btn {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  white-space: nowrap;
  cursor: pointer;
  user-select: none;
  -webkit-user-select: none;
  touch-action: manipulation;
  outline-offset: 2px;
  transition:
    background-color 125ms ease-out,
    color 125ms ease-out,
    filter 125ms ease-out,
    scale var(--spring-dur) var(--spring);
}
.btn:focus-visible { outline: 1px solid var(--fg); }
.btn--solid { background: var(--cta); color: var(--cta-fg); }
@media (pointer: fine) {
  .btn--solid:hover { background: var(--cta-hover); }
}
.btn--solid:active, .btn--solid[data-active] { filter: var(--cta-press); }
/* a theme change fades the button with the page instead of snapping */
.is-theming .btn { transition: background-color 1s var(--ease-faster), color 1s var(--ease-faster), scale var(--spring-dur) var(--spring); }

/* -------------------------------------------------------------------- home */

.plate {
  position: absolute;
  left: 50%;
  top: var(--plate-y);
  width: var(--plate);
  height: var(--plate);
  translate: -50% -50%;
}
.plate__canvas {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 118%;
  height: 118%;
  translate: -50% -50%;
  cursor: crosshair;
  touch-action: none;
}
.plate__poster { display: none; width: 100%; height: 100%; }
/* v2: the canvas covers the page so the sand can form large around the plate */
.home--converge .plate { pointer-events: none; } /* the empty plate box would swallow clicks meant for the sand */
.home--converge > .plate__canvas { left: 0; top: 0; width: 100%; height: 100%; translate: none; cursor: auto; }
.no-webgl .plate__canvas { display: none; }
.no-webgl .plate__poster { display: block; }
[data-theme="light"] .plate__poster { filter: invert(1); mix-blend-mode: multiply; }

.headline {
  position: absolute;
  left: 50%;
  top: 85.59svh;
  translate: -50% -50%;
  margin: 0;
  font-size: var(--headline);
  font-weight: 300;
  line-height: 1.28;
  letter-spacing: -.005em;
  text-align: center;
  white-space: nowrap;
}
.headline__line { display: block; perspective: 900px; }
.headline__line--2 { font-weight: 200; }
.w {
  display: inline-block;
  transform-origin: 50% 100%;
  transition: opacity .8s var(--ease-faster), filter .8s var(--ease-faster), transform .8s var(--ease-faster);
}
.headline.is-tuning .w { opacity: .3; }

/* the turning line (reel.js): the line's own words and each statement share
   one grid cell, so the line keeps its place while they cross */
.reel { display: inline-grid; }
.reel__p { grid-area: 1 / 1; justify-self: center; }
.reel__w { display: inline-block; white-space: nowrap; }
.reel__c { display: inline-block; transform-origin: 50% 100%; }
.headline.is-tuning .w.is-active { opacity: 1; }

/* ------------------------------------------------------------- essay pages */
/* Services and About share a layout. The left column sits on the 1728 × 1117
   design board, which is scaled to fit, and stays put while the essay on the
   right scrolls past it. essay.js sets --k (board scale), --bl and --bt
   (board left / top in px). Each page sets where its essay column sits on the
   board (--track-*, in board px). */

.essay { position: absolute; inset: 0; }
.essay__board {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 1728px;
  height: 1117px;
  transform: translate(-50%, -50%) scale(var(--k, 1));
  pointer-events: none;
  z-index: 2;
}
.essay__board > * { pointer-events: auto; }

.essay__scroller {
  position: absolute;
  inset: 0;
  overflow: hidden;
  z-index: 1;
  -webkit-mask-image: linear-gradient(to bottom, transparent 0, #000 calc(var(--bt, 0px) + 150px * var(--k, 1)), #000 calc(100% - var(--bt, 0px) - 70px * var(--k, 1)), transparent 100%);
  mask-image: linear-gradient(to bottom, transparent 0, #000 calc(var(--bt, 0px) + 150px * var(--k, 1)), #000 calc(100% - var(--bt, 0px) - 70px * var(--k, 1)), transparent 100%);
}
.essay__track {
  position: absolute;
  top: 0;
  left: calc(var(--bl, 0px) + var(--track-x) * var(--k, 1));
  width: calc(var(--track-w) * var(--k, 1));
  padding: calc(var(--bt, 0px) + var(--track-top) * var(--k, 1)) 0 calc(var(--bt, 0px) + var(--track-end) * var(--k, 1));
  will-change: transform;
}

/* lines rise out of their own masks as they arrive */
.ln { display: block; overflow: hidden; }
.ln__in {
  display: block;
  transform: translate3d(0, 105%, 0);
  opacity: 0;
  transition:
    transform 1.25s var(--ease-fast) var(--delay, 0ms),
    opacity .9s var(--ease-fast) var(--delay, 0ms);
}
.ln.is-in .ln__in { transform: none; opacity: 1; }

/* ---------------------------------------------------------------- services */
/* read to the end, the last row of services comes to rest level with the
   bottom of the "Let's talk" button (board y 1037) */
.svc { --track-x: 948px; --track-w: 557px; --track-top: 206px; --track-end: 80px; }

.svc__bpw {
  position: absolute;
  left: 400px;
  top: 245px;
  translate: 0 -50%;
  margin: 0;
  display: flex;
  align-items: center;
  gap: 42px;
  font-size: 70px;
  font-weight: 200;
  line-height: 1;
}
.svc__arrow {
  width: 50px;
  height: 19px;
  overflow: visible;
  fill: none;
  stroke: currentColor;
  stroke-width: 2.3;
  stroke-linecap: round;
  stroke-linejoin: round;
  stroke-dasharray: 100;
  stroke-dashoffset: 0;
  transition: stroke-dashoffset 1.4s var(--ease-fast) calc(.45s + var(--d) * 90ms), translate .8s var(--ease-faster);
}
.svc__bpw:hover .svc__arrow { translate: 6px 0; }

.svc__label {
  margin: 0;
  font-size: 20px;
  font-weight: 400;
  line-height: 20px;
  letter-spacing: .12em;
  text-transform: uppercase;
}
.svc__contact { position: absolute; left: 400px; top: 839px; width: 345px; }
.svc__clock {
  display: flex;
  flex-wrap: wrap;
  gap: 6px 1.25em;
  margin: 10.5px 0 0;
  font-size: 12px;
  line-height: 12px;
  letter-spacing: .12em;
  text-transform: uppercase;
  font-variant-numeric: tabular-nums;
}
/* the clock and the links sit quiet beside it; a link wakes up under the pointer */
.svc__clock > [data-clock], .svc__links a { opacity: .5; transition: opacity .5s var(--ease-faster); }
.svc__links { display: flex; gap: 0 1.25em; }
.svc__links a:hover, .svc__links a:focus-visible { opacity: 1; }
.svc__links a:hover .ch__a, .svc__links a:hover .ch__b { transform: translateY(-100%); }
.svc__invite { margin: 26.5px 0 0; font-size: 16px; font-weight: 300; line-height: 21px; }
.svc__cta-wrap { position: absolute; left: 0; top: 161px; }
.svc__cta {
  height: 37px;
  padding: 0 16px;
  border-radius: 50px;
  font-size: 14px;
  letter-spacing: -.01em;
}

/* the essay */
.svc__headline {
  margin: 0 0 calc(33px * var(--k, 1));
  font-size: calc(45px * var(--k, 1));
  font-weight: 300;
  line-height: calc(60px * var(--k, 1));
  letter-spacing: -.003em;
}
.svc__headline .para { display: block; }
.svc__body {
  font-size: calc(20px * var(--k, 1));
  font-weight: 300;
  line-height: calc(27px * var(--k, 1));
}
.svc__body p { margin: 0 0 calc(27px * var(--k, 1)); }
.svc__body p:last-child { margin: 0; }
.svc__body .is-strong { font-weight: 500; }

/* the close: three short lines, then what the work covers.
   Spacing is set baseline to baseline from the design (Söhne: ascent 1.037,
   descent .289, cap height .718 em). */
.svc__closing { margin: calc(35px * var(--k, 1)) 0 0; }          /* last essay line → 88 → first line */
.svc .essay__track .svc__label {
  margin-top: calc(26px * var(--k, 1));                             /* 57 baseline to baseline */
  font-size: calc(20px * var(--k, 1));
  line-height: calc(20px * var(--k, 1));
}
.svc__chips {
  display: grid;
  grid-template-columns: calc(272px * var(--k, 1)) auto;
  justify-items: start;
  row-gap: calc(9.4px * var(--k, 1));                               /* a chip every 30 */
  margin: calc(37.6px * var(--k, 1)) 0 0;                           /* 40 below the label's baseline */
  padding: 0;
  list-style: none;
}
.svc__chip { display: block; }
.chip {
  display: block;
  padding: calc(6px * var(--k, 1)) calc(14px * var(--k, 1));
  border-radius: calc(7px * var(--k, 1));
  background: var(--chip);
  color: var(--chip-fg);
  font-size: calc(12px * var(--k, 1));
  line-height: calc(12px * .718 * var(--k, 1));                     /* cap height: 6 above, 6 below */
  letter-spacing: .19em;
  text-transform: uppercase;
  white-space: nowrap;
  transition: background-color 1s var(--ease-faster), color 1s var(--ease-faster);
}

/* chips rise in whole, a little later than the text around them */
.svc__chip .chip {
  opacity: 0;
  translate: 0 70%;
  transition:
    translate 1.1s var(--ease-fast) var(--delay, 0ms),
    opacity .8s var(--ease-fast) var(--delay, 0ms),
    background-color 1s var(--ease-faster), color 1s var(--ease-faster);
}
.svc__chip.is-in .chip { opacity: 1; translate: none; }

/* ------------------------------------------------------------------- about */
/* Spacing follows the design baseline to baseline. Headlines are 45/60 and
   body text is 20/27.2. A headline's last baseline sits 49 above the cap
   line of the body under it, and a body's last baseline sits 79 above the
   next headline. */

.about { --track-x: 819px; --track-w: 592px; --track-top: 171.3px; --track-end: 80px; }

/* who: hangs off the name label, so the three stay together at any size */
.about__id { position: absolute; left: var(--edge-left); top: var(--plate-y); z-index: 2; }
.about__portrait {
  position: absolute;
  left: 0;
  bottom: calc(42px * var(--k, 1));                                 /* 42 above the name's centre */
  display: block;
  width: calc(283px * var(--k, 1));
  height: calc(283px * var(--k, 1));
  border-radius: calc(26.326px * var(--k, 1));
  object-fit: cover;
}
.about__role {
  position: absolute;
  left: 0;
  top: calc(28.1px * var(--k, 1));
  margin: 0;
  font-size: calc(20px * var(--k, 1));
  font-weight: 300;
  line-height: 1;
  white-space: nowrap;
  opacity: .75;
}

/* the logo, live in chrome (logo3d.js); the flat mark stands in without WebGL */
.about__logo {
  position: absolute;
  left: -60px;
  top: 575px;
  width: 870px;
  height: 580px;
  cursor: grab;
  touch-action: pan-y;
  -webkit-tap-highlight-color: transparent;
}
.about__logo.is-dragging { cursor: grabbing; }
.about__logo canvas { display: block; width: 100%; height: 100%; }
.about__logo-flat { display: none; position: absolute; left: 50%; top: 50%; width: 74%; height: auto; translate: -50% -50%; }
.about__logo.no-3d { cursor: auto; }
.about__logo.no-3d canvas { display: none; }
.about__logo.no-3d .about__logo-flat { display: block; }
[data-theme="light"] .about__logo-flat { filter: invert(1); }

.about__head {
  margin: 0;
  font-size: calc(45px * var(--k, 1));
  font-weight: 300;
  line-height: calc(60px * var(--k, 1));
}
.about__head .para { display: block; white-space: nowrap; }
.about__head .ln { width: max-content; } /* a long headline runs past the column instead of being cut */
.about__body {
  max-width: calc(557px * var(--k, 1));
  font-size: calc(20px * var(--k, 1));
  font-weight: 300;
  line-height: calc(27.2px * var(--k, 1));
}
.about__body--wide { max-width: none; }
.about__body p { margin: 0 0 calc(26.7px * var(--k, 1)); }
.about__body p:last-child { margin: 0; }
.about__head + .about__body { margin-top: calc(29.2px * var(--k, 1)); }
.about__body + .about__head { margin-top: calc(58.6px * var(--k, 1)); }

/* -------------------------------------------------------------------- work */
/* The grid (js/work.js packs it) and one project opened out of its cover.
   Sizes are board px from the Figma frames, scaled by --k like the essays. */

.work { position: absolute; inset: 0; }
.work__scroller {
  position: absolute;
  inset: 0;
  overflow: hidden;
  -webkit-mask-image: linear-gradient(to bottom, transparent 0, #000 calc(var(--bt, 0px) + 140px * var(--k, 1)), #000 calc(100% - 6vh), transparent 100%);
  mask-image: linear-gradient(to bottom, transparent 0, #000 calc(var(--bt, 0px) + 140px * var(--k, 1)), #000 calc(100% - 6vh), transparent 100%);
}
.work__track {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  padding: calc(var(--bt, 0px) + 167px * var(--k, 1)) 0 calc(140px * var(--k, 1));
  will-change: transform;
}
.work__title {
  margin: 0 0 calc(37px * var(--k, 1));
  font-size: calc(20px * var(--k, 1));
  font-weight: 400;
  line-height: calc(20px * var(--k, 1));
  letter-spacing: .12em;
  text-transform: uppercase;
  text-align: center;
}
.work__grid { position: relative; margin: 0 auto; padding: 0; list-style: none; }
.is-project .work__scroller { pointer-events: none; }

.tile { position: absolute; left: 0; top: 0; }
.tile__link {
  display: block;
  opacity: 0;
  transform: translateY(calc(56px * var(--k, 1)));
  transition:
    opacity .9s var(--ease-fast) var(--delay, 0ms),
    transform 1.3s var(--ease-fast) var(--delay, 0ms),
    scale var(--spring-dur) var(--spring);
}
.tile.is-in .tile__link { opacity: 1; transform: none; }
.tile__media {
  position: relative;
  overflow: hidden;
  border-radius: calc(8px * var(--k, 1));
  background: var(--chip);
  transition: background-color 1s var(--ease-faster);
}
.tile__media > * {
  position: absolute;
  inset: 0;
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
  transition: scale 1.2s var(--ease-faster);
}
@media (hover: hover) and (pointer: fine) {
  .tile__link:hover .tile__media > * { scale: 1.045; }
}
.tile__cap {
  margin: calc(8px * var(--k, 1)) 0 0;
  font-size: max(11px, calc(12px * var(--k, 1)));
  line-height: 1.3;
}
.tile__name { display: block; font-weight: 500; }
.tile__kind { display: block; opacity: .5; }

/* one project */
.proj { position: absolute; inset: 0; z-index: 3; }
.proj[hidden] { display: none; }
.proj__bar { position: absolute; inset: 0 0 auto; z-index: 4; }
.proj__back, .proj__id, .proj__about {
  position: absolute;
  top: calc(var(--bt, 0px) + 158px * var(--k, 1));
  margin: 0;
  font-size: max(11px, calc(14px * var(--k, 1)));
  line-height: max(15px, calc(18px * var(--k, 1)));
}
.proj__back { left: calc(var(--bl, 0px) + 190px * var(--k, 1)); letter-spacing: .12em; text-transform: uppercase; }
.proj__id { left: calc(var(--bl, 0px) + 366px * var(--k, 1)); }
.proj__kind { opacity: .5; }
.proj__about {
  left: calc(var(--bl, 0px) + 1500px * var(--k, 1));
  top: calc(var(--bt, 0px) + 176px * var(--k, 1));
  translate: -100% 0;
  text-align: right;
}
.proj__back, .proj__id, .proj__about { transition: left .95s var(--ease-fast), top .95s var(--ease-fast), translate .95s var(--ease-fast); }

/* scrolled: the header glides into the left margin and stacks under the logo */
.view--work .mark {
  transition:
    clip-path 1.9s var(--ease-slow) .1s,
    opacity 1.4s var(--ease-fast) .1s,
    filter 1.6s var(--ease-fast) .1s,
    scale var(--spring-dur) var(--spring),
    translate .95s var(--ease-fast);
}
.view--work.is-docked .mark { translate: calc(var(--edge-left) - 50vw) 0; }
.view--work.is-docked .proj__back { left: var(--edge-left); }
.view--work.is-docked .proj__id {
  left: var(--edge-left);
  top: calc(var(--bt, 0px) + 186px * var(--k, 1));
  max-width: calc(var(--bl, 0px) + 176px * var(--k, 1) - var(--edge-left));
}
/* in the margin each line stays one line (a long name ends in …), so it never runs into About */
.view--work.is-docked .proj__id .rv {
  max-width: 100%;
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
  vertical-align: top;
}
.view--work.is-docked .proj__about {
  left: var(--edge-left);
  /* under the name's two lines, whose height has a floor on small screens (236 on the board) */
  top: calc(var(--bt, 0px) + 186px * var(--k, 1) + 2 * max(15px, 18px * var(--k, 1)) + max(6px, 14px * var(--k, 1)));
  translate: 0 0;
}
.view--work.is-docked .proj__about .ab { justify-self: start; }
.proj__about .rv { display: inline-grid; }
.proj__about .ab { grid-area: 1 / 1; justify-self: end; transition: transform .8s var(--ease-faster), opacity .5s var(--ease-faster); }
.proj__about .ab--close { transform: translateY(100%); opacity: 0; }
.proj.is-about .proj__about .ab:first-child { transform: translateY(-100%); opacity: 0; }
.proj.is-about .proj__about .ab--close { transform: none; opacity: 1; }

.proj__scroller { position: absolute; inset: 0; overflow: hidden; z-index: 1; }
.proj__track {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  padding: calc(var(--bt, 0px) + 224px * var(--k, 1)) 0 calc(var(--bt, 0px) + 140px * var(--k, 1));
  will-change: transform;
}
/* --s scales the whole column: with the About panel open it is the same
   column at 715 wide, every image whole and in proportion */
.proj__col {
  --s: 1;
  display: flex;
  flex-direction: column;
  gap: calc(30px * var(--k, 1) * var(--s));
  width: calc(1310px * var(--k, 1) * var(--s));
  margin-left: calc(var(--bl, 0px) + 190px * var(--k, 1));
  transform-origin: 0 0;
}
.proj__col.is-narrow { --s: calc(715 / 1310); }
.blk { display: flex; align-items: flex-start; gap: calc(30px * var(--k, 1) * var(--s, 1)); }
/* every file whole, at its own proportions (--a); a row's files share a height */
.m {
  position: relative;
  /* grow by aspect; ×1000 so tall ones (whose ratios sum under 1) still fill the row */
  flex: calc(var(--a, 1.7778) * 1000) 1 0;
  aspect-ratio: var(--a, 1.7778);
  min-width: 0;
  margin: 0;
  overflow: hidden;
  border-radius: calc(12px * var(--k, 1));
  background: var(--chip);
}
.m__in {
  position: absolute;
  left: 0;
  top: 0;
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
}
/* the images below the first rise in as they arrive */
.m:not(.m--hero) {
  opacity: 0;
  transform: translateY(calc(70px * var(--k, 1)));
  transition: opacity 1s var(--ease-fast), transform 1.4s var(--ease-fast);
}
.m.is-in { opacity: 1; transform: none; }

/* about the project */
.proj__info {
  position: absolute;
  z-index: 2;
  left: calc(var(--bl, 0px) + 927px * var(--k, 1));
  top: calc(var(--bt, 0px) + 224px * var(--k, 1));
  width: calc(573px * var(--k, 1));
  max-height: calc(100% - var(--bt, 0px) - 264px * var(--k, 1));
  overflow: auto;
  padding: calc(32px * var(--k, 1)) calc(34px * var(--k, 1));
  border-radius: calc(12px * var(--k, 1));
  background: var(--panel);
  transition: background-color 1s var(--ease-faster);
}
.proj__info[hidden] { display: none; }
/* closing, the lines leave upward and quickly, the way the panel folds */
.proj__info.is-folding .ln__in {
  transform: translate3d(0, -105%, 0);
  transition: transform .5s cubic-bezier(.55, 0, .75, 0), opacity .3s cubic-bezier(.55, 0, .75, 0);
}
.proj__text p {
  margin: 0 0 calc(16px * var(--k, 1));
  font-size: max(12px, calc(15px * var(--k, 1)));
  line-height: 1.5;
}
.proj__meta {
  display: grid;
  gap: calc(16px * var(--k, 1));
  margin: calc(30px * var(--k, 1)) 0 0;
  font-size: max(11px, calc(12px * var(--k, 1)));
  line-height: 1.45;
}
.proj__meta dt { font-weight: 500; }
.proj__meta dd { margin: 0; opacity: .55; }

/* the moving cover */
.ghost { position: absolute; z-index: 7; overflow: hidden; pointer-events: none; background: var(--chip); }
.ghost > * { display: block; width: 100%; height: 100%; object-fit: cover; }

/* private work: a lock on locked covers, and the password card (js/gate.js) */
.tile__lock {
  display: inline-block;
  width: .62em;
  height: .74em;
  margin-left: .45em;
  vertical-align: -.02em;
  fill: currentColor;
  opacity: .45;
  transition: opacity .6s var(--ease-faster), width .6s var(--ease-faster), margin .6s var(--ease-faster);
}
.work.is-unlocked .tile__lock { opacity: 0; width: 0; margin-left: 0; }
.work.is-unlocked .tile__private { display: none; }
.tile--open .tile__lock, .tile--open .tile__private { display: none; }
/* a private image fades in once it is decrypted */
.m__in { transition: opacity .7s var(--ease-fast); }
.m__in.is-pending { opacity: 0; }

.gate[open] {
  position: fixed;
  inset: 0;
  display: grid;
  place-items: center;
  width: 100%;
  height: 100%;
  max-width: none;
  max-height: none;
  margin: 0;
  padding: 16px;
  border: 0;
  background: transparent;
  color: var(--fg);
  overflow: hidden;
}
.gate::backdrop { background: transparent; }
.gate__veil {
  position: absolute;
  inset: 0;
  background: color-mix(in oklch, var(--bg) 58%, transparent);
  -webkit-backdrop-filter: blur(18px) saturate(1.15);
  backdrop-filter: blur(18px) saturate(1.15);
}
.gate__card {
  position: relative;
  width: min(400px, 100%);
  padding: 20px 20px 18px;
  border-radius: 18px;
  background: var(--panel);
  box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--fg) 7%, transparent);
  font-size: 14px;
  line-height: 1.45;
}
.gate__head { display: flex; align-items: center; gap: 14px; }
.gate__thumb {
  position: relative;
  flex: none;
  width: 52px;
  height: 52px;
  overflow: hidden;
  border-radius: 10px;
  background: var(--chip);
}
.gate__thumb img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; }
.gate__id { flex: 1; min-width: 0; margin: 0; }
.gate__name { display: block; font-size: 16px; font-weight: 500; line-height: 1.3; }
.gate__kind { display: block; opacity: .5; line-height: 1.3; }
.gate__x {
  align-self: flex-start;
  display: grid;
  place-items: center;
  width: 28px;
  height: 28px;
  margin: -4px -4px 0 0;
  border-radius: 99px;
  opacity: .55;
  transition: opacity .3s var(--ease-faster), background-color .3s var(--ease-faster), scale var(--spring-dur) var(--spring);
}
.gate__x:hover { opacity: 1; background: color-mix(in oklch, var(--fg) 8%, transparent); }
.gate__x svg { width: 12px; height: 12px; fill: none; stroke: currentColor; stroke-width: 1.3; stroke-linecap: round; }
.gate__note { margin: 18px 0 16px; opacity: .72; text-wrap: pretty; }
.gate__lock { display: inline-block; width: 9px; height: 11px; margin-right: 5px; vertical-align: -1px; fill: currentColor; }

.gate__field {
  position: relative;
  display: flex;
  align-items: center;
  height: 46px;
  padding: 4px;
  border-radius: 99px;
  background: color-mix(in oklch, var(--fg) 5%, transparent);
  box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--fg) 12%, transparent);
  transition: box-shadow .35s var(--ease-faster), background-color .35s var(--ease-faster);
}
.gate__field:focus-within { box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--fg) 42%, transparent); }
.gate__field.is-wrong { box-shadow: inset 0 0 0 1px oklch(.68 .17 25 / .85); }
.gate__input {
  flex: 1;
  min-width: 0;
  height: 100%;
  padding: 0 10px 0 15px;
  border: 0;
  outline: 0;
  background: none;
  color: inherit;
  font: inherit;
  font-size: 16px; /* under 16px, iOS zooms the page when the field takes focus */
  letter-spacing: .02em;
}
.gate__input::placeholder { color: inherit; opacity: .4; }
.gate__go {
  position: relative;
  flex: none;
  display: grid;
  place-items: center;
  width: 38px;
  height: 38px;
  border-radius: 99px;
  background: var(--cta);
  color: var(--cta-fg);
  transition: background-color 125ms ease-out, filter 125ms ease-out, scale var(--spring-dur) var(--spring);
}
@media (pointer: fine) { .gate__go:hover { background: var(--cta-hover); } }
.gate__go:active { filter: var(--cta-press); }
.gate__go:focus-visible { outline-offset: 3px; border-radius: 99px; }
.gate__go > * { grid-area: 1 / 1; transition: opacity .3s var(--ease-faster), transform .5s var(--ease-faster); }
.gate__arrow, .gate__tick { width: 16px; height: 16px; fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }
.gate__spin {
  width: 16px;
  height: 16px;
  border-radius: 50%;
  border: 1.6px solid currentColor;
  border-right-color: transparent;
  opacity: 0;
  animation: gate-spin .7s linear infinite;
}
@keyframes gate-spin { to { rotate: 1turn; } }
.gate__tick { opacity: 0; transform: scale(.6); stroke-dasharray: 16; stroke-dashoffset: 16; transition: opacity .2s, transform .5s var(--spring), stroke-dashoffset .45s var(--ease-fast) .05s; }
.gate__field:not(.is-busy):not(.is-done) .gate__go:hover .gate__arrow { transform: translateX(2px); }
.is-busy .gate__arrow, .is-done .gate__arrow { opacity: 0; transform: translateX(8px); }
.is-busy .gate__spin { opacity: 1; }
.is-done .gate__tick { opacity: 1; transform: none; stroke-dashoffset: 0; }
.gate__msg { min-height: 1.45em; margin: 10px 0 0 15px; font-size: 13px; color: oklch(.74 .14 25); }
[data-theme="light"] .gate__msg { color: oklch(.55 .17 25); }
[data-theme="light"] .gate__field.is-wrong { box-shadow: inset 0 0 0 1px oklch(.55 .17 25 / .8); }
.gate__ask { margin: 6px 0 0 15px; font-size: 13px; }
.gate__ask { color: color-mix(in oklch, var(--fg) 50%, transparent); }
.gate__mail { color: var(--fg); opacity: .8; transition: opacity .4s var(--ease-faster); }
.gate__mail:hover { opacity: 1; }
.gate__mail:hover .ch__a, .gate__mail:hover .ch__b { transform: translateY(-100%); }

/* ----------------------------------------------------------------- writing */
/* The list (js/writing.js packs it) and one post. Board px from the Figma,
   scaled by --k. */

.wr__crumb {
  position: absolute;
  z-index: 5;
  left: calc(var(--bl, 0px) + 190px * var(--k, 1));
  top: var(--logo-mid);
  translate: 0 -50%;
  display: flex;
  align-items: center;
  font-size: var(--label);
  line-height: 1;
  letter-spacing: .12em;
  text-transform: uppercase;
  white-space: nowrap;
  transition: opacity .45s var(--ease-faster), translate .7s var(--ease-faster);
}
.wr__crumb a { display: inline-flex; }
.wr__crumb-sep { margin: 0 .55em; opacity: .5; }
.wr__crumb a:hover .ch__a, .wr__crumb a:hover .ch__b { transform: translateY(-100%); }
.wr__crumb-here { text-decoration: underline transparent; text-underline-offset: .3em; transition: text-decoration-color .4s var(--ease-faster); }
.view--writing.is-post .wr__crumb-here:hover { text-decoration-color: currentColor; }

/* reading down the page, the header steps out of the way; scrolling up brings it back */
.view--writing .mark {
  transition:
    clip-path 1.9s var(--ease-slow) .1s,
    opacity .45s var(--ease-faster),
    filter 1.6s var(--ease-fast) .1s,
    scale var(--spring-dur) var(--spring),
    translate .7s var(--ease-faster);
}
.view--writing.is-tucked .mark { opacity: 0; translate: -50% -18px; pointer-events: none; }
.view--writing.is-tucked .wr__crumb { opacity: 0; translate: 0 calc(-50% - 18px); pointer-events: none; }

.wr { position: absolute; inset: 0; }
.wr__scroller { position: absolute; inset: 0; overflow: hidden; }
.wr__track {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  padding: calc(var(--bt, 0px) + 163px * var(--k, 1)) 0 calc(var(--bt, 0px) + 70px * var(--k, 1)) calc(var(--bl, 0px) + 190px * var(--k, 1));
  will-change: transform;
}
.is-post .wr__scroller { pointer-events: none; }

.wr__filters {
  display: flex;
  flex-wrap: wrap;
  gap: 0 calc(22px * var(--k, 1));
  margin: 0 0 calc(39px * var(--k, 1));
  font-size: max(12px, calc(14px * var(--k, 1)));
  line-height: calc(24px * var(--k, 1));
}
.wr__filter { transition: opacity .5s var(--ease-faster), scale var(--spring-dur) var(--spring); }
.wr__filters.has-on .wr__filter:not(.is-on) { opacity: .38; }
@media (hover: hover) and (pointer: fine) {
  .wr__filters.has-on .wr__filter:not(.is-on):hover { opacity: .8; }
}

.wr__grid { position: relative; margin: 0; padding: 0; list-style: none; }
.card { position: absolute; left: 0; top: 0; }
.card[hidden] { display: none; }
.card__link {
  display: block;
  opacity: 0;
  transform: translateY(calc(56px * var(--k, 1)));
  transition:
    opacity .9s var(--ease-fast) var(--delay, 0ms),
    transform 1.3s var(--ease-fast) var(--delay, 0ms),
    scale var(--spring-dur) var(--spring);
}
.card.is-in .card__link { opacity: 1; transform: none; }
.card__cover {
  border-radius: calc(8px * var(--k, 1));
  overflow: hidden;
  transition: filter .7s var(--ease-faster);
}
/* a cover picture fills its frame, which already has its shape */
.card__cover > img, .art__cover > img, .art__next-cover > img { display: block; width: 100%; height: 100%; object-fit: cover; }
.card__cap {
  margin: calc(10px * var(--k, 1)) 0 0;
  font-size: max(12px, calc(14px * var(--k, 1)));
  line-height: 1.4;
}
.card__title { display: block; }
.card__date { display: block; height: 1.4em; overflow: hidden; }
.card__roll { display: flex; flex-direction: column; transition: transform .75s var(--ease-faster); }
.card__roll > span:first-child { opacity: .5; }
@media (hover: hover) and (pointer: fine) {
  .card__link:hover .card__cover { filter: brightness(1.08) saturate(1.06); }
  .card__link:hover .card__roll { transform: translateY(-50%); }
}
.wr__foot { margin: calc(170px * var(--k, 1)) 0 0; font-size: 11px; letter-spacing: .04em; opacity: .4; }

/* one post */
.art { position: absolute; inset: 0; z-index: 3; }
.art[hidden] { display: none; }
.art__scroller { position: absolute; inset: 0; overflow: hidden; }
.art__track {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  padding: calc(var(--bt, 0px) + 198px * var(--k, 1)) 0 calc(var(--bt, 0px) + 70px * var(--k, 1));
  will-change: transform;
}
.art__grid {
  display: grid;
  grid-template-columns: calc(285px * var(--k, 1)) calc(570px * var(--k, 1));
  column-gap: calc(90px * var(--k, 1));
  align-items: start;
  margin-left: calc(var(--bl, 0px) + 190px * var(--k, 1));
}
.art__side { padding-top: calc(6px * var(--k, 1)); }
.art__meta { margin: 0; font-size: max(12px, calc(14px * var(--k, 1))); line-height: max(1.45em, calc(24px * var(--k, 1))); } /* the floor keeps lines apart where the type stops shrinking */
.art__meta--dim { opacity: .5; }
.art__cover { margin-top: calc(45px * var(--k, 1)); aspect-ratio: 1; overflow: hidden; border-radius: calc(8px * var(--k, 1)); }
.art__title { margin: 0; font-size: calc(45px * var(--k, 1)); font-weight: 300; line-height: calc(54px * var(--k, 1)); letter-spacing: -.005em; }
.art__body { margin-top: calc(56px * var(--k, 1)); }
.art__p { margin: 0 0 calc(30px * var(--k, 1)); font-size: max(14px, calc(18px * var(--k, 1))); line-height: 2; }
.art__h { margin: calc(58px * var(--k, 1)) 0 calc(16px * var(--k, 1)); font-size: max(16px, calc(22px * var(--k, 1))); font-weight: 400; line-height: 1.45; }
.art__body a {
  color: var(--link);
  text-decoration: underline;
  text-decoration-thickness: 1px;
  text-underline-offset: .22em;
  transition: color .4s var(--ease-faster), text-decoration-color .4s var(--ease-faster);
}
.art__body a:hover { text-decoration-color: transparent; }
.art__fig { margin: calc(52px * var(--k, 1)) 0 calc(52px * var(--k, 1)) calc(-91px * var(--k, 1)); width: calc(778px * var(--k, 1)); height: calc(440px * var(--k, 1)); border-radius: calc(12px * var(--k, 1)); }
.art__q { margin: calc(46px * var(--k, 1)) 0 calc(46px * var(--k, 1)) calc(-16px * var(--k, 1)); width: calc(602px * var(--k, 1)); padding: calc(26px * var(--k, 1)) calc(30px * var(--k, 1)); border-radius: calc(12px * var(--k, 1)); background: var(--panel); transition: background-color 1s var(--ease-faster); }
.art__q p { margin: 0; font-size: max(14px, calc(17px * var(--k, 1))); line-height: 1.75; }
.art__q cite { display: block; margin-top: calc(14px * var(--k, 1)); font-size: max(11px, calc(13px * var(--k, 1))); font-style: normal; opacity: .5; }
.art__share {
  display: inline-flex;
  align-items: center;
  gap: calc(6px * var(--k, 1));
  height: calc(30px * var(--k, 1));
  margin-top: calc(30px * var(--k, 1));
  padding: 0 calc(13px * var(--k, 1)) 0 calc(11px * var(--k, 1));
  border-radius: 99px;
  box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--fg) 24%, transparent);
  font-size: max(11px, calc(12px * var(--k, 1)));
  line-height: calc(30px * var(--k, 1));
  transition: box-shadow .5s var(--ease-faster), scale var(--spring-dur) var(--spring);
}
.art__share:hover { box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--fg) 60%, transparent); }
.art__share-icon { width: max(11px, calc(14px * var(--k, 1))); height: max(11px, calc(14px * var(--k, 1))); flex: none; fill: currentColor; fill-opacity: .733; }
/* the word rolls over to the result; the width follows the word (set from js) */
.art__share-labels { display: block; height: calc(30px * var(--k, 1)); overflow: hidden; text-align: left; transition: width .55s var(--ease-faster); }
.art__share-l { display: block; width: max-content; height: calc(30px * var(--k, 1)); white-space: nowrap; transition: transform .7s var(--ease-faster); }
.art__share.is-done .art__share-l { transform: translateY(-100%); }
.art__next {
  position: absolute;
  left: calc(var(--bl, 0px) + 1309px * var(--k, 1));
  bottom: calc(var(--bt, 0px) + 150px * var(--k, 1));
  width: calc(277px * var(--k, 1));
  font-size: max(12px, calc(14px * var(--k, 1)));
  line-height: 1.4;
}
.art__next > span { display: block; }
.art__next-label { margin-bottom: calc(10px * var(--k, 1)); font-size: max(11px, calc(12px * var(--k, 1))); opacity: .5; }
.art__next-cover { aspect-ratio: 1; overflow: hidden; border-radius: calc(8px * var(--k, 1)); transition: filter .7s var(--ease-faster); }
.art__next:hover .art__next-cover { filter: brightness(1.08) saturate(1.06); }
.art__next-title { margin-top: calc(10px * var(--k, 1)); }
.art__next-date { opacity: .5; }
.art .wr__foot { margin-left: calc(var(--bl, 0px) + 190px * var(--k, 1)); }
/* blocks rise in like the lines do */
.art__fig, .art__q, .art__share, .art__next {
  opacity: 0;
  transform: translateY(calc(44px * var(--k, 1)));
  transition: opacity 1s var(--ease-fast) var(--delay, 0ms), transform 1.3s var(--ease-fast) var(--delay, 0ms), filter .7s var(--ease-faster), box-shadow .5s var(--ease-faster), scale var(--spring-dur) var(--spring);
}
.art__fig.is-in, .art__q.is-in, .art__share.is-in, .art__next.is-in { opacity: 1; transform: none; }

/* -------------------------------------------------------------- index ui */

.index-ui { position: absolute; inset: 0; z-index: 10; pointer-events: none; color: var(--index-fg); }

.card-hit { position: absolute; left: 0; top: 0; }
.is-index .card-hit { pointer-events: auto; }
.card-hit:focus-visible { outline: 1px solid var(--index-fg); outline-offset: 8px; }

/* ------------------------------------------------------------------- intro */

.is-loading .mark { clip-path: inset(0 50% 0 50%); opacity: 0; filter: blur(8px); }
.is-loading .theme-toggle { opacity: 0; }
.is-loading .side .ch__a { transform: translateY(105%); }
.is-loading .w { opacity: 0; filter: blur(14px); transform: translateY(.42em) rotateX(-55deg); }

.is-intro .side .ch__a { transition: transform 1.5s var(--ease-fast) calc(.6s + var(--i) * 32ms); }
.is-intro .w {
  transition:
    opacity 1.5s var(--ease-fast) calc(1.15s + var(--i) * 75ms),
    filter 1.9s var(--ease-fast) calc(1.15s + var(--i) * 75ms),
    transform 2s var(--ease-slow) calc(.95s + var(--i) * 75ms);
}

/* services: lines rise out of their masks, the rest settles in */
.mask { display: block; overflow: hidden; } /* one line box tall, so the rhythm stays exact */
.svc__bpw .mask { display: inline-block; }
.rv { display: inline-block; transition: transform 1.7s var(--ease-fast) calc(.4s + var(--d) * 90ms); }
.rv-fade { transition: opacity 1.4s var(--ease-fast) calc(.4s + var(--d) * 90ms), transform 1.7s var(--ease-fast) calc(.4s + var(--d) * 90ms); }
.is-loading .rv { transform: translateY(112%); }
.is-loading .rv-fade { opacity: 0; transform: translateY(16px); }
.is-loading .svc__arrow { stroke-dashoffset: 100; }

/* ------------------------------------------------------------------ mobile */

@media (max-width: 720px), (max-aspect-ratio: 4/5) {
  :root {
    --edge-left: 20px;
    --edge-right: 20px;
    --plate: min(82vw, 46svh);
    --plate-y: 44svh;
    --label: 11px;
    --headline: clamp(26px, 7.4vw, 40px);
    --logo-mid: calc(var(--logo-top) + 17px);
  }
  .side { top: var(--logo-mid); }
  .side--right { right: calc(var(--edge-right) + 30px); }
  .headline { top: auto; bottom: max(8svh, 40px); translate: -50% 0; white-space: normal; width: 92vw; }
  .headline__line { white-space: nowrap; }
  .reel__p:not(.reel__p--home) { white-space: normal; width: max-content; max-width: 92vw; } /* long statements wrap on a phone */

  /* essay pages scroll natively as one column */
  .essay {
    display: flex;
    flex-direction: column;
    gap: 40px;
    padding: calc(var(--logo-top) + 96px) 20px 64px;
    overflow-y: auto;
    -webkit-overflow-scrolling: touch;
    overscroll-behavior: contain;
    /* text fades out before it reaches the logo and the labels */
    -webkit-mask-image: linear-gradient(to bottom, transparent calc(var(--logo-top) + 40px), #000 calc(var(--logo-top) + 84px));
    mask-image: linear-gradient(to bottom, transparent calc(var(--logo-top) + 40px), #000 calc(var(--logo-top) + 84px));
  }
  .essay__board, .essay__scroller { position: static; width: auto; height: auto; transform: none; -webkit-mask-image: none; mask-image: none; overflow: visible; }
  .essay__board { display: contents; }
  .essay__scroller { order: 1; }
  .essay__track { position: static; width: auto; padding: 0; will-change: auto; }

  /* services: the contact block closes the essay */
  .svc__bpw { position: static; translate: none; font-size: 48px; gap: 26px; order: 0; }
  .svc__arrow { width: 36px; height: 14px; }
  .svc__headline { font-size: 30px; line-height: 1.3; margin-bottom: 28px; }
  .svc__body { font-size: 17px; line-height: 1.5; }
  .svc__body p { margin-bottom: 1em; }
  .svc__closing { margin-top: 44px; }
  .svc__label, .svc .essay__track .svc__label { font-size: 13px; line-height: 13px; }
  .svc .essay__track .svc__label { margin-top: 32px; }
  .svc__chips { display: flex; flex-wrap: wrap; gap: 8px; margin-top: 18px; }
  .chip { padding: 7px 11px; border-radius: 7px; font-size: 11px; line-height: 8px; }
  .svc__contact { order: 2; position: relative; left: auto; top: auto; width: auto; padding: 24px 0 60px; }
  .svc__cta-wrap { position: relative; top: auto; margin-top: 28px; }

  /* work: two columns that scroll natively; a project is one column, and its
     panel comes up from the bottom */
  .work__track { padding: calc(var(--logo-top) + 92px) 0 60px; }
  .work__title { margin-bottom: 26px; font-size: 13px; line-height: 13px; }
  .proj__back, .proj__id, .proj__about { top: calc(var(--logo-top) + 64px); font-size: 12px; line-height: 16px; }
  .proj__back { left: 20px; }
  .proj__id { left: 96px; }
  .proj__about { left: auto; right: 20px; top: calc(var(--logo-top) + 80px); translate: none; }
  .view--work.is-docked .mark { translate: -50% 0; }
  .view--work.is-docked .proj__back { left: 20px; }
  .view--work.is-docked .proj__id { left: 96px; top: calc(var(--logo-top) + 64px); max-width: none; }
  .view--work.is-docked .proj__about { left: auto; top: calc(var(--logo-top) + 80px); translate: none; }
  .proj__bar { transition: opacity .5s var(--ease-faster), translate .6s var(--ease-faster); }
  .view--work.is-docked .proj__bar { opacity: 0; translate: 0 -10px; pointer-events: none; }
  .proj__scroller { -webkit-mask-image: linear-gradient(to bottom, transparent calc(var(--logo-top) + 100px), #000 calc(var(--logo-top) + 124px)); mask-image: linear-gradient(to bottom, transparent calc(var(--logo-top) + 100px), #000 calc(var(--logo-top) + 124px)); }
  .proj__track { padding: calc(var(--logo-top) + 126px) 20px 60px; }
  .proj__col, .proj__col.is-narrow { width: auto; margin: 0; gap: 12px; }
  .blk { gap: 8px; }
  .m { border-radius: 10px; }
  .proj__info { left: 12px; right: 12px; top: auto; bottom: 12px; width: auto; max-height: 72svh; padding: 22px; border-radius: 14px; }
  .proj__text p { font-size: 14px; }

  /* writing: one column; the breadcrumb keeps just where you are */
  .wr__crumb { left: 20px; font-size: 11px; }
  .wr__crumb > a:first-child, .wr__crumb-sep { display: none; }
  .wr__track { padding: calc(var(--logo-top) + 92px) 20px 60px; }
  .wr__filters { gap: 0 16px; margin-bottom: 26px; font-size: 13px; line-height: 22px; }
  .card__cap, .art__next { font-size: 13px; }
  .art__track { padding: calc(var(--logo-top) + 92px) 0 60px; }
  .art__grid { grid-template-columns: 1fr; row-gap: 28px; margin: 0 20px; }
  .art__cover { width: 56%; margin-top: 18px; }
  .art__title { font-size: 30px; line-height: 1.25; }
  .art__body { margin-top: 26px; }
  .art__p { font-size: 16px; line-height: 1.75; margin-bottom: 20px; }
  .art__fig { margin: 30px 0; width: auto; height: auto; aspect-ratio: 16 / 9; }
  .art__q { width: auto; margin: 30px 0; padding: 20px; }
  .art__share { height: 32px; gap: 6px; margin-top: 24px; padding: 0 13px 0 11px; font-size: 12px; line-height: 32px; }
  .art__share-labels, .art__share-l { height: 32px; }
  .art__share-icon { width: 13px; height: 13px; }
  .art__next { position: relative; left: auto; bottom: auto; display: block; width: 60%; margin: 60px 20px 0; }
  .art .wr__foot { margin-left: 20px; }

  /* about: who, the essay, then the logo to close */
  .about__id { position: relative; left: auto; top: auto; order: 0; display: flex; flex-direction: column; gap: 18px; }
  .about__portrait { position: static; width: 132px; height: 132px; border-radius: 14px; }
  .about__role { position: static; font-size: 17px; line-height: 1.3; white-space: normal; }
  .about__head { font-size: 30px; line-height: 1.3; }
  .about__head .para { white-space: normal; }
  .about__head .ln { width: auto; }
  .about__body { max-width: none; font-size: 17px; line-height: 1.5; }
  .about__body p { margin-bottom: 1em; }
  .about__head + .about__body { margin-top: 20px; }
  .about__body + .about__head { margin-top: 48px; }
  .about__logo { order: 2; position: relative; left: auto; top: auto; width: auto; height: auto; aspect-ratio: 3 / 2; margin: 0 -20px; }
}

/* on touch the work page scrolls natively */
@media (hover: none), (pointer: coarse) {
  .work__scroller, .proj__scroller, .wr__scroller, .art__scroller { overflow-y: auto; -webkit-overflow-scrolling: touch; overscroll-behavior: contain; }
  .work__track, .proj__track, .wr__track, .art__track { position: relative; will-change: auto; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { transition-duration: .01s !important; transition-delay: 0s !important; }
}
