/* Coastline: quiet sea tones, open spacing, and drawn accents. */

@font-face{font-family:'Bricolage';src:url(fonts/bricolage.woff2) format('woff2');
  font-weight:400 800;font-stretch:75% 100%;font-display:swap;
  unicode-range:U+0000-00FF,U+2000-206F,U+2190-21FF,U+2200-22FF}
@font-face{font-family:'Newsreader';src:url(fonts/newsreader.woff2) format('woff2');
  font-weight:300 600;font-display:swap;
  unicode-range:U+0000-00FF,U+2000-206F,U+2190-21FF}
@font-face{font-family:'PlexMono';src:url(fonts/plexmono.woff2) format('woff2');
  font-weight:400;font-display:swap;
  unicode-range:U+0000-00FF,U+2000-206F,U+2190-21FF}

:root{
  color-scheme:light;

  /* --- surface ---------------------------------------------------------- */
  --paper:#dfeae7;
  --paper-lift:#edf4f1;
  --ink:#1f322e;
  --ink-2:#3d554d;
  --mute:#4b6058;
  --rule:#9db5b0;
  --rule-soft:#c3d6d2;

  /* --- measurement state ------------------------------------------------ */
  --trace:#1d6064;
  --flag:#9b3041;
  --trace-wash:#1d606410;
  --flag-wash:#9b304110;

  /* --- type ------------------------------------------------------------- */
  --display:'Newsreader',Georgia,'Times New Roman',serif;
  --body:'Newsreader',Georgia,'Times New Roman',serif;
  --data:'PlexMono',ui-monospace,SFMono-Regular,Menlo,monospace;

  /* fluid scale, 8pt-derived */
  --t-mega:clamp(2.8rem,6.5vw,5.7rem);
  --t-xl:clamp(2.1rem,4.6vw,4rem);
  --t-lg:clamp(1.6rem,2.6vw,2.4rem);
  --t-md:clamp(1.15rem,1.5vw,1.4rem);
  --t-body:1.125rem;
  --t-data:.8125rem;
  --t-micro:.75rem;

  /* --- rhythm (intentionally uneven per section, see each block) --------- */
  --gut:clamp(1.25rem,5vw,4rem);
  --measure:64ch;
  --tap:44px;          /* minimum comfortable touch target */
  --head:53px;         /* masthead height; JS re-syncs it after font load */
  --ease:cubic-bezier(.22,.61,.36,1);
}

[data-theme="scope"]{
  color-scheme:dark;
  --paper:#0f1e20;
  --paper-lift:#172b2d;
  --ink:#e0eae4;
  --ink-2:#bacfc4;
  --mute:#9cb8aa;
  --rule:#607e71;
  --rule-soft:#304b41;
  --trace:#81cfc3;
  --flag:#f0a4ae;
  --trace-wash:#81cfc310;
  --flag-wash:#f0a4ae10;
}
@media (prefers-color-scheme:dark){
  :root:not([data-theme="bench"]){
    color-scheme:dark;
    --paper:#0f1e20;--paper-lift:#172b2d;
    --ink:#e0eae4;--ink-2:#bacfc4;--mute:#9cb8aa;
    --rule:#607e71;--rule-soft:#304b41;
    --trace:#81cfc3;--flag:#f0a4ae;
    --trace-wash:#81cfc310;--flag-wash:#f0a4ae10;
  }
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;scroll-behavior:smooth}
body{
  margin:0;background:var(--paper);color:var(--ink);
  font-family:var(--body);font-size:var(--t-body);line-height:1.6;
  font-variation-settings:'opsz' 16;
  -webkit-font-smoothing:antialiased;
  overflow-wrap:break-word;
}
svg{display:block;max-width:100%}
a{color:inherit}
h1,h2,h3{margin:0;font-family:var(--display);font-weight:600;line-height:1.02;
  letter-spacing:-.025em;font-variation-settings:'wdth' 90}
p,figure,dl,dd{margin:0}
:focus-visible{outline:2px solid var(--trace);outline-offset:3px;border-radius:2px}
::selection{background:var(--ink);color:var(--paper)}

.shell{max-width:1200px;margin-inline:auto;padding-inline:var(--gut)}
.skip{position:absolute;left:-9999px;top:0;background:var(--ink);color:var(--paper);
  padding:.75rem 1rem;font-family:var(--data);font-size:var(--t-data);z-index:99}
.skip:focus{left:.5rem;top:.5rem}

/* --- utility label. lowercase on purpose: all-caps eyebrows are a tell --- */
.tag{font-family:var(--data);font-size:var(--t-micro);letter-spacing:.06em;
  color:var(--mute);display:flex;flex-wrap:wrap;align-items:baseline;gap:.2rem .6rem;line-height:1.5}
.tag b{color:var(--ink);font-weight:400}
.num{font-family:var(--data);font-variant-numeric:tabular-nums}

/* ============================ masthead =================================== */
.masthead{position:sticky;top:0;z-index:40;background:var(--sand);
  border-bottom:1px solid var(--rule-soft)}
.masthead .shell{display:flex;align-items:center;justify-content:space-between;
  gap:1rem;height:52px;font-family:var(--data);font-size:var(--t-data)}
.masthead nav{min-width:0}
.masthead nav ul{display:flex;flex-wrap:wrap;gap:.4rem 1.25rem;list-style:none;margin:0;padding:0}
/* With JavaScript a phone gets one header row and a Menu button (640px block).
   Without it the nav takes its own row under the name; if a narrow screen
   still clips it, scroll the nav instead of the page. */
@media (max-width:560px){
  .masthead nav{overflow-x:auto;scrollbar-width:none}
  .masthead nav::-webkit-scrollbar{display:none}
  .masthead nav ul{flex-wrap:nowrap}
}
.masthead nav a{text-decoration:none;color:var(--ink-2);white-space:nowrap;
  display:flex;align-items:center;min-height:var(--tap);padding:0 .1rem;border-bottom:1px solid transparent;transition:color .18s var(--ease),border-color .18s var(--ease)}
.masthead nav a:hover,.masthead nav a:focus-visible{color:var(--ink);border-bottom-color:var(--trace)}
.masthead nav a[aria-current]{color:var(--ink);border-bottom-color:var(--ink)}
.masthead nav{margin-left:auto}
.mark{font-family:var(--display);font-weight:700;letter-spacing:-.03em;font-size:1.25rem;font-style:italic;white-space:nowrap;
  text-decoration:none;font-variation-settings:'wdth' 78;
  display:inline-flex;align-items:center;min-height:var(--tap);padding-right:.5rem}
.themer{display:none;font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  background:none;border:0;padding:.55rem 0 .55rem .1rem;min-height:var(--tap);cursor:pointer;
  gap:.5rem;transition:color .18s var(--ease)}
.js .themer{display:inline-flex;align-items:center}
/* drawn icons, not font glyphs: they inherit the text colour, so both themes
   and forced-colours modes recolour them */
.icon{width:12px;height:12px;flex:none}
.themer .icon{transition:transform .18s var(--ease),color .18s var(--ease)}
.themer[aria-pressed="true"] .icon{color:var(--trace);transform:rotate(180deg)}
.themer:hover{color:var(--ink)}
.ext{display:inline-block;width:.72em;height:.72em;vertical-align:baseline}
.menu-toggle{display:none}
.menu-toggle .x{display:none}
.menu-toggle[aria-expanded="true"] .bars{display:none}
.menu-toggle[aria-expanded="true"] .x{display:inline}

/* ============================ hero ======================================= */
/* Shape: oversized display type, then the role and the ways to reach me. */
.hero{padding-top:clamp(2rem,6vh,4.5rem);border-bottom:1px solid var(--rule)}
.hero h1{font-size:var(--t-mega);max-width:15ch;font-weight:700;
  font-variation-settings:'wdth' 84;letter-spacing:-.038em;text-wrap:balance}
.hero-role{margin-top:1.35rem;max-width:26ch;font-family:var(--display);font-weight:600;
  font-size:clamp(1.6rem,3.2vw,2.75rem);line-height:1.15;letter-spacing:-.025em;
  font-variation-settings:'wdth' 86}
.hero-role b{font-weight:600;color:var(--trace)}
.hero-lead{margin-top:1rem;max-width:44ch;font-size:var(--t-md);color:var(--ink-2);
  font-variation-settings:'opsz' 24}


.hero-strip{margin-top:2.25rem;display:flex;flex-wrap:wrap;
  gap:.5rem 2.5rem;font-family:var(--data);font-size:var(--t-data);color:var(--mute)}
.hero-strip b{color:var(--ink);font-weight:400}
.hero-links{margin-top:1.1rem;display:flex;flex-wrap:wrap;gap:.15rem 1.75rem;font-family:var(--data);font-size:var(--t-data)}
.hero-links a{color:var(--ink);text-decoration:none;border-bottom:1px solid var(--rule);
  padding:.6rem 0 .25rem;min-height:var(--tap);display:inline-flex;align-items:center;transition:border-color .18s var(--ease),color .18s var(--ease)}
.hero-links a:hover,.hero-links a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}


/* --- activity wire (Projects & Fun): a chart-recorder band from the events API */
.wire{display:block;grid-column:1/-1;min-width:0;margin-top:1rem;
  border-top:1px solid var(--rule-soft);padding-top:.8rem}
.wire-source,.wire-details{font-family:var(--data);font-size:var(--t-micro);margin-top:.7rem}
.wire-details summary{cursor:pointer;padding:.65rem 0;width:fit-content}
.wire-table{max-height:20rem;overflow:auto;margin-top:.5rem}
.wire table{width:100%;border-collapse:collapse;text-align:left}
.wire caption{text-align:left;padding:.5rem 0;color:var(--mute)}
.wire th,.wire td{padding:.55rem .7rem;border-bottom:1px solid var(--rule-soft);vertical-align:top}
.wire th{font-weight:400}
.wire tbody th{white-space:nowrap}
.wire td:last-child{overflow-wrap:anywhere}
.wire figcaption{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  letter-spacing:.02em;line-height:1.6;display:flex;flex-wrap:wrap;gap:.2rem 1.5rem;
  justify-content:space-between}
.wire figcaption b{color:var(--ink);font-weight:400}
.wire .wire-meta{color:var(--mute)}
.wire .wire-meta b{color:var(--trace)}
.wire svg{width:100%;height:132px;margin-top:.4rem;cursor:crosshair;touch-action:pan-y}
.wire svg[hidden]{display:none}
.wire .scrubline{stroke:var(--mute);stroke-width:1;stroke-dasharray:1 3}
.wire .scrubdot{fill:var(--flag)}
.wire .scrubtext{fill:var(--ink);font-size:10.5px}
.wire .scrub{transition:opacity .2s linear}
.wire .needle{transition:transform .16s var(--ease)}
@media (prefers-reduced-motion:reduce){.wire .needle{transition:none}}
.wire .pen{stroke:var(--trace);fill:none;stroke-width:1.6;stroke-linejoin:round;
  stroke-linecap:round}
.wire .base{stroke:var(--rule);stroke-width:1}
.wire .daytick{stroke:var(--rule);stroke-width:1;stroke-dasharray:2 4}
.wire .nib{fill:var(--trace)}
.wire text{font-family:var(--data);font-size:10px;fill:var(--mute)}
@media (max-width:640px){.wire text{font-size:11px}.wire .scrubtext{font-size:11.5px}}
@media (prefers-reduced-motion:no-preference){
  .js .wire .nib{animation:nib 1.6s steps(2,start) infinite}
}
@keyframes nib{50%{opacity:.25}}

/* ============================ section frame ============================== */
/* Deliberately different vertical rhythm per shelf. Uniform section padding
   is a named signature of generated pages. */
.shelf{border-bottom:1px solid var(--rule);padding-bottom:4rem}
.shelf-head{display:flex;flex-wrap:wrap;align-items:baseline;gap:.75rem 1.5rem;
  padding-block:2.25rem 1rem}
/* four sections sit the deck under the heading; tools and about keep it
   right-aligned, so the header band is not one repeated formula six times */
