/* Distinctive Media — miami "d." identity, dark mode */

:root{
  --night: oklch(0.16 0.025 265);       /* page ground  ~#0d1120 */
  --night-2: oklch(0.13 0.02 265);      /* deeper band  */
  --panel: oklch(0.20 0.03 265);        /* raised card  ~#161d31 */
  --panel-2: oklch(0.24 0.035 265);     /* hover card   */
  --ink: oklch(0.96 0.005 220);         /* text  #F2F6F7 */
  --dim: oklch(0.74 0.02 250);          /* secondary text */
  --miami: oklch(0.79 0.128 208);       /* #1ED1E7 */
  --miami-deep: oklch(0.55 0.09 215);   /* #007E99 */
  --miami-wash: oklch(0.79 0.128 208 / 0.12);
  --faint: oklch(0.62 0.03 250);        /* smallest legible muted, 5.3:1 on night */
  --line: oklch(0.29 0.03 265);
  --disp: "Bricolage Grotesque", "Display Fallback", sans-serif;
  --body-face: "Instrument Sans", system-ui, sans-serif;
  /* technical labels — DESIGN.md: Martian Mono, variable wght 300..700.
     It is a wide mono (~0.63em advance), so the fallback stack is ordered
     widest-first; ui-monospace and generic monospace are the last resorts. */
  --mono: "Martian Mono", "Cascadia Mono", Consolas, "SF Mono", Menlo, ui-monospace, monospace;

  /* ---- type ramp ----
     Prose (Archivo): caption 14 / body 16 / lede 18, then display clamps.
     Labels (Bricolage 700, uppercase): two sizes only — label 12.5, spec 14.
     Nothing else. Every font-size on the site resolves to one of these. */
  --t-caption: 0.875rem;                 /* 14px — captions, fine print, meta */
  --t-body: 1rem;                        /* 16px — all prose, form controls */
  --t-lede: 1.125rem;                    /* 18px — section subs, hero sub */
  --t-h4: 1.375rem;                      /* 22px — card + widget headings */
  --t-h3: clamp(1.35rem, 2.2vw, 1.65rem);
  --t-h2: clamp(1.65rem, 2.9vw, 2.2rem);
  --t-h1: clamp(1.95rem, 4vw, 3.1rem);   /* section headline */
  --t-page: clamp(2.3rem, 5vw, 3.9rem);  /* subpage h1 */
  --t-hero: clamp(2.5rem, 5.6vw, 4.4rem);
  --t-stat: clamp(1.75rem, 3vw, 2.5rem); /* big numbers */
  --m-label: 0.78rem;                    /* 12.5px — uppercase grotesque labels, badges */
  --m-spec: 0.875rem;                    /* 14px — spec lines, prices */

  /* Plate inks — the ONE source of truth. The register-snap runs on the hero
     h1, on every .dk-h, on the wordmarks and on the 404, so the tokens live
     at the root where every host can resolve them. js/home.js reads these
     exact names and carries no literals of its own. */
  --plate-c: oklch(0.78 0.11 210);
  --plate-m: oklch(0.66 0.19 356);

  --wrap: 1180px;
  --z-callbar: 40;
  --z-sticky: 50;
  --ease: cubic-bezier(.16,1,.3,1);
}

/* Metric-matched fallback so the webfont swap doesn't shift layout */
@font-face{
  font-family:"Display Fallback";
  src:local("Arial");
  size-adjust:104%;
  ascent-override:91%;
  descent-override:23%;
  line-gap-override:0%;
}

*{margin:0;padding:0;box-sizing:border-box}
html{scroll-behavior:smooth}
@media (prefers-reduced-motion: reduce){ html{scroll-behavior:auto} }
body{
  background:var(--night);
  color:var(--ink);
  font-family:var(--body-face);
  font-size:var(--t-body);
  line-height:1.6;              /* +0.05 for light-on-dark */
  letter-spacing:0.005em;       /* light type on dark reads thin; open it slightly */
  font-optical-sizing:auto;
  font-kerning:normal;
  overflow-x:hidden;
}
img{max-width:100%;display:block}
a{color:inherit;text-decoration:none}
.wrap{max-width:var(--wrap);margin:0 auto;padding-inline:clamp(20px,4vw,40px)}

h1,h2,h3,h4,.btn,.sm-kpi b,.hero-chip b,.fix-head b,.mini-tik .mt-price,
.tk-price b,.addon-price b,.pdlg-price,.cart-total,.pc-price,.proj-stats div b,
.route h3,.pager b,.flow b,.cl-h,.foot-word,.rl,.nf-word,.brand{
  font-family:var(--disp);
}
/* No font-stretch guard here. DESIGN.md warns that Bricolage's width axis tops
   out at 100%, but the css2 request on every page that loads this file asks for
   the `opsz,wght` tuple only — no `wdth` axis is served, so the family cannot
   render narrower or wider than 100% and the guard could never fire. Dropping
   the guard rather than adding `wdth` to the request: the site never varies
   width, so paying for a third axis to defend against a value nothing sets
   would be the more expensive half of the trade. */
h1,h2,h3{font-weight:800;letter-spacing:-0.028em;line-height:1.0;text-wrap:balance;color:var(--ink);overflow-wrap:break-word}
/* figures that get scanned or compared line up */
.sm-kpi b,.proj-stats div b,.hero-chip b,.mini-tik .mt-price,.fix-head b,
.pc-price,.pdlg-price,.ci-price,.ck-line,.cart-total,.pol-table td:last-child{
  font-variant-numeric:tabular-nums;
}
.acc{color:var(--miami)}

/* Buttons */
.btn{
  display:inline-block;
  font-family:var(--disp);
  font-weight:700;font-size:var(--t-body);letter-spacing:0.01em;
  /* border-radius:0 stays: .btn is a <button> on the lead form and the store,
     and iOS/Safari's UA sheet rounds native button corners. This is one of the
     few radius resets on the sheet that overrides something real. */
  padding:14px 28px;border-radius:0;border:2px solid transparent;
  background:transparent;color:var(--ink);
  cursor:pointer;
  /* No will-change here. Every page that loads this file has buttons, and a
     static will-change:transform promotes a compositor layer for each of them
     for the whole session — the documented misuse of a hint that is meant to
     be applied shortly before a move and released after. The magnetic effect
     (js/home.js, [data-mag]) drives x/y through GSAP, whose default
     force3D:"auto" promotes for the duration of the tween and drops the layer
     when it finishes. Same wake/rest discipline the press-check plates use. */
  transition:background .25s var(--ease), color .25s var(--ease), border-color .25s var(--ease);
}
.btn-lg{padding:17px 32px}
.btn-miami{background:var(--miami);color:var(--night-2)}
.btn-miami:hover{background:oklch(0.85 0.11 208)}
.btn-hero{border-color:oklch(0.96 0.005 220 / 0.45);color:var(--ink)}
.btn-hero:hover{background:var(--ink);color:var(--night-2);border-color:var(--ink)}
.btn-nav{padding:10px 20px;font-size:var(--t-caption);background:var(--miami);color:var(--night-2)}
.btn-nav:hover{background:oklch(0.85 0.11 208)}

