@font-face{font-family:"Source Sans 3";font-style:normal;font-weight:400;font-display:swap;src:url("../fonts/source-sans-400.woff2") format("woff2")}
@font-face{font-family:"Source Sans 3";font-style:normal;font-weight:600;font-display:swap;src:url("../fonts/source-sans-600.woff2") format("woff2")}
@font-face{font-family:"Source Sans 3";font-style:normal;font-weight:700;font-display:swap;src:url("../fonts/source-sans-700.woff2") format("woff2")}
@font-face{font-family:"Cormorant Garamond";font-style:normal;font-weight:400;font-display:swap;src:url("../fonts/cormorant-400.woff2") format("woff2")}
@font-face{font-family:"Cormorant Garamond";font-style:normal;font-weight:600;font-display:swap;src:url("../fonts/cormorant-600.woff2") format("woff2")}
@font-face{font-family:"Cormorant Garamond";font-style:normal;font-weight:700;font-display:swap;src:url("../fonts/cormorant-700.woff2") format("woff2")}
/* real italics. without these the browser fakes one by slanting the roman,
   which is visibly wrong on a face whose italic has its own letterforms. */
@font-face{font-family:"Cormorant Garamond";font-style:italic;font-weight:400;font-display:swap;src:url("../fonts/cormorant-400-italic.woff2") format("woff2")}
@font-face{font-family:"Cormorant Garamond";font-style:italic;font-weight:600;font-display:swap;src:url("../fonts/cormorant-600-italic.woff2") format("woff2")}

/* ============================================================
   CORSAC VANTAGE
   Dark throughout. One living canvas behind the whole site.
   ============================================================ */

button,input,textarea,select{font-family:inherit}