.shelf-head.wide{display:block}
.shelf-head.wide .said{margin:.6rem 0 0;text-align:left;
  max-width:56ch;font-family:var(--body);font-size:1.05rem;color:var(--ink-2)}
.shelf-head h2{font-size:var(--t-xl);font-weight:700;font-variation-settings:'wdth' 80}
/* the shelves are not equal, so they do not announce themselves equally */
#measured .shelf-head h2{font-size:clamp(2.4rem,5.4vw,4.75rem)}
#friends .shelf-head h2,#tools .shelf-head h2,#about .shelf-head h2{
  font-size:clamp(1.7rem,3vw,2.6rem)}
.shelf-head .said{font-family:var(--data);font-size:var(--t-data);color:var(--mute);
  max-width:52ch;margin-left:auto;text-align:right}
@media (max-width:820px){
  .shelf-head .said,.shelf-head.wide .said{font-family:var(--body);font-size:1rem;color:var(--ink-2)}
.shelf-head .said{margin-left:0;text-align:left}}

/* ---------- 01 measured: asymmetric case studies with real plots --------- */
#measured{padding-bottom:5rem}
.cases{list-style:none;margin:0;padding:0}
.case{padding-block:clamp(2.5rem,6vh,4rem);border-top:1px solid var(--rule-soft);
  display:grid;grid-template-columns:minmax(0,1.15fr) minmax(0,.85fr);
  gap:clamp(1.5rem,4vw,4rem);align-items:start}
.cases > li:first-child .case{border-top:0}
.case.solo{grid-template-columns:minmax(0,1.1fr) minmax(0,.9fr)}
.case.solo .aside{grid-column:2;grid-row:1}
.case.solo .case-what{max-width:var(--measure)}
@media (max-width:980px){
  .case.solo{grid-template-columns:minmax(0,1fr)}
  .case.solo .aside{grid-column:1;grid-row:2}
}
.case-title{display:flex;flex-wrap:wrap;align-items:baseline;gap:.5rem 1rem}
.case-title h3{font-size:var(--t-lg);font-weight:700}
.case-title a{color:inherit;text-decoration:none;border-bottom:2px solid var(--trace);
  transition:color .45s var(--ease)}
.case-title a:hover,.case-title a:focus-visible{color:var(--trace)}
.case-what{margin-top:1rem;max-width:var(--measure);color:var(--ink-2)}
.case-what + .case-what{margin-top:.85rem}
.case-what strong{font-weight:600;color:var(--ink)}

.readout{margin-top:1.5rem;display:grid;grid-template-columns:repeat(auto-fit,minmax(118px,1fr));
  gap:1px;background:var(--rule);border:1px solid var(--rule)}
.readout div{background:var(--paper);padding:.7rem .8rem;display:flex;flex-direction:column}
@media (max-width:560px){
  /* stack as label/value rows so a short final row cannot leave an empty cell */
  .readout{grid-template-columns:1fr}
  .readout div{display:grid;grid-template-columns:1fr auto;align-items:baseline;gap:.75rem}
  .readout dt{min-height:0}
  .readout dd{margin-top:0;text-align:right}
}

.readout dt{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);margin:0;
  min-height:2.1em;padding-bottom:.15rem}
.readout .u{font-size:.6em}
.readout dd{margin:auto 0 0;font-family:var(--display);font-size:1.4rem;font-weight:600;
  letter-spacing:-.02em;font-variant-numeric:tabular-nums}

/* the honest miss. its own visual state, not a footnote. */
.miss{margin-top:1.5rem;border-left:3px solid var(--flag);background:var(--flag-wash);
  padding:.9rem 1.1rem}
.miss .tag b{color:var(--flag)}
.miss p{margin-top:.5rem;color:var(--ink-2);max-width:60ch}

.plot{position:sticky;top:calc(var(--head) + 14px);border:1px solid var(--rule);
  background:var(--paper-lift);padding:1rem 1.1rem 1.1rem;grid-column:2}
.case > div{grid-column:1;grid-row:1}
.plot figcaption{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  line-height:1.5;margin-bottom:.9rem}
.plot figcaption b{color:var(--ink);font-weight:400}
.plot > svg{width:100%;height:auto;overflow:visible;max-width:520px}
.src{margin-top:1.1rem;font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  line-height:1.9}
.plot .src{margin-top:.85rem;line-height:2}
.src a{color:var(--ink-2)}
.src a:hover,.src a:focus-visible,
.essay p a:hover,.essay p a:focus-visible{color:var(--trace)}
.go,.h{white-space:nowrap}
.gridline{stroke:var(--rule);stroke-width:1;vector-effect:non-scaling-stroke}
.barok{fill:var(--trace)}
.barbad{fill:var(--flag)}
.plotlabel{font-family:var(--data);font-size:7px;fill:var(--mute)}
.plotbar-label{font-family:var(--data);font-size:7.5px;fill:var(--ink)}

/* ---------- 02 shipped: a ledger. rows, not cards. ---------------------- */
.ledger{border-top:1px solid var(--rule);list-style:none;margin:0;padding:0}
.row{display:grid;grid-template-columns:8.5rem minmax(0,1fr);gap:.4rem 2rem;
  padding-block:1.5rem;border-bottom:1px solid var(--rule-soft);
  transition:background .12s linear}
.ledger > li:hover .row{background:var(--trace-wash)}
@media (min-width:1100px){
  .row{grid-template-columns:7.5rem minmax(0,1fr) 11rem;gap:.4rem 1.75rem}
  .row .built{grid-column:3;grid-row:1;margin-top:.4rem}
}
.row > .when{font-family:var(--data);font-size:var(--t-data);color:var(--mute);padding-top:.2rem}
.row h3{font-size:1.35rem;font-weight:600}
.row h3 a{color:inherit;text-decoration:none;border-bottom:1px solid var(--rule);
  transition:border-color .18s var(--ease),color .18s var(--ease)}
.row h3 a:hover,.row h3 a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}
.row p{margin-top:.55rem;color:var(--ink-2);max-width:var(--measure)}
.row .built{margin-top:.7rem;font-family:var(--data);font-size:var(--t-micro);color:var(--mute)}

/* ---------- 03 books: narrow prose. widest margins on the page. --------- */
#books{padding-bottom:4.5rem}
.essay{max-width:62ch;padding-top:1rem}
.essay p{margin-top:1.15rem;font-size:1.15rem;line-height:1.65;font-variation-settings:'opsz' 22}
.essay p:first-child{margin-top:0;font-size:1.3rem;line-height:1.5}
#books .three{margin-top:2.25rem;display:grid;gap:1px;background:var(--rule);list-style:none;padding:0;
  border:1px solid var(--rule)}
#books .three > li{background:var(--paper);padding:.9rem 1rem;
  display:grid;grid-template-columns:1fr auto;grid-template-rows:auto auto;gap:.3rem 1rem;align-items:baseline;
  transition:background .22s var(--ease)}
#books .three > li:hover{background:var(--paper-lift)}
#books .three a{text-decoration:none;color:inherit}
.essay p a{transition:color .26s var(--ease)}
/* the books essay runs beside its screenshot, same two-column read as a case. */
.essay-wrap{display:grid;grid-template-columns:minmax(0,1.15fr) minmax(0,.85fr);
  gap:clamp(1.5rem,4vw,4rem);align-items:start}
.essay-wrap .essay{grid-column:1}
.shot{grid-column:2;position:sticky;top:calc(var(--head) + 14px);margin-top:1rem;
  border:1px solid var(--rule);background:var(--paper-lift);padding:1rem 1.1rem 1.1rem}
.shot figcaption{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  line-height:1.5;margin-bottom:.9rem}
.shot figcaption b{color:var(--ink);font-weight:400}
.shot img{display:block;width:100%;max-width:260px;height:auto;margin-inline:auto;
  border:1px solid var(--rule-soft);border-radius:14px}
.shot .src{margin-top:.85rem;line-height:2}
@media (max-width:900px){
  .essay-wrap{grid-template-columns:minmax(0,1fr)}
  .essay-wrap .essay,.shot{grid-column:1}
  .shot{position:static;margin-top:2rem}
}
#books .three h3 a{transition:color .22s var(--ease)}
#books .three h3 a:hover,#books .three h3 a:focus-visible{color:var(--trace)}
#books .three h3 a,.strip h3 a,.row h3 a{display:inline-block;padding-block:.6rem .4rem}
#books .three .n{font-family:var(--display);font-weight:600;font-size:1.05rem;margin:0;
  letter-spacing:-.015em;transition:color .22s var(--ease)}
#books .three .d{grid-column:1/-1;font-family:var(--data);font-size:var(--t-micro);color:var(--mute);line-height:1.6}
@media (min-width:900px){
  /* the three artefacts run the full measure under the narrative, so the
     section reads as essay-then-evidence and leaves no dead column */
  #books .three{grid-template-columns:repeat(3,minmax(0,1fr))}
}
#books .three .go{font-family:var(--data);font-size:var(--t-micro);color:var(--trace)}

/* ---------- 04 friends: a directory listing. one line each. ------------- */
.dir{border-top:1px solid var(--rule);font-family:var(--data);font-size:var(--t-data);
  list-style:none;margin:0;padding:0}
.dir a{display:grid;grid-template-columns:1.5rem 11.5rem minmax(0,1fr) auto;
  gap:.9rem;align-items:baseline;padding:.8rem .25rem;min-height:var(--tap);text-decoration:none;
  border-bottom:1px solid var(--rule-soft);transition:background .09s linear,padding-left .34s var(--ease)}
.dir a:hover,.dir a:focus-visible{background:var(--trace-wash);padding-left:.75rem}
.dir .i{color:var(--mute);font-variant-numeric:tabular-nums}
.dir .n{color:var(--ink);font-family:var(--display);font-weight:600;font-size:.95rem;
  letter-spacing:-.01em;margin:0;line-height:1.3}
.dir .d{color:var(--mute);line-height:1.5}
.dir .h{color:var(--trace)}
@media (max-width:720px){
  .dir a{grid-template-columns:1.5rem minmax(0,1fr) auto;gap:.25rem .8rem}
  .dir .n{grid-column:2;grid-row:1}
  /* .d spans the full width on row 2, so .h must be placed or it wraps to a
     third row and hangs off the left edge */
  .dir .h{grid-column:3;grid-row:1}
  .dir .d{grid-column:2/-1;grid-row:2}
}

/* ---------- 05 tools: compact strip ------------------------------------- */
.strip{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));
  gap:1px;background:var(--rule);border:1px solid var(--rule);list-style:none;margin:0;padding:0}
.strip > li{display:flex}
@media (max-width:560px){.strip{grid-template-columns:minmax(0,1fr)}}
@media (min-width:1150px){.strip{grid-template-columns:repeat(4,minmax(0,1fr))}}
/* upstream mixes one long-form entry with short ones: never stretch it to four */
@media (min-width:1150px){#upstream .strip{grid-template-columns:repeat(2,minmax(0,1fr))}}
/* five entries in two columns would otherwise leave a lit empty cell */
@media (min-width:561px){#upstream .strip > li:last-child:nth-child(odd){grid-column:1/-1}}
.strip article{background:var(--paper);padding:1.1rem 1.15rem;display:flex;flex-direction:column;gap:.5rem;flex:1;
  transition:background .12s linear;position:relative}
.strip li:hover article{background:var(--paper-lift)}
.strip h3{font-size:1.05rem;font-weight:600}
.strip h3 a{color:inherit;text-decoration:none;border-bottom:1px solid var(--rule);
  transition:border-color .18s var(--ease),color .18s var(--ease)}
/* the whole card is the target; the title stays the visible affordance */
.strip h3 a::after{content:"";position:absolute;inset:0}
.strip h3 a:hover,.strip h3 a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}
.strip p{font-size:.95rem;color:var(--ink-2)}
#tools .strip li:last-child{grid-column:1/-1}
.strip .why{margin-top:auto;font-family:var(--data);font-size:var(--t-micro);color:var(--mute)}

/* ---------- 06 about: colophon ------------------------------------------ */
.colophon{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(100%,270px),1fr));
  gap:2rem clamp(1.5rem,4vw,4rem);border-top:1px solid var(--rule);padding-top:1.75rem}