/* ---------- Header ---------- */
.site-head{
  position:sticky;top:0;z-index:var(--z-sticky);
  background:oklch(0.16 0.025 265 / 0.88);
  backdrop-filter:blur(10px);
  border-bottom:1px solid var(--line);
}
.site-head nav{
  max-width:var(--wrap);margin:0 auto;
  padding:16px clamp(20px,4vw,40px);
  display:flex;align-items:center;justify-content:space-between;gap:20px;
  flex-wrap:wrap;   /* survives 200% user text size */
}
/* The wordmark is 20px tall but the link around it is a target, so it carries
   its own 44px minimum rather than inheriting the image's box. */
.brand{display:flex;align-items:center;min-height:44px}
.brand:focus-visible{outline:3px solid var(--miami);outline-offset:3px}
.brand-word{height:20px;width:auto;display:block}
.nav-links{display:flex;gap:26px;flex-wrap:wrap;align-items:stretch}
/* Every item in the row is a flex child of the same height, so the 2px
   underline lands on one baseline across links and the Services button, and
   each one clears the 24px minimum target on its own. */
.nav-links a{
  display:flex;align-items:center;min-height:24px;
  font-size:var(--t-caption);font-weight:600;color:var(--dim);
  background:linear-gradient(var(--miami),var(--miami)) no-repeat 0 100%/0 2px;
  transition:color .25s, background-size .3s var(--ease);
  padding-bottom:3px;
}
.nav-links a:hover{color:var(--ink);background-size:100% 2px}
.nav-links a:focus-visible{outline:3px solid var(--miami);outline-offset:3px}

/* ---------- Phone navigation -----------------------------------------------
   Below 640 the desktop row cannot fit, so the phone gets its own control
   instead of nothing. It is a native <details> disclosure on purpose:

   - No JavaScript. js/ is owned elsewhere and a nav that dies with a failed
     script is not a nav. The UA opens and closes this, and exposes the
     expanded state to assistive tech itself — which is also why no static
     aria-expanded is written on the <summary>: it would go stale on the
     first tap.
   - Keyboard: <summary> is focusable and toggles on Enter and Space for free.
   - Targets: 44px on the button, 52px rows in the panel.

   Geometry per DESIGN.md — square, hairline borders, --miami accent, and the
   open row marked with the same 3px accent edge the data panels use.
--------------------------------------------------------------------------- */
.nav-m{display:none}
/* 44x44 square. The brand wordmark (100px) and the "Start a project" button
   (145px) already spend 245 of the 335px the header has at 390, so a button
   carrying the word "MENU" as well pushed the row onto a second line and made
   the sticky header 134px tall. The label is kept in the markup and clipped
   instead of deleted, so the summary still has the accessible name "Menu". */
.nav-m-btn{
  display:flex;align-items:center;justify-content:center;
  width:44px;height:44px;padding:0;
  list-style:none;cursor:pointer;
  background:var(--night-2);border:1px solid var(--line);
  transition:border-color .2s;
}
.nav-m-btn::-webkit-details-marker{display:none}
.nav-m-btn::marker{content:""}
.nav-m-btn:hover{border-color:var(--miami-deep)}
.nav-m-btn:focus-visible{outline:3px solid var(--miami);outline-offset:2px}
.nav-m-label{
  position:absolute;width:1px;height:1px;overflow:hidden;
  clip-path:inset(50%);white-space:nowrap;
}
.nav-m-bars{display:flex;flex-direction:column;gap:3px;width:18px;flex:none}
.nav-m-bars i{display:block;width:100%;height:2px;background:var(--miami);transition:width .2s var(--ease)}
.nav-m[open] .nav-m-btn{border-color:var(--miami)}
.nav-m[open] .nav-m-bars i:nth-child(2){width:55%}
/* the panel hangs off .site-head, which is the nearest positioned ancestor
   (position:sticky), so it spans the full header width rather than the
   summary's box */
.nav-m-panel{
  position:absolute;left:0;right:0;top:100%;
  background:var(--night);
  border-top:1px solid var(--line);border-bottom:1px solid var(--line);
  max-height:calc(100dvh - 100%);overflow-y:auto;
}
.nav-m-panel ul{list-style:none}
.nav-m-panel li + li{border-top:1px solid var(--line)}
.nav-m-panel a{
  display:flex;align-items:center;min-height:52px;
  padding:13px clamp(20px,4vw,40px);
  font-size:var(--t-body);font-weight:600;color:var(--ink);
  border-left:3px solid transparent;
  transition:color .2s, border-color .2s, background .2s;
}
.nav-m-panel a:hover{color:var(--miami);border-left-color:var(--miami);background:var(--night-2)}
.nav-m-panel a:focus-visible{outline:3px solid var(--miami);outline-offset:-3px}
@media (prefers-reduced-motion: reduce){
  .nav-m-bars i,.nav-m-panel a{transition:none}
}

/* ---------- Hero — "the press check", full sheet ------------------------
   The proof is trimmed to the viewport: one photo, full bleed, `100svh`
   (svh, not vh — dvh/vh both jump when the mobile URL bar retracts and the
   pin/exit trigger would resample mid-scroll). The registration furniture
   goes to the trim edges with it — crop marks on all four corners, slug
   line along the head, CMYK target opposite. DESIGN.md requires photos to
   be framed with registration furniture, so "full bleed" here means the
   sheet grew to the screen, not that the frame was dropped.

   LEGIBILITY IS THE SCRIM'S JOB, NOT A SHADOW'S. DESIGN.md bans shadows
   outright, and the earlier full-bleed hero used two text-shadows to buy
   contrast over this same photo. Every value in .hero-scrim below was
   tuned against the real composited pixels under the type (canvas sample
   of photo × scrim), not estimated — see the measurement note there.

   OWNERSHIP: this file is the only owner of the hero. css/home-deck.css
   loads after it but no longer carries any `.hero…` rule, so `.hero.hero-reg`
   (0,2,0) is enough and these rules win uncontested. If you ever add a hero
   rule to home-deck.css it will load later and take over on source order —
   put it here instead.
------------------------------------------------------------------------- */
.hero.hero-reg{
  --reg-line: oklch(0.96 0.005 220 / 0.62);
  --reg-hair: oklch(0.96 0.005 220 / 0.24);   /* hairline that survives a photo under it */
  --reg-snap: cubic-bezier(0.55, 0.055, 0.675, 0.19);   /* ease-in: contact, not fade */
  /* .site-head is sticky IN FLOW, so a plain 100svh hero hangs its own bottom
     trim exactly one header below the fold. Measured 79.4px and flat across
     390 / 768 / 1440 (the nav row never wraps — below 640 .nav-links is
     swapped for the shorter <details> button). This is a min-height, so a
     header that grows under user text zoom costs a few px past the fold and
     nothing else. */
  --head-h: 80px;
  --trim: clamp(14px, 2vw, 26px);      /* crop marks sit on this line */
  --furn: clamp(30px, 3.6vw, 52px);    /* slug + registration target line */
  position:relative;
  min-height:calc(100svh - var(--head-h));
  display:flex;flex-direction:column;justify-content:center;
  overflow:hidden;
  border-bottom:1px solid var(--line); /* a trim rule instead of the old chevron notch */
  padding:calc(var(--furn) + 38px) 0 calc(var(--furn) + 30px);
}