:root{
  --purple:        #1A0B2E;
  --purple-deep:   #0C0518;
  --purple-raised: #32184E;
  --amber:         #D97706;
  --amber-lt:      #F0A03A;
  --gold:          #D4AF37;
  --gold-lt:       #E3CA7B;
  --ink:           #241633;
  --card-tint:     #F3EFF8;
  --off-white:     #FBFAFD;

  --on-dark:     #EFE8F7;
  --on-dark-dim: #A395BC;
  --on-dark-mute:#8578A0;
  --hair:        rgba(212,175,55,.20);
  --hair-soft:   rgba(212,175,55,.10);

  /* Serif matches the Financial Command Center wordmark. */
  --serif: "Cormorant Garamond", "Hoefler Text", Baskerville, Georgia, serif;
  --sans:  "Source Sans 3", Calibri, ui-sans-serif, system-ui, -apple-system, "Segoe UI", sans-serif;

  --ease:  cubic-bezier(.22,.61,.36,1);
  --ease-o:cubic-bezier(.16,1,.3,1);
  --wrap:  1560px;
  --gut:   clamp(1.5rem,5vw,5.5rem);
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;background:var(--purple-deep)}
body{
  margin:0;background:transparent;color:var(--on-dark);
  font-family:var(--sans);font-size:1.0625rem;line-height:1.65;
  -webkit-font-smoothing:antialiased;text-rendering:optimizeLegibility;
  overflow-x:hidden;
}
h1,h2,h3,h4,p,figure,blockquote,ol,ul{margin:0}
img{max-width:100%;display:block}
a{color:inherit;text-decoration:none}
::selection{background:rgba(217,119,6,.35);color:#fff}

.wrap{width:min(var(--wrap),100% - var(--gut)*2);margin-inline:auto;position:relative;z-index:2}

/* ---------- the living canvas ---------- */
#terrain{position:fixed;inset:0;width:100%;height:100%;z-index:0;display:block;pointer-events:none}
.grain{
  position:fixed;inset:0;z-index:1;pointer-events:none;opacity:.035;
  background-image:radial-gradient(rgba(255,255,255,.9) .5px,transparent .5px);
  background-size:3px 3px;
}
main,.site-head,.site-foot{position:relative;z-index:2}

/* ---------- type ---------- */
.serif{font-family:var(--serif)}

.eyebrow{
  font-family:var(--sans);font-weight:700;font-size:.7rem;
  letter-spacing:.34em;text-transform:uppercase;color:var(--amber-lt);
  display:flex;align-items:center;gap:1rem;
}
.eyebrow::before{content:"";width:38px;height:1px;background:linear-gradient(90deg,var(--amber),transparent)}

.hero-h{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(2.6rem,min(12vw,17vh),11.5rem);
  line-height:.88;letter-spacing:-.018em;color:#fff;
}
.sec-h{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(2.5rem,6.2vw,5.25rem);
  line-height:1.0;letter-spacing:-.014em;color:#fff;text-wrap:balance;
}
.sec-h .gold{color:var(--gold-lt)}
.lede{font-size:clamp(1.05rem,1.5vw,1.3rem);line-height:1.6;color:var(--on-dark-dim)}
.dim{color:var(--on-dark-dim)}
.mute{color:var(--on-dark-mute)}

/* ghost numeral, the editorial signature */
.ghost-n{
  font-family:var(--serif);font-weight:600;line-height:1;
  /* was clamp(5rem,13vw,12rem), which topped out at 192px against a 84px
     section heading. Ornament must never outrank the thing it marks. */
  font-size:clamp(1.5rem,2.5vw,2.25rem);
  color:rgba(212,175,55,.45);-webkit-text-stroke:0;
  letter-spacing:.06em;user-select:none;
  display:block;
}
/* The numeral sits in two different layouts. In .sec-head it is a top-right
   section marker and should align with the eyebrow beside it. In .split-side
   it follows the heading and needs air above it. One margin cannot serve
   both, which is why it looked orphaned on the homepage. */
.sec-head .ghost-n{align-self:start;margin-top:.15rem}
.split-side .ghost-n{margin-top:1.4rem}

hr.hair{height:1px;background:var(--hair);border:0;margin:0}

/* ---------- sections ---------- */
section[id]{scroll-margin-top:5rem}
.sec{padding-block:clamp(2.25rem,3.6vw,3.4rem);position:relative}
.sec-lg{padding-block:clamp(2.75rem,4.6vw,4.25rem);position:relative}

/* reading panels: soft-edged scrim so copy stays legible over the canvas */
.panel::before{
  content:"";position:absolute;inset:0;z-index:1;pointer-events:none;
  background:linear-gradient(180deg,
    rgba(12,5,24,0) 0%, rgba(12,5,24,.8) 7%,
    rgba(12,5,24,.8) 93%, rgba(12,5,24,0) 100%);
}
.panel > *{position:relative;z-index:2}
/* open sections stay transparent so the canvas breathes through */

.sec-head{display:flex;align-items:flex-end;justify-content:space-between;gap:2rem;flex-wrap:wrap}
.sec-head .eyebrow{margin-bottom:.85rem}

/* ---------- buttons ---------- */
.btn{
  display:inline-flex;align-items:center;gap:.7em;position:relative;overflow:hidden;
  font-family:var(--sans);font-weight:700;font-size:.9rem;letter-spacing:.06em;
  text-transform:uppercase;padding:1.05em 2.2em;border:1px solid transparent;cursor:pointer;
  transition:transform .45s var(--ease-o),box-shadow .45s var(--ease-o),
             color .35s var(--ease),border-color .35s var(--ease);
}
.btn span{position:relative;z-index:2}
.btn::before{
  content:"";position:absolute;inset:0;z-index:1;transform:translateY(101%);
  transition:transform .5s var(--ease-o);
}
.btn-primary{background:var(--amber);color:#fff;box-shadow:0 18px 50px rgba(217,119,6,.3)}
.btn-primary::before{background:var(--gold)}
.btn-primary:hover{transform:translateY(-3px);box-shadow:0 26px 66px rgba(217,119,6,.42);color:var(--purple-deep)}
.btn-primary:hover::before{transform:translateY(0)}
.btn-ghost{border-color:rgba(212,175,55,.42);color:var(--gold-lt)}
.btn-ghost::before{background:var(--gold)}
.btn-ghost:hover{transform:translateY(-3px);color:var(--purple-deep);border-color:var(--gold)}
.btn-ghost:hover::before{transform:translateY(0)}
.btn-row{display:flex;flex-wrap:wrap;gap:1rem;margin-top:1.75rem}

/* The end of page jump strip. Centred, hairline above it so it reads as a
   footer rail rather than another content block, and the row's own top margin
   is cleared because the section already supplies the spacing. */
.jump{border-top:1px solid var(--hair-soft)}
.jump .btn-row{margin-top:0;justify-content:center}

/* ---------- header ---------- */
.site-head{
  position:fixed;inset:0 0 auto 0;z-index:60;
  display:flex;align-items:center;justify-content:space-between;gap:2rem;
  padding:1.3rem var(--gut);
  transition:background .5s var(--ease),backdrop-filter .5s var(--ease),
             border-color .5s var(--ease),padding .5s var(--ease);
  border-bottom:1px solid transparent;
}
.site-head.stuck{
  background:rgba(12,5,24,.86);backdrop-filter:blur(16px) saturate(140%);
  border-bottom-color:var(--hair-soft);padding-block:.9rem;
}
.scroll-bar{
  position:fixed;left:0;top:0;height:2px;width:100%;z-index:70;
  background:linear-gradient(90deg,var(--gold-lt),var(--gold));
  transform:scaleX(0);transform-origin:left;will-change:transform;
}
.lockup{display:flex;align-items:center;gap:.9rem;flex:none;position:relative;z-index:2}
.lockup img{width:42px;height:42px;object-fit:contain;transition:transform .5s var(--ease-o)}
.lockup:hover img{transform:translateY(-2px) scale(1.04)}
.lockup .txt{display:flex;flex-direction:column;line-height:1.15}
.lockup .nm{font-family:var(--serif);font-size:1.24rem;font-weight:600;color:#fff;letter-spacing:.24em;text-transform:uppercase}
.lockup .tg{font-size:.58rem;color:var(--gold-lt);letter-spacing:.26em;text-transform:uppercase;margin-top:.2rem}

.nav{display:flex;align-items:center;gap:2.4rem}
.nav a{
  font-size:.72rem;font-weight:700;letter-spacing:.2em;text-transform:uppercase;
  color:var(--on-dark-dim);position:relative;padding-block:.3rem;
  transition:color .3s var(--ease);
}
.nav a::after{
  content:"";position:absolute;left:0;bottom:0;width:100%;height:1px;
  background:var(--gold);transform:scaleX(0);transform-origin:right;
  transition:transform .45s var(--ease-o);
}
.nav a:hover{color:#fff}
.nav a:hover::after{transform:scaleX(1);transform-origin:left}
.nav a[aria-current="page"]{color:#fff}
.nav a[aria-current="page"]::after{transform:scaleX(1)}
.nav a.cta{color:var(--gold-lt)}
.nav-toggle{display:none;background:none;border:0;color:#fff;font-family:var(--sans);padding:.5rem;cursor:pointer;position:relative;z-index:2}

@media (max-width:900px){
  .nav-toggle{display:block}
  .nav{
    position:fixed;inset:0 0 auto 0;flex-direction:column;align-items:flex-start;
    gap:.2rem;padding:6rem var(--gut) 2.5rem;background:rgba(12,5,24,.98);
    border-bottom:1px solid var(--hair);
    transform:translateY(-101%);transition:transform .5s var(--ease-o);
  }
  .nav.open{transform:translateY(0)}
  .nav a{font-size:1.35rem;font-family:var(--serif);text-transform:none;letter-spacing:0;padding:.75rem 0}
  .lockup .nm{font-size:1.02rem;letter-spacing:.18em}
}

/* ---------- hero ---------- */
.hero{position:relative}
.hero-pin{position:sticky;top:0;height:100vh;height:100svh;overflow:hidden}
.hero-vig{
  position:absolute;inset:0;pointer-events:none;z-index:1;
  background:
    radial-gradient(125% 88% at 50% 44%, transparent 36%, rgba(12,5,24,.46) 88%),
    linear-gradient(180deg, rgba(12,5,24,.6) 0%, transparent 22% 70%, rgba(12,5,24,.55) 100%),
    linear-gradient(90deg, rgba(12,5,24,.68) 0%, transparent 46%);
}
.hero-inner{
  position:absolute;inset:0;z-index:3;display:flex;flex-direction:column;justify-content:center;
  padding-inline:var(--gut);padding-top:3rem;
  /* reserve the skip control's strip so centred content can never sit on it */
  padding-bottom:5.5rem;
  width:min(var(--wrap),100%);margin-inline:auto;
}
.hero .eyebrow{margin-bottom:2rem;opacity:0;animation:fadeUp .8s var(--ease-o) .15s forwards}
/* A hook rather than a three word headline. Eleven words cannot take the
   11.5rem clamp above, so this drops the ceiling and opens the leading a
   little. Each .ln still clips its own line for the reveal, so the manual
   breaks below are load bearing: let a line wrap inside .ln and the clip
   cuts it in half. */
.hero-h-long{font-size:clamp(1.85rem,min(4.6vw,7.2vh),4.1rem);line-height:1.06;letter-spacing:-.012em}
.hero-close{font-family:var(--serif);font-style:italic;color:#E3CA7B;
  font-size:clamp(1.15rem,min(1.9vw,3vh),1.6rem);line-height:1.35;margin-top:1rem;
  opacity:0;animation:fadeUp .9s var(--ease-o) .72s forwards}

.hero-h .ln{display:block;overflow:hidden;padding-bottom:.08em}
.hero-h .ln > span{display:block;transform:translateY(105%);animation:riseIn 1.15s var(--ease-o) forwards}
.hero-h .ln:nth-child(2) > span{animation-delay:.12s}
@keyframes riseIn{to{transform:translateY(0)}}
.hero-sub{
  max-width:44ch;margin-top:2.4rem;color:var(--on-dark-dim);
  font-size:clamp(1rem,min(1.45vw,2.4vh),1.28rem);line-height:1.55;
  opacity:0;animation:fadeUp .9s var(--ease-o) .5s forwards;
}
.hero .btn-row{opacity:0;animation:fadeUp .9s var(--ease-o) .68s forwards}
@keyframes fadeUp{from{opacity:0;transform:translateY(22px)}to{opacity:1;transform:none}}

.mark-stage{
  position:absolute;z-index:2;right:5vw;top:50%;translate:0 -50%;
  width:clamp(190px,29vw,480px);aspect-ratio:1;perspective:1200px;pointer-events:none;
  opacity:0;transition:opacity .8s var(--ease-o);
}
.mark-stage.lit{opacity:1}
.mark-3d{
  position:relative;width:100%;height:100%;transform-style:preserve-3d;
  transform:rotateX(var(--mx,0deg)) rotateY(var(--my,0deg));
  transition:transform .6s var(--ease-o);will-change:transform;
}
.mark-3d img{
  width:100%;height:100%;object-fit:contain;
  filter:drop-shadow(0 34px 70px rgba(0,0,0,.66)) drop-shadow(0 0 54px rgba(212,175,55,.22));
}
.mark-3d .sheen{
  position:absolute;inset:0;
  -webkit-mask:url("../img/foxhead-gold.webp") center/contain no-repeat;
          mask:url("../img/foxhead-gold.webp") center/contain no-repeat;
  background:linear-gradient(105deg,transparent 33%,rgba(255,248,222,.9) 48%,transparent 63%);
  background-size:280% 100%;animation:sweep 7s var(--ease) infinite;
  mix-blend-mode:screen;opacity:.72;
}
@keyframes sweep{0%,60%{background-position:172% 0}100%{background-position:-72% 0}}

.skip-hero{
  position:absolute;right:var(--gut);bottom:2.2rem;z-index:4;
  font-family:var(--sans);
  font-size:.64rem;letter-spacing:.28em;text-transform:uppercase;font-weight:700;
  color:var(--on-dark-mute);background:none;border:0;cursor:pointer;padding:.6rem 0;
  display:flex;align-items:center;gap:.85rem;transition:color .3s var(--ease);
}
.skip-hero:hover{color:var(--gold)}
.skip-hero::after{content:"";width:40px;height:1px;background:currentColor;transition:width .4s var(--ease-o);order:-1}
.skip-hero:hover::after{width:60px}

@media (max-width:900px){
  .mark-stage{right:50%;translate:50% -50%;top:84%;width:min(190px,42vw);opacity:.12}
  .mark-stage.lit{opacity:.17}
  .hero-inner{justify-content:flex-end;padding-bottom:6.5rem}
}

/* ---------- statement ---------- */
.big{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(2.1rem,4.8vw,4rem);line-height:1.1;letter-spacing:-.012em;
  color:#fff;text-wrap:balance;max-width:20ch;
}
.statement .sub{margin-top:1.5rem;max-width:56ch;color:var(--on-dark-dim);font-size:1.08rem}

/* ---------- the name behind the firm ---------- */
.name-sec{position:relative;overflow:hidden}
.name-mark{
  position:absolute;right:-6%;top:50%;translate:0 -50%;
  width:min(46vw,620px);opacity:.055;pointer-events:none;z-index:0;
  filter:grayscale(.15);
}
.name-grid{
  display:grid;grid-template-columns:1.25fr .95fr;gap:clamp(2.25rem,5vw,4.5rem);
  align-items:start;margin-top:clamp(1.35rem,2.6vw,2.1rem);
}
.name-grid .prose p{font-size:1.14rem;line-height:1.8}
.triad{list-style:none;padding:0;margin:0;display:grid;gap:0;border-top:1px solid var(--hair)}
.triad li{
  display:grid;grid-template-columns:auto 1fr;gap:1.3rem;align-items:baseline;
  padding-block:.95rem;border-bottom:1px solid var(--hair-soft);
}
/* smallest serif on the site, italic, gold on dark. weight 400 left the
   hairlines too thin to survive light-on-dark halation, so it takes 600. */
.triad .t-n{
  font-family:var(--serif);font-style:italic;font-weight:600;font-size:1.18rem;
  color:var(--gold);width:2.1rem;letter-spacing:.06em;
}
.triad .t-t{
  font-family:var(--serif);font-weight:600;font-size:clamp(1.4rem,2.4vw,2.05rem);
  line-height:1.15;color:#fff;letter-spacing:-.008em;
}
.name-close{
  margin-top:clamp(1.5rem,2.8vw,2.25rem);font-family:var(--serif);font-weight:600;
  font-size:clamp(1.5rem,3.2vw,2.6rem);line-height:1.24;letter-spacing:-.01em;
  color:var(--on-dark-dim);max-width:38ch;
  /* the grid above runs prose left, triad right. this closes on the right so
     the eye keeps travelling instead of snapping back to the gutter. */
  margin-left:auto;text-align:right;
}
@media (max-width:860px){.name-close{margin-left:0;text-align:left;max-width:none}}
.name-close em{font-style:normal;color:var(--gold-lt);display:block;margin-top:.4rem}
@media (max-width:860px){
  .name-grid{grid-template-columns:1fr;gap:2rem}
  .name-mark{opacity:.04;width:70vw;right:-18%}
}

/* ---------- method: offset editorial grid ---------- */
.principles{margin-top:clamp(1.4rem,2.6vw,2.1rem);border-top:1px solid var(--hair-soft)}
.principle{
  display:grid;grid-template-columns:minmax(90px,.5fr) 1.15fr 1.35fr;
  gap:clamp(1.5rem,4vw,4rem);align-items:start;
  padding-block:clamp(1.15rem,2vw,1.7rem);border-bottom:1px solid var(--hair-soft);
  transition:background .5s var(--ease);
}
.principle:hover{background:rgba(212,175,55,.028)}
.principle .n{
  font-family:var(--serif);font-weight:700;font-size:clamp(1.6rem,2.6vw,2.6rem);
  line-height:1;color:transparent;-webkit-text-stroke:1px rgba(212,175,55,.55);
  font-variant-numeric:tabular-nums;transition:color .5s var(--ease);
}
.principle:hover .n{color:rgba(212,175,55,.2)}
.principle h3{
  font-family:var(--serif);font-weight:600;font-size:clamp(1.2rem,1.9vw,1.55rem);
  line-height:1.2;color:#fff;letter-spacing:-.012em;
}
.principle p{color:var(--on-dark-dim);font-size:1rem;line-height:1.65}
@media (max-width:880px){
  .principle{grid-template-columns:auto 1fr;gap:1.1rem 1.4rem}
  .principle p{grid-column:2}
}

/* ---------- engagements: editorial list, no cards ---------- */
.group-label{
  display:flex;align-items:center;gap:1.4rem;margin:clamp(1.5rem,2.8vw,2.3rem) 0 0;
  font-family:var(--serif);font-size:clamp(1.7rem,3.3vw,2.7rem);font-weight:600;letter-spacing:.02em;color:var(--gold-lt);
}
.group-label::after{content:"";flex:1;height:1px;background:var(--hair)}
.eng{border-bottom:1px solid var(--hair-soft)}
.eng-item{
  display:grid;/* fixed, not auto: an auto track sizes to each card's own label, so a
     longer spec squeezed the fr columns and every card started its copy at
     a different place. widest label here is 31 characters. */
  grid-template-columns:1.1fr 1.5fr 17rem;gap:clamp(1.2rem,3.5vw,3.5rem);
  align-items:start;padding-block:clamp(1.1rem,1.85vw,1.55rem);
  border-top:1px solid var(--hair-soft);position:relative;
}
/* optical top-align: nudge the smaller text down to the heading's cap line */
.eng-item p,.eng-item .spec{padding-top:.42em}
.eng-item::after{
  content:"";position:absolute;left:0;top:-1px;width:100%;height:1px;
  background:var(--gold);transform:scaleX(0);transform-origin:left;
  transition:transform .7s var(--ease-o);
}
.eng-item:hover::after{transform:scaleX(1)}
.eng-item h3{
  font-family:var(--serif);font-weight:600;font-size:clamp(1.5rem,2.6vw,2.2rem);
  line-height:1.12;color:#fff;letter-spacing:-.008em;transition:color .4s var(--ease);
}
.eng-item:hover h3{color:var(--gold-lt)}
.eng-item p{color:var(--on-dark-dim);font-size:1rem;line-height:1.65}
.eng-item .spec{
  font-size:.68rem;letter-spacing:.17em;text-transform:uppercase;font-weight:700;
  color:var(--gold);white-space:nowrap;text-align:right;line-height:1.9;
}
@media (max-width:920px){
  .eng-item{grid-template-columns:1fr;gap:.8rem}
  .eng-item .spec{text-align:left;white-space:normal}
}
.qualifier{margin-top:clamp(1.35rem,2.4vw,2.1rem);color:var(--on-dark-mute);font-size:1rem;max-width:64ch}

/* ---------- fit ---------- */
.fit{display:grid;grid-template-columns:repeat(auto-fit,minmax(min(320px,100%),1fr));gap:clamp(2.25rem,5vw,4.5rem);margin-top:clamp(1.25rem,2.4vw,1.9rem)}
.fit h3{font-family:var(--serif);font-size:clamp(1.2rem,1.9vw,1.55rem);font-weight:600;margin-bottom:1.8rem;color:#fff}
.fit ul{list-style:none;display:grid;gap:1.15rem;padding:0}
.fit li{display:grid;grid-template-columns:auto 1fr;gap:1.1rem;align-items:baseline;color:var(--on-dark-dim);line-height:1.55}
.fit li::before{content:"";width:16px;height:1px;background:var(--gold);translate:0 -.35em}
.fit .no li::before{background:rgba(163,149,188,.5)}

/* ---------- FAQ ---------- */
.faq{margin-top:clamp(1.25rem,2.4vw,1.9rem);border-top:1px solid var(--hair-soft)}
.faq details{border-bottom:1px solid var(--hair-soft)}
.faq summary{
  list-style:none;cursor:pointer;padding:1.35rem 3.5rem 1.35rem 0;position:relative;
  font-family:var(--serif);font-weight:600;font-size:clamp(1.18rem,1.75vw,1.5rem);
  line-height:1.35;color:#fff;transition:color .3s var(--ease);
}
.faq summary::-webkit-details-marker{display:none}
.faq summary:hover{color:var(--gold-lt)}
.faq summary::after{
  content:"";position:absolute;right:.4rem;top:50%;width:14px;height:14px;translate:0 -50%;
  transition:transform .4s var(--ease-o);
  background:
    linear-gradient(var(--gold),var(--gold)) center/14px 1.5px no-repeat,
    linear-gradient(var(--gold),var(--gold)) center/1.5px 14px no-repeat;
}
.faq details[open] summary::after{transform:rotate(90deg);background:linear-gradient(var(--gold),var(--gold)) center/14px 1.5px no-repeat}
.faq .ans{overflow:hidden}
.faq .ans p{padding:0 clamp(1rem,10vw,8rem) 1.9rem 0;color:var(--on-dark-dim);max-width:76ch}

/* ---------- three doors into the firm ---------- */
.doors{
  list-style:none;padding:0;margin:clamp(1.6rem,3vw,2.4rem) 0 0;
  display:grid;gap:0;border-top:1px solid var(--hair);
}
.doors li{border-bottom:1px solid var(--hair-soft)}
.doors a{
  /* full page width now, so the heading gets a proper rail and the copy is
     capped rather than running the whole way to the gutter */
  display:grid;grid-template-columns:minmax(0,.58fr) minmax(0,1fr);
  gap:clamp(1rem,4vw,3.5rem);align-items:baseline;
  padding-block:clamp(1.2rem,2.3vw,1.9rem);position:relative;
  transition:color .35s var(--ease);
}
.doors b{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(1.45rem,2.6vw,2.15rem);line-height:1.12;
  color:#fff;letter-spacing:-.008em;transition:color .35s var(--ease);
}
/* non-breaking space binds the arrow to the last word so it cannot orphan
   onto a line of its own when the heading wraps */
.doors b::after{content:"\00A0\2197";font-family:var(--sans);font-size:.62em;color:var(--gold)}
.doors span{color:var(--on-dark-dim);font-size:1.02rem;line-height:1.65;max-width:58ch}
.doors a::before{
  content:"";position:absolute;left:0;bottom:-1px;width:100%;height:1px;
  background:var(--gold);transform:scaleX(0);transform-origin:left;
  transition:transform .6s var(--ease-o);
}
.doors a:hover b{color:var(--gold-lt)}
.doors a:hover::before{transform:scaleX(1)}
@media (max-width:720px){
  .doors a{grid-template-columns:1fr;gap:.5rem}
}

/* ---------- intake panel ----------
   Opens from a door. No bubble following the page down, because the first
   thing a visitor meets should be the writing, not a robot asking if they
   need help. */
.ik{position:fixed;inset:0;z-index:200;display:grid;place-items:center;padding:clamp(.75rem,3vw,2rem)}
.ik[hidden]{display:none}
.ik-scrim{position:absolute;inset:0;background:rgba(12,5,24,.86);backdrop-filter:blur(6px)}
.ik-box{
  position:relative;width:min(680px,100%);max-height:min(88vh,860px);overflow:hidden;
  display:flex;flex-direction:column;
  background:linear-gradient(168deg,var(--purple-raised),var(--purple-deep));
  border:1px solid var(--hair);box-shadow:0 40px 120px rgba(0,0,0,.6);
}
.ik-head{
  display:flex;align-items:flex-start;justify-content:space-between;gap:1rem;
  padding:clamp(1.1rem,2.6vw,1.7rem);border-bottom:1px solid var(--hair-soft);
}
.ik-tier{
  display:inline-block;font-size:.58rem;letter-spacing:.24em;text-transform:uppercase;
  font-weight:700;color:var(--gold);border:1px solid rgba(212,175,55,.4);
  padding:.3rem .6rem;
}
.ik-title{
  font-family:var(--serif);font-weight:600;font-size:clamp(1.5rem,3vw,2rem);
  color:#fff;line-height:1.1;margin-top:.7rem;letter-spacing:-.01em;
}
.ik-x{
  background:none;border:0;color:var(--on-dark-dim);font-size:1.8rem;line-height:1;
  cursor:pointer;padding:.2rem .5rem;transition:color .3s var(--ease);
}
.ik-x:hover{color:var(--gold-lt)}
.ik-rules{
  padding:clamp(.9rem,2.2vw,1.3rem) clamp(1.1rem,2.6vw,1.7rem);
  border-bottom:1px solid var(--hair-soft);background:rgba(12,5,24,.35);
}
.ik-rules p{font-size:.9rem;line-height:1.55;color:var(--on-dark-dim);margin-top:.5rem}
.ik-rules p:first-child{margin-top:0}
.ik-rules b{color:var(--gold-lt);font-weight:600}
/* The box is height capped, so every band around the transcript must refuse
   to grow and the transcript itself must be allowed to shrink. Without this
   the chooser, the explainer and the pivot bar together push the input field
   out through the bottom of the panel. */
.ik-head,.ik-rules,.ik-pivot,.ik-form,.ik-status{flex:none}
.ik-choose{flex:0 1 auto;overflow-y:auto}
.ik-log{
  flex:1 1 auto;overflow-y:auto;padding:clamp(1rem,2.6vw,1.6rem);
  display:flex;flex-direction:column;gap:1.2rem;min-height:120px;
}
.ik-msg{display:flex;flex-direction:column;gap:.35rem}
.ik-who{
  font-size:.56rem;letter-spacing:.24em;text-transform:uppercase;font-weight:700;
  color:var(--on-dark-mute);
}
.ik-msg p{font-size:1rem;line-height:1.62;color:var(--on-dark);white-space:pre-wrap}
.ik-link{
  color:var(--gold-lt);text-decoration:underline;
  text-underline-offset:.18em;word-break:break-all;
}
.ik-link:hover{color:var(--gold)}
.ik-you .ik-who{color:var(--gold)}
.ik-you p{color:var(--on-dark-dim)}
.ik-note{
  font-size:.82rem;line-height:1.5;color:var(--gold);
  border-left:2px solid rgba(240,160,58,.5);padding-left:.8rem;
}
.ik-form{
  display:flex;gap:.7rem;align-items:flex-end;
  padding:clamp(.8rem,2.2vw,1.2rem) clamp(1.1rem,2.6vw,1.7rem);
  border-top:1px solid var(--hair-soft);
}
.ik-form textarea{
  flex:1;resize:none;background:rgba(12,5,24,.6);border:1px solid var(--hair);
  color:var(--on-dark);font-family:var(--sans);font-size:1rem;line-height:1.5;
  padding:.7rem .85rem;max-height:140px;
}
.ik-form textarea:focus{outline:none;border-color:var(--gold)}
.ik-send{
  background:var(--amber);color:#fff;border:0;cursor:pointer;
  font-family:var(--sans);font-weight:700;font-size:.76rem;letter-spacing:.14em;
  text-transform:uppercase;padding:.85em 1.5em;transition:background .3s var(--ease)}
.ik-send:hover:not(:disabled){background:var(--gold);color:var(--purple-deep)}
.ik-send:disabled{opacity:.45;cursor:default}
.ik-status{
  min-height:1.1rem;padding:0 clamp(1.1rem,2.6vw,1.7rem) .9rem;
  font-size:.68rem;letter-spacing:.2em;text-transform:uppercase;
  font-weight:700;color:var(--on-dark-mute);
}
.ik-sr{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0 0 0 0)}

/* An explicit display on an element beats the user agent [hidden] rule, so
   .ik-choose and .ik-pivot stayed on screen when the script hid them. Scoped
   to the panel rather than set globally. */
/* Legal links sit on the footer base line, between the copyright and the
   tagline, which is where people look for them. */
.foot-legal{display:inline-flex;gap:1.1rem}
.foot-legal a{color:var(--on-dark-mute);transition:color .3s var(--ease)}
.foot-legal a:hover{color:var(--gold-lt)}

.ik [hidden]{display:none !important}

/* ---------- intake: dictation ---------- */
/* Sits between the field and Send. Hidden entirely where the browser has no
   speech API, so nobody is offered a control that cannot work. */
.ik-mic{
  display:inline-flex;align-items:center;justify-content:center;
  width:2.6rem;flex:none;cursor:pointer;
  background:none;border:1px solid var(--hair);border-radius:.4rem;
  color:var(--on-dark-mute);
  transition:color .3s var(--ease),border-color .3s var(--ease),background .3s var(--ease);
}
.ik-mic:hover{color:var(--gold-lt);border-color:rgba(212,175,55,.5)}
.ik-mic-live{color:var(--purple-deep);background:var(--gold);border-color:var(--gold)}
/* A steady pulse while it is listening, because a microphone that looks the
   same on and off is how people talk to a control that is not recording. */
.ik-mic-live svg{animation:ikMic 1.4s var(--ease) infinite}
@keyframes ikMic{0%,100%{opacity:1}50%{opacity:.45}}
@media (prefers-reduced-motion:reduce){
  .ik-mic-live svg{animation:none}
}

/* ---------- intake: chooser ---------- */
.ik-choose{padding:clamp(1.1rem,2.6vw,1.7rem);display:flex;flex-direction:column;gap:.85rem}
.ik-choose-lede{font-size:.72rem;letter-spacing:.22em;text-transform:uppercase;
  font-weight:700;color:var(--on-dark-mute)}
.ik-pick{
  display:block;width:100%;text-align:left;cursor:pointer;
  padding:1rem 1.15rem;border-radius:.55rem;
  border:1px solid rgba(212,175,55,.28);background:rgba(255,255,255,.028);
  transition:border-color .3s var(--ease),background .3s var(--ease),transform .3s var(--ease);
}
.ik-pick:hover{border-color:var(--gold);background:rgba(212,175,55,.08);transform:translateY(-2px)}
.ik-pick b{display:block;font-family:var(--serif);font-weight:600;
  font-size:1.3rem;color:#fff;margin-bottom:.3rem}
.ik-pick em{display:block;font-style:normal;font-size:.92rem;line-height:1.55;
  color:var(--on-dark-dim)}
/* Intake is the path the firm wants people on, so it carries the weight. */
.ik-pick-main{border-color:rgba(212,175,55,.5);background:rgba(212,175,55,.06)}
.ik-pick-main b{color:var(--gold-lt)}
.ik-choose-note{font-size:.86rem;line-height:1.6;color:var(--on-dark-mute);
  border-top:1px solid var(--hair-soft);padding-top:.85rem;margin-top:.2rem}
.ik-choose-note b{color:var(--gold-lt);font-weight:600}

/* ---------- intake: collapsible explainer ---------- */
/* Open on arrival, collapsed the moment the conversation starts, because after
   the first exchange it is a wall of text sitting on top of the thing being read. */
.ik-rules-toggle{
  display:block;width:100%;text-align:left;cursor:pointer;background:none;border:0;
  padding:.7rem clamp(1.1rem,2.6vw,1.7rem);
  font-size:.66rem;letter-spacing:.22em;text-transform:uppercase;font-weight:700;
  color:var(--on-dark-mute);transition:color .3s var(--ease);
}
.ik-rules-toggle:hover{color:var(--gold-lt)}
.ik-rules-toggle::after{content:" +";color:var(--gold)}
.ik-rules-open .ik-rules-toggle::after{content:" -"}
.ik-rules .ik-rules-body{display:none}
.ik-rules-open .ik-rules-body{display:block}

/* ---------- intake: message sides ---------- */
/* The agent runs long, three paragraphs at a time, so it is not bubbled. It sits
   on the panel ground at full measure. The visitor is bubbled and pushed right,
   which is what actually separates the two voices. */
.ik-msg{max-width:100%}
.ik-msg.ik-you{align-items:flex-end;margin-left:auto;max-width:82%}
.ik-you .ik-who{text-align:right}
.ik-you p{
  background:rgba(212,175,55,.11);border:1px solid rgba(212,175,55,.24);
  border-radius:.7rem .7rem .18rem .7rem;padding:.7rem .9rem;
  color:var(--on-dark);text-align:left;
}
.ik-bot p{padding-right:.4rem}

/* ---------- intake: pivot bar ---------- */
.ik-pivot{
  display:flex;align-items:center;justify-content:space-between;gap:1rem;
  padding:.7rem clamp(1.1rem,2.6vw,1.7rem);
  border-top:1px solid var(--hair-soft);background:rgba(212,175,55,.05);
}
.ik-pivot span{font-size:.85rem;color:var(--on-dark-dim)}
.ik-pivot-go{
  cursor:pointer;background:none;border:1px solid rgba(212,175,55,.45);
  border-radius:.4rem;padding:.42rem .8rem;
  font-size:.66rem;letter-spacing:.16em;text-transform:uppercase;font-weight:700;
  color:var(--gold-lt);transition:background .3s var(--ease),color .3s var(--ease);
}
.ik-pivot-go:hover{background:var(--gold);color:var(--purple-deep)}

/* Chat thinking indicator. Three dots on a staggered pulse, in the brand gold,
   sized off the status row rather than the tiny .68rem label type so they stay
   legible. The animation is decorative: the accompanying screen reader text is
   what actually reports the state. */
.ik-status .ik-dots{display:inline-flex;align-items:center;gap:.34rem;height:1.1rem}
.ik-status .ik-dots i{
  width:.4rem;height:.4rem;border-radius:50%;background:var(--gold);
  opacity:.3;animation:ikThink 1.15s var(--ease) infinite;
}
.ik-status .ik-dots i:nth-child(2){animation-delay:.15s}
.ik-status .ik-dots i:nth-child(3){animation-delay:.3s}
@keyframes ikThink{
  0%,68%,100%{opacity:.3;transform:translateY(0) scale(1)}
  34%{opacity:1;transform:translateY(-.2rem) scale(1.18)}
}

/* With motion suppressed the dots convey nothing, so fall back to the word
   they replaced rather than leaving three static specks on the panel. */
@media (prefers-reduced-motion:reduce){
  .ik-status .ik-dots{display:none}
  .ik-status .ik-sr{position:static;width:auto;height:auto;overflow:visible;clip:auto}
}
@media (prefers-reduced-motion:reduce){.ik-scrim{backdrop-filter:none}}

/* ---------- closer ---------- */
.closer{
  margin-top:clamp(1.9rem,3.6vw,3rem);text-align:right;font-family:var(--serif);
  font-style:italic;font-weight:600;color:var(--gold-lt);
  font-size:clamp(1.25rem,2vw,1.7rem);line-height:1.5;max-width:50ch;margin-left:auto;
}

/* ---------- gallery strip ---------- */
.gallery{
  display:grid;grid-auto-flow:column;grid-auto-columns:minmax(240px,1fr);
  gap:1px;background:var(--hair-soft);margin-top:clamp(1.25rem,2.4vw,1.9rem);
  border-block:1px solid var(--hair-soft);
}
.tile{position:relative;display:block;aspect-ratio:3/4;overflow:hidden;background:var(--purple-deep)}
.tile img{width:100%;height:100%;object-fit:cover;opacity:.72;
  transform:scale(1.04);transition:transform 1.1s var(--ease-o),opacity .6s var(--ease)}
.tile::after{
  content:"";position:absolute;inset:0;
  background:linear-gradient(180deg,rgba(12,5,24,.2) 0%,transparent 40%,rgba(12,5,24,.94) 100%);
}
.tile:hover img{transform:scale(1);opacity:.9}
.tile-c{
  position:absolute;left:0;right:0;bottom:0;z-index:2;padding:1.5rem 1.4rem;
  display:flex;flex-direction:column;gap:.5rem;
}
.tile-c b{font-family:var(--serif);font-size:1.2rem;font-weight:600;color:#fff;line-height:1.25}
.tile-c i{font-style:normal;font-size:.6rem;letter-spacing:.22em;text-transform:uppercase;color:var(--gold);font-weight:700}
@media (max-width:1080px){
  .gallery{grid-auto-flow:row;grid-template-columns:repeat(auto-fit,minmax(min(220px,100%),1fr));grid-auto-columns:auto}
  .tile{aspect-ratio:4/3}
}

/* ---------- CTA film ---------- */
.cta-film{position:relative;overflow:hidden;min-height:clamp(430px,62vh,660px);display:flex;align-items:center}
.cta-media{position:absolute;inset:0;z-index:0}
.cta-media video,.cta-media img{width:100%;height:100%;object-fit:cover;opacity:.62}
.cta-media::after{
  content:"";position:absolute;inset:0;
  background:
    linear-gradient(180deg,rgba(12,5,24,.9) 0%,rgba(12,5,24,.6) 45%,rgba(12,5,24,.95) 100%),
    linear-gradient(90deg,rgba(12,5,24,.9) 0%,rgba(12,5,24,.25) 65%);
}

/* ---------- cinematic panels (Built) ---------- */
.film{position:relative;min-height:clamp(470px,68vh,700px);display:flex;align-items:flex-end;overflow:hidden}
.film + .film{border-top:1px solid var(--hair-soft)}
.film-bg{position:absolute;inset:0;z-index:0;will-change:transform}
/* over-scanned so the parallax drift never exposes an edge */
.film-bg img{width:100%;height:100%;object-fit:cover;transform:scale(1.16);transition:transform 1.4s var(--ease-o)}
.film:hover .film-bg img{transform:scale(1.09)}
.film-bg::after{
  content:"";position:absolute;inset:0;
  background:
    linear-gradient(180deg, rgba(12,5,24,.72) 0%, rgba(12,5,24,.24) 34%, rgba(12,5,24,.92) 100%),
    linear-gradient(90deg, rgba(12,5,24,.86) 0%, transparent 62%);
}
.film.right .film-bg::after{
  background:
    linear-gradient(180deg, rgba(12,5,24,.72) 0%, rgba(12,5,24,.24) 34%, rgba(12,5,24,.92) 100%),
    linear-gradient(270deg, rgba(12,5,24,.86) 0%, transparent 62%);
}
.film-copy{position:relative;z-index:2;width:min(var(--wrap),100% - var(--gut)*2);margin-inline:auto;padding-block:clamp(3rem,7vw,5.5rem)}
.film-copy .inner{max-width:52ch}

/* a work item that carries a film of its own. the video is typographic, so it
   gets its own frame rather than being dimmed behind the copy. */
/* Media is a supporting element, not the subject. The copy column takes the
   room; the media column sizes to its own capped width and sits on the outer
   edge. Anyone who wants it larger uses the player's own fullscreen control. */
.film.has-media .film-copy{
  display:grid;grid-template-columns:minmax(0,1fr) auto;
  gap:clamp(1.5rem,4vw,3.5rem);align-items:center;
}
.film.right.has-media .film-copy{grid-template-columns:auto minmax(0,1fr)}
.film.has-media .film-copy .inner{max-width:54ch}
.film-media{margin:0}
.film-media img{width:100%;height:auto;display:block}
/* a device illustration carries its own frame, so it gets no border of ours */
.film-media.device img{filter:drop-shadow(0 26px 60px rgba(0,0,0,.5))}
/* a diagram is a flat panel, so it takes the same hairline the video frames use */
.film-media.diagram img{border:1px solid var(--hair);box-shadow:0 26px 60px rgba(0,0,0,.45)}
/* the framework panel is portrait, so it is capped nearer the vertical film */
.film-media.diagram{width:440px}

/* a second subject inside one work item: large enough to read as its own
   heading, a shade under the item title so the section still has one lead */
.film .sub-h{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(1.85rem,4.1vw,3.3rem);line-height:1.05;letter-spacing:-.012em;
  color:#fff;margin-top:clamp(2rem,3.6vw,2.9rem);
  padding-top:clamp(1.4rem,2.6vw,2rem);border-top:1px solid var(--hair);
}
.film.right .sub-h{text-align:right}
/* on a right-aligned item the media belongs on the outside, opposite the copy */
.film.right.has-media .film-copy .inner{order:2}
.film.right.has-media .film-media{order:1}
.film.right .film-media figcaption{justify-content:flex-end}
.film.right .film-media figcaption::before{order:2}
.film-media video{
  width:100%;aspect-ratio:16/9;display:block;background:var(--purple-deep);
  border:1px solid var(--hair);box-shadow:0 30px 80px rgba(0,0,0,.5);
}
/* a 9:16 film would be over 1000px tall in a half-width column, so it is
   capped to read as a phone rather than a billboard.
   NOTE: not `.portrait` - that class is the founder headshot frame and carries
   its own padding, border and 4:5 ratio. */
/* Sized to sit level with the copy column, which resolves to about 456px at
   54ch. Bigger than this and the media takes over the section; much smaller
   and it reads as an afterthought floating in the margin. */
/* explicit width, not max-width: the media sits in an `auto` grid track, and a
   track cannot size itself from a child whose width is a percentage. max-width
   alone left the column to collapse to min-content. */
.film-media{width:520px;max-width:100%}
.film-media.device{width:542px}
.film-media.tall{width:285px}
.film-media.tall video{aspect-ratio:9/16}
.film-media figcaption{
  margin-top:.85rem;font-size:.66rem;letter-spacing:.22em;text-transform:uppercase;
  font-weight:700;color:var(--gold);display:flex;align-items:center;gap:.8rem;
}
.film-media figcaption::before{content:"";width:26px;height:1px;background:var(--gold)}

/* live link out to the product itself */
.film-link{
  display:inline-flex;align-items:center;gap:.6em;margin-top:1.5rem;
  font-size:.72rem;letter-spacing:.18em;text-transform:uppercase;font-weight:700;
  color:var(--gold-lt);border-bottom:1px solid rgba(212,175,55,.4);padding-bottom:.35rem;
  transition:color .3s var(--ease),border-color .3s var(--ease),gap .3s var(--ease-o);
}
.film-link::after{content:"\2197";font-size:1.05em;line-height:1}
.film-link:hover{color:#fff;border-color:var(--gold);gap:.95em}
.film.right .film-copy .inner .film-link{margin-left:auto}

/* small, quiet escape hatch for the still image, which has no player controls */
.media-full{
  display:inline-block;margin-top:.55rem;font-size:.6rem;letter-spacing:.18em;
  text-transform:uppercase;font-weight:700;color:var(--on-dark-mute);
  border-bottom:1px solid rgba(212,175,55,.28);padding-bottom:.2rem;
  transition:color .3s var(--ease),border-color .3s var(--ease);
}
.media-full:hover{color:var(--gold-lt);border-color:var(--gold)}

/* side by side holds much further down now that the media is small */
@media (max-width:760px){
  /* minmax(0,1fr), not 1fr: a bare 1fr keeps min-width:auto and will not
     shrink below the media's fixed width, pushing it off the screen */
  .film.has-media .film-copy,
  .film.right.has-media .film-copy{grid-template-columns:minmax(0,1fr);gap:1.6rem}
  .film-media,.film-media.device,.film-media.tall{width:100%;max-width:100%}
  .film-media.tall{max-width:285px}
  /* stacked, every item reads copy first, so the right-aligned one falls back in line */
  .film.right.has-media .film-copy .inner{order:1}
  .film.right.has-media .film-media{order:2}
  .film.right .film-media figcaption{justify-content:flex-start}
  .film.right .film-media figcaption::before{order:0}
}
.film.right .film-copy .inner{margin-left:auto;text-align:right}
.film.right .film-copy .eyebrow{justify-content:flex-end}
.film.right .film-copy .eyebrow::before{display:none}
.film.right .film-copy .eyebrow::after{content:"";width:38px;height:1px;background:linear-gradient(270deg,var(--gold),transparent)}
.film h2{
  font-family:var(--serif);font-weight:600;font-size:clamp(2.2rem,5vw,4.2rem);
  line-height:1.0;letter-spacing:-.014em;color:#fff;margin:1.5rem 0 .8rem;
}
.film .what{font-size:clamp(1.18rem,1.7vw,1.45rem);color:var(--gold-lt);font-family:var(--serif);font-weight:600}
.film .body{color:var(--on-dark-dim);margin-top:1.3rem;line-height:1.7}
.film .spec{
  margin-top:2rem;padding-top:1.1rem;border-top:1px solid var(--hair);
  font-size:.68rem;letter-spacing:.18em;text-transform:uppercase;font-weight:700;color:var(--gold);
  display:flex;flex-wrap:wrap;gap:.5rem 2rem;
}
.film.right .spec{justify-content:flex-end}
/* "Waitlist open" is a claim that invites an action, so it has to be one.
   Neither product site captures a list yet, so this routes to the inbox. */
.spec a{
  color:var(--gold-lt);border-bottom:1px solid rgba(212,175,55,.45);
  padding-bottom:.15rem;transition:color .3s var(--ease),border-color .3s var(--ease);
}
.spec a:hover{color:#fff;border-color:var(--gold)}
@media (max-width:820px){
  .film-copy .inner,.film.right .film-copy .inner{max-width:none;text-align:left;margin-left:0}
  .film.right .spec{justify-content:flex-start}
  .film.right .film-copy .eyebrow{justify-content:flex-start}
  .film.right .film-copy .eyebrow::after{display:none}
  .film.right .film-copy .eyebrow::before{display:block}
  .film-bg::after,.film.right .film-bg::after{
    background:linear-gradient(180deg, rgba(12,5,24,.68) 0%, rgba(12,5,24,.42) 30%, rgba(12,5,24,.95) 100%);
  }
}

/* ---------- founder ---------- */
/* Interior page hero. Centred on purpose: with only a heading and one line
   under it, the split grid leaves a wide gap and reads unbalanced. Top padding
   matches .founder-head so it clears the fixed header. */
.page-head{
  padding-top:clamp(8rem,13vw,11rem);padding-bottom:clamp(3rem,6vw,5rem);
  text-align:center;max-width:62rem;margin-inline:auto;
}
.page-head .eyebrow{display:block}
.page-head h1{margin-top:1.1rem}
.page-head .lede{margin-inline:auto;max-width:44rem}
.page-head .btn-row{justify-content:center}

.founder-head{
  display:grid;grid-template-columns:.78fr 1.22fr;gap:clamp(2.5rem,6vw,5.5rem);align-items:center;
  padding-top:clamp(8rem,13vw,11rem);padding-bottom:clamp(3.5rem,7vw,6rem);
}
/* A vertical gold rule that passes behind the subject. It starts above the
   frame and ends below it, so both ends are off-image and the line reads as
   continuous, interrupted only by her. */
.portrait::before{
  content:"";position:absolute;z-index:-1;pointer-events:none;
  left:54%;top:-12%;bottom:-18%;width:1px;
  background:linear-gradient(to bottom,
    rgba(212,175,55,0) 0%, rgba(212,175,55,.55) 14%,
    rgba(212,175,55,.55) 82%, rgba(212,175,55,0) 100%);
}

.portrait{
  aspect-ratio:4/5;position:relative;
  /* no box, no border. the frame is a separate offset element and the image
     dissolves into the page at the bottom, so there is no hard rectangle. */
  isolation:isolate;
}
.portrait img,.portrait picture{
  position:absolute;inset:0;width:100%;height:100%;object-fit:cover;display:block;z-index:1;
  filter:saturate(1.04) contrast(1.02);
}
/* One mask layer, no compositing, and only where support is certain. If the
   browser cannot do it the photograph simply renders square, which is the
   correct failure. */
@supports (mask-image: linear-gradient(#000, #000)) or (-webkit-mask-image: linear-gradient(#000, #000)){
  .portrait img,.portrait picture{
    -webkit-mask-image:linear-gradient(200deg,#000 62%,rgba(0,0,0,.45) 86%,transparent 100%);
    mask-image:linear-gradient(200deg,#000 62%,rgba(0,0,0,.45) 86%,transparent 100%);
  }
}
.portrait .ph{font-size:.66rem;letter-spacing:.26em;text-transform:uppercase;color:var(--gold);font-weight:700;line-height:2.2}
.portrait::after{
  content:"";position:absolute;inset:0;pointer-events:none;z-index:2;
  background:linear-gradient(180deg,rgba(12,5,24,0) 55%,rgba(12,5,24,.35) 100%);
}
/* Opt back in to top alignment where the right column is long enough that
   the sticky heading has real travel. */
.split.split-top{align-items:start}
/* the heading holds its place while the copy beside it scrolls */
.split-side{position:sticky;top:7rem}
.split-side .sec-h,
.split-side .pull,
.split-side .big,
.split-side .hero-h{max-width:none}
.split-side .eyebrow + .sec-h,
.split-side .eyebrow + .pull,
.split-side .eyebrow + .big,
.split-side .eyebrow + .hero-h{margin-top:1.3rem}
.split-side .ghost-n{display:block;margin-top:clamp(1.1rem,2.4vw,1.9rem)}
/* two classes, declared after the section rules, so a page-level cap like
   `.statement .sub{max-width:56ch}` cannot re-narrow a column it now owns */
.split .split-main > *{max-width:none}
.split-main > *:first-child{margin-top:0}
.split-main .lede{margin-top:.5rem}

/* .hero-h runs a line-height of .88, shorter than its own font size, so a
   paragraph set directly beneath it collides with the descenders. Everywhere
   else the hero and its lede sit in separate grid columns; the services hero
   stacks them, so it needs the space put back. */
.hero-h + .lede{margin-top:clamp(1rem,2vw,1.6rem)}
.split-main .btn-row{margin-top:clamp(1.6rem,3vw,2.2rem)}

@media (max-width:900px){
  .split-side{position:static}
  .split-side .ghost-n{display:none}
  .split-main .lede{margin-top:0}
}
/* sticky needs a normal flow; reduced motion users get the plain stack */
@media (prefers-reduced-motion:reduce){.split-side{position:static}}
/* real numbers only. every figure here is on the resume. */
.stats{
  list-style:none;padding:0;display:grid;gap:0;
  grid-template-columns:repeat(auto-fit,minmax(min(180px,100%),1fr));
  margin-top:clamp(1.8rem,3.4vw,2.75rem);border-top:1px solid var(--hair);
}
.stats li{
  padding:1.4rem 1.4rem 1.4rem 0;border-bottom:1px solid var(--hair-soft);
  display:flex;flex-direction:column;gap:.5rem;
}
.stats b{
  font-family:var(--serif);font-weight:600;font-size:clamp(2.2rem,3.6vw,3.2rem);
  line-height:.95;color:var(--gold-lt);letter-spacing:-.015em;font-variant-numeric:tabular-nums;
}
.stats span{font-size:.9rem;line-height:1.5;color:var(--on-dark-dim);max-width:26ch}

.creds{list-style:none;padding:0;display:grid;gap:0;margin-top:clamp(1.6rem,3vw,2.4rem);border-top:1px solid var(--hair)}
.creds li{
  display:grid;grid-template-columns:minmax(200px,.9fr) 1.4fr;gap:1rem clamp(1.5rem,4vw,3.5rem);
  padding-block:1.05rem;border-bottom:1px solid var(--hair-soft);align-items:baseline;
}
.creds b{font-family:var(--serif);font-weight:600;font-size:1.22rem;color:#fff;line-height:1.25}
.creds span{color:var(--on-dark-dim);font-size:.96rem;line-height:1.55}
@media (max-width:720px){.creds li{grid-template-columns:1fr;gap:.35rem}}

.mantra{
  margin-top:clamp(2rem,4vw,3.25rem);font-family:var(--serif);font-style:italic;
  font-weight:600;font-size:clamp(1.4rem,2.6vw,2.1rem);color:var(--gold-lt);letter-spacing:-.008em;
}

.todo{
  border-left:2px solid var(--gold);background:rgba(212,175,55,.07);
  padding:1.3rem 1.6rem;margin-top:2.5rem;font-size:.95rem;color:var(--on-dark-dim);max-width:68ch;
}
.todo b{color:var(--gold);letter-spacing:.2em;text-transform:uppercase;font-size:.64rem;display:block;margin-bottom:.5rem}

/* ---------- footer ---------- */
.site-foot{background:rgba(12,5,24,.94);border-top:1px solid var(--hair-soft);padding-block:clamp(3rem,6vw,5rem) 2.5rem}
.foot-grid{display:flex;flex-wrap:wrap;gap:3rem;justify-content:space-between;align-items:flex-start}
.foot-col h3{font-size:.64rem;letter-spacing:.28em;text-transform:uppercase;color:var(--gold);margin-bottom:1.3rem;font-weight:700}
.foot-col p,.foot-col a{font-size:.95rem;line-height:1.95;display:block;color:var(--on-dark-dim);transition:color .3s var(--ease)}
.foot-col a:hover{color:var(--gold-lt)}
.foot-base{
  margin-top:clamp(2.5rem,5vw,4rem);padding-top:1.6rem;border-top:1px solid var(--hair-soft);
  font-size:.75rem;letter-spacing:.1em;color:var(--on-dark-mute);
  display:flex;flex-wrap:wrap;gap:1rem;justify-content:space-between;
}

/* ---------- reveal: clip wipe, reads as a camera move ---------- */
/* Visible is the BASE state. JS adds .rv-hide only to elements that are
   off-screen at load, and removes it when they scroll in. Nothing is ever
   left invisible waiting on a transition that may never composite. */
/* The hero rises its headline 105% from behind a mask over 1.15s. Everything
   below used to get 18px over .42s, which reads as nothing. These are scaled
   to sit in the same film as the hero rather than apologise for existing. */
.js .rv,.js .rv-w{
  transition:opacity .78s var(--ease-o),transform .95s var(--ease-o),clip-path 1.05s var(--ease-o);
  will-change:transform,opacity;
}
.js .rv.rv-hide{opacity:0;transform:translateY(68px)}
.js .rv-w.rv-hide{opacity:0;transform:translateY(84px);clip-path:inset(0 0 100% 0)}

/* Directional entry. The rail arrives from its own side and the body from the
   other, so a split reads as two things converging rather than one nudge. */
.js .split-side > .rv.rv-hide,
.js .split-side > .rv-w.rv-hide{transform:translate(-58px,48px)}
.js .split-main > .rv.rv-hide,
.js .split-main > .rv-w.rv-hide{transform:translate(58px,48px)}

/* Work items enter from the edge their copy sits on. */
.js .film .inner.rv-hide{transform:translate(-66px,44px)}
.js .film.right .inner.rv-hide{transform:translate(66px,44px)}
.js .film .film-media.rv-hide{transform:translate(66px,38px) scale(.955)}
.js .film.right .film-media.rv-hide{transform:translate(-66px,38px) scale(.955)}

/* Rows that arrive as a set stagger themselves rather than landing as a block. */
.js .principles .principle.rv-hide{transform:translateY(76px)}
.js .eng-item.rv-hide{transform:translateY(64px)}
.js .stats.rv-hide,.js .creds.rv-hide{transform:translateY(60px)}

/* ---------- reduced 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;
  }
  .hero-pin{position:relative;height:auto;min-height:90vh}
  .hero-h .ln > span{transform:none}
  .hero-sub,.hero .btn-row,.hero .eyebrow{opacity:1}
  /* never let the mark depend on a transition or a JS class here */
  .mark-stage{opacity:1 !important;transition:none !important}
  .mark-3d .sheen{display:none}
  .rv,.rv-w,.rv-hide{opacity:1 !important;transform:none !important;clip-path:none !important}
  .skip-hero{display:none}
  .film-bg,.film-bg img{transform:none !important}
}

/* ===========================================================================
   Engagement tracks.

   Replaces twelve cards, each carrying a paragraph, with three tracks that
   state the reader's own situation in display type and then list the work as
   single-line rows. The design idea is the inversion: the problem is the
   headline and the product name is the footnote. Twelve paragraphs is twelve
   walls of text no matter what you box them in.
   ========================================================================= */
.eng-track{padding:clamp(3rem,6vw,5rem) 0;border-top:1px solid rgba(212,175,55,.16);position:relative}
/* The terrain canvas runs behind everything. Without a scrim its lines cut
   straight through the rows and the text stops being readable. Full bleed so
   the scrim never draws a rectangle and starts reading as a card again. */
.eng-track::before{content:"";position:absolute;z-index:1;pointer-events:none;
  top:0;bottom:0;left:calc(50% - 50vw);right:calc(50% - 50vw);
  background:linear-gradient(180deg,rgba(12,5,24,0) 0%,rgba(12,5,24,.86) 6%,
             rgba(12,5,24,.86) 94%,rgba(12,5,24,0) 100%)}
.eng-track > *{position:relative;z-index:2}

.eng-top{display:grid;grid-template-columns:.85fr 1.15fr;gap:clamp(2rem,5vw,4.5rem);
  align-items:end;margin-bottom:clamp(2.2rem,4vw,3.2rem)}
.eng-track-name{font-family:var(--sans);font-size:.74rem;letter-spacing:.22em;
  text-transform:uppercase;color:var(--amber-lt);margin:0 0 1rem}
.eng-problem{font-family:var(--serif);font-weight:500;line-height:1.16;
  font-size:clamp(1.75rem,3.2vw,2.7rem);color:#fff;margin:0}
.eng-answer{font-size:clamp(1rem,1.35vw,1.1rem);line-height:1.7;color:var(--on-dark-dim);margin:0}
.eng-answer b{color:#fff;font-weight:600}

.eng-rows{border-top:1px solid rgba(163,149,188,.14)}
.eng-row{display:grid;
  /* the third column is a fixed width, not auto. auto sized itself to each
     row's own label, so a longer spec squeezed the fr columns and every row
     started its description at a slightly different place. */
  grid-template-columns:.85fr 1.15fr 14rem;gap:clamp(1.2rem,3vw,3rem);
  align-items:baseline;padding:1.15rem 0;border-bottom:1px solid rgba(163,149,188,.14);
  transition:background .25s ease}
.eng-row:hover{background:rgba(212,175,55,.035)}
.eng-row h3{font-family:var(--serif);font-weight:500;font-size:clamp(1.2rem,1.9vw,1.55rem);
  color:#fff;margin:0;letter-spacing:.01em}
.eng-row p{font-size:.95rem;line-height:1.6;color:var(--on-dark-dim);margin:0}
.eng-row .spec{font-family:var(--sans);font-size:.68rem;letter-spacing:.14em;
  text-transform:uppercase;color:var(--on-dark-mute);text-align:right;white-space:nowrap;line-height:1.7}
@media(max-width:860px){
  .eng-top{grid-template-columns:1fr}
  .eng-row{grid-template-columns:1fr;gap:.4rem}
  .eng-row .spec{text-align:left}
}

/* ===========================================================================
   Enclosures.

   Her note, and it was the right diagnosis: "the text needs to be behind
   something, something's missing." Every content section on this site was
   typography sitting directly on an animated gradient, with nothing holding
   it. However well type is set, with no surface under it the page reads thin.

   This is the nested-enclosure pattern: an outer shell with a hairline and a
   large radius, an inner core with its own ground and a top inset highlight,
   and a concentric inner radius calculated from the outer one. The point is
   that it should read as a machined object, a glass plate sitting in a tray,
   rather than a box drawn around some words.

   Deliberately not the boxed cards she rejected earlier. Those were twelve
   identical containers repeating down a page. This is one quiet surface that
   sits under content and lets the terrain show through it.
   ========================================================================= */
.enclosure{
  --shell: .5rem;
  --r: clamp(1.25rem, 2vw, 1.75rem);
  padding: var(--shell);
  border-radius: var(--r);
  background: rgba(255,255,255,.022);
  border: 1px solid rgba(212,175,55,.10);
  position: relative;
  z-index: 2;
}
.enclosure > .enclosure-core{
  border-radius: calc(var(--r) - var(--shell));
  padding: clamp(1.75rem, 3.4vw, 3rem);
  background: linear-gradient(180deg, rgba(50,24,78,.72), rgba(26,11,46,.86));
  box-shadow: inset 0 1px 0 rgba(255,255,255,.07);
}

/* A lighter variant for places that need separation without a full container */
.enclosure-flat{
  border-radius: clamp(1rem,1.6vw,1.4rem);
  padding: clamp(1.5rem,3vw,2.5rem);
  background: rgba(26,11,46,.72);
  border: 1px solid rgba(212,175,55,.09);
  box-shadow: inset 0 1px 0 rgba(255,255,255,.05);
  position: relative; z-index: 2;
}

@media (max-width:640px){
  .enclosure{--shell:.375rem}
  .enclosure > .enclosure-core{padding:clamp(1.25rem,5vw,1.75rem)}
}

/* ===========================================================================
   Biography.

   The career section was converted from prose to rows to kill a 105 word
   paragraph, and it worked, but her read was right: rows carry facts well and
   voice badly, so it came out reading as a resume. Prose was never the
   problem. Paragraph length was.

   So: narrative back, held to roughly 45 words a paragraph, on a reading
   measure, with one pull quote breaking the column so the eye gets a rest
   without the text turning into a table.
   ========================================================================= */
.bio{max-width:none;margin-inline:0}
.bio p{font-size:1.14rem;line-height:1.9;margin:0 0 1.7rem}
.bio p:last-child{margin-bottom:0}
.bio .bio-pull{max-width:38ch;
  font-family:var(--serif);font-weight:600;
  font-size:clamp(1.5rem,2.9vw,2.3rem);line-height:1.22;
  color:var(--gold-lt);text-wrap:balance;letter-spacing:-.008em;
  margin:2.6rem 0;padding-left:1.4rem;
  border-left:2px solid rgba(212,175,55,.45);
}
@media(min-width:1100px){
  /* the quote breaks out of the reading measure so it interrupts rather than
     sits politely inside the column */
  .bio .bio-pull{margin-left:-3.5rem;padding-left:3.5rem}
}

/* ===========================================================================
   Statement block.

   Some sections are one idea and one paragraph. Forcing those into the split
   grid gave a five line heading beside a six line paragraph and a large empty
   area beneath, repeated down the site, which is most of why it read as
   slides. This is the alternative shape.
   ========================================================================= */
.statement{max-width:72rem;margin-inline:auto;text-align:center}
.statement .eyebrow{display:inline-flex;margin-bottom:1.4rem}
.statement .pull{margin:0 auto}
.statement .lede{max-width:none;margin:1.8rem auto 0}

/* A section header centred across the full width, for sections whose content
   below spans. The left-aligned .sec-head leaves a wide gap between a short
   heading and the numeral on the right, which reads as a half-used row. */
.sec-head-center{text-align:center;margin-bottom:clamp(2rem,4vw,3.25rem)}
.sec-head-center .eyebrow{display:inline-flex;justify-content:center}
.sec-head-center .sec-h{max-width:24ch;margin-inline:auto}
.sec-head-center .ghost-n{display:block;margin:1rem auto 0}

/* The eyebrow now sits above the grid rather than inside the left column, so
   the heading and the prose beside it start on the same line. It needs its own
   bottom spacing since it is no longer stacked with the heading. */
.eyebrow + .split{margin-top:1.15rem}

/* The founder quote sits right of centre against the video, set in italic with
   a hanging open quote so it reads as speech rather than another heading. */
/* Scoped to the quote wrap only. As .cta-film .wrap this also caught the
   homepage contact section, whose wrap holds five stacked children, and a
   flex row laid all five side by side and crushed every column. */
.cta-film .wrap-quote{display:flex;justify-content:flex-end}

/* The contact lede sits in a .split, the door copy sits in .doors a, and the
   two grids had different column ratios and different gaps. That put the lede
   about 71px right of every description under it. Matching the doors grid here
   lines the whole right column up. Scoped to #contact because .split is used
   across every page and its own ratio is correct everywhere else. */
#contact .split{
  grid-template-columns:minmax(0,.58fr) minmax(0,1fr);
  gap:clamp(1rem,4vw,3.5rem);
}
.quote{position:relative;font-style:italic}
.quote p{position:relative;margin:0}
.quote p::before{
  content:"\201C";position:absolute;left:-.58em;top:-.02em;
  font-style:normal;font-size:1.9em;line-height:1;
  color:var(--gold);opacity:.42;pointer-events:none;
}
.quote p::after{content:"\201D";font-style:normal;color:var(--gold);opacity:.42}
.quote cite{font-style:normal}
.quote cite::before{content:"\2014\00a0"}
@media(max-width:780px){
  .cta-film .wrap-quote{justify-content:flex-start}
  .quote::before{left:-.42em}
}

/* The gold sweep .eng-item has always had. The new rows were built without it,
   which is why the cards lost their movement. */
.eng-row{position:relative}
.eng-row::after{
  content:"";position:absolute;left:0;bottom:-1px;width:100%;height:1px;
  background:var(--gold);transform:scaleX(0);transform-origin:left;
  transition:transform .7s var(--ease-o);
}
.eng-row:hover::after{transform:scaleX(1)}

/* 6. the statement paragraph must never run wider than the heading above it */
.statement .pull{text-wrap:pretty}
.statement .pull,.statement .lede{max-width:62rem;margin-inline:auto}


/* ===========================================================================
   Restored 2026-08-19. These were deleted by an over-broad regex while
   editing the portrait rules, which is why the founder name lost its serif
   and the prose lost its measure. Kept together so the loss is visible.
   ========================================================================= */
.founder-head h1{
  font-family:var(--serif);font-weight:600;font-size:clamp(3.1rem,8.2vw,6.6rem);
  line-height:.9;color:#fff;letter-spacing:-.018em;
}
.founder-head .role{margin-top:2rem;color:var(--gold-lt);font-size:1.28rem;line-height:1.7;font-family:var(--serif);font-weight:600}
.prose{max-width:68ch}
.prose p{margin-top:1.1rem;color:var(--on-dark-dim);line-height:1.78;font-size:1.08rem}
.prose p:first-child{margin-top:0}
.prose strong{color:#fff;font-weight:600}
.pull{
  font-family:var(--serif);font-weight:600;font-size:clamp(2rem,4.9vw,4rem);
  line-height:1.08;letter-spacing:-.012em;text-wrap:balance;color:#fff;
}
.split{
  display:grid;grid-template-columns:minmax(0,.86fr) minmax(0,1.14fr);
  gap:clamp(1.8rem,5vw,5rem);align-items:center;
}

/* ===========================================================================
   Second restore pass. The first compared selector names only, so it missed
   rules that still existed but had been stripped of their declarations.
   ========================================================================= */
.quote{
  font-family:var(--serif);font-weight:600;font-size:clamp(1.7rem,4vw,3.2rem);line-height:1.2;
  color:var(--gold-lt);text-wrap:balance;letter-spacing:-.008em;
}
.quote cite{
  display:block;margin-top:2rem;font-family:var(--sans);font-style:normal;
  font-size:.88rem;letter-spacing:.18em;text-transform:uppercase;color:var(--on-dark-mute);font-weight:700;
}
@media (max-width:820px){.founder-head{grid-template-columns:1fr}}
/* the statement heading holds two lines rather than three */
.statement .pull{font-size:clamp(1.85rem,3.95vw,3.3rem)}

/* The Position: heading flush left, supporting paragraph justified so both of
   its edges are even. hyphenation is on because justified text in a narrow
   column opens rivers of white space without it. */
#position .big{text-align:left}
#position .sub{text-align:justify;hyphens:auto;-webkit-hyphens:auto}

/* ===========================================================================
   The Name Behind the Firm.

   Two words converge into one name, so the layout says that rather than
   describing it. Each word gets the size its importance warrants, the mark
   sits in the gutter where the two ideas meet, and the triad runs full width
   underneath so the sentence introducing it points down at it.

   No new devices. The serif, the hairlines and the mark already existed. The
   old version buried both words in body copy at 1.14rem while the closing
   line ran at 2.6rem, which had the hierarchy exactly backwards.
   ========================================================================= */
.name-def{
  display:grid;grid-template-columns:1fr auto 1fr;
  gap:clamp(1.5rem,4vw,3.5rem);align-items:start;
  margin-top:clamp(1.75rem,3.4vw,2.75rem);
}
.name-word h3{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(2.4rem,5.4vw,4.4rem);line-height:1;
  color:#fff;letter-spacing:-.014em;margin:0 0 1.1rem;
}
.name-word p{font-size:1.06rem;line-height:1.75;color:var(--on-dark-dim);margin:0;max-width:38ch}
.name-word:last-child{text-align:right}
.name-word:last-child p{margin-left:auto}

/* the mark as the join, not as wallpaper */
.name-join{display:flex;flex-direction:column;align-items:center;gap:1.1rem;align-self:stretch;justify-content:center}
.name-join img{width:clamp(52px,5vw,74px);height:auto;opacity:.9;display:block}
.name-rule{flex:1;width:1px;min-height:2.5rem;
  background:linear-gradient(to bottom,rgba(212,175,55,0),rgba(212,175,55,.5))}
.name-join .name-rule:last-child{background:linear-gradient(to bottom,rgba(212,175,55,.5),rgba(212,175,55,0))}

.name-lead{
  margin:clamp(2.5rem,5vw,4rem) 0 0;text-align:center;
  font-family:var(--sans);font-size:.72rem;letter-spacing:.28em;
  text-transform:uppercase;color:var(--amber-lt);
}
.name-sec .triad{max-width:44rem;margin-inline:auto;margin-top:1.4rem;border-top:0}
.name-sec .triad li{justify-items:start;grid-template-columns:2.6rem 1fr}
.name-sec .name-close{text-align:center;max-width:46rem;margin-inline:auto}

@media(max-width:860px){
  .name-def{grid-template-columns:1fr;gap:1.5rem}
  .name-word:last-child{text-align:left}
  .name-word:last-child p{margin-left:0}
  .name-join{flex-direction:row;align-self:auto;padding:.5rem 0}
  .name-rule{width:auto;height:1px;min-height:0;flex:1;
    background:linear-gradient(to right,rgba(212,175,55,0),rgba(212,175,55,.5))}
  .name-join .name-rule:last-child{background:linear-gradient(to right,rgba(212,175,55,.5),rgba(212,175,55,0))}
}

/* both definitions justified, so each column has two clean edges */
.name-word p{text-align:justify;hyphens:auto;-webkit-hyphens:auto}
.name-word:last-child p{text-align:justify}

/* the mark needs its own top offset now the columns align to the top */
.name-join{padding-top:clamp(1.5rem,3vw,2.75rem)}

/* Three short phrases introduced by a label do not need numbering or bullets.
   A marker here would be decoration standing in for structure. They are
   centred as a group and share a left edge so they read as a set. */
.triad-plain{
  list-style:none;padding:0;margin:clamp(1.4rem,2.6vw,2rem) auto 0;
  width:max-content;max-width:100%;display:grid;
  gap:clamp(.7rem,1.4vw,1.15rem);
}
.triad-plain li{
  font-family:var(--serif);font-weight:600;
  font-size:clamp(1.35rem,2.4vw,2rem);line-height:1.2;
  color:#fff;letter-spacing:-.006em;
}

/* the closing line steps back so the two words own the section */
.name-sec .name-close{font-size:clamp(1.2rem,2.1vw,1.75rem)}

/* A soft radial scrim, not a panel. The terrain keeps showing through at the
   edges, which suits a section about a fox in a hard environment, but the
   text gets ground under it. A hard band would box the section and fight the
   full-bleed feel. */
.name-sec .wrap::before{
  content:"";position:absolute;z-index:-1;pointer-events:none;
  left:50%;top:50%;translate:-50% -50%;
  width:min(1100px,108%);height:118%;
  background:radial-gradient(60% 52% at 50% 50%,
    rgba(12,5,24,.82) 0%, rgba(12,5,24,.62) 55%, rgba(12,5,24,0) 100%);
}

/* ---------------------------------------------------------------------------
   Selected work dialog. Native <dialog>, so escape, focus trapping and inert
   background come from the browser rather than from script.
   ------------------------------------------------------------------------- */
.wk{
  border:0;padding:0;background:transparent;color:inherit;
  width:min(1040px,94vw);max-height:90vh;overflow:visible;
}
.wk::backdrop{background:rgba(6,2,14,.82)}
.wk-body{
  max-height:90vh;overflow:auto;border-radius:clamp(1rem,1.6vw,1.5rem);
  background:linear-gradient(180deg,rgba(50,24,78,.96),rgba(18,8,34,.98));
  border:1px solid rgba(212,175,55,.22);
  box-shadow:0 40px 120px rgba(0,0,0,.6);
  padding:clamp(1.75rem,3.4vw,3.25rem);
}
.wk-body:focus{outline:none}
/* Inside the dialog the full-page film layout does not apply. The .right
   variants exist to alternate sides down a long page; in a modal they just
   invert the reading order and push the text to the wrong edge. Neutralised
   here rather than in the markup, so built.html keeps its own layout. */
.wk-body .film{display:block;min-height:0;overflow:visible;align-items:stretch}
.wk-body .film-copy{display:block;width:auto;margin:0;padding:0}
.wk-body .film.has-media .film-copy{display:block}
/* only the full-bleed background layer is hidden. the project video is
   content, not decoration, and belongs in the dialog. */
.wk-body .film-bg{display:none}
.wk-body .film-media video{width:100%;height:auto;aspect-ratio:16/9;display:block;
  border:1px solid var(--hair);border-radius:.5rem}
.wk-body .inner,.wk-body .film-copy .inner,.wk-body .film.has-media .film-copy .inner{max-width:none;order:0}
.wk-body .film.right .sub-h,.wk-body .film.right *{text-align:left}
.wk-body .film.right .film-media figcaption{justify-content:flex-start}
.wk-body .film-media{order:0;width:auto;max-width:520px;margin:clamp(1.5rem,3vw,2.25rem) 0 0}
.wk-body .film-media.diagram{width:auto}
.wk-body .film-media img{width:100%;height:auto}
.wk-body .spec{margin-top:1.75rem}
.wk-x{
  position:absolute;top:-.4rem;right:-.4rem;z-index:2;
  width:2.6rem;height:2.6rem;border-radius:50%;cursor:pointer;
  background:var(--purple-deep);color:#fff;font-size:1.5rem;line-height:1;
  border:1px solid rgba(212,175,55,.35);font-family:var(--sans);
  transition:background .3s var(--ease),border-color .3s var(--ease);
}
.wk-x:hover{background:var(--purple-raised);border-color:var(--gold)}

/* the tile now carries a line of substance, not just a label */
.tile-c em{
  display:block;font-style:normal;font-size:.92rem;line-height:1.5;
  color:var(--on-dark-dim);margin:.5rem 0 .55rem;max-width:34ch;
}

/* ===========================================================================
   Mobile collapse for .split.

   This lived in the max-width:900px block near the top of the file, several
   hundred lines BEFORE the base .split rule. Same selector, same specificity,
   same properties, so the base rule won and the breakpoint never fired once.
   Every split on the site stayed two columns on every phone: headings squeezed
   to about 128px and body copy to about 170px, both overflowing the viewport.
   That was the "letters all over the place".

   It lives at the end of the stylesheet now, which is where a breakpoint has
   to sit to beat the rule it is overriding.
   ======================================================================== */
@media (max-width:900px){
  .split{grid-template-columns:1fr;gap:clamp(1rem,3vw,1.5rem)}

  /* Justified text needs roughly 45 characters a line to set without rivers.
     At phone width these columns run about 40, and the word spacing stretches
     visibly. Ranged left below the breakpoint. */
  #position .sub,
  .name-word p,
  .name-word:last-child p{text-align:left}

  /* #contact .split carries an id, so it outranks the plain .split above no
     matter where either sits. It has to be collapsed by name. */
  #contact .split{grid-template-columns:1fr;gap:clamp(1rem,3vw,1.5rem)}

  /* The directional reveals slide in from the side by up to 66px. On a 375px
     screen that pushes content past the edge for the length of the animation,
     which flashes a horizontal scrollbar and shifts the whole page sideways as
     you scroll. Vertical only below the breakpoint: the effect still reads, and
     nothing leaves the viewport. */
  .js .split-side > .rv.rv-hide,
  .js .split-side > .rv-w.rv-hide,
  .js .split-main > .rv.rv-hide,
  .js .split-main > .rv-w.rv-hide,
  .js .film .inner.rv-hide,
  .js .film.right .inner.rv-hide{transform:translateY(46px)}
  .js .film .film-media.rv-hide,
  .js .film.right .film-media.rv-hide{transform:translateY(38px) scale(.97)}
}

/* ===========================================================================
   The intake panel on a phone.

   As a centred card it was unusable. At 375x600 the explainer alone took 254px,
   over 40 percent of the viewport, the conversation got 120px, and the status
   line sat below the fold. Once the keyboard opened, the input went with it.

   Full sheet instead, sized in dynamic viewport units so it shrinks with the
   keyboard rather than being pushed under it. dvh first, svh and vh behind it
   for anything that does not know dvh.
   ======================================================================== */
@media (max-width:640px), (max-height:700px){
  .ik{padding:0;display:block}
  .ik-box{
    width:100%;max-width:none;border:0;border-radius:0;
    height:100vh;height:100svh;height:100dvh;max-height:none;
  }
  .ik-head{padding:1rem 1.1rem}
  .ik-title{font-size:1.5rem}
  .ik-log{padding:1rem 1.1rem}
  .ik-form{padding:.8rem 1.1rem}
  .ik-choose{padding:1.1rem}

  /* The visitor bubble can run wider when the screen is this narrow. */
  .ik-msg.ik-you{max-width:92%}

  /* Tap targets. 2.6rem was fine beside a mouse. */
  .ik-mic{width:3rem;min-height:2.9rem}
  .ik-send{min-height:2.9rem}
}