.colophon h3{font-family:var(--data);font-size:var(--t-micro);font-weight:400;color:var(--mute);
  letter-spacing:.06em;margin-bottom:.75rem}
.colophon p{color:var(--ink-2)}
.colophon p + p{margin-top:.7rem}
.colophon a{color:var(--ink);text-decoration:none;border-bottom:1px solid var(--rule);
  transition:border-color .26s var(--ease),color .26s var(--ease);
  display:inline-block;padding-block:.35rem .1rem}
.colophon a:hover,.colophon a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}
.colophon .big{font-family:var(--display);font-size:1.25rem;font-weight:600;letter-spacing:-.02em}

footer{padding-block:2rem 3rem;font-family:var(--data);font-size:var(--t-micro);color:var(--mute)}
footer .shell{display:flex;flex-wrap:wrap;gap:.5rem 2rem;justify-content:space-between}

/* Every page starts on the beach: dry sand with the sun on it, damp sand
   toward the water, and the coast drawing behind readable content. */
.hero,.page-head{position:relative;isolation:isolate;background:var(--sand)}
.hero::before,.page-head::before{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background:radial-gradient(ellipse 75% 85% at 0 0,var(--sand-lift),transparent 70%),
    linear-gradient(transparent 55%,var(--sand-wet))}
.hero::after,.page-head::after{content:"";position:absolute;right:0;top:0;
  width:min(70%,780px);height:260px;z-index:-1;background:var(--trace);opacity:.12;
  mask:url('/images/coastline.svg') right top / cover no-repeat;pointer-events:none}
.hero{padding-block:clamp(3rem,8vw,6rem) 3rem}
.hero h1{font-weight:400;line-height:1.04;letter-spacing:-.035em;max-width:17ch}
.hero-role{font-weight:400;font-size:clamp(1.35rem,2.6vw,2rem);line-height:1.3}
.hero-role b{font-weight:500}
.shelf{padding-block:clamp(3rem,7vw,5.5rem)}
.shelf-head h2,.page-head h1{font-weight:400;line-height:1.12}
.shelf-head{margin-bottom:2rem}
.shelf-head h2::after{content:"";display:block;width:3.5rem;height:.5rem;margin-top:.65rem;
  border-top:2px solid var(--trace);border-radius:50%;transform:rotate(-3deg)}
.said{line-height:1.7}
.shot,.plot,.screens figure{border-radius:8px 3px 9px 4px}
.picks,.strip{background:transparent;border:0;gap:clamp(1.5rem,4vw,3rem)}
.picks > li,.strip article{background:transparent;border-top:1px solid var(--rule);
  padding:1.5rem 0}
.picks h3{font-weight:400}
.picks h3 a,.strip h3 a,.row h3 a{border-bottom-width:1px;text-decoration-thickness:1px}
.row{padding-block:2rem}
.miss{border-radius:0 8px 8px 0}
.mark{font-weight:500}
.themer{color:var(--ink-2)}
.menu-toggle,.themer{border-radius:6px}
footer{border-top:1px solid var(--rule-soft);padding-block:2.5rem 3rem}
@media (max-width:640px){
  .hero::after,.page-head::after{width:100%;height:160px;opacity:.09}
  .hero{padding-block:2.75rem 2rem}
  .mark{font-size:1.2rem}
}

/* ============================ motion ===================================== */
@media (prefers-reduced-motion:reduce){
  *,*::before,*::after{animation-duration:.001ms!important;animation-iteration-count:1!important;
    transition-duration:.001ms!important;scroll-behavior:auto!important}
}
:target,.shelf,[id]{scroll-margin-top:calc(var(--head) + 22px)}

/* ============================ responsive ================================= */
@media (max-width:980px){
  .case{grid-template-columns:minmax(0,1fr);gap:1.75rem}
  .plot{position:static;grid-column:1;grid-row:2;width:100%}
  .plotlabel{font-size:9.5px}
  .plotbar-label{font-size:10px}
}
@media (max-width:640px){
  :root{--t-body:1rem}
  .row{grid-template-columns:1fr;gap:.15rem}
  .row > .when{padding-top:0}
  .hero-strip{gap:.35rem 1.5rem}
  .readout dd{font-size:1.2rem}
}
/* The six-link nav needs the phone header (one row: name, Menu, theme) up to 860px. */
@media (max-width:860px){
  .masthead .shell{height:auto;padding-block:.5rem;flex-wrap:wrap;gap:.5rem}
  .masthead nav{order:3;width:100%}
  .masthead nav{margin-left:0}
  .masthead nav ul{gap:1.3rem .4rem;font-size:.75rem;justify-content:space-between;flex-wrap:nowrap}
@media (max-width:360px){.masthead nav ul{flex-wrap:wrap;justify-content:flex-start;gap:0 .9rem}}
  .masthead nav a{padding:0 .28rem}
  .themer{padding:.62rem .8rem}
  .mark{padding-inline:.3rem .8rem}
  .js .masthead .shell{flex-wrap:wrap;height:auto;padding-block:6px;gap:0 .25rem}
  .js .mark{margin-right:auto}
  /* one header row: name, Menu, theme. The links open in a panel beneath. */
  .js .menu-toggle{display:inline-flex;align-items:center;gap:.5rem;order:2;min-height:var(--tap);
    padding:0 .8rem;font:inherit;color:var(--ink);background:none;border:1px solid var(--rule);
    border-radius:2px;cursor:pointer}
  .js #themer-label{position:absolute;width:1px;height:1px;overflow:hidden;clip-path:inset(50%);white-space:nowrap}
  .js .menu-toggle .icon,.js .themer .icon{width:16px;height:16px}
  .js .menu-toggle[aria-expanded="true"]{border-color:var(--ink)}
  .js .themer{order:3;width:var(--tap);height:var(--tap);padding:0;justify-content:center}
  .js .masthead nav{display:none;order:4;width:100%;overflow:visible}
  .js .masthead.nav-open nav{display:block}
  .js .masthead nav ul{flex-direction:column;flex-wrap:nowrap;gap:0;font-size:var(--t-data);
    padding:.25rem 0 .75rem;justify-content:flex-start}
  .js .masthead nav li+li{border-top:1px solid var(--rule-soft)}
  .js .masthead nav a{min-height:48px;padding:0 .3rem 0 .75rem;border-bottom:0;border-left:2px solid transparent}
  .js .masthead nav a:hover,.js .masthead nav a:focus-visible{border-left-color:var(--trace)}
  .js .masthead nav a[aria-current]{border-left-color:var(--ink)}
}
@media print{
  /* override the tokens, not body: descendants read tokens, so a dark-theme
     print was emitting dark panels and grey text onto white paper */
  /* must match the specificity of :root:not([data-theme="bench"]) in the
     prefers-color-scheme block, or a dark-theme print keeps the dark tokens */
  :root,:root:not([data-theme="bench"]),[data-theme="scope"]{
    --paper:#fff;--paper-lift:#fff;--ink:#000;--ink-2:#222;--mute:#444;
    --rule:#999;--rule-soft:#ccc;--trace:#000;--flag:#000;
    --trace-wash:transparent;--flag-wash:transparent;
    --sand:#fff;--sand-lift:#fff;--sand-wet:#fff;--deep:#fff;--deep-ink:#000;--deep-mute:#444;
  }
  .masthead{display:none}
  .row,.case,.strip li,.dir li{break-inside:avoid}
}

/* ============================ multi-page shell =========================== */
/* Everything below serves the split from one long page into Home, Work &
   Projects, project pages, Writing and About. Same tokens, same type. */

/* page header: a breadcrumb, the page title and its deck */
.page-head{padding-block:clamp(2rem,6vh,4rem) 2rem;border-bottom:1px solid var(--rule)}
.page-head h1{font-size:var(--t-xl);font-weight:700;font-variation-settings:'wdth' 80;
  letter-spacing:-.035em;max-width:22ch;text-wrap:balance}
.page-head .tag{margin-top:1rem}
.page-head .said{margin-top:1rem;max-width:56ch;font-size:1.05rem;color:var(--ink-2)}
.crumbs{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);margin-bottom:1.1rem}
.crumbs ol{list-style:none;margin:0;padding:0;display:flex;flex-wrap:wrap;gap:.2rem .5rem}
.crumbs li+li::before{content:"/";margin-right:.5rem;color:var(--rule)}
.crumbs a{color:var(--ink-2);display:inline-flex;align-items:center;min-height:var(--tap)}
.crumbs a:hover,.crumbs a:focus-visible{color:var(--trace)}
.crumbs [aria-current]{display:inline-flex;align-items:center;min-height:var(--tap)}

/* the "where it went" link at the foot of a summary on Home */
.more{margin-top:1.25rem;font-family:var(--data);font-size:var(--t-data)}
.more a{color:var(--ink);text-decoration:none;border-bottom:1px solid var(--trace);
  display:inline-flex;align-items:center;min-height:var(--tap);transition:color .18s var(--ease)}
.more a:hover,.more a:focus-visible{color:var(--trace)}

/* home: the selected projects, each a summary with a detail page behind it */
.picks{list-style:none;margin:0;padding:0;display:grid;gap:1px;background:var(--rule);
  border:1px solid var(--rule);grid-template-columns:minmax(0,1fr)}
@media (min-width:1000px){.picks{grid-template-columns:repeat(3,minmax(0,1fr))}}
.picks > li{background:var(--paper);padding:1.4rem 1.3rem 1.2rem;display:flex;flex-direction:column}
.picks h3{font-size:var(--t-md);font-weight:700}
.picks h3 a{color:inherit;text-decoration:none;border-bottom:2px solid var(--trace);
  display:inline-block;padding-block:.35rem .1rem;transition:color .18s var(--ease)}
.picks h3 a:hover,.picks h3 a:focus-visible{color:var(--trace)}
.picks .tag{margin-top:.6rem}
.picks p:not(.tag):not(.more):not(.src){margin-top:.8rem;color:var(--ink-2);font-size:1rem}
.picks .miss{margin-top:1rem}
.picks .miss p{font-size:.95rem}
.picks .src{margin-top:.8rem}
.picks .more{margin-top:auto;padding-top:1rem}
.picks img{display:block;width:100%;max-width:150px;height:auto;margin-top:1rem;
  border:1px solid var(--rule-soft);border-radius:10px}



/* project pages: the case runs at full width, with the figure beside it */
.project .case{border-top:0;padding-top:2rem}

/* work: real screenshots beside the friends directory */
.screens{display:grid;gap:1.5rem;margin-top:2rem;grid-template-columns:minmax(0,1fr)}
@media (min-width:860px){.screens{grid-template-columns:repeat(2,minmax(0,1fr))}}
.screens figure{border:1px solid var(--rule);background:var(--paper-lift);padding:1rem 1.1rem 1.1rem}
.screens img{display:block;width:100%;height:auto;border:1px solid var(--rule-soft);border-radius:6px}
.screens figcaption{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  line-height:1.6;margin-top:.8rem}
.screens figcaption b{color:var(--ink);font-weight:400}

/* writing: the honest empty state, and the article layout the editor uses */
.empty{padding-block:2.5rem 1rem;color:var(--ink-2);font-size:var(--t-md)}
.posts{list-style:none;margin:0;padding:0;border-top:1px solid var(--rule)}
.posts li{padding-block:1.2rem;border-bottom:1px solid var(--rule-soft)}
.posts h2{font-size:var(--t-md);font-weight:600}
.posts h2 a{color:inherit;text-decoration:none;border-bottom:1px solid var(--rule)}
.posts h2 a:hover,.posts h2 a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}
.posts p{margin-top:.4rem;color:var(--ink-2)}
.article{max-width:var(--measure);padding-block:2rem 3rem}
.article .meta{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);
  display:flex;flex-wrap:wrap;gap:.2rem 1.25rem}