/* ---- the sheet ---- */
.hero.hero-reg .hero-proof{position:absolute;inset:0;margin:0}
/* The one earned promotion on the page. This plate is scrubbed continuously
   by the hero-exit ScrollTrigger (js/home.js: scale 1.04→1.14, yPercent -2→4)
   and the trigger stays live for the whole session — scrolling back up
   re-scrubs it. Re-promoting the largest image on the page on every scroll
   direction change costs more than holding one layer, so this one stays.
   It is a single element, not a class of them, which is the difference
   between a hint and a leak. */
.hero.hero-reg .hero-bg{
  position:absolute;inset:0;width:100%;height:100%;
  object-fit:cover;object-position:62% 52%;
  will-change:transform;
}
/* …but under reduced motion the exit timeline is never built, so the plate
   can never move and the layer is pure cost. Release it. */
@media (prefers-reduced-motion: reduce){
  .hero.hero-reg .hero-bg{will-change:auto}
}

/* MEASURED, NOT ESTIMATED. The scrim is four stacked layers:
     1. a flat floor over the whole sheet — this is what carries the
        one-column layouts, where the type runs the full width and the
        reading side is the whole photo;
     2. a reading-side ramp, near-solid where the type column sits and
        released on the right so the truck is still a photograph;
     3+4. head and foot ramps that settle the sheet under the sticky header
        and hand off to the next band's ground.
   Worst-case body-text contrast over the composited result is reported in
   the build notes; the floor was raised until the sampled minimum cleared
   4.5:1 with margin. Do not thin these without re-sampling. */
.hero.hero-reg .hero-scrim{
  position:absolute;inset:0;pointer-events:none;
  background:
    linear-gradient(oklch(0.11 0.02 265 / 0.50), oklch(0.11 0.02 265 / 0.50)),
    linear-gradient(97deg,
      oklch(0.10 0.02 265 / 0.90) 0%,
      oklch(0.10 0.02 265 / 0.86) 40%,
      oklch(0.11 0.02 265 / 0.48) 68%,
      oklch(0.12 0.02 265 / 0.10) 94%,
      oklch(0.12 0.02 265 / 0.06) 100%),
    linear-gradient(oklch(0.09 0.02 265 / 0.55), transparent 20%),
    linear-gradient(transparent 58%, oklch(0.16 0.025 265 / 0.90) 100%);
}

/* ---- the type, over the sheet ---- */
.hero.hero-reg .hero-inner{
  position:relative;z-index:2;width:100%;
  display:grid;grid-template-columns:minmax(0,1.32fr) minmax(0,0.68fr);
  gap:clamp(24px,4vw,56px);align-items:end;
}
.hero.hero-reg .hero-copy{grid-column:1;min-width:0;max-width:none}
.hero.hero-reg h1{
  font-size:min(var(--t-hero),12vw);
  line-height:0.96;letter-spacing:-0.03em;
  margin:0;color:var(--ink);max-width:14ch;
}
.hero.hero-reg h1 em{font-style:normal;color:var(--miami);display:block}
.hero.hero-reg .hero-sub{
  color:oklch(0.92 0.01 250);   /* lifted for the photo ground; still on-ramp */
  max-width:46ch;font-size:var(--t-lede);line-height:1.6;
  margin-top:22px;text-wrap:pretty;
}
.hero.hero-reg .hero-ctas{display:flex;gap:12px;flex-wrap:wrap;margin-top:34px}
.hero.hero-reg .btn:focus-visible{outline:3px solid var(--ink);outline-offset:4px}

/* trust row: three plates in a hairline register, not three floating words.
   Cell 1 stays flush left so it registers with the headline above it. The
   rules use --reg-hair, not --line: a 0.29-lightness hairline disappears
   against a photograph. */
.hero.hero-reg .hero-trust{
  list-style:none;display:grid;gap:0;margin-top:36px;
  grid-template-columns:repeat(3,minmax(0,1fr));
  border-top:1px solid var(--reg-hair);
}
.hero.hero-reg .hero-trust li{
  min-width:0;   /* grid item: don't let a long word push the track wider */
  padding:18px 20px 0 0;
  font-size:var(--t-caption);line-height:1.5;color:oklch(0.84 0.015 250);
  text-wrap:pretty;
}
.hero.hero-reg .hero-trust li + li{border-left:1px solid var(--reg-hair);padding-left:20px}
/* Martian Mono, per DESIGN.md: technical labels are mono everywhere else on
   the site (.dk-eyebrow and ~50 siblings) and these two were the last rules
   still setting the display face. Mono is ~1.4x wider than tracked
   Bricolage at the same size, so tracking drops from 0.14em to 0.08em —
   still inside the 0.05–0.14em band — to keep the three tracks from
   wrapping. */
.hero.hero-reg .hero-trust li b{
  display:block;font-family:var(--mono);font-weight:600;font-size:var(--m-label);
  letter-spacing:0.08em;text-transform:uppercase;color:var(--miami);margin-bottom:7px;
}

/* spec register: the two operating numbers, bottom of the sheet opposite
   the copy. Opaque plates — they are furniture taped to the proof, and an
   opaque ground is also what guarantees their contrast over the photo. */
.hero.hero-reg .hero-spec{
  grid-column:2;justify-self:end;align-self:end;
  width:min(100%,340px);
  display:grid;grid-template-columns:1fr 1fr;gap:1px;
  background:var(--line);border:1px solid var(--line);
}

/* ---- registration furniture at the trim ---- */
.hero.hero-reg .hero-slug{
  position:absolute;z-index:3;
  top:var(--furn);left:var(--furn);right:calc(var(--furn) + 56px);
  display:flex;flex-wrap:wrap;align-items:center;gap:0 12px;
  font-family:var(--mono);font-weight:500;font-size:var(--m-label);
  letter-spacing:0.08em;text-transform:uppercase;color:oklch(0.84 0.015 250);
}
.hero.hero-reg .hero-slug span{display:inline-flex;align-items:center;gap:12px}
.hero.hero-reg .hero-slug span:first-child{color:var(--miami)}
.hero.hero-reg .hero-slug span + span::before{
  content:"";width:16px;height:1px;background:var(--reg-hair);flex:none;
}

/* crop marks: an L at each trim corner of the sheet, i.e. of the viewport */
.hero.hero-reg .hero-crop{position:absolute;z-index:3;width:22px;height:22px;pointer-events:none}
.hero.hero-reg .hero-crop::before,
.hero.hero-reg .hero-crop::after{content:"";position:absolute;background:var(--reg-line)}
.hero.hero-reg .hero-crop::before{width:100%;height:1px}
.hero.hero-reg .hero-crop::after{height:100%;width:1px}
.hero.hero-reg .c-tl{top:var(--trim);left:var(--trim)}
.hero.hero-reg .c-tr{top:var(--trim);right:var(--trim)}
.hero.hero-reg .c-bl{bottom:var(--trim);left:var(--trim)}
.hero.hero-reg .c-br{bottom:var(--trim);right:var(--trim)}
.hero.hero-reg .c-tl::before,.hero.hero-reg .c-tr::before{top:0}
.hero.hero-reg .c-bl::before,.hero.hero-reg .c-br::before{bottom:0}
.hero.hero-reg .c-tl::after,.hero.hero-reg .c-bl::after{left:0}
.hero.hero-reg .c-tr::after,.hero.hero-reg .c-br::after{right:0}

/* registration target: three plates land as one mark, head of the sheet
   opposite the slug */
.hero.hero-reg .hero-target{
  position:absolute;z-index:3;
  top:calc(var(--furn) - 1px);right:var(--furn);
  width:30px;height:30px;pointer-events:none;
}
.hero.hero-reg .hero-target i{
  position:absolute;inset:0;border-radius:50%;   /* a target is a circle, not a rounded box */
  border:1.5px solid currentColor;mix-blend-mode:screen;
}
.hero.hero-reg .hero-target i::before,
.hero.hero-reg .hero-target i::after{content:"";position:absolute;background:currentColor}
.hero.hero-reg .hero-target i::before{left:50%;top:-8px;bottom:-8px;width:1.5px;margin-left:-0.75px}
.hero.hero-reg .hero-target i::after{top:50%;left:-8px;right:-8px;height:1.5px;margin-top:-0.75px}
/* Second beat of the signature: the headline registers (js/home.js), then
   the mark does. Plates accelerate into contact and vanish on impact. */
.hero.hero-reg .pl-c{color:var(--plate-c);animation:reg-plate-c 1s var(--reg-snap) 0.9s both}
.hero.hero-reg .pl-m{color:var(--plate-m);animation:reg-plate-m 1s var(--reg-snap) 0.9s both}
.hero.hero-reg .pl-k{color:var(--ink);animation:reg-plate-k 0.62s var(--ease) 1.55s both}
@keyframes reg-plate-c{
  0%{transform:translate(-15px,8px) rotate(-3deg);opacity:0}
  12%{opacity:0.9}
  66%{transform:translate(0,0) rotate(0deg);opacity:0.9}
  88%,100%{transform:translate(0,0) rotate(0deg);opacity:0}
}
@keyframes reg-plate-m{
  0%{transform:translate(14px,-9px) rotate(3deg);opacity:0}
  12%{opacity:0.9}
  66%{transform:translate(0,0) rotate(0deg);opacity:0.9}
  88%,100%{transform:translate(0,0) rotate(0deg);opacity:0}
}
/* the mark recoils once against the impact, then settles */
@keyframes reg-plate-k{
  0%{transform:scale(1,1)}
  14%{transform:scale(1.09,0.93)}
  42%{transform:scale(0.975,1.03)}
  72%{transform:scale(1.01,0.99)}
  100%{transform:scale(1,1)}
}
@media (prefers-reduced-motion: reduce){
  .hero.hero-reg .pl-c,.hero.hero-reg .pl-m{animation:none;opacity:0}
  .hero.hero-reg .pl-k{animation:none}
}

/* Plain block. The position/inset/z-index/border/backdrop-filter resets that
   used to sit here were guards against `body.deck .hero…` rules that no longer
   exist in any stylesheet — home.css is the sole owner of the hero now. */
.hero.hero-reg .hero-chip{
  background:var(--night-2);border-top:3px solid var(--miami);
  padding:18px 18px 16px;
}
.hero.hero-reg .hero-chip b{
  display:block;font-family:var(--disp);font-weight:800;font-size:var(--t-stat);
  color:var(--ink);line-height:1;letter-spacing:-0.03em;font-variant-numeric:tabular-nums;
}
.hero.hero-reg .hero-chip b small{font-size:var(--m-spec);color:var(--miami);letter-spacing:0.04em}
.hero.hero-reg .hero-chip span{
  display:block;margin-top:9px;font-size:var(--t-caption);color:var(--dim);
}

/* The "Services bento grid" block that stood here (.services, .svc-grid,
   .svc-box, .sb-body, .sb-tags, .sb-link, .sb-photo/.sb-print/.sb-sys/.sb-web/
   .sb-consult, .sb-feed, .sbf*) is gone. Not one of those class names appears
   in any live page - index.html ships the deck plates instead - and the only
   markup that ever used them lives under _archive/. */