.article p,.article ul,.article ol,.article blockquote{margin:1.15rem 0 0;font-size:1.15rem;
  line-height:1.65;font-variation-settings:'opsz' 22}
.article h2{font-size:var(--t-lg);margin-top:2.5rem}
.article h3{font-size:var(--t-md);margin-top:2rem}
.article a{color:var(--ink);text-decoration-color:var(--trace);text-underline-offset:.2em}
.article a:hover,.article a:focus-visible{color:var(--trace)}
.article figure{margin:2rem 0 0;border:1px solid var(--rule);background:var(--paper-lift);padding:1rem}
.article figure img{display:block;width:100%;height:auto}
.article figcaption{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);margin-top:.7rem;line-height:1.6}
.article blockquote{border-left:3px solid var(--trace);padding-left:1rem;color:var(--ink-2)}
.article .sources{margin-top:2.5rem;border-top:1px solid var(--rule);padding-top:1rem;
  font-family:var(--data);font-size:var(--t-data);color:var(--mute)}
.article .sources li{margin-top:.4rem}

/* 404 */
.lost ul{list-style:none;margin:1.5rem 0 0;padding:0;font-family:var(--data);font-size:var(--t-data)}
.lost li a{color:var(--ink);display:inline-flex;align-items:center;min-height:var(--tap)}
.readout dt small{display:block;margin-top:.2rem;font-size:.95em;color:var(--mute)}
.about-line{margin-top:1.4rem;max-width:26ch;font-family:var(--display);font-weight:600;
  font-size:clamp(1.6rem,3.2vw,2.75rem);line-height:1.15;letter-spacing:-.025em;font-variation-settings:'wdth' 86}
.page-head .hero-role{font-size:clamp(1.2rem,2vw,1.6rem)}
.page-head .hero-strip{margin-top:1.5rem}
.picks .readout,.strip .readout{margin-top:1rem}
.essay p.more{font-size:var(--t-data);line-height:1.6;margin-top:1.4rem;font-variation-settings:normal}
.page-head + .shelf > .shell > .colophon{border-top:0;padding-top:2.25rem}
.article .sources h2{font-size:var(--t-md);color:var(--ink);margin-top:0}
.article .sources ul{font-size:var(--t-data);line-height:1.6;padding-left:1.1rem;margin-top:.6rem}

/* ============================ tides ====================================== */
/* The site reads like walking from the beach out to sea. Every page starts on
   sand under the same coast drawing, meets the water at a line of surf, gets
   deeper toward the end and finishes in deep water. Section edges are drawn
   waves, not ruled lines. */
:root{
  --grot:'Bricolage','Helvetica Neue',Arial,sans-serif;
  --shallow:#d3e5e2;
  --shallow-2:#c6dcd9;
  --deep:#173a3d;
  --deep-ink:#e6efe9;
  --deep-mute:#b2cabf;
  --deep-trace:#94d8cc;
  --mark:#1d606426;
  /* the shore every page starts on: dry sand, damp sand, and the foam line */
  --sand:#ece5d5;
  --sand-lift:#f5f0e5;
  --sand-wet:#e0d8c5;
  --foam:#fbfaf4;
}
[data-theme="scope"]{
  --shallow:#12272a;--shallow-2:#152f32;
  --deep:#08171a;--deep-ink:#e0eae4;--deep-mute:#a6c0b4;--deep-trace:#81cfc3;
  --mark:#81cfc32e;
  --sand:#1c2320;--sand-lift:#252c28;--sand-wet:#171d1b;--foam:#cfe6de5c;
}
@media (prefers-color-scheme:dark){
  :root:not([data-theme="bench"]){
    --shallow:#12272a;--shallow-2:#152f32;
    --deep:#08171a;--deep-ink:#e0eae4;--deep-mute:#a6c0b4;--deep-trace:#81cfc3;
    --mark:#81cfc32e;
    --sand:#1c2320;--sand-lift:#252c28;--sand-wet:#171d1b;--foam:#cfe6de5c;
  }
}

/* waves replace the ruled section edges */
.shelf,.hero,.page-head{border-bottom:0;position:relative}
.shelf + .shelf::before{
  content:"";position:absolute;left:0;right:0;top:0;height:16px;background:var(--rule);
  mask:url('/images/wave-line.svg') center / 100% 100% no-repeat;pointer-events:none}
.page-head + .shell{position:relative;display:block}
.shelf:nth-of-type(even)::before{transform:scaleX(-1)}
/* a filled wave: the next band of water rises over the last one */
.tide,.contact,.home #writing{background:var(--band,var(--paper))}
.shelf.tide::before,.shelf.contact::before{content:"";position:absolute;left:0;right:0;top:-27px;height:28px;
  background:var(--band,var(--paper));mask:url('/images/wave-fill.svg') center / 100% 100% no-repeat;
  transform:none}

/* the surf: the first band of water washes up over the bottom of the sand,
   with a line of foam on its edge and the last wave's reach above it. The
   drawing tiles at its own width, so a phone sees gentle water, not chop. */
.hero + .shelf::before,.page-head + .shelf::before,.page-head + .shell::before,
.hero + .shelf::after,.page-head + .shelf::after,.page-head + .shell::after{content:"";position:absolute;
  left:0;right:0;top:-55px;height:56px;transform:none;opacity:1;pointer-events:none}
.hero + .shelf::before,.page-head + .shelf::before,.page-head + .shell::before{background:var(--band,var(--paper));
  mask:url('/images/surf.svg') 0 0 / 1440px 100% repeat-x}
.hero + .shelf::after,.page-head + .shelf::after,.page-head + .shell::after{z-index:1;background:var(--foam);
  mask:url('/images/surf-foam.svg') 0 0 / 1440px 100% repeat-x}

/* every page ends in the same deep water as Home */
footer{border-top:0;position:relative;background:var(--deep);color:var(--deep-mute)}
footer::before{content:"";position:absolute;left:0;right:0;top:-27px;height:28px;background:var(--deep);
  mask:url('/images/wave-fill.svg') center / 100% 100% no-repeat}

/* the drawn underline under section headings, kept from the last design */
.shelf-head h2::after{border-top-color:var(--trace)}

/* ---- arrival: content settles in once, never loops --------------------- */
@media (prefers-reduced-motion:no-preference){
  .hero .shell > *,.page-head .shell > *{animation:settle .7s var(--ease) both}
  .hero .shell > :nth-child(2),.page-head .shell > :nth-child(2){animation-delay:.06s}
  .hero .shell > :nth-child(3),.page-head .shell > :nth-child(3){animation-delay:.12s}
  .hero .shell > :nth-child(n+4),.page-head .shell > :nth-child(n+4){animation-delay:.18s}
  .hero::after,.page-head::after{animation:drift 1.6s var(--ease) both}
  @view-transition{navigation:auto}
  .masthead{view-transition-name:masthead}
  ::view-transition-old(root){animation:.18s ease-in both ebb}
  ::view-transition-new(root){animation:.42s var(--ease) both flow}
}
@keyframes settle{from{opacity:0;transform:translateY(10px)}}
@keyframes drift{from{opacity:0;translate:24px 0}}
@keyframes ebb{to{opacity:0}}
@keyframes flow{from{opacity:0;transform:translateY(8px)}}

/* ============================ home ======================================= */
/* Restrained: who I am, the work, the record, how to reach me. The bands
   deepen as the page goes on and it ends in deep water at Contact. */
.home .hero{padding-block:clamp(3.5rem,9vw,7rem) clamp(3.5rem,7vw,5.5rem)}
.home .hero h1{max-width:16ch}
.home .hero-role{max-width:32ch}
.home .hero-strip{margin-top:2.5rem}
.home #shipped{--band:var(--paper)}
.home #upstream{--band:var(--shallow)}
.home #about{--band:var(--shallow-2)}
.home #writing{--band:var(--shallow-2);padding-block:0 clamp(3rem,6vw,4.5rem)}
.home #about + #writing::before,.home #about + .shelf::before{content:none}

.works{list-style:none;margin:0;padding:0}
.work{display:grid;grid-template-columns:8.5rem minmax(0,1fr);gap:.4rem 2rem;padding-block:1.9rem;
  border-top:1px solid var(--rule-soft)}
.works > li:first-child .work{border-top:0;padding-top:.5rem}
@media (min-width:1100px){
  .work{grid-template-columns:8.5rem minmax(0,1fr) 12rem}
  .work .built{grid-column:3;grid-row:1;margin-top:.45rem}
}
.work .when{font-family:var(--data);font-size:var(--t-data);color:var(--mute);padding-top:.35rem}
.work h3{font-size:clamp(1.35rem,2vw,1.7rem);font-weight:500}
.work h3 a{text-decoration:none;color:inherit;background:linear-gradient(var(--trace),var(--trace)) 0 100% / 0 2px no-repeat;
  padding-bottom:.1rem;transition:background-size .45s var(--ease),color .2s var(--ease)}
.work h3 a:hover,.work h3 a:focus-visible{background-size:100% 2px;color:var(--trace)}
.work p{margin-top:.6rem;color:var(--ink-2);max-width:var(--measure)}
.work .built{font-family:var(--data);font-size:var(--t-micro);color:var(--mute)}
/* the result line wears a soft highlighter stroke, slightly off-level like a pen */
.result{color:var(--ink)!important;font-style:italic}
.result{text-decoration:underline;text-decoration-color:var(--mark);text-decoration-thickness:.42em;
  text-underline-offset:-.22em;text-decoration-skip-ink:none}
.work .result{margin-top:.7rem}
@media (max-width:640px){.work{grid-template-columns:1fr;gap:.2rem}.work .when{padding-top:0}}

.contrib{display:grid;gap:1rem clamp(2rem,6vw,6rem)}
@media (min-width:980px){.contrib{grid-template-columns:minmax(0,.8fr) minmax(0,1.2fr);align-items:start}
  .contrib .shelf-head{padding-top:0}}
.contrib-body h3{font-size:clamp(1.35rem,2vw,1.7rem);font-weight:500}
.contrib-body h3 a{color:inherit;text-decoration-color:var(--trace);text-underline-offset:.22em;text-decoration-thickness:1px}
.contrib-body h3 a:hover,.contrib-body h3 a:focus-visible{color:var(--trace)}
.contrib-body > p:not(.more){margin-top:.8rem;color:var(--ink-2);max-width:60ch}
.contrib .readout{max-width:34rem;background:var(--rule-soft);border-color:var(--rule-soft);border-radius:6px 2px 8px 3px;overflow:hidden}
.contrib .readout div{background:var(--band)}

.record{display:grid;gap:3rem clamp(2rem,6vw,6rem)}
@media (min-width:900px){.record{grid-template-columns:minmax(0,1.25fr) minmax(0,.75fr)}}
.record-head{font-family:var(--data);font-size:var(--t-micro);font-weight:400;color:var(--mute);
  letter-spacing:.06em;margin-bottom:1rem;font-variation-settings:normal}
/* the timeline rail is drawn, not ruled: a soft wavering line down the left */
.timeline{list-style:none;margin:0;padding:0 0 0 1.6rem;position:relative}
.timeline::before{content:"";position:absolute;left:.3rem;top:.6rem;bottom:.6rem;width:1.5px;
  border-radius:2px;background:linear-gradient(var(--trace),var(--rule) 30%,var(--rule) 85%,transparent)}
.timeline li{position:relative;padding-bottom:1.6rem}
.timeline li:last-child{padding-bottom:0}
.timeline li::before{content:"";position:absolute;left:-1.6rem;top:.45rem;width:.75rem;height:.75rem;
  border:1.5px solid var(--trace);border-radius:52% 48% 55% 45%;background:var(--band)}