/* ---------- dstnct.dev wordmark + system window ---------------------------
   What is left of the old "System (dstnct.dev)" band. The section chrome
   (.system, .sys-grid, .sys-kicker, .sys-sub, .sys-feats, .sys-ctas,
   .sys-note, .about-kicker) matched nothing on any live page and is gone,
   but the rest is NOT dead: projects.html renders a .sm-window with the
   .dd-mark lockup in its bar, and js/store*.js never touches these. Verified
   against every non-archive page before cutting. .sm-dm went with the band —
   only _archive/ ever emitted that tag.
--------------------------------------------------------------------------- */
.dd-mark{
  font-family:"Schibsted Grotesk",system-ui,sans-serif;
  font-weight:700;letter-spacing:-0.02em;text-transform:none;
  font-size:var(--t-lede);color:#fff;
}
.dd-dot{color:#00AECB}
.dd-mark-sm{font-size:var(--t-caption) !important;color:var(--dim) !important;font-weight:700 !important;letter-spacing:-0.01em !important}
.sm-bar .dd-dot{margin-left:0}
.sm-window{
  background:var(--panel);border:1px solid var(--line);
  overflow:hidden;
}
.sm-bar{display:flex;align-items:center;gap:7px;padding:13px 16px;border-bottom:1px solid var(--line)}
.sm-bar i{width:9px;height:9px;background:var(--line)}
.sm-bar span{margin-left:8px}
.sm-kpis{display:grid;grid-template-columns:repeat(3,1fr);border-bottom:1px solid var(--line)}
.sm-kpi{padding:18px 14px;border-right:1px solid var(--line)}
.sm-kpi:last-child{border-right:0}
.sm-kpi b{display:block;font-size:var(--t-h4);font-weight:800;color:var(--miami)}
.sm-kpi span{font-size:var(--t-caption);color:var(--dim);line-height:1.3;display:block;margin-top:3px}
.sm-feed{list-style:none;padding:8px 0}
.sm-feed li{
  display:flex;align-items:center;gap:11px;
  padding:12px 16px;font-size:var(--t-caption);color:oklch(0.87 0.012 250);
}
.sm-feed li + li{border-top:1px solid oklch(0.25 0.03 265)}
.sm-feed b{color:#fff}
.sm-tag{
  font-family:var(--disp);font-weight:700;
  font-size:var(--m-label);font-weight:600;letter-spacing:0.08em;
  padding:4px 8px;flex-shrink:0;color:var(--night-2);
}
.sm-call{background:oklch(0.68 0.16 25);color:var(--night-2)}
.sm-book{background:oklch(0.72 0.14 155)}
.sm-rev{background:oklch(0.8 0.13 90)}

/* ---------- Gallery masonry ---------- */
.masonry{columns:3;column-gap:16px}
.masonry figure{
  break-inside:avoid;margin-bottom:16px;position:relative;overflow:hidden;
  border:1px solid var(--line);
}
.masonry img{width:100%;display:block;transition:transform .5s var(--ease)}
.masonry figure:hover img{transform:scale(1.03)}
/* The caption is the slug line on a proof — it names the job. It used to be
   opacity:0 until :hover, which meant nine captions that a phone, a keyboard
   and a scripting-off browser could never reach. There is no opacity here at
   all now: they are simply printed, like everything else on the sheet.
   (Layout, gradient and face come from `body.deck .masonry figcaption` in
   css/home-deck.css, which outranks this block; these declarations are the
   fallback for any page that renders a .masonry without the deck theme.) */
.masonry figcaption{
  position:absolute;left:0;right:0;bottom:0;
  padding:26px 14px 12px;
  font-family:var(--disp);font-weight:700;
  font-size:var(--m-label);font-weight:600;letter-spacing:0.06em;text-transform:uppercase;color:var(--ink);
  background:linear-gradient(transparent, oklch(0.13 0.02 265 / 0.9));
}
.m-tall img{aspect-ratio:3/4.4;object-fit:cover}

/* ---------- Reviews ---------- */
.rev-grid{display:grid;grid-template-columns:minmax(0,1.15fr) minmax(0,0.85fr);gap:clamp(34px,5vw,80px);align-items:start}
.rev-rotator{
  background:var(--panel);border:1px solid var(--line);padding:clamp(28px,4vw,48px);
}
.rev-stars{color:var(--miami);font-size:1.2rem;letter-spacing:0.2em}
#revQuote{min-height:170px;display:flex;flex-direction:column;justify-content:center}
#revQuote p{
  font-size:var(--t-h3);font-weight:600;line-height:1.3;
  color:var(--ink);letter-spacing:-0.01em;text-wrap:pretty;margin:16px 0 14px;
}
#revQuote cite{font-style:normal;font-size:var(--t-caption);color:var(--dim);font-weight:600}
.rev-dots{display:flex;gap:8px;margin-top:12px}
.rev-dots button{
  width:10px;height:10px;border-radius:0;border:0;background:var(--line);cursor:pointer;
  transition:background .25s, transform .25s;
}
.rev-dots button.on{background:var(--miami);transform:scale(1.25)}
/* The reviews column runs beside a rotator, not across the page, so its
   headline steps down one rung off --t-h1. This used to be an inline
   `style="font-size:var(--t-h2)"` on the markup with a dead `.rev-why .sec-h`
   rule sitting here doing nothing. `.dk-h` itself is defined in
   css/home-deck.css and is not this file's to edit — but the component scope
   is (0,2,0) against that file's (0,1,0), so it wins on specificity without
   touching it. */
.rev-why .dk-h{font-size:var(--t-h2);margin-bottom:8px}
.why-list{list-style:none;margin-top:16px}
.why-list li{padding:14px 0 14px 26px;position:relative;color:var(--dim);font-size:var(--t-body);border-bottom:1px solid var(--line)}
.why-list li:last-child{border-bottom:0}
.why-list b{display:block;color:var(--ink);font-size:var(--t-body);margin-bottom:2px}
.why-list li::before{
  content:"";position:absolute;left:0;top:21px;width:11px;height:11px;
  background:var(--miami);
}

/* ---------- About ---------- */
.about-grid{display:grid;grid-template-columns:minmax(0,0.9fr) minmax(0,1.1fr);gap:clamp(34px,5vw,80px);align-items:center}
.about-photo{position:relative;overflow:hidden;border:1px solid var(--line)}
.about-photo img{aspect-ratio:4/5;object-fit:cover;width:100%}
.about-photo figcaption{
  position:absolute;left:12px;bottom:12px;
  background:oklch(0.16 0.025 265 / 0.92);border:1px solid var(--line);
  padding:8px 12px;
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;letter-spacing:0.05em;text-transform:uppercase;color:var(--ink);
}
.about-body > p{color:var(--dim);margin-top:16px;max-width:58ch;text-wrap:pretty}
.about-facts{list-style:none;display:flex;gap:30px;flex-wrap:wrap;margin-top:26px}
.about-facts li{font-size:var(--t-caption);color:var(--dim)}
.about-facts b{display:block;color:var(--ink);font-size:var(--t-body)}

/* ---------- Who we work with ---------- */
.who-wall{
  list-style:none;margin-top:40px;
  display:grid;grid-template-columns:repeat(auto-fit,minmax(250px,1fr));gap:14px;
}
.who-wall li{
  border:1px solid var(--line);padding:18px 20px;
  background:var(--panel);
  transition:border-color .25s, background .25s, transform .25s var(--ease);
}
.who-wall li:hover{border-color:var(--miami-deep);background:var(--panel-2);transform:translateY(-3px)}
.who-wall b{display:block;font-size:var(--t-body)}
.who-wall span{font-size:var(--t-caption);color:var(--dim)}

/* ---------- FAQ ---------- */
.faq{padding:clamp(70px,9vw,120px) 0}
.faq-cols{margin-top:36px;columns:2;column-gap:40px}
.faq details{
  break-inside:avoid;margin-bottom:14px;
  background:var(--panel);padding:0 20px;
  border:1px solid var(--line);transition:border-color .25s;
}
.faq details[open]{border-color:var(--miami-deep)}
.faq summary{
  cursor:pointer;list-style:none;
  display:flex;justify-content:space-between;align-items:center;gap:16px;
  padding:17px 0;font-weight:700;font-size:var(--t-body);color:var(--ink);
}
.faq summary::-webkit-details-marker{display:none}
.faq summary::after{
  content:"";width:10px;height:10px;flex-shrink:0;
  background:var(--miami);
  transition:transform .3s var(--ease), background .3s;
}
.faq details[open] summary::after{transform:scale(0.5)}
.faq details p{color:var(--dim);font-size:var(--t-body);padding:0 0 18px;max-width:60ch}
.faq details a{color:var(--miami);font-weight:600}

/* ---------- Contact ---------- */
.contact{background:var(--night-2);border-top:1px solid var(--line);padding:clamp(70px,9vw,120px) 0 clamp(60px,8vw,100px)}
.contact-grid{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,0.85fr);gap:clamp(34px,5vw,70px);align-items:center}
.contact h2{color:#fff;font-size:var(--t-h1);line-height:1.02}
.contact-copy > p{color:var(--dim);margin:18px 0 30px;max-width:50ch;text-wrap:pretty}
.contact-ctas{display:flex;gap:14px;flex-wrap:wrap}
.contact-meta{margin-top:28px;font-size:var(--t-caption);color:var(--dim);line-height:1.9;overflow-wrap:anywhere}

/* ---------- Footer ---------- */
.site-foot{background:var(--night);color:var(--dim);padding:clamp(50px,6vw,80px) 0 0;border-top:1px solid var(--line)}
.foot-grid{
  display:grid;
  grid-template-columns:minmax(0,1.3fr) minmax(0,0.7fr) minmax(0,0.8fr) minmax(0,1.1fr);
  gap:clamp(26px,4vw,50px);
  padding-bottom:44px;
}
/* long addresses must wrap, not push the page wide at large text sizes */
.foot-col a,.foot-col span,.foot-base{overflow-wrap:anywhere}
.foot-brand > img:first-child{margin-bottom:14px}
.foot-word{height:16px;width:auto;margin-bottom:14px}
.foot-brand p{font-size:var(--t-caption);max-width:32ch;text-wrap:pretty;overflow-wrap:break-word}
.foot-col{display:flex;flex-direction:column;gap:9px;font-size:var(--t-caption)}
.foot-col b{color:var(--ink);font-size:var(--t-caption);margin-bottom:4px}
.foot-col a:hover{color:var(--miami)}
.foot-base{
  display:flex;justify-content:space-between;flex-wrap:wrap;gap:12px;
  border-top:1px solid var(--line);
  padding-top:20px;padding-bottom:26px;
  font-size:var(--t-caption);
}
.foot-social{display:flex;gap:18px}
.foot-social a:hover{color:var(--miami)}

/* ---------- Mobile call bar ---------- */
.callbar{
  display:none;
  position:fixed;left:12px;right:12px;bottom:12px;z-index:var(--z-callbar);
  background:var(--miami);color:var(--night-2);text-align:center;
  font-weight:800;font-size:var(--t-body);
  padding:15px;
}

/* ---------- Responsive ---------- */
@media (max-width:980px){
  /* one column: type block, then the spec register under it. The furniture
     stays at the trim — it is the point. */
  .hero.hero-reg .hero-inner{grid-template-columns:minmax(0,1fr);gap:clamp(24px,4vw,34px)}
  .hero.hero-reg .hero-spec{grid-column:1;justify-self:stretch;width:100%}
  /* the headline gets the measure back: at 768 a 14ch cap left 40% of the
     column empty, which is a two-column setting stranded in one column. */
  .hero.hero-reg h1{max-width:20ch}
  .hero.hero-reg .hero-sub{margin-top:18px}
  .hero.hero-reg .hero-ctas{margin-top:26px}
  .hero.hero-reg .hero-trust{margin-top:30px}
  .hero.hero-reg .hero-bg{object-position:64% 50%}
  /* The type now runs the FULL width of the sheet, so the reading-side ramp
     has nothing left to protect — it is replaced by a flat floor plus head
     and foot ramps. Same sampled-contrast rule applies: these numbers were
     read off the composited pixels, not guessed. */
  .hero.hero-reg .hero-scrim{
    background:
      linear-gradient(oklch(0.10 0.02 265 / 0.80), oklch(0.10 0.02 265 / 0.80)),
      linear-gradient(oklch(0.09 0.02 265 / 0.55), transparent 18%),
      linear-gradient(transparent 52%, oklch(0.13 0.02 265 / 0.80) 100%);
  }
}
@media (max-width:900px){
  .rev-grid,.about-grid,.contact-grid{grid-template-columns:minmax(0,1fr)}
  .masonry{columns:2}
  .faq-cols{columns:1}
  .foot-grid{grid-template-columns:1fr 1fr}
}
@media (max-width:640px){
  /* phone: one screen of hero, not one and a half. Every band tightens and
     the trust labels run into their own lines instead of sitting on top of
     them — same three facts, roughly a third of the column height. */
  .hero.hero-reg{
    --furn: 22px;
    padding-top:calc(var(--furn) + 30px);
    padding-bottom:calc(var(--furn) + 24px);
  }
  .hero.hero-reg .hero-inner{gap:20px}
  /* lede steps down to the prose floor on a 390px column — 18px cost four
     lines of hero height and bought nothing at this measure */
  .hero.hero-reg .hero-sub{margin-top:14px;font-size:var(--t-body)}
  .hero.hero-reg .hero-ctas{margin-top:20px}
  .hero.hero-reg .hero-trust{grid-template-columns:minmax(0,1fr);margin-top:22px}
  .hero.hero-reg .hero-trust li{padding:11px 0}
  .hero.hero-reg .hero-trust li b{display:inline;margin-bottom:0;margin-right:9px}
  .hero.hero-reg .hero-trust li + li{border-left:0;border-top:1px solid var(--reg-hair);padding-left:0}
  .hero.hero-reg .hero-chip{padding:13px 14px 12px}
  .hero.hero-reg .btn-lg{padding:15px 26px}
  /* Martian Mono is a wide face: the three-part slug does not fit a 390px
     trim on one line at 0.08em. Tracking goes to the 0.05em floor and the
     separator rules tighten; if it still wraps it wraps to two lines — the
     flex container wraps, so it can never push the page sideways. */
  .hero.hero-reg .hero-slug{letter-spacing:0.05em;gap:0 9px;right:calc(var(--furn) + 46px)}
  .hero.hero-reg .hero-slug span{gap:9px}
  .hero.hero-reg .hero-slug span + span::before{width:9px}
  .hero.hero-reg .hero-target{width:26px;height:26px}
  /* The desktop row does not fit a 390px header, so it hands off to the
     <details> disclosure rather than to nothing. Both halves are declared
     here so the swap is a single edit and neither can be left showing. */
  .nav-links{display:none}
  .nav-m{display:block}
  .site-head nav{gap:12px}
  .masonry{columns:1}
  .foot-grid{grid-template-columns:1fr}
  .callbar{display:block}
  /* The callbar is fixed at bottom:12px and measures 55.6px tall, so it
     occupies 67.6px of the viewport. 64px left the last 3.6px of the page
     under it; 80px clears the bar with a 12px gap of its own. */
  body{padding-bottom:80px}
}

/* ================= Subpages ================= */
.crumb{
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;letter-spacing:0.12em;text-transform:uppercase;
  color:var(--miami);display:flex;align-items:center;gap:8px;
}
.crumb a{color:var(--dim)}
.crumb a:hover{color:var(--miami)}
.page-hero{padding:clamp(60px,8vw,110px) 0 clamp(40px,5vw,70px);border-bottom:1px solid var(--line)}
.page-hero.has-media{border-bottom:0;padding-bottom:0}
.ph-grid{display:grid;grid-template-columns:minmax(0,1.1fr) minmax(0,0.9fr);gap:clamp(30px,5vw,70px);align-items:center}
.page-hero h1{font-size:var(--t-page);line-height:1.0;letter-spacing:-0.03em;margin:18px 0 16px}
.page-hero h1 .acc{display:block}
.ph-sub{color:var(--dim);max-width:54ch;font-size:var(--t-lede);text-wrap:pretty}
.ph-ctas{display:flex;gap:14px;flex-wrap:wrap;margin-top:28px}
.ph-media{overflow:hidden;border:1px solid var(--line)}
.ph-media img{width:100%;aspect-ratio:4/3.4;object-fit:cover}

/* The subpage stat strip (.stat-strip, .stat and its b/span/i) is gone with
   the same evidence as the two blocks above: no live page emits those class
   names, only the seven _archive/system pages ever did. The deck theme's
   .dk-slab carries this job now. .sec-h / .sec-sub went the same way. */

/* alternating splits */
.split-sec{padding:clamp(60px,8vw,100px) 0}
.split{display:grid;grid-template-columns:1fr 1fr;gap:clamp(30px,5vw,80px);align-items:center;padding:clamp(30px,4vw,50px) 0}
.split + .split{border-top:1px solid var(--line)}
.split.flip .split-media{order:2}
.split-media{overflow:hidden;border:1px solid var(--line)}
.split-media img{width:100%;aspect-ratio:4/3;object-fit:cover}
.split-copy h2{font-size:var(--t-h2);line-height:1.1}
.split-copy > p{color:var(--dim);margin-top:14px;max-width:54ch;text-wrap:pretty}
.split-copy .plain{list-style:none;margin-top:18px}
.split-copy .plain li{padding:10px 0 10px 24px;position:relative;color:var(--dim);font-size:var(--t-body);border-bottom:1px solid var(--line)}
.split-copy .plain li:last-child{border-bottom:0}
.split-copy .plain li::before{content:"";position:absolute;left:0;top:17px;width:9px;height:9px;background:var(--miami)}
.split-copy .plain b{color:var(--ink)}

/* category grid (photo page) */
.cat-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(230px,1fr));gap:14px;margin-top:40px}
.cat-grid figure{position:relative;overflow:hidden;border:1px solid var(--line)}
.cat-grid img{width:100%;aspect-ratio:4/5;object-fit:cover;transition:transform .5s var(--ease)}
.cat-grid figure:hover img{transform:scale(1.04)}
.cat-grid figcaption{
  position:absolute;left:0;right:0;bottom:0;padding:30px 14px 12px;
  font-weight:700;color:#fff;
  background:linear-gradient(transparent, oklch(0.13 0.02 265 / 0.92));
}