.timeline li:first-child::before{background:var(--trace)}
.timeline .when{font-family:var(--data);font-size:var(--t-micro);color:var(--mute)}
.timeline .what{color:var(--ink-2);margin-top:.15rem;max-width:58ch}
.timeline .what b{display:block;font-weight:500;color:var(--ink);font-size:1.15rem;line-height:1.35;margin-bottom:.15rem}
.awards{list-style:none;margin:0;padding:0}
.awards li + li{margin-top:1.75rem;padding-top:1.5rem;border-top:1px solid var(--rule-soft)}
.awards .big{font-family:var(--display);font-size:1.3rem;font-weight:500;letter-spacing:-.02em;line-height:1.3}
.awards p{color:var(--ink-2)}
.awards p + p{margin-top:.5rem}
.awards a{color:var(--ink);text-decoration-color:var(--trace);text-underline-offset:.2em;
  display:inline-block;padding-block:.3rem .1rem}
.awards a:hover,.awards a:focus-visible{color:var(--trace)}

/* recent writing on Home stays a quiet single line beside the record */
.home #writing .shelf-head{padding-block:0 .25rem;margin-bottom:.75rem}
.home #writing .shelf-head h2{font-family:var(--data);font-size:var(--t-micro);font-weight:400;
  letter-spacing:.06em;color:var(--mute);font-variation-settings:normal}
.home #writing .shelf-head h2::after{content:none}
.home #writing .picks{background:transparent;border:0}
.home #writing .picks > li{border-top:1px solid var(--rule-soft);padding:1rem 0 0;background:transparent}
.home #writing .picks h3{font-size:1.2rem;font-weight:500}
.home #writing .picks h3 a{border-bottom-width:1px}
.home #writing .picks p:not(.tag){display:none}
.home #writing .more{margin-top:.5rem}

/* contact: the deep end of the page */
.contact{--band:var(--deep);color:var(--deep-ink);padding-block:clamp(4rem,9vw,7rem) clamp(3.5rem,7vw,5rem);overflow:hidden}
.contact::after{content:"";position:absolute;right:0;bottom:0;width:min(70%,760px);height:300px;
  background:var(--deep-trace);opacity:.1;transform:scaleY(-1);
  mask:url('/images/coastline.svg') right top / cover no-repeat;pointer-events:none}
.contact h2{font-family:var(--data);font-size:var(--t-micro);font-weight:400;letter-spacing:.06em;
  color:var(--deep-mute);font-variation-settings:normal}
.contact-mail{margin-top:1rem;font-family:var(--display);font-size:clamp(1.6rem,5.2vw,3.6rem);
  letter-spacing:-.03em;line-height:1.15}
.contact-mail a{color:var(--deep-ink);text-decoration:none;background:linear-gradient(var(--deep-trace),var(--deep-trace)) 0 100% / 100% 2px no-repeat;
  padding-bottom:.08em;overflow-wrap:anywhere;transition:color .2s var(--ease)}
.contact-mail a:hover,.contact-mail a:focus-visible{color:var(--deep-trace)}
.contact-links{list-style:none;margin:1.75rem 0 0;padding:0;display:flex;flex-wrap:wrap;gap:.25rem 2rem;
  font-family:var(--data);font-size:var(--t-data)}
.contact-links a{color:var(--deep-ink);display:inline-flex;align-items:center;gap:.35rem;min-height:var(--tap);
  text-decoration:underline;text-decoration-color:var(--deep-mute);text-underline-offset:.3em}
.contact-links a:hover,.contact-links a:focus-visible{color:var(--deep-trace);text-decoration-color:var(--deep-trace)}
.elsewhere{margin-top:3rem;max-width:60ch;color:var(--deep-mute);font-size:1rem}
.elsewhere a{color:var(--deep-ink);font-family:var(--data);font-size:var(--t-data);min-height:var(--tap);
  display:inline-flex;margin-right:1.25rem;align-items:center;text-decoration-color:var(--deep-mute);text-underline-offset:.3em}
.elsewhere a:hover,.elsewhere a:focus-visible{color:var(--deep-trace)}
.contact :focus-visible{outline-color:var(--deep-trace)}
.home + footer::before,.page-work + footer::before{top:0;height:16px;background:#ffffff1f;
  mask-image:url('/images/wave-line.svg')}

/* ============================ work ======================================= */
/* Professional and plain: the roles hang off one wavering rail in date
   order, and the page goes from shore to open water as the record goes back
   in time. */
.page-work #shipped{background:linear-gradient(var(--paper),var(--shallow))}
.page-work #leadership{--band:var(--shallow-2)}
.page-work #moved{--band:var(--deep);color:var(--deep-ink)}
.page-work #moved::before{transform:scaleX(-1)}
.page-work #moved .shelf-head h2{color:var(--deep-ink)}
.page-work #moved .shelf-head h2::after{border-top-color:var(--deep-trace)}
.page-work #moved .more a{color:var(--deep-ink);border-bottom-color:var(--deep-mute)}
.page-work #moved .more a:hover,.page-work #moved .more a:focus-visible{color:var(--deep-trace);border-bottom-color:var(--deep-trace)}
.page-work #moved :focus-visible{outline-color:var(--deep-trace)}
.page-work .ledger{border-top:0;position:relative}
@media (min-width:641px){
  .page-work .ledger::before{content:"";position:absolute;left:calc(6.6rem - 4px);top:1.9rem;bottom:1rem;width:10px;
    background:linear-gradient(var(--trace),var(--rule) 25%,var(--rule) 80%,transparent);
    mask:url('/images/rail.svg') center / 100% 100% no-repeat}
  .page-work .row > .when{position:relative}
  .page-work .row > .when::after{content:"";position:absolute;left:6.25rem;top:.45rem;width:.7rem;height:.7rem;
    border:1.5px solid var(--trace);border-radius:52% 48% 55% 45%;background:var(--band,var(--paper))}
  .page-work .row{grid-template-columns:8.5rem minmax(0,1fr)}
}
@media (min-width:1100px){.page-work .row{grid-template-columns:8.5rem minmax(0,1fr) 11rem}}
.page-work .row{border-bottom:0;background:linear-gradient(90deg,var(--trace-wash),transparent) 0 0 / 0 100% no-repeat;
  transition:background-size .5s var(--ease)}
.page-work .ledger > li:hover .row{background-color:transparent;background-size:100% 100%}
.page-work .row h3{font-weight:500;font-size:clamp(1.35rem,2vw,1.65rem)}
.page-work #moved .more{display:inline-block;margin-right:2rem}

/* ============================ projects & fun ============================= */
/* The playful side: a grotesque face for headings, pebble-shaped panels,
   bands that go in and out like a tide pool, and my public GitHub activity
   drawn as a tide chart at the top. */
.page-projects h1,.page-projects .shelf-head h2,.page-projects .strip h3,.page-projects .three .n,.page-projects .dir .n{
  font-family:var(--grot);font-stretch:88%;letter-spacing:-.02em}
.page-projects h1{font-weight:700;font-size:clamp(2.6rem,6vw,4.8rem);letter-spacing:-.045em}
.page-projects .shelf-head h2{font-weight:600}
.page-projects .page-head .said{font-size:var(--t-md)}
.page-projects .wire{margin-top:2.25rem;border-top:0;padding-top:0}
.page-projects .wire .pen{fill:var(--mark)}
.page-projects .wire svg{height:132px}
.page-projects #books{--band:var(--shallow)}
.page-projects #friends{--band:var(--paper)}
.page-projects #tools{--band:var(--shallow)}
.page-projects #upstream{--band:var(--shallow-2)}
.page-projects #friends::before,.page-projects #upstream::before{transform:scaleX(-1)}
.page-projects .strip{gap:1rem}
.page-projects .strip article,.page-case .three > li,.page-projects .three > li{
  background:var(--paper-lift);border:1px solid var(--rule-soft);border-radius:18px 6px 20px 8px;
  padding:1.25rem 1.3rem;transition:transform .3s var(--ease),border-color .3s var(--ease)}
.page-projects .strip article,.page-projects .three > li,.page-projects .screens figure{
  background:color-mix(in srgb,var(--paper-lift) 52%,transparent);
  border-color:color-mix(in srgb,var(--trace) 24%,transparent)}
.page-projects #tools .strip > li:nth-child(4n+1) article{background:color-mix(in srgb,var(--trace) 7%,transparent)}
.page-projects #tools .strip > li:nth-child(4n+3) article{background:color-mix(in srgb,#5f8fa6 9%,transparent)}
.page-projects .strip > li:nth-child(even) article,.page-projects .three > li:nth-child(even){border-radius:6px 20px 8px 18px}
.page-projects .strip li:hover article,.page-projects .three > li:hover{transform:translateY(-3px);border-color:var(--trace);
  background:var(--paper-lift)}
.page-projects .readout{border-radius:10px 3px 10px 3px;overflow:hidden}
.page-projects .readout div{background:var(--paper-lift)}
.page-projects .dir{border-top:0}
.page-projects .dir a{border-bottom:0;border-radius:10px;background:linear-gradient(90deg,var(--mark),transparent) 0 0 / 0 100% no-repeat;
  transition:background-size .45s var(--ease),padding-left .34s var(--ease)}
.page-projects .dir li + li a{box-shadow:0 -1px 0 var(--rule-soft)}
.page-projects .dir a:hover,.page-projects .dir a:focus-visible{background-size:100% 100%;background-color:transparent}
.page-projects .dir .n{font-size:1.05rem;font-weight:600}
.page-projects .screens figure{border-radius:18px 6px 20px 8px;border-color:var(--rule-soft)}

/* ============================ project pages ============================== */
.page-case .readout{border-radius:10px 3px 10px 3px;overflow:hidden}
.page-case .miss{border-radius:4px 18px 6px 16px;border-left-width:2px}
.page-case .plot,.page-case .shot{border-radius:18px 6px 20px 8px}
.case-audio .essay p:first-child{font-size:clamp(1.3rem,2vw,1.55rem);font-style:italic}
.case-audio .three,.page-projects .three{background:transparent;border:0;gap:1rem;position:relative}
.case-audio .three > li:nth-child(even),.page-projects #books .three > li:nth-child(even){border-radius:6px 20px 8px 18px}

/* ============================ writing ==================================== */
/* A reading list, set narrow and quiet. */
.page-writing .shell{max-width:56rem}
.page-writing .shelf-head{padding-top:0}
.page-writing .shelf-head h2{font-family:var(--data);font-size:var(--t-micro);font-weight:400;letter-spacing:.06em;
  color:var(--mute);font-variation-settings:normal}
.page-writing .shelf-head h2::after{content:none}
.page-writing .picks{background:transparent;border:0;gap:0}
.page-writing .picks > li{background:transparent;padding:1.75rem 0 2rem;border-top:1px solid var(--rule-soft);display:grid;
  grid-template-columns:minmax(0,1fr);gap:.2rem}
.page-writing .picks h3{font-size:clamp(1.6rem,3.4vw,2.4rem);font-weight:400;line-height:1.15;letter-spacing:-.025em;order:2}
.page-writing .picks h3 a{border-bottom:0;text-decoration:none;background:linear-gradient(var(--trace),var(--trace)) 0 100% / 0 1.5px no-repeat;
  transition:background-size .5s var(--ease),color .2s var(--ease)}
.page-writing .picks h3 a:hover,.page-writing .picks h3 a:focus-visible{background-size:100% 1.5px}
.page-writing .picks .tag{order:1;margin:0 0 .5rem}
.page-writing .picks p:not(.tag){order:3;font-style:italic;font-size:1.1rem!important;max-width:52ch;margin-top:.75rem}

/* ============================ article ==================================== */
/* The reading experience only: a calmer header, a wider line height, a
   measured column, and a thin waterline that fills as you read. */
main:has(> .shell > .article) .shell{max-width:50rem}
/* the article column is narrow, but its surf still runs the full width */
main:has(> .shell > .article){overflow-x:clip}
main:has(> .shell > .article) .page-head + .shell::before,main:has(> .shell > .article) .page-head + .shell::after{
  left:calc(50% - 50vw);right:calc(50% - 50vw)}
main:has(> .shell > .article) .page-head{padding-block:clamp(2rem,6vw,4rem) clamp(3rem,6vw,4.5rem)}
main:has(> .shell > .article) .page-head h1{font-weight:400;font-size:clamp(2.3rem,5.4vw,4rem);line-height:1.08;max-width:18ch}
.article{max-width:36em;padding-block:1rem 4rem}
.article .meta{padding-bottom:1.5rem}
.article p,.article ul,.article ol,.article blockquote{font-size:1.2rem;line-height:1.75;margin-top:1.3rem}
.article .meta + p{font-size:clamp(1.3rem,2.2vw,1.45rem);line-height:1.6;color:var(--ink)}
.article h2{font-weight:500;font-size:clamp(1.55rem,2.8vw,2rem);margin-top:3.25rem;line-height:1.2}
.article h2::before{content:"";display:block;width:2.75rem;height:10px;margin-bottom:1rem;background:var(--trace);
  mask:url('/images/wave-line.svg') center / 100% 100% no-repeat}
@media (min-width:641px){.article p,.article ul,.article ol{font-size:1.25rem}}
@supports (animation-timeline:scroll()){
  @media (prefers-reduced-motion:no-preference){
    main:has(> .shell > .article)::before{content:"";position:fixed;z-index:41;left:0;right:0;top:var(--head);height:2px;
      background:var(--trace);transform-origin:0 50%;animation:waterline linear both;animation-timeline:scroll(root)}
  }
}
@keyframes waterline{from{transform:scaleX(0)}to{transform:scaleX(1)}}

/* ============================ about ====================================== */
/* Personal: the details read as three columns divided by hand. */
.page-about .page-head{padding-block:clamp(3rem,8vw,6rem) clamp(3rem,6vw,4.5rem)}
.page-about .tide{--band:var(--shallow);background:linear-gradient(var(--shallow) 40%,var(--shallow-2))}
.page-about .colophon{gap:2.5rem clamp(2rem,5vw,4.5rem)}
@media (min-width:880px){
  .page-about .colophon > div + div{position:relative}
  .page-about .colophon > div + div::before{content:"";position:absolute;left:calc(-1 * clamp(1rem,2.5vw,2.25rem));top:.2rem;bottom:0;
    width:1.5px;background:linear-gradient(var(--rule),transparent)}
}
.page-about .colophon .big{font-weight:500;font-size:1.4rem}

/* ============================ 404 ======================================== */
/* Low tide: the page went out with the water. A wide empty beach, the deep
   water far down the screen, and the way back laid out in one row. */
.page-lost .page-head{min-height:min(72vh,640px);display:flex;align-items:center;padding-block:4rem 7rem}
.page-lost .page-head .shell{width:100%}
.page-lost h1{font-style:italic;font-weight:400;font-size:clamp(3rem,9vw,7rem);letter-spacing:-.045em}
.page-lost .said{font-size:var(--t-md)}
.page-lost ul{display:flex;flex-wrap:wrap;gap:.25rem 1.75rem;margin-top:2rem}
.page-lost li a{text-decoration-color:var(--trace);text-underline-offset:.3em}
.page-lost li a:hover,.page-lost li a:focus-visible{color:var(--trace)}
@media (min-width:561px){.page-projects #measured .strip{grid-template-columns:repeat(2,minmax(0,1fr))}}
.page-projects #books .three,.case-audio .three{background:transparent;border:0;gap:1rem}
.case-audio .three{list-style:none;margin:2.5rem 0 0;padding:0;display:grid}
@media (min-width:900px){.case-audio .three{grid-template-columns:repeat(3,minmax(0,1fr))}}
.case-audio .three > li{display:grid;grid-template-columns:1fr;gap:.4rem;align-content:start}
.case-audio .three a{text-decoration:none;color:inherit}
.case-audio .three h3 a{display:inline-block;padding-block:.6rem .4rem;transition:color .22s var(--ease)}
.case-audio .three h3 a:hover,.case-audio .three h3 a:focus-visible{color:var(--trace)}
.case-audio .three .n{font-family:var(--display);font-weight:600;font-size:1.05rem;margin:0;letter-spacing:-.015em}
.case-audio .three .go{font-family:var(--data);font-size:var(--t-micro);color:var(--trace)}
.case-audio .three .d{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);line-height:1.6}
.case-audio .three .d a{text-decoration:underline;color:var(--ink-2)}

/* drawings and their arrival drift never widen the page */
.hero,.page-head,.shelf{overflow-x:clip}
@media (max-width:640px){
  .contact::after{width:100%;height:180px;opacity:.08}
}
/* a long current-page crumb wraps as text, keeping its separator beside it */
.crumbs li{display:flex;align-items:baseline}
.crumbs li+li::before{flex:none}
.crumbs [aria-current]{display:inline;min-height:0;padding-block:.75rem}

/* ============================ follow-up: about, projects, writing ======== */
.page-about .page-head .shell > *{max-width:min(100%,40rem)}
.page-about .about-line{font-weight:400;font-size:clamp(2rem,4.2vw,3.4rem);max-width:15ch;line-height:1.1;text-wrap:balance}

/* Projects & Fun: found things on a beach. Sea glass in the site's own
   colours lies on the sand in place of the coast, beside a hand-set ampersand. */
.page-projects .page-head::after{content:none}
.seaglass{position:absolute;z-index:-1;right:max(var(--gut),calc((100vw - 1200px) / 2 + var(--gut)));top:clamp(1.5rem,4vw,3rem);
  width:min(36vw,420px);height:auto;pointer-events:none;overflow:visible}