/* numbered fixes (system page) */
.fixes{counter-reset:fx}
.fix{
  display:grid;grid-template-columns:minmax(0,0.42fr) minmax(0,0.58fr);gap:clamp(24px,4vw,60px);
  padding:clamp(30px,4vw,46px) 0;border-top:1px solid var(--line);counter-increment:fx;
}
.fix-head::before{
  content:"0" counter(fx);
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;color:var(--miami);letter-spacing:0.1em;
  display:block;margin-bottom:10px;
}
.fix-head b{display:block;font-size:var(--t-stat);font-weight:800;color:var(--miami);letter-spacing:-0.02em;line-height:1}
.fix-head span{display:block;color:var(--dim);font-size:var(--t-body);margin-top:8px;max-width:30ch;text-wrap:pretty}
.fix-body h3{font-size:var(--t-h3);margin-bottom:10px}
.fix-body > p{color:var(--dim);font-size:var(--t-body);max-width:56ch;text-wrap:pretty}
.fix-body .plain{list-style:none;margin-top:14px}
.fix-body .plain li{padding:8px 0 8px 22px;position:relative;color:var(--dim);font-size:var(--t-body)}
.fix-body .plain li::before{content:"→";position:absolute;left:0;color:var(--miami);font-weight:700}

/* mini package tickets (websites page) */
.mini-tix{display:grid;grid-template-columns:repeat(auto-fit,minmax(240px,1fr));gap:16px;margin-top:36px}
.mini-tik{
  background:var(--panel);border:1px solid var(--line);padding:24px;
  transition:border-color .25s, transform .3s var(--ease);
}
.mini-tik:hover{border-color:var(--miami-deep);transform:translateY(-3px)}
.mini-tik.feat{border-color:var(--miami)}
.mini-tik h3{font-size:var(--t-h4)}
.mini-tik .mt-price{font-size:var(--t-h4);font-weight:800;color:var(--miami);margin:8px 0 6px;letter-spacing:-0.02em}
.mini-tik p{color:var(--dim);font-size:var(--t-body);text-wrap:pretty}
.mini-tik .sb-link{margin-top:12px}