.seaglass path{stroke:var(--ink);stroke-opacity:.18;stroke-width:1.2;transform-box:fill-box;transform-origin:center}
.seaglass .g1{fill:color-mix(in srgb,var(--trace) 34%,transparent)}
.seaglass .g2{fill:color-mix(in srgb,var(--trace) 18%,transparent)}
.seaglass .g3{fill:color-mix(in srgb,#5f8fa6 36%,transparent)}
.seaglass .g4{fill:color-mix(in srgb,var(--flag) 30%,transparent)}
.seaglass .g5{fill:color-mix(in srgb,#c9a34a 38%,transparent)}
.seaglass path:nth-child(odd){rotate:-6deg}
.seaglass path:nth-child(3n){rotate:9deg}
@media (prefers-reduced-motion:no-preference){
  .seaglass path{animation:wash 1.1s var(--ease) both}
  .seaglass path:nth-child(2){animation-delay:.08s}.seaglass path:nth-child(3){animation-delay:.16s}
  .seaglass path:nth-child(4){animation-delay:.24s}.seaglass path:nth-child(5){animation-delay:.32s}
  .seaglass path:nth-child(n+6){animation-delay:.4s}
}
@keyframes wash{from{opacity:0;translate:0 14px}}
.page-projects h1 .amp{font-family:var(--display);font-style:italic;font-weight:400;color:var(--flag);
  display:inline-block;rotate:-8deg;translate:0 .04em;font-size:1.08em;letter-spacing:0}
@media (max-width:640px){
  .seaglass{width:112px;top:1.4rem;opacity:.9}
  .page-projects .page-head .said{max-width:30ch}
}

/* Writing: the list sits where the water comes in, each entry set off by its
   own thin wash line. */
.page-writing .page-head{padding-block:clamp(3.5rem,9vw,6.5rem) clamp(3.5rem,7vw,5rem);text-align:center}
.page-writing .page-head .crumbs ol{justify-content:center}
.page-writing .page-head h1{font-style:italic;font-weight:400;font-size:clamp(3rem,8vw,6rem);letter-spacing:-.04em;
  margin-inline:auto;max-width:none}
.page-writing .page-head + .shelf{--band:var(--shallow);padding-top:clamp(2.5rem,5vw,3.5rem);background:linear-gradient(var(--shallow),var(--shallow-2))}
.page-writing .picks > li{border-top:0;position:relative}
.page-writing .picks > li::before{content:"";position:absolute;left:0;top:0;width:min(100%,24rem);height:10px;
  background:var(--trace);opacity:.5;mask:url('/images/wave-line.svg') center / 100% 100% no-repeat}
@media (min-width:760px){
  .page-writing .picks > li:nth-child(even of :not([hidden])){padding-left:clamp(2rem,8vw,6rem)}
  .page-writing .picks > li:nth-child(even of :not([hidden]))::before{left:auto;right:0}
}

/* ============================ ML & Research ============================== */
/* A lab notebook set in water: each section rises over the last, and each
   experiment is a log entry whose left column records machine, licence and
   status before the result. */
.page-ml .shelf{--band:var(--paper);background:var(--band)}
.page-ml .shelf:nth-of-type(2){--band:var(--shallow)}
.page-ml .shelf:nth-of-type(3){--band:var(--shallow-2)}
.page-ml .shelf + .shelf::before{content:"";position:absolute;left:0;right:0;top:-27px;height:28px;
  background:var(--band);mask:url('/images/wave-fill.svg') center / 100% 100% no-repeat}
.page-ml .page-head h1{font-family:var(--data);font-weight:400;font-variation-settings:normal;
  font-size:clamp(2.2rem,5.6vw,4.4rem);letter-spacing:-.04em}
.page-ml .page-head .said{max-width:52ch}
.ml-index{list-style:none;margin:1.75rem 0 0;padding:0;display:flex;flex-wrap:wrap;gap:.1rem 1.4rem;
  font-family:var(--data);font-size:var(--t-data)}
.ml-index a{display:inline-flex;align-items:center;min-height:var(--tap);color:var(--ink);text-decoration:none;
  border-bottom:1px dashed var(--rule)}
.ml-index a:hover,.ml-index a:focus-visible{color:var(--trace);border-bottom-color:var(--trace)}
.page-ml .shelf-head .said a{color:var(--ink)}
.log{list-style:none;margin:0;padding:0}
.entry{display:grid;grid-template-columns:minmax(0,1fr);gap:1rem 3rem;padding-block:2rem 2.25rem;border-top:1px solid var(--rule-soft)}
.log > li:first-child .entry{border-top:0;padding-top:.5rem}
@media (min-width:900px){.entry{grid-template-columns:13.5rem minmax(0,1fr)}}
.entry-meta{margin:0;font-family:var(--data);font-size:var(--t-micro);color:var(--mute);display:grid;gap:.55rem;align-content:start}
.entry-meta div{display:grid;gap:.05rem}
.entry-meta dt{color:var(--mute);letter-spacing:.06em}
.entry-meta dd{margin:0;color:var(--ink);line-height:1.45}
@media (max-width:899px){.entry-meta{grid-template-columns:repeat(auto-fit,minmax(9.5rem,1fr));gap:.6rem 1.25rem;order:2}}
.entry-body h3{font-family:var(--data);font-weight:400;font-size:clamp(1.15rem,1.8vw,1.45rem);letter-spacing:-.02em;
  font-variation-settings:normal;line-height:1.3}
.entry-body h3 a{color:inherit;text-decoration-color:var(--trace);text-underline-offset:.25em;text-decoration-thickness:1px}
.entry-body h3 a:hover,.entry-body h3 a:focus-visible{color:var(--trace)}
.entry-body > p{margin-top:.8rem;color:var(--ink-2);max-width:66ch}
.entry-body .readout{margin-top:1.1rem;border-radius:2px;max-width:46rem}
.entry-body .readout div{background:var(--band,var(--paper))}
.entry-body .readout .off dt,.entry-body .readout .off dd{color:var(--flag)}
.entry-body .limits{border-left:2px solid var(--flag);padding-left:.9rem;font-size:1rem}
.entry-body .limits b{font-weight:600;color:var(--ink)}
.entry-body .why{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);line-height:1.7}
.entry-body .src{max-width:70ch}
.entry.negative .entry-meta div:first-child dd{color:var(--flag)}

/* project pages and Projects & Fun: where moved work went */
.page-head .context,.page-head .moved{margin-top:1rem;max-width:60ch;color:var(--ink-2);font-size:1rem}
.page-head .context a,.page-head .moved a{color:var(--ink);text-decoration-color:var(--trace);text-underline-offset:.2em}
.page-head .moved{font-family:var(--data);font-size:var(--t-data)}
.page-projects #upstream .said a{color:var(--ink)}

/* Writing: topic vocabulary and the topic filter */
.page-writing .topics{margin:1.25rem auto 0;max-width:46ch;color:var(--ink-2);font-size:1.05rem;text-wrap:balance}
.topic-filter{display:flex;flex-wrap:wrap;gap:.4rem 1.25rem;margin:0 0 .25rem;font-family:var(--data);font-size:var(--t-data)}
.topic-filter[hidden]{display:none}
.topic-filter button{font:inherit;color:var(--ink-2);background:none;border:0;border-bottom:1px solid transparent;
  min-height:var(--tap);padding:0 .1rem;cursor:pointer;display:inline-flex;align-items:center;gap:.35rem}
.topic-filter button small{font-size:var(--t-micro);color:var(--mute)}
.topic-filter button:hover{color:var(--ink);border-bottom-color:var(--rule)}
.topic-filter button[aria-pressed="true"]{color:var(--ink);border-bottom-color:var(--flag)}
.topic-status{font-family:var(--data);font-size:var(--t-micro);color:var(--mute);min-height:1.2em;margin-bottom:1rem}
.picks > li[hidden]{display:none}
.picks .tag .also{color:var(--mute)}

/* Home: recent writing, one row per article, newest first, up to three */
.home #writing .picks{grid-template-columns:minmax(0,1fr)!important;gap:0}
.home #writing .picks > li{display:grid;grid-template-columns:minmax(0,1fr);gap:.2rem;padding:.85rem 0}
@media (min-width:760px){
  .home #writing .picks > li{grid-template-columns:minmax(0,1fr) auto;align-items:baseline;gap:.2rem 2rem}
  .home #writing .picks .tag{margin:0;justify-content:flex-end}
}
.home #writing .picks > li + li{border-top:1px solid var(--rule-soft)}
/* the new edges keep their drawn proportions on narrow screens instead of
   squeezing into spikes */
.page-work .shelf.tide::before,.page-ml .shelf + .shelf::before,.page-projects .shelf.tide::before,
.page-writing .page-head + .shelf::before,.page-about .shelf.tide::before{mask-size:max(100%,1440px) 100%}

/* ============================ inner pages: one voice ===================== */
/* Every inner page now speaks Home's type: a light, tight serif display for
   titles, serif 500 for item titles, serif body for anything that reads as a
   sentence, and mono only for labels, dates and figures. Each page keeps its
   own composition below; none of these rules reach Home. */
.page-work .page-head h1,.page-ml .page-head h1,.page-projects .page-head h1,.page-about .page-head h1,.page-case .page-head h1{
  font-family:var(--display);font-weight:400;font-stretch:normal;font-variation-settings:normal;
  font-size:clamp(2.9rem,6.4vw,5.4rem);line-height:1.02;letter-spacing:-.04em;max-width:16ch}
.page-work .page-head,.page-ml .page-head,.page-projects .page-head,.page-about .page-head,.page-case .page-head{
  padding-block:clamp(2.5rem,6vw,4.75rem) clamp(3rem,6vw,4.75rem)}
.page-work .page-head .said,.page-ml .page-head .said,.page-projects .page-head .said,.page-case .page-head .said{
  margin-top:1.4rem;max-width:44ch;font-size:var(--t-md);line-height:1.5;color:var(--ink-2);font-variation-settings:'opsz' 24}
.page-work .shelf-head h2,.page-ml .shelf-head h2,.page-projects .shelf-head h2{font-family:var(--display);font-stretch:normal;
  font-weight:400;letter-spacing:-.03em}

/* one soft instrument surface for readouts on measurement pages */
.page-ml .entry-body .readout,.page-case .readout{background:var(--rule-soft);border:1px solid var(--rule-soft);
  border-radius:12px;overflow:hidden;gap:1px}
.page-ml .entry-body .readout div,.page-case .readout div{background:color-mix(in srgb,var(--paper-lift) 78%,var(--band,var(--paper)));
  padding:.85rem 1rem .9rem}
.page-ml .readout dd,.page-case .readout dd{font-weight:500;font-size:clamp(1.35rem,2vw,1.65rem);letter-spacing:-.025em}
.page-ml .readout dt,.page-case .readout dt{letter-spacing:.03em}

/* ---- Work: a career record. The section title holds still on the left
   while the roles run down their rail on the right. ---------------------- */
.page-work .page-head h1{font-size:clamp(3.2rem,8vw,6.25rem)}
.page-work .row{padding-block:2.1rem}
.page-work .row h3{font-size:clamp(1.45rem,2.2vw,1.8rem);line-height:1.2}
.page-work .row > div > p{font-size:1.1rem;line-height:1.65}
.page-work .row .built{line-height:1.6;max-width:var(--measure);color:var(--mute)}
@media (min-width:641px){
  .page-work .row{grid-template-columns:8.5rem minmax(0,1fr)}
  .page-work .row .built{grid-column:2;grid-row:auto;margin-top:1rem;padding-top:.8rem;
    border-top:1px dashed var(--rule-soft)}
}
@media (min-width:1100px){.page-work .row{grid-template-columns:8.5rem minmax(0,1fr)}}
@media (min-width:980px){
  .page-work #shipped > .shell,.page-work #leadership > .shell{display:grid;
    grid-template-columns:minmax(0,16rem) minmax(0,1fr);gap:0 clamp(2.5rem,5vw,5rem);align-items:start}
  .page-work #shipped .shelf-head,.page-work #leadership .shelf-head{position:sticky;top:calc(var(--head) + 2.5rem);
    margin:0;padding-top:1.6rem}
  .page-work #shipped .shelf-head h2,.page-work #leadership .shelf-head h2{font-size:clamp(2.4rem,3.4vw,2.9rem);overflow-wrap:normal}
  .page-work #shipped .shelf-head .said{font-size:1rem;color:var(--mute)}
}
.page-work #shipped{padding-bottom:clamp(4rem,8vw,6.5rem)}
.page-work #leadership{padding-block:clamp(3.5rem,7vw,5rem) clamp(4.5rem,8vw,6.5rem)}
/* the closing band: an orderly index of where the rest of the work lives */
.page-work #moved{padding-block:clamp(3.5rem,7vw,5rem) clamp(3.5rem,7vw,5rem)}
.page-work #moved > .shell{display:grid;grid-template-columns:minmax(0,1fr);column-gap:3rem}
@media (min-width:760px){.page-work #moved > .shell{grid-template-columns:repeat(2,minmax(0,1fr))}}
.page-work #moved .shelf-head{grid-column:1/-1;margin-bottom:1rem}
.page-work #moved .shelf-head h2{font-size:clamp(1.9rem,3.4vw,2.8rem)}
.page-work #moved .more{display:block;margin:0;border-top:1px solid color-mix(in srgb,var(--deep-ink) 16%,transparent)}
.page-work #moved .more a{display:flex;width:100%;min-height:3.5rem;padding-block:.6rem;border-bottom:0;
  font-family:var(--display);font-size:1.2rem;letter-spacing:-.01em;line-height:1.3;
  background:linear-gradient(var(--deep-trace),var(--deep-trace)) 0 100% / 0 1px no-repeat;
  transition:background-size .45s var(--ease),color .2s var(--ease)}
.page-work #moved .more a:hover,.page-work #moved .more a:focus-visible{background-size:100% 1px}

/* ---- ML & Research: a lab notebook. Each entry keeps a ruled spec sheet
   beside its result; values read off soft instrument panels. ------------- */
.page-ml .page-head .said{max-width:46ch}
.page-ml .ml-index{gap:.5rem .5rem;margin-top:2rem}
.page-ml .ml-index a{border:1px solid var(--rule-soft);border-radius:999px;padding:0 1rem;
  background:color-mix(in srgb,var(--paper-lift) 60%,transparent);transition:border-color .2s var(--ease),color .2s var(--ease)}
.page-ml .ml-index a:hover,.page-ml .ml-index a:focus-visible{border-color:var(--trace)}
.page-ml .shelf{padding-block:clamp(3.5rem,7vw,5.5rem) clamp(4rem,8vw,6rem)}
@media (min-width:980px){
  .page-ml .shelf-head.wide{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1fr);align-items:end;gap:1rem 4rem}
  .page-ml .shelf-head.wide .said{margin:0 0 .9rem;font-size:1.1rem}
}
.page-ml .entry{padding-block:2.5rem 2.75rem}
.page-ml .entry-body h3{font-family:var(--display);font-weight:500;font-size:clamp(1.55rem,2.4vw,2rem);
  letter-spacing:-.025em;line-height:1.15}
.page-ml .entry-body > p:not(.src):not(.why):not(.limits){font-size:1.1rem;line-height:1.65}
.page-ml .entry-body .readout{max-width:44rem;margin-top:1.4rem}
.page-ml .entry-body .limits{background:color-mix(in srgb,var(--flag) 6%,var(--paper-lift));border-left-width:2px;
  border-radius:0 12px 12px 0;padding:.95rem 1.2rem;max-width:44rem;margin-top:1.25rem;font-size:1.02rem}
.page-ml .entry-body .why{max-width:62ch}
@media (min-width:900px){
  .page-ml .entry-meta{position:sticky;top:calc(var(--head) + 1.75rem);gap:0;padding-top:.45rem}
  .page-ml .entry-meta div{padding-block:.55rem;border-top:1px solid var(--rule-soft)}
  .page-ml .entry-meta div:first-child{border-top:0;padding-top:0}
}

/* ---- Projects & Fun: a pinboard. Serif voice, a framed activity chart,
   the audiobook trio as three linked stages, and a two-column directory. -- */
.page-projects h1,.page-projects .shelf-head h2,.page-projects .strip h3,.page-projects .three .n,.page-projects .dir .n{
  font-family:var(--display);font-stretch:normal;letter-spacing:-.02em}
.page-projects .page-head .moved{margin-top:1.1rem}
.page-projects .wire{margin-top:2.5rem;padding:1.1rem 1.3rem 1rem;border:1px solid var(--rule-soft);border-radius:14px;
  background:color-mix(in srgb,var(--paper-lift) 82%,transparent)}
.page-projects .shelf-head .said{font-family:var(--body);font-size:1.05rem;color:var(--ink-2);text-align:left;max-width:36ch}
.page-projects .shelf-head h2{font-size:clamp(2.1rem,4.2vw,3.5rem)}
/* three stages on one line: book to audio, the engine, the player */
.page-projects #books .three{display:grid;gap:1.75rem 2.5rem;padding-top:1.9rem}
.page-projects #books .three::before{content:"";position:absolute;left:5px;right:0;top:5px;height:1.5px;
  background:linear-gradient(90deg,var(--trace),color-mix(in srgb,var(--trace) 25%,transparent))}
.page-projects #books .three > li,.page-projects #books .three > li:nth-child(even){background:none;border:0;border-radius:0;
  padding:0;position:relative;transform:none;align-content:start}
.page-projects #books .three > li::before{content:"";position:absolute;left:0;top:calc(-1.9rem - 0px);width:12px;height:12px;
  border-radius:50%;border:1.5px solid var(--trace);background:var(--band)}
.page-projects #books .three > li:first-child::before{background:var(--trace)}
.page-projects #books .three .n{font-size:1.35rem;font-weight:500}
.page-projects #books .three .d{font-family:var(--body);font-size:1rem;line-height:1.6;color:var(--ink-2)}
@media (max-width:899px){
  .page-projects #books .three{padding:0 0 0 1.9rem}
  .page-projects #books .three::before{left:5px;right:auto;top:6px;bottom:0;width:1.5px;height:auto;
    background:linear-gradient(var(--trace),color-mix(in srgb,var(--trace) 25%,transparent))}
  .page-projects #books .three > li::before{left:-1.9rem;top:.6rem}
}
/* apps for friends: a directory, read down the first column then the second */
.page-projects .dir a{grid-template-columns:2rem minmax(0,1fr) auto;gap:.15rem .9rem;padding:1rem .5rem;
  border-radius:10px;box-shadow:none}
.page-projects .dir li + li a{box-shadow:none}
.page-projects .dir li{border-bottom:1px solid var(--rule-soft)}
.page-projects .dir .i{grid-column:1;grid-row:1;font-size:var(--t-micro);padding-top:.2rem}
.page-projects .dir .n{grid-column:2;grid-row:1;font-size:1.2rem;font-weight:500}
.page-projects .dir .h{grid-column:3;grid-row:1;font-size:var(--t-micro)}
.page-projects .dir .d{grid-column:2/-1;grid-row:2;font-family:var(--body);font-size:1rem;line-height:1.5;color:var(--ink-2)}
@media (min-width:1100px){
  .page-projects .dir{display:grid;grid-auto-flow:column;grid-template-rows:repeat(6,auto);
    grid-template-columns:repeat(2,minmax(0,1fr));column-gap:3.5rem}
  .page-projects .dir li:nth-child(6n+1){border-top:1px solid var(--rule-soft)}
}
@media (max-width:1099px){.page-projects .dir li:first-child{border-top:1px solid var(--rule-soft)}}
.page-projects .screens{margin-top:2.75rem}
.page-projects .screens figure{border-radius:14px;border:1px solid var(--rule-soft);
  background:color-mix(in srgb,var(--paper-lift) 70%,transparent)}
/* personal tools: three across, the last two sharing the second row */
.page-projects #tools .strip{gap:1.1rem}
@media (min-width:1100px){
  .page-projects #tools .strip{grid-template-columns:repeat(3,minmax(0,1fr))}
  .page-projects #tools .strip li:last-child{grid-column:span 2}
}
.page-projects #tools .strip article,.page-projects #tools .strip > li:nth-child(n) article{
  background:color-mix(in srgb,var(--paper-lift) 70%,transparent);border:1px solid var(--rule-soft);
  border-radius:14px;padding:1.4rem 1.45rem 1.35rem;gap:.6rem}
.page-projects #tools .strip li:hover article{transform:translateY(-2px);border-color:var(--trace);background:var(--paper-lift)}
.page-projects .strip h3{font-size:1.3rem;font-weight:500}
.page-projects .strip h3 a{display:inline-flex;align-items:center;gap:.25rem;min-height:var(--tap);padding-block:0}
.page-projects .strip p{font-size:1rem;line-height:1.6}
.page-projects #tools .strip .why{font-family:var(--body);font-style:italic;font-size:.95rem;line-height:1.55;
  color:var(--mute);padding-top:.7rem;border-top:1px dashed var(--rule-soft)}
/* contributions: a light row of four, no boxes */
.page-projects #upstream .strip{gap:1.5rem 2rem}
@media (min-width:1100px){.page-projects #upstream .strip{grid-template-columns:repeat(4,minmax(0,1fr))}}
.page-projects #upstream .strip article,.page-projects #upstream .strip > li:nth-child(n) article{background:none;border:0;
  border-top:1.5px solid var(--trace);border-radius:0;padding:1.1rem 0 0;transform:none}
.page-projects #upstream .strip li:hover article{transform:none;background:none}

/* ---- Writing: a reading room. A left rail holds the label, topics and
   status; the articles read as large teasers beside it. ----------------- */
.page-writing .shell{max-width:1200px}
.page-writing .page-head{text-align:left;padding-block:clamp(3rem,8vw,6rem) clamp(4rem,8vw,6rem)}
.page-writing .page-head .crumbs ol{justify-content:flex-start}
.page-writing .page-head h1{font-size:clamp(3.4rem,9vw,7rem);margin-inline:0;line-height:1}
.page-writing .topics{margin:1.4rem 0 0;max-width:40ch;font-size:var(--t-md);line-height:1.5;text-wrap:pretty}
.page-writing .page-head + .shelf{padding-block:clamp(3rem,6vw,4.5rem) clamp(4.5rem,9vw,7rem)}
.page-writing .picks > li{padding:2.6rem 0 2.75rem}
.page-writing .picks > li:first-child{padding-top:.4rem}
.page-writing .picks > li::before{width:4.5rem;opacity:.7}
.page-writing .picks > li:first-child::before{content:none}
.page-writing .picks > li + li{border-top:1px solid var(--rule-soft)}
.page-writing .picks > li + li::before{top:-5px}
@media (min-width:760px){
  .page-writing .picks > li:nth-child(even of :not([hidden])){padding-left:0}
  .page-writing .picks > li:nth-child(even of :not([hidden]))::before{left:0;right:auto}
}
.page-writing .picks h3{font-size:clamp(1.9rem,3.6vw,3rem);line-height:1.1;letter-spacing:-.03em;max-width:22ch}
.page-writing .picks p:not(.tag){font-size:clamp(1.12rem,1.5vw,1.3rem)!important;line-height:1.55;max-width:46ch;margin-top:1rem}
@media (min-width:900px){
  .page-writing .page-head + .shelf > .shell{display:grid;grid-template-columns:minmax(0,13rem) minmax(0,1fr);
    column-gap:clamp(3rem,8vw,7rem);align-items:start;grid-template-rows:auto auto 1fr}
  .page-writing .shelf-head{grid-column:1;grid-row:1;margin:0 0 .5rem;padding:.55rem 0 0}
  .page-writing .topic-filter{grid-column:1;grid-row:2;flex-direction:column;align-items:stretch;gap:0;margin:0}
  .page-writing .topic-filter button{justify-content:space-between;border-bottom:0;border-left:2px solid transparent;
    padding:0 .25rem 0 .85rem;text-align:left}
  .page-writing .topic-filter button + button{border-top:1px solid var(--rule-soft)}
  .page-writing .topic-filter button:hover{border-left-color:var(--rule)}
  .page-writing .topic-filter button[aria-pressed="true"]{border-left-color:var(--flag)}
  .page-writing .topic-status{grid-column:1;grid-row:3;margin:1rem 0 0;padding-left:.85rem}
  .page-writing .picks{grid-column:2;grid-row:1 / span 3}
}

/* ---- About: a profile. The details open into two columns, and Contact
   sits in deep water as the page's one panel. -------------------------- */
.page-about .page-head{padding-block:clamp(2.5rem,7vw,5.5rem) clamp(4rem,8vw,6rem)}
.page-about .page-head h1{font-size:clamp(3.2rem,8vw,6.25rem)}
.page-about .about-line{margin-top:1.25rem;font-size:clamp(1.65rem,3vw,2.4rem);line-height:1.18;max-width:20ch;color:var(--ink)}
.page-about .page-head .hero-role{margin-top:1.25rem;max-width:34ch;font-size:clamp(1.15rem,1.7vw,1.4rem);line-height:1.45;color:var(--ink-2)}
.page-about .page-head .hero-lead{max-width:44ch;font-size:1.1rem;line-height:1.6}
.page-about .shelf.tide{padding-block:clamp(4rem,8vw,6rem) clamp(4rem,8vw,6rem)}
.page-about .colophon{align-items:start}
.page-about .colophon h3{margin-bottom:1rem}
.page-about .colophon .big{font-size:clamp(1.45rem,2.2vw,1.8rem);line-height:1.2;margin-bottom:.4rem}
.page-about .colophon p{font-size:1.08rem;line-height:1.6}
.page-about .colophon > div:nth-child(3){background:var(--deep);color:var(--deep-ink);border-radius:16px;
  padding:clamp(1.5rem,3vw,2.25rem)}
.page-about .colophon > div:nth-child(3)::before{content:none}
.page-about .colophon > div:nth-child(3) h3{color:var(--deep-mute)}
.page-about .colophon > div:nth-child(3) .big{font-size:clamp(1rem,1.15vw,1.15rem);overflow-wrap:anywhere}
.page-about .colophon > div:nth-child(3) a{color:var(--deep-ink);border-bottom-color:color-mix(in srgb,var(--deep-ink) 30%,transparent)}
.page-about .colophon > div:nth-child(3) a:hover,.page-about .colophon > div:nth-child(3) a:focus-visible{color:var(--deep-trace);border-bottom-color:var(--deep-trace)}
.page-about .colophon > div:nth-child(3) :focus-visible{outline-color:var(--deep-trace)}
@media (min-width:980px){
  .page-about .colophon{grid-template-columns:minmax(0,.95fr) minmax(0,1fr) minmax(0,1.05fr)}
}

/* ---- Kestrel: a measurement report. ---------------------------------- */
.case-kestrel .project{padding-block:clamp(3rem,6vw,4.5rem) clamp(4rem,8vw,6rem)}
.page-case .case-what{font-size:1.1rem;line-height:1.7}
.page-case .readout{margin-block:1.5rem 1.75rem}
.page-case .miss{margin-top:2rem;padding:1.25rem 1.5rem 1.35rem;border:1px solid color-mix(in srgb,var(--flag) 26%,transparent);
  border-left:3px solid var(--flag);border-radius:4px 14px 14px 4px;
  background:color-mix(in srgb,var(--flag) 6%,var(--paper-lift))}
.page-case .miss p:not(.tag){font-size:1.05rem;line-height:1.65}
.page-case .plot,.page-case .shot{border-radius:14px;border-color:var(--rule-soft);background:color-mix(in srgb,var(--paper-lift) 90%,transparent)}

/* ---- PHiLIP: a short brief, its three figures stacked large. --------- */
.case-philip .project{padding-block:clamp(3rem,6vw,4.5rem) clamp(3.5rem,7vw,5rem)}
.case-philip .case-what:first-child{font-size:var(--t-md);line-height:1.55;color:var(--ink)}
.case-philip .readout{grid-template-columns:minmax(0,1fr)}
.case-philip .readout div{display:grid;grid-template-columns:minmax(0,1fr) auto;align-items:baseline;gap:1rem;padding:1.1rem 1.25rem}
.case-philip .readout dt{min-height:0;font-size:var(--t-data)}
.case-philip .readout dd{margin:0;font-size:clamp(1.8rem,3vw,2.4rem);text-align:right}
.case-philip .aside .src{font-family:var(--body);font-size:1rem;line-height:1.65;color:var(--ink-2);margin-top:1.25rem}

/* ---- My audiobook setup: a story, then the three parts as a list. ---- */
.case-audio .shelf{padding-block:clamp(3rem,6vw,4.5rem) clamp(4rem,8vw,6rem)}
.case-audio .three{gap:0;margin-top:clamp(3rem,6vw,4.5rem);border-top:1px solid var(--rule)}
@media (min-width:900px){.case-audio .three{grid-template-columns:minmax(0,1fr)}}
.case-audio .three > li,.case-audio .three > li:nth-child(even){background:none;border:0;border-bottom:1px solid var(--rule-soft);
  border-radius:0;padding:1.4rem 0 1.5rem;transform:none}
.case-audio .three > li:hover{transform:none;background:none}
@media (min-width:760px){
  .case-audio .three > li{grid-template-columns:minmax(0,15rem) minmax(0,1fr);gap:.4rem 2.5rem}
  .case-audio .three > li .d{padding-top:.55rem}
}
.case-audio .three .n{font-size:1.35rem;font-weight:500}
.case-audio .three h3 a{display:inline-flex;align-items:center;flex-wrap:wrap;gap:0 .2rem;min-height:var(--tap);padding-block:0}
.case-audio .three .d{font-family:var(--body);font-size:1.05rem;line-height:1.65;color:var(--ink-2);max-width:62ch}
.case-audio .three .d a{color:var(--ink);text-decoration-color:var(--trace);text-underline-offset:.2em}

/* ---- Article: the published HTML stays as written; only the meta line
   gets a quiet rule under it. ------------------------------------------ */
.article .meta{border-bottom:1px solid var(--rule-soft);margin-bottom:.5rem}

/* ---- 404: the page always reaches the bottom of the window. ---------- */
body:has(> main.page-lost){min-height:100vh;min-height:100dvh;display:flex;flex-direction:column}
body:has(> main.page-lost) > main.page-lost{flex:1;display:flex;flex-direction:column}
.page-lost .page-head{flex:1}