/* projects page */
.proj{
  display:grid;grid-template-columns:minmax(0,0.95fr) minmax(0,1.05fr);gap:clamp(28px,4.5vw,70px);
  align-items:center;padding:clamp(40px,5.5vw,70px) 0;
}
.proj + .proj{border-top:1px solid var(--line)}
.proj.flip .proj-media{order:2}
.proj-media{overflow:hidden;border:1px solid var(--line);position:relative}
.proj-media img{width:100%;aspect-ratio:4/3.1;object-fit:cover}
.proj-num{
  position:absolute;top:14px;left:14px;
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;letter-spacing:0.1em;
  background:oklch(0.16 0.025 265 / 0.9);border:1px solid var(--line);
  padding:6px 10px;color:var(--miami);
}
.proj-tags{list-style:none;display:flex;gap:8px;flex-wrap:wrap;margin-bottom:14px}
.proj-tags li{
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;letter-spacing:0.06em;text-transform:uppercase;
  color:var(--miami);background:var(--miami-wash);
  border:1px solid oklch(0.79 0.128 208 / 0.3);
  padding:4px 9px;
}
.proj-copy h2{font-size:var(--t-h2);line-height:1.06}
.proj-copy .proj-role{font-family:var(--disp);font-weight:700;font-size:var(--m-label);color:var(--dim);letter-spacing:0.08em;text-transform:uppercase;margin-top:8px}
.proj-copy > p{color:var(--dim);margin-top:14px;max-width:56ch;text-wrap:pretty}
.proj-stats{display:flex;gap:28px;flex-wrap:wrap;margin-top:22px}
.proj-stats div b{display:block;font-size:var(--t-h4);font-weight:800;color:var(--miami);letter-spacing:-0.01em}
.proj-stats div span{font-size:var(--t-caption);color:var(--dim)}
.proj-media .sm-window{border:0}
.proj-media .sm-bar{justify-content:flex-end}
.proj-media .sm-bar i{display:none}

/* sources note */
.src-note{
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);color:var(--faint);
  max-width:60ch;line-height:1.8;letter-spacing:0.02em;
  padding:26px 0 0;
}

@media (max-width:900px){
  .ph-grid,.split,.fix,.proj{grid-template-columns:1fr}
  .split.flip .split-media,.proj.flip .proj-media{order:0}

}

/* ================= Services dropdown ================= */
.nav-drop{position:relative}
/* A menu button, not a run of inline text — no 24px exemption applies to it,
   and min-height matches the links it sits in a row with. */
.nav-drop-btn{
  display:flex;align-items:center;gap:6px;min-height:24px;
  background:linear-gradient(var(--miami),var(--miami)) no-repeat 0 100%/0 2px;
  border:0;cursor:pointer;
  font-family:var(--disp);font-size:var(--t-caption);font-weight:600;color:var(--dim);
  padding:0 0 3px;
  transition:color .25s, background-size .3s var(--ease);
}
.nav-drop-btn svg{width:10px;height:10px;transition:transform .25s var(--ease)}
.nav-drop-btn:focus-visible{outline:3px solid var(--miami);outline-offset:3px}
.nav-drop:hover .nav-drop-btn,.nav-drop.open .nav-drop-btn{color:var(--ink);background-size:100% 2px}
.nav-drop.open .nav-drop-btn svg{transform:rotate(180deg)}
.nav-drop-menu{
  position:absolute;top:calc(100% + 14px);left:-16px;
  min-width:270px;
  background:var(--panel);border:1px solid var(--line);
  padding:8px;
  opacity:0;visibility:hidden;transform:translateY(8px);
  transition:opacity .22s var(--ease), transform .22s var(--ease), visibility .22s;
  z-index:60;
}
.nav-drop:hover .nav-drop-menu,.nav-drop.open .nav-drop-menu,.nav-drop:focus-within .nav-drop-menu{
  opacity:1;visibility:visible;transform:translateY(0);
}
.nav-drop-menu::before{content:"";position:absolute;top:-14px;left:0;right:0;height:14px}
.nav-drop-menu a{
  display:block;padding:10px 12px;
  background:none;transition:background .2s;
}
.nav-drop-menu a:hover{background:var(--panel-2)}
.nav-drop-menu a b{display:block;font-size:var(--t-body);color:var(--ink)}
.nav-drop-menu a span{display:block;font-size:var(--t-caption);color:var(--dim);margin-top:1px}
.nav-drop-menu .nd-all{
  border-top:1px solid var(--line);margin-top:6px;padding-top:12px;
  font-weight:700;font-size:var(--t-caption);color:var(--miami);
}
.nav-drop-menu .nd-all:hover{background:none;color:oklch(0.85 0.11 208)}

/* ================= Lead form ================= */
.lead-form{
  background:var(--panel);border:1px solid var(--line);
  padding:clamp(22px,3vw,32px);
}
.lf-row{display:grid;gap:14px}
.lf-2col{grid-template-columns:1fr 1fr}
.lf-field{display:flex;flex-direction:column;gap:6px;margin-bottom:14px;border:0;padding:0;min-width:0}
.lf-field label,.lf-field legend{
  font-size:var(--t-caption);font-weight:700;color:var(--ink);
}
.lf-field label i{font-style:normal;color:var(--miami)}
.lf-field input,.lf-field select,.lf-field textarea{
  font-family:var(--disp);font-size:var(--t-body);color:var(--ink);
  /* border-radius:0 stays: iOS Safari's UA sheet rounds text inputs, selects
     and textareas. Every other radius reset on this sheet was overriding
     nothing and has been removed. */
  background:var(--night);border:1px solid var(--line);border-radius:0;
  padding:12px 14px;width:100%;
  transition:border-color .2s;
}
.lf-field textarea{resize:vertical;min-height:96px}
.lf-field input::placeholder,.lf-field textarea::placeholder{color:var(--faint)}
.lf-field input:hover,.lf-field select:hover,.lf-field textarea:hover{border-color:oklch(0.4 0.04 250)}
.lf-field input:focus,.lf-field select:focus,.lf-field textarea:focus{outline:none}
/* 1px of border colour is not an indicator — WCAG 2.4.11 wants 2px of contrast
   change. Shadows are banned, so the ring is an outline: 2px, square, sitting
   1px off the control so the cyan reads against --panel rather than against
   the control's own edge. */
.lf-field input:focus-visible,.lf-field select:focus-visible,.lf-field textarea:focus-visible{
  border-color:var(--miami);
  outline:3px solid var(--miami);
  outline-offset:1px;
}
.lf-field select{
  appearance:none;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M1 3l4 4 4-4' fill='none' stroke='%2374809E' stroke-width='1.6'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 14px center;background-size:11px;
  padding-right:38px;
}
.lf-field.lf-invalid input{border-color:oklch(0.62 0.13 25)}
.lf-err{font-size:var(--t-caption);color:oklch(0.72 0.13 25);min-height:0;margin:0}
.lf-err:empty{display:none}
.lf-hint{font-size:var(--t-caption);color:var(--dim);margin:-6px 0 16px}
.lf-chips{display:flex;gap:8px;flex-wrap:wrap}
.lf-chip{position:relative;cursor:pointer}
.lf-chip input{position:absolute;opacity:0;pointer-events:none}
.lf-chip span{
  display:inline-block;
  font-family:var(--disp);font-weight:700;font-size:var(--m-label);font-weight:600;letter-spacing:0.05em;text-transform:uppercase;
  color:var(--dim);background:var(--night);
  border:1px solid var(--line);
  padding:8px 14px;
  transition:color .2s, border-color .2s, background .2s;
  user-select:none;
}
.lf-chip:hover span{border-color:var(--miami-deep);color:var(--ink)}
.lf-chip input:checked + span{
  color:var(--night-2);background:var(--miami);border-color:var(--miami);font-weight:600;
}
/* The real checkbox is opacity:0 / pointer-events:none, so its own UA ring
   paints nothing — the visible chip has to carry the indicator. A shadow
   sweep left this rule empty (`box-shadow:none` and nothing else), which is
   how five checkboxes ended up with no focus state at all.
   Shadows are banned, so: a 2px square outline, offset clear of the chip so
   it is drawn on the form's --panel ground. Cyan on --panel for an unchecked
   chip; on a checked chip the fill is already --miami, so the ring flips to
   --ink and stays legible either way. */
.lf-chip input:focus-visible + span{
  outline:3px solid var(--miami);
  outline-offset:2px;
  border-color:var(--miami);
  color:var(--ink);
}
.lf-chip input:checked:focus-visible + span{
  outline-color:var(--ink);
  color:var(--night-2);
}
.lf-submit{width:100%;text-align:center;margin-top:6px}
.lf-submit[disabled]{opacity:0.6;cursor:default}
.lf-status{font-size:var(--t-caption);color:oklch(0.72 0.13 25);margin-top:10px;text-align:center;min-height:1.2em}
.lf-status a{color:var(--miami);font-weight:600}
.lf-success{
  background:var(--panel);border:1px solid var(--miami-deep);
  padding:clamp(30px,4vw,48px);text-align:center;
}
.lf-check{
  display:inline-flex;align-items:center;justify-content:center;
  width:52px;height:52px;
  background:var(--miami);color:var(--night-2);
  font-size:1.5rem;font-weight:800;margin-bottom:16px;
}
.lf-success h3{font-size:var(--t-h4)}
.lf-success p{color:var(--dim);margin-top:10px;max-width:44ch;margin-inline:auto;text-wrap:pretty}
.lf-success a{color:var(--miami);font-weight:700}
@media (max-width:640px){ .lf-2col{grid-template-columns:1fr} }
