/* ==========================================================================
   build-site BASELINE stylesheet — copy verbatim, then THEME the block below.
   To theme per client, change ONLY: (1) the color tokens, (2) --font-sans /
   --font-display, (3) the --radius-* scale, and load the matching Google font
   <link> in each HTML <head>. Do NOT edit the component rules or structural
   tokens further down — that is what guarantees the consistent, slick result.

   ⛔ THE TOKEN VALUES BELOW ARE PLACEHOLDERS, NOT A PALETTE TO SHIP. They are an
   arbitrary slate-teal + lime example so the file renders before theming. You MUST
   overwrite --primary / --accent / the band + surface colors / the fonts / radius
   with the CLIENT'S MEASURED brand (from 02-brand.spec.json design_system, derived
   from the logo swatches + Firecrawl branding). Shipping a site still on this teal/
   lime/Manrope default when the client's brand is different is THE "every site looks
   the same" defect — it is a build failure, not an acceptable fallback.

   COLOR PAIRING CONTRACT (the fix for white-on-white / invisible header):
   - Keep these EXACT token names — the components read them. Do not rename to
     --brand/--ink/--accent-ink (those are ignored -> defaults -> unreadable text).
   - --text/--text-secondary/--text-muted are for LIGHT bands only (--bg/--surface).
     On dark bands (--dark/--dark-mid/--primary) text is #fff / rgba(255,255,255,.8).
   - --accent is ALWAYS a BRIGHT highlight (CTA fills, dots, underlines). Never a
     text color on a light band. If the brand's main color is dark, it is --primary
     (a band/button color), NOT --accent — pick a separate bright accent.
   - --text must be near-black; --bg near-white. Verify body contrast >=4.5:1.
   ========================================================================== */

:root{
  /* --- FONT (v3 build guide): heavy, tight-tracked grotesque. Helvetica Neue Bold or the
     closest available equivalent; fallback Arial / Helvetica Neue. No rounded, decorative,
     or serif faces anywhere. System stack only — no webfont request. --- */
  --font-sans:'Helvetica Neue',Helvetica,Arial,'Segoe UI',Roboto,system-ui,sans-serif;
  --font-display:'Helvetica Neue',Helvetica,Arial,'Segoe UI',Roboto,system-ui,sans-serif;
  /* --- COLOR (v3 build guide): black primary, silver as the secondary tone used most often,
     graphite for copy needing more contrast, red as SINGLE-POINT emphasis only. No blue. --- */
  --primary:#0D0D0D;        /* black — bands, secondary buttons, headings */
  --primary-dark:#000000;
  --primary-darker:#000000;
  --accent:#B3211B;         /* red — one per section, primary action only */
  --accent-dark:#8E1A15;
  --silver:#C7C7C7;         /* primary secondary tone */
  --graphite:#4A4A4A;       /* icons, secondary text */
  --secondary:#F5F5F5;
  --bg:#FFFFFF;
  --surface:#F5F5F5;
  --surface-2:#EDEDED;
  --text:#0D0D0D;
  --text-secondary:#4A4A4A;
  --text-muted:#4A4A4A;
  --border:#C7C7C7;
  --dark:#0D0D0D;
  --dark-mid:#161616;
  --dark-soft:#222222;
  --white:#fff;
  /* Print-editorial: square corners everywhere. --radius-chip is the one exception,
     used by the eyebrow "background pill" the guide explicitly calls for. */
  --radius-sm:0px;
  --radius-md:0px;
  --radius-lg:0px;
  --radius-pill:0px;
  --radius-chip:999px;
  --shadow-sm:0 1px 2px rgba(13,13,13,.08);
  --shadow-md:0 6px 20px rgba(13,13,13,.10);
  --shadow-lg:0 18px 50px rgba(13,13,13,.16);
  --maxw:1200px;
  --header-h:72px;       /* nav bar height */
  --topbar-h:0px;        /* v3: no utility top bar — minimal white header sitewide */
  --header-total:72px;   /* body offset on non-transparent pages */
}

/* ---------- Reset & Base ---------- */
*,*::before,*::after{box-sizing:border-box;margin:0;padding:0}
html{scroll-behavior:smooth;-webkit-text-size-adjust:100%}
body{font-family:var(--font-sans);color:var(--text);background:var(--bg);-webkit-font-smoothing:antialiased;line-height:1.65;min-height:100vh;display:flex;flex-direction:column;overflow-x:hidden}
img{max-width:100%;height:auto;display:block}/* height:auto is REQUIRED: without it an HTML height="N" attribute on an inline-styled img leaks through and stretches the image (a width:100%+aspect-ratio img with no CSS height renders at the attribute height). Canonical responsive-image rule. */
/* SAFETY NET — inline ICONS never balloon. Every icon is a 24-grid line SVG; this gives a
   small default size so an icon dropped in a container without its own rule (faq-ico, ci-ico,
   a bare <ul><li>, an improvised block, etc.) can't render at its 300×150 intrinsic size.
   The specific `.x svg{width:Npx}` component rules below are higher-specificity and override
   this for the known containers. Logos are <img> (PNG/webp), not inline SVG, so they're safe. */
svg{width:1.25em;height:1.25em;flex-shrink:0;vertical-align:middle}
/* SAFETY NET — a large source photo must never blow a section apart (the "images broke in size"
   bug: a 1500px product PNG rendered full-width, one per row). Content images are capped and
   cover-cropped; full-bleed hero/CTA backgrounds and logos are explicitly exempt. The canonical
   card/media wrappers (.cat-card/.img-card/.related-card/.split-media …) still set their own
   fixed aspect ratios; this only catches improvised bare <img>. */
main img:not(.hero-dark-bg):not(.cta-band-bg):not(.logo-img):not(.footer-logo):not([class*="-bg"]):not([src*="/logos/"]){max-height:560px;object-fit:cover}
a{color:inherit;text-decoration:none}
ul,ol{list-style:none}
button,input,select,textarea{font:inherit;color:inherit;border:none;outline:none;background:none}
button{cursor:pointer}
h1,h2,h3,h4,h5,h6{font-family:var(--font-display);font-weight:700;letter-spacing:-.02em;line-height:1.14;color:var(--text)}
h1{font-size:clamp(2.1rem,5vw,3.6rem)}
h2{font-size:clamp(1.7rem,3.4vw,2.5rem)}
h3{font-size:1.3rem}
p{color:var(--text-secondary)}
main{flex:1 0 auto}
::selection{background:var(--accent);color:#fff}

/* ---------- Utilities ---------- */
.container{width:100%;max-width:var(--maxw);margin:0 auto;padding:0 20px}
@media(min-width:640px){.container{padding:0 24px}}
@media(min-width:1024px){.container{padding:0 32px}}
.text-center{text-align:center}
.text-accent{color:var(--accent)}
.text-primary{color:var(--primary)}
.text-white{color:#fff}
.muted{color:var(--text-muted)}
.mb-0{margin-bottom:0}.mb-1{margin-bottom:8px}.mb-2{margin-bottom:16px}.mb-3{margin-bottom:24px}.mb-4{margin-bottom:32px}.mt-2{margin-top:16px}.mt-3{margin-top:24px}
.flex{display:flex}.items-center{align-items:center}.justify-center{justify-content:center}.justify-between{justify-content:space-between}.flex-wrap{flex-wrap:wrap}.gap-2{gap:8px}.gap-3{gap:12px}.gap-4{gap:16px}.gap-6{gap:24px}
.lead{font-size:1.12rem;color:var(--text-secondary)}
.eyebrow{display:inline-flex;align-items:center;gap:7px;font-size:.72rem;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:#fff;background:var(--primary);padding:6px 14px;border-radius:var(--radius-chip);margin-bottom:16px}
.eyebrow::before{content:"";width:6px;height:6px;border-radius:50%;background:var(--silver)}
.eyebrow-light{color:#fff;background:var(--primary)}
.line-clamp-2{display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
.line-clamp-3{display:-webkit-box;-webkit-line-clamp:3;-webkit-box-orient:vertical;overflow:hidden}

/* ---------- Buttons ---------- */
.btn{display:inline-flex;align-items:center;justify-content:center;gap:9px;font-weight:700;font-size:.97rem;line-height:1;padding:14px 26px;border-radius:var(--radius-pill);border:2px solid transparent;transition:transform .18s ease,box-shadow .18s ease,background .18s ease,color .18s ease;cursor:pointer;white-space:nowrap}
.btn svg{width:17px;height:17px;flex-shrink:0}
.btn-primary{background:var(--accent);color:#fff;border-color:var(--accent)}
.btn-primary:hover{background:var(--accent-dark);color:#fff;border-color:var(--accent-dark);transform:translateY(-2px);box-shadow:0 8px 20px rgba(13,13,13,.22)}
.btn-dark{background:var(--primary);color:#fff;border-color:var(--primary)}
.btn-dark:hover{background:var(--primary-dark);border-color:var(--primary-dark);transform:translateY(-2px);box-shadow:var(--shadow-md)}
.btn-outline{background:transparent;color:#fff;border-color:rgba(255,255,255,.55)}
.btn-outline:hover{background:#fff;color:var(--text);border-color:#fff;transform:translateY(-2px)}
.btn-outline-dark{background:transparent;color:var(--primary);border-color:var(--primary)}
.btn-outline-dark:hover{background:var(--primary);color:#fff;transform:translateY(-2px)}
.btn-sm{padding:10px 18px;font-size:.88rem}
.btn-lg{padding:17px 34px;font-size:1.05rem}
.btn-block{width:100%}

/* ---------- Header ---------- */
.site-header{position:fixed;top:0;left:0;right:0;z-index:1000;background:rgba(255,255,255,.92);backdrop-filter:saturate(160%) blur(12px);-webkit-backdrop-filter:saturate(160%) blur(12px);border-bottom:1px solid var(--border);transition:background .25s ease,box-shadow .25s ease}
body{padding-top:var(--header-total)}
body.has-transparent-header{padding-top:0}
/* No utility topbar (SITE.topbar=false): header is just the 72px nav, so the offset
   that body padding + the mobile menu read collapses to --header-h. */
html.no-topbar{--topbar-h:0px;--header-total:var(--header-h)}
.topbar{background:var(--primary-darker);color:rgba(255,255,255,.82);font-size:.82rem}
.topbar-inner{display:flex;align-items:center;justify-content:space-between;gap:16px;height:36px}
.topbar a{color:rgba(255,255,255,.82);display:inline-flex;align-items:center;gap:6px;transition:color .15s}
.topbar a:hover{color:var(--accent)}
.topbar svg{width:14px;height:14px}
.topbar-right{display:flex;gap:20px;align-items:center}
.topbar-hours{display:none;align-items:center;gap:6px;color:rgba(255,255,255,.82)}
.topbar .topbar-loc{display:none}
@media(min-width:768px){.topbar .topbar-loc{display:inline-flex}.topbar-hours{display:inline-flex}}
/* white-space:nowrap on the bar INHERITS to every text descendant, so no header item
   (logo wordmark, nav link, phone, CTA — even one added later) can ever wrap to a 2nd/3rd
   line. If items then exceed the width they overflow horizontally, and initHeaderFit sheds
   them / collapses to the hamburger. Dropdown + mobile panels reset to normal wrapping. */
.header-inner{display:flex;align-items:center;justify-content:space-between;gap:20px;flex-wrap:nowrap;white-space:nowrap;height:var(--header-h)}
.dropdown-menu,.mobile-menu{white-space:normal}
.logo{display:flex;align-items:center;gap:10px;flex-shrink:0;max-width:min(46vw,240px)}
/* The logo is CAPPED in both axes so a large/wide brand mark can never push the nav to a
   second line. A tall or wide source logo is scaled down (object-fit:contain), not allowed
   to dictate the header width. */
.logo-img{height:42px;width:auto;max-width:200px;object-fit:contain}
/* TWO-INK BRAND LOCKUP — the client's real logo art ships in both inks (861×56, transparent
   bg). The art already contains the words "Evidence Communications", so NO text wordmark sits
   beside it (that would print the name twice). Exactly one <img> is visible per header state:
   dark ink is the default, because the bar is light in every state EXCEPT .header-transparent.
   (.header-solid — the state SITE.solidHeader=true currently ships — is an opaque white bar,
   so it correctly falls through to this default.) State overrides live with the header states. */
.logo-ink-light{display:none}
/* LOGO VISIBILITY GUARD — set at runtime by initLogoContrast(): the chip contrasts the
   LOGO (not the bar), so a light/white logo stays visible on the white header and a dark
   logo stays visible over a dark hero, in every header state. A chip that happens to match
   the bar is simply invisible (harmless). Never ship a logo that blends into its bar. */
.logo.logo-chip-dark{background:var(--dark,#0D0D0D);padding:5px 9px;border-radius:9px}
.logo.logo-chip-light{background:#fff;padding:5px 9px;border-radius:9px}
/* …but the two-ink lockup above already guarantees contrast in every state by SWAPPING the
   art, so the runtime chip is redundant here — and harmful, since one static chip cannot suit
   both inks (it measures only the first .logo-img). Neutralize it on the header lockup. The
   initLogoContrast() hook itself is untouched and still guards the footer logo. */
.site-header .logo.logo-chip-dark,.site-header .logo.logo-chip-light{background:transparent;padding:0;border-radius:0}
/* Text wordmark beside the logo — FORBIDDEN unless the logo is a bare icon/monogram with
   no legible name, attested with data-icon-only-logo="true" on the .logo anchor (the QA
   probe blocks any unattested text beside the logo: the name-written-twice defect). MUST
   be styled (never let it inherit the dark body --text, or it goes dark-on-dark over the
   transparent hero header — a real defect). Color flips with the header state below. */
.logo-wordmark{font-weight:700;font-size:1.12rem;letter-spacing:-.02em;line-height:1.06;color:var(--text);white-space:nowrap}
.logo-wordmark-sub{display:block;font-weight:700;font-size:.68rem;letter-spacing:.01em;text-transform:none;color:var(--text-muted)}
.desktop-nav{display:none;align-items:center;gap:4px;flex-wrap:nowrap}
@media(min-width:1024px){.desktop-nav{display:flex}}
/* Each nav item is a clearly-separated, clearly-clickable pill: real horizontal padding
   (so items read as distinct buttons, not a run-on text string), a rounded hover fill,
   and an animated underline as an unmistakable link affordance. */
.nav-link{position:relative;display:inline-flex;align-items:center;gap:5px;padding:10px 16px;font-weight:700;font-size:.95rem;white-space:nowrap;color:var(--text);border-radius:var(--radius-pill);transition:color .15s,background .15s}
.nav-link::after{content:"";position:absolute;left:16px;right:16px;bottom:7px;height:2px;border-radius:0;background:var(--primary);transform:scaleX(0);transform-origin:center;transition:transform .18s ease}
.nav-link:hover{color:var(--primary);background:var(--surface)}
.nav-link:hover::after{transform:scaleX(.66)}
.nav-link svg{width:14px;height:14px;transition:transform .2s}
.nav-dropdown{position:relative}
.nav-dropdown:hover .nav-link svg{transform:rotate(180deg)}
.dropdown-menu{position:absolute;top:calc(100% + 6px);left:0;min-width:480px;background:#fff;border:1px solid var(--border);border-radius:var(--radius-md);box-shadow:var(--shadow-lg);padding:14px;opacity:0;visibility:hidden;transform:translateY(8px);transition:all .2s ease;display:grid;grid-template-columns:1fr 1fr;gap:4px}
.dropdown-menu.single-col{grid-template-columns:1fr;min-width:260px}
.nav-dropdown:hover .dropdown-menu,
.nav-dropdown:focus-within .dropdown-menu{opacity:1;visibility:visible;transform:translateY(0)}
.dropdown-item{display:flex;flex-direction:column;gap:2px;padding:10px 12px;border-radius:var(--radius-sm);transition:background .15s}
.dropdown-item:hover{background:var(--surface)}
.dropdown-item .di-title{font-weight:700;font-size:.92rem;color:var(--text);display:flex;align-items:center;gap:8px}
.dropdown-item .di-title svg{width:16px;height:16px;color:var(--primary)}
.dropdown-item .di-sub{font-size:.8rem;color:var(--text-muted);padding-left:24px}
.dropdown-foot{grid-column:1/-1;margin-top:6px;padding:10px 12px;border-top:1px solid var(--border);font-weight:700;font-size:.88rem;color:var(--primary);display:flex;align-items:center;gap:6px}
.dropdown-foot svg{width:15px;height:15px}
/* mega menu (Our Services) */
.dropdown-menu.mega{min-width:560px}
.mega-col{padding:10px 12px}
.mega-col .mc-head{display:flex;align-items:center;gap:9px;font-weight:700;font-size:.92rem;color:var(--text);margin-bottom:9px;border-radius:var(--radius-sm)}
.mega-col .mc-head .mc-ico{width:30px;height:30px;border-radius:8px;background:var(--secondary);color:var(--primary);display:flex;align-items:center;justify-content:center;flex-shrink:0}
.mega-col .mc-head .mc-ico svg{width:16px;height:16px}
.mega-col .mc-head:hover{color:var(--primary)}
.mega-col .mc-links{display:flex;flex-direction:column;gap:2px}
.mega-col .mc-links a{font-size:.85rem;color:var(--text-secondary);padding:5px 8px 5px 39px;border-radius:var(--radius-sm);transition:background .15s,color .15s}
.mega-col .mc-links a:hover{background:var(--surface);color:var(--primary)}
.header-actions{display:none;align-items:center;gap:14px}
@media(min-width:1024px){.header-actions{display:flex}}
/* Header phone is redundant with the top-bar phone and its width was crowding the nav
   into a cramped "text string" (triggering the fit-guard's tight mode). Hidden here so
   the nav can breathe; the number stays in the top bar, the footer, and the CTA flow. */
.header-phone{display:none !important}
.mobile-toggle{display:inline-flex;align-items:center;justify-content:center;width:44px;height:44px;border-radius:var(--radius-sm);color:var(--text)}
.mobile-toggle svg{width:26px;height:26px}
@media(min-width:1024px){.mobile-toggle{display:none}}

/* transparent header over dark hero */
.header-transparent{background:transparent;border-bottom-color:transparent}
.header-transparent .nav-link,.header-transparent .header-phone{color:#fff}
.header-transparent .nav-link:hover{background:rgba(255,255,255,.12);color:#fff}
.header-transparent .header-phone svg{color:var(--accent)}
.header-transparent .mobile-toggle{color:#fff}
.header-transparent .logo-wordmark{color:#fff}
.header-transparent .logo-wordmark-sub{color:rgba(255,255,255,.78)}
/* Over the dark hero the bar is transparent → white ink. */
.header-transparent .logo-ink-dark{display:none}
.header-transparent .logo-ink-light{display:block}
.header-scrolled{background:rgba(255,255,255,.95);border-bottom-color:var(--border);box-shadow:var(--shadow-sm)}
.header-scrolled .nav-link,.header-scrolled .header-phone{color:var(--text)}
.header-scrolled .nav-link:hover{color:var(--primary);background:var(--surface)}
.header-scrolled .header-phone svg{color:var(--primary)}
.header-scrolled .mobile-toggle{color:var(--text)}
.header-scrolled .logo-img{filter:none}
.header-scrolled .logo-wordmark{color:var(--text)}
.header-scrolled .logo-wordmark-sub{color:var(--text-muted)}
/* Past 50px `header-scrolled` is added ALONGSIDE `header-transparent` (it is never removed),
   so the bar turns white while both classes are on the element. These two rules carry the same
   specificity as the .header-transparent pair above and MUST stay below them to win on source
   order: white bar → dark ink. Do not reorder these blocks. */
.header-scrolled .logo-ink-dark{display:block}
.header-scrolled .logo-ink-light{display:none}

/* Keep the ENTIRE header on ONE line — a big/wide logo must SHRINK before the nav wraps.
   When the brand logo is large, it is capped (above) and the nav is tightened at mid widths
   rather than allowed to fall to a second row (the "crammed, two-line header" defect). */
@media(min-width:1024px) and (max-width:1279px){
  .header-inner{gap:14px}
  .nav-link{padding:9px 10px;font-size:.9rem}
  .logo-img{height:38px;max-width:168px}
}

/* Header FIT-GUARD states (toggled by initHeaderFit so the bar never wraps/overflows).
   Step 1 — tight: shed the phone + wordmark and tighten nav so a heavy nav still fits one line. */
.site-header.header-tight .header-phone{display:none}
.site-header.header-tight .logo-wordmark{display:none}
.site-header.header-tight .desktop-nav{gap:2px}
.site-header.header-tight .nav-link{padding:8px 9px;font-size:.9rem}
/* Step 2 — collapse: still doesn't fit → fall back to the hamburger drawer at desktop width
   (far better than a wrapped/overflowing bar; the build should also lean the header). */
.site-header.header-collapse .desktop-nav,
.site-header.header-collapse .header-actions{display:none}
.site-header.header-collapse .mobile-toggle{display:inline-flex}

/* SOLID header over a dark hero — for a DARK brand logo that would vanish on the transparent
   (white-text) header. The header stays OPAQUE WHITE with DARK nav text, sitting on top of the
   dark hero, so the dark logo + nav are always legible. Set via SITE.solidHeader=true in main.js
   (no `header-transparent` is added; the body still gets `has-transparent-header` so the hero is
   full-bleed and the white bar overlaps its top). */
.header-solid{background:rgba(255,255,255,.97);border-bottom:1px solid var(--border);box-shadow:var(--shadow-sm)}
.header-solid .nav-link,.header-solid .header-phone{color:var(--text)}
.header-solid .nav-link:hover{color:var(--primary);background:var(--surface)}
.header-solid .header-phone svg{color:var(--primary)}
.header-solid .mobile-toggle{color:var(--text)}
.header-solid .logo-img{filter:none}
.header-solid .logo-wordmark{color:var(--text)}
.header-solid .logo-wordmark-sub{color:var(--text-muted)}

/* mobile menu */

/* gw-drawer-fix-2026-07-28 — the drawer is position:fixed inside the frosted .site-header, whose
   backdrop-filter makes it the containing block for fixed descendants. Sized with bottom:0
   it resolved against the 72px bar, not the viewport, and opened 58px tall. Explicit height
   here + hoistMobileMenu() in js/main.js. Never restore `bottom:0` on this rule. */
.mobile-menu{position:fixed;top:var(--header-total);left:0;right:0;height:calc(100vh - var(--header-total));height:calc(100dvh - var(--header-total));max-height:none;z-index:1050;transform:translateX(-100%);visibility:hidden;transition:transform .28s var(--ease-hover,cubic-bezier(.4,0,.2,1)),visibility 0s linear .28s;overflow-y:auto;overscroll-behavior:contain;-webkit-overflow-scrolling:touch;background:#fff;padding:18px 20px 40px}
.mobile-menu.active{visibility:visible;transition:transform .28s var(--ease-hover,cubic-bezier(.4,0,.2,1)),visibility 0s;transform:translateX(0)}
.mobile-menu .mm-link{display:block;padding:14px 6px;font-weight:700;font-size:1.05rem;border-bottom:1px solid var(--border)}
.mobile-menu .mm-group-label{padding:16px 6px 6px;font-size:.78rem;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--text-muted)}
.mobile-menu .mm-sub{display:block;padding:10px 6px 10px 18px;font-weight:700;color:var(--text-secondary);border-bottom:1px solid var(--surface)}
.mobile-menu .mm-cta{margin-top:22px}
.mobile-menu .mm-contact{margin-top:22px;padding-top:18px;border-top:1px solid var(--border);display:flex;flex-direction:column;gap:10px;font-size:.92rem}
.mobile-menu .mm-contact a{display:flex;align-items:center;gap:9px;color:var(--text-secondary)}
.mobile-menu .mm-contact svg{width:16px;height:16px;color:var(--primary)}

/* ---------- Sections ---------- */
.section{padding:80px 0}
.section-sm{padding:52px 0}
.section-lg{padding:104px 0}
.section.surface{background:var(--surface)}
.section.dark{background:var(--dark);color:#fff}
.section.dark h1,.section.dark h2,.section.dark h3,.section.dark h4{color:#fff}
.section.dark p{color:rgba(255,255,255,.74)}
.section-header{max-width:680px;margin:0 auto 48px;text-align:center;display:flex;flex-direction:column;align-items:center}
.section-header.left{margin-left:0;text-align:left;align-items:flex-start}
.section-header.label-below{display:flex;flex-direction:column;align-items:center;text-align:center}
.section-header.label-below .eyebrow{order:1;margin:0 0 16px}
.section-header.label-below h2{order:2;margin:0}
.section-header.label-below p{order:3;margin-top:20px}
.section-header h2{margin:10px 0 14px}
.section-header p{font-size:1.08rem}

/* ---------- Hero (dark) ---------- */
.hero-dark{position:relative;color:#fff;overflow:hidden;background:var(--dark)}
.hero-dark-bg{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;filter:saturate(.6) brightness(.62);z-index:0}
.hero-dark::before{content:"";position:absolute;inset:0;background:linear-gradient(105deg,rgba(13,13,13,.88) 0%,rgba(13,13,13,.72) 48%,rgba(13,13,13,.55) 100%);z-index:1}
.hero-dark .container{position:relative;z-index:2}
.hero-pad{padding:130px 0 96px}
.hero-pad-sm{padding:120px 0 70px}
.hero-fullscreen{min-height:88vh;display:flex;flex-direction:column;justify-content:center;padding:150px 0 96px}
.hero-content{max-width:760px}
.hero-content.center{max-width:820px;margin:0 auto;text-align:center}
.hero-label{display:inline-flex;align-items:center;gap:8px;background:rgba(13,13,13,.82);border:1px solid rgba(255,255,255,.22);color:#fff;font-weight:700;font-size:.82rem;letter-spacing:.1em;text-transform:uppercase;padding:7px 16px;border-radius:var(--radius-chip);margin-bottom:20px}
.hero-label svg{width:15px;height:15px}
.hero-dark h1{color:#fff;margin-bottom:18px}
.hero-dark h1 .hl{color:var(--accent)}
.hero-sub{font-size:1.18rem;color:rgba(255,255,255,.82);max-width:600px;margin-bottom:30px}
.hero-content.center .hero-sub{margin-left:auto;margin-right:auto}
.hero-actions{display:flex;flex-wrap:wrap;gap:14px}
.hero-content.center .hero-actions{justify-content:center}
.hero-trust{display:flex;flex-wrap:wrap;gap:10px 22px;margin-top:26px;font-size:.9rem;color:rgba(255,255,255,.8)}
.hero-trust span{display:inline-flex;align-items:center;gap:8px}
.hero-trust svg{width:17px;height:17px;color:var(--accent)}

/* hero stat ticker (inline) */
.hero-ticker{display:flex;gap:48px;flex-wrap:wrap;max-width:760px;margin:42px 0 0;padding-top:28px;border-top:1px solid rgba(255,255,255,.18)}
.hero-content.center .hero-ticker{margin-left:auto;margin-right:auto;justify-content:center}
.hero-ticker .ht-num{font-size:2rem;font-weight:700;color:#fff;line-height:1}
.hero-ticker .ht-num .text-accent{color:var(--accent)}
.hero-ticker .ht-label{font-size:.84rem;color:rgba(255,255,255,.66);margin-top:5px}

/* breadcrumb */
.breadcrumb{background:var(--surface);border-bottom:1px solid var(--border)}
.breadcrumb-inner{display:flex;flex-wrap:wrap;align-items:center;gap:7px;padding:13px 0;font-size:.86rem;color:var(--text-muted)}
.breadcrumb-inner a{color:var(--text-secondary);transition:color .15s}
.breadcrumb-inner a:hover{color:var(--primary)}
.breadcrumb-inner .sep{width:14px;height:14px;color:var(--text-muted);display:inline-flex}
.breadcrumb-inner .current{color:var(--text);font-weight:700}

/* ---------- Stat bar ---------- */
.stat-bar{background:var(--primary);color:#fff}
/* Flex (not a fixed 4-col grid) so 3/5/6/7 stats stay centered instead of
   filling the left columns and leaving an empty track on the right. The items
   form a centered cluster; basis keeps ~2-up on mobile, ~4-up on desktop.
   Targets the direct children so it applies whether they are bare <div> (the
   markup reference) or .stat-item. */
.stat-grid{display:flex;flex-wrap:wrap;justify-content:center;gap:30px 40px;padding:48px 0}
.stat-grid>*,.stat-item{text-align:center;flex:0 1 160px}
.stat-num{font-size:clamp(2rem,4vw,2.8rem);font-weight:700;line-height:1;color:#fff}
.stat-num .text-accent{color:var(--accent)}
.stat-label{font-size:.9rem;color:rgba(255,255,255,.8);margin-top:8px}

/* ---------- Trust bar ---------- */
.trust-bar{background:var(--dark);padding:34px 0}
.trust-inner{display:flex;flex-wrap:wrap;align-items:center;justify-content:center;gap:12px}
.trust-pill{display:inline-flex;align-items:center;gap:9px;background:rgba(255,255,255,.07);border:1px solid rgba(255,255,255,.14);color:rgba(255,255,255,.9);font-weight:700;font-size:.9rem;padding:10px 18px;border-radius:var(--radius-pill)}
.trust-pill svg{width:17px;height:17px;color:var(--accent)}

/* brands strip — see the canonical (single-track, seamless) definition in the v3 layer at the
   end of this file. The duplicate ruleset that used to live here has been removed. */

/* ---------- Grids ---------- */
/* display:grid lives on EVERY grid class, not just the base `.grid`, so `class="grid-3"`
   on its own lays out as a grid. (Before, `.grid-3` alone only set columns with no
   display:grid, so a card grid written as class="grid-3" — without the base `grid` —
   rendered as display:block and the cards stacked VERTICALLY full-width. Real defect.) */
.grid,.grid-2,.grid-3,.grid-4{display:grid;gap:24px}
.grid-2{grid-template-columns:1fr}
.grid-3{grid-template-columns:1fr}
.grid-4{grid-template-columns:1fr}
@media(min-width:640px){.grid-2{grid-template-columns:repeat(2,1fr)}.grid-3{grid-template-columns:repeat(2,1fr)}.grid-4{grid-template-columns:repeat(2,1fr)}}
@media(min-width:1024px){.grid-3{grid-template-columns:repeat(3,1fr)}.grid-4{grid-template-columns:repeat(4,1fr)}}

/* ---------- Cards ---------- */
.card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:30px 26px;transition:transform .2s ease,box-shadow .2s ease,border-color .2s ease;height:100%;display:flex;flex-direction:column}
.card:hover{transform:translateY(-5px);box-shadow:var(--shadow-md);border-color:transparent}
.card-icon{width:54px;height:54px;border-radius:14px;display:flex;align-items:center;justify-content:center;background:var(--secondary);color:var(--primary);margin-bottom:18px;flex-shrink:0}
.card-icon svg{width:26px;height:26px}
.card h3{font-size:1.18rem;margin-bottom:10px}
.card p{font-size:.95rem;flex:1}
.card-link{display:inline-flex;align-items:center;gap:7px;margin-top:16px;font-weight:700;font-size:.9rem;color:var(--primary)}
.card-link svg{width:15px;height:15px;transition:transform .18s}
.card:hover .card-link svg{transform:translateX(4px)}

/* service/category card with accent top */
.svc-card{position:relative;overflow:hidden}
.svc-card::before{content:"";position:absolute;top:0;left:0;right:0;height:4px;background:var(--accent);transform:scaleX(0);transform-origin:left;transition:transform .25s ease}
.svc-card:hover::before{transform:scaleX(1)}
.svc-card .num{position:absolute;top:24px;right:26px;font-size:1.4rem;font-weight:700;color:var(--surface-2)}

/* image card */
.img-card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);overflow:hidden;transition:transform .2s ease,box-shadow .2s ease;height:100%;display:flex;flex-direction:column}
.img-card:hover{transform:translateY(-5px);box-shadow:var(--shadow-md)}
.img-card .ic-media{aspect-ratio:16/10;overflow:hidden;position:relative}
.img-card .ic-media img{width:100%;height:100%;object-fit:cover;transition:transform .4s ease}
.img-card:hover .ic-media img{transform:scale(1.06)}
.img-card .ic-body{padding:22px 22px 26px;flex:1;display:flex;flex-direction:column}
.img-card h3{font-size:1.1rem;margin-bottom:8px}
.img-card p{font-size:.92rem;flex:1}

/* category card */
.cat-card{display:flex;flex-direction:column;background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:30px 28px;transition:transform .2s,box-shadow .2s,border-color .2s;height:100%}
.cat-card:hover{transform:translateY(-5px);box-shadow:var(--shadow-md);border-color:transparent}
.cat-card .cc-icon{width:auto;height:28px;border-radius:0;background:none;color:var(--graphite);display:flex;align-items:center;justify-content:flex-start;margin-bottom:18px}
.cat-card .cc-icon svg{width:28px;height:28px}
.cat-card h3{font-size:1.32rem;margin-bottom:10px}
.cat-card p{font-size:.95rem;margin-bottom:16px}
.cat-card ul{margin-bottom:20px;display:flex;flex-direction:column;gap:9px}
.cat-card ul li{display:flex;align-items:flex-start;gap:9px;font-size:.92rem;color:var(--text-secondary)}
.cat-card ul li svg{width:17px;height:17px;color:var(--accent-dark);flex-shrink:0;margin-top:2px}
.cat-card .cc-foot{margin-top:auto;display:inline-flex;align-items:center;gap:7px;font-weight:700;font-size:.92rem;color:var(--primary)}
.cat-card .cc-foot svg{width:15px;height:15px;transition:transform .18s}
.cat-card:hover .cc-foot svg{transform:translateX(4px)}
.cat-card .cc-count{display:inline-block;font-size:.76rem;font-weight:700;color:var(--primary);background:var(--secondary);padding:4px 11px;border-radius:var(--radius-pill);margin-bottom:18px}

/* retention / feature card (image top) */
.retention-card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);overflow:hidden;height:100%;display:flex;flex-direction:column;transition:transform .2s,box-shadow .2s}
.retention-card:hover{transform:translateY(-5px);box-shadow:var(--shadow-md)}
.retention-card .rc-media{aspect-ratio:3/2;overflow:hidden}
.retention-card .rc-media img{width:100%;height:100%;object-fit:cover;transition:transform .4s}
.retention-card:hover .rc-media img{transform:scale(1.06)}
.retention-card .rc-body{padding:22px 22px 26px;flex:1}
.retention-card h3{font-size:1.08rem;margin-bottom:8px}
.retention-card p{font-size:.9rem}

/* ---------- Movable card carousel ----------
   A horizontal scroll-snap rail used INSTEAD of a `.grid-*` when a card row may
   overflow (mobile, or many cards). It only "moves" when the cards actually
   overflow the container: on a wide desktop a small set (3–4 cards) flexes to
   fill the row and there is nothing to scroll, so it reads as a static grid —
   you never hide content behind a swipe when it already fits. Native overflow
   gives swipe (touch) + trackpad for free; main.js adds mouse drag-to-scroll
   and (only with data-autoscroll) a slow auto-drift that respects
   prefers-reduced-motion and pauses on hover/focus/drag. The cards inside are
   the SAME `.img-card` / `.cat-card` / `.retention-card` divs — never anchors. */
.card-carousel{display:flex;gap:24px;overflow-x:auto;scroll-snap-type:x mandatory;scroll-behavior:smooth;-webkit-overflow-scrolling:touch;scrollbar-width:none;padding:4px 2px 8px;margin:0 -2px}
.card-carousel::-webkit-scrollbar{display:none}
.card-carousel>*{scroll-snap-align:start;flex:0 0 auto;width:300px;max-width:82%}
.card-carousel.dragging{scroll-snap-type:none;scroll-behavior:auto;cursor:grabbing;user-select:none}
@media(min-width:1024px){
  /* enough room: cards flex to fill the row and only scroll if they overflow */
  .card-carousel>*{width:auto;flex:1 1 0;min-width:262px;max-width:none}
}
@media(prefers-reduced-motion:reduce){.card-carousel{scroll-behavior:auto}}
/* optional author-supplied prev/next controls (wired by main.js if present) */
.cc-nav{display:flex;justify-content:flex-end;gap:10px;margin-top:18px}
.cc-nav button{width:42px;height:42px;border-radius:50%;border:1px solid var(--border);background:#fff;color:var(--text);display:inline-flex;align-items:center;justify-content:center;cursor:pointer;transition:background .18s,color .18s,border-color .18s}
.cc-nav button:hover{background:var(--primary);color:#fff;border-color:transparent}
.cc-nav button svg{width:18px;height:18px}
.cc-nav button[disabled]{opacity:.35;cursor:default;pointer-events:none}

/* ---------- Split section ---------- */
.split{display:grid;grid-template-columns:1fr;gap:40px;align-items:center}
@media(min-width:1024px){.split{grid-template-columns:1fr 1fr;gap:64px}.split.reverse .split-media{order:2}}
.split-media{position:relative}
.split-media img{width:100%;border-radius:var(--radius-lg);box-shadow:var(--shadow-md);aspect-ratio:4/3;object-fit:cover}
.split-media .badge-float{position:absolute;bottom:-22px;left:24px;background:#fff;border-radius:var(--radius-md);box-shadow:var(--shadow-lg);padding:16px 22px;display:flex;align-items:center;gap:14px}
.split-media .badge-float .bf-num{font-size:1.9rem;font-weight:700;color:var(--accent);line-height:1}
.split-media .badge-float .bf-label{font-size:.82rem;color:var(--text-secondary);max-width:130px}
.split-body h2{margin-bottom:16px}
.split-body p{margin-bottom:14px}
.split-body .check-list{margin:20px 0 26px}
.check-list{display:flex;flex-direction:column;gap:12px;list-style:none}
/* The <li> is NORMAL FLOW, never a flex container — so inline content (text mixed with
   <strong>/<a>/<em>) flows as one sentence and can NEVER fragment into mis-sized columns
   (the real "Up / to | 15%… | from…" defect: a flex <li> turns each text node + inline
   element into a separate flex item). The check marker is an absolutely-positioned ::before
   disc + tick; an authored leading <svg> becomes the marker instead and suppresses it. */
.check-list li{position:relative;padding-left:30px;color:var(--text-secondary)}
.check-list li::before{content:"";position:absolute;left:0;top:.3em;width:19px;height:19px;border-radius:50%;background:var(--surface-2)}
.check-list li::after{content:"";position:absolute;left:6.5px;top:.5em;width:5px;height:9px;border:solid var(--primary);border-width:0 2.5px 2.5px 0;transform:rotate(45deg)}
.check-list li:has(> svg:first-child)::before,.check-list li:has(> svg:first-child)::after{display:none}
.check-list li > svg:first-child{position:absolute;left:0;top:.16em;width:20px;height:20px;margin:0;color:var(--graphite)}
.check-list li b,.check-list li strong{color:var(--text);font-weight:700}

/* ---------- Process ---------- */
.process{background:var(--dark);color:#fff}
.process-grid{display:grid;grid-template-columns:1fr;gap:30px;counter-reset:step}
@media(min-width:768px){.process-grid{grid-template-columns:repeat(3,1fr)}}
@media(min-width:1024px){.process-grid.cols-5{grid-template-columns:repeat(5,1fr);gap:20px}}
.process-step{position:relative;padding-top:8px}
.process-num{width:54px;height:54px;border-radius:50%;border:2px solid rgba(255,255,255,.45);color:#fff;display:flex;align-items:center;justify-content:center;font-weight:700;font-size:1.2rem;margin-bottom:18px}
.process-step h3{color:#fff;font-size:1.08rem;margin-bottom:8px}
.process-step p{color:rgba(255,255,255,.7);font-size:.92rem}

/* ---------- Industry scroll ---------- */
.industry-scroll{display:flex;gap:20px;overflow-x:auto;padding:6px 4px 22px;scroll-snap-type:x mandatory;-webkit-overflow-scrolling:touch}
.industry-scroll::-webkit-scrollbar{height:7px}
.industry-scroll::-webkit-scrollbar-thumb{background:var(--border);border-radius:10px}
.ind-card{position:relative;flex:0 0 270px;aspect-ratio:3/4;border-radius:var(--radius-lg);overflow:hidden;scroll-snap-align:start}
.ind-card img{width:100%;height:100%;object-fit:cover;transition:transform .4s}
.ind-card:hover img{transform:scale(1.07)}
.ind-card::after{content:"";position:absolute;inset:0;background:linear-gradient(to top,rgba(13,13,13,.88) 0%,rgba(13,13,13,.15) 55%,transparent 100%)}
.ind-card .ind-label{position:absolute;left:20px;right:20px;bottom:18px;z-index:2;color:#fff}
.ind-card .ind-label h3{color:#fff;font-size:1.18rem;margin-bottom:4px}
.ind-card .ind-label p{color:rgba(255,255,255,.82);font-size:.85rem}
.ind-card .ind-arrow{position:absolute;top:16px;right:16px;z-index:2;width:34px;height:34px;border-radius:50%;background:rgba(255,255,255,.18);backdrop-filter:blur(4px);display:flex;align-items:center;justify-content:center;color:#fff;transition:background .2s}
.ind-card:hover .ind-arrow{background:var(--accent);color:var(--text)}
.ind-card .ind-arrow svg{width:16px;height:16px}

/* ---------- Testimonials ---------- */
.testi-grid{display:grid;grid-template-columns:1fr;gap:24px}
@media(min-width:768px){.testi-grid{grid-template-columns:repeat(3,1fr)}}
.testi-card{background:var(--dark-mid);border:1px solid rgba(255,255,255,.08);border-radius:var(--radius-lg);padding:30px 28px;display:flex;flex-direction:column;height:100%}
.testi-stars{display:flex;gap:3px;margin-bottom:16px}
.testi-stars svg{width:18px;height:18px;color:var(--accent)}
.testi-quote{color:rgba(255,255,255,.86);font-size:1rem;line-height:1.7;flex:1;margin-bottom:20px}
.testi-author{display:flex;align-items:center;gap:13px}
.testi-avatar{width:46px;height:46px;border-radius:50%;background:var(--primary);color:#fff;display:flex;align-items:center;justify-content:center;font-weight:700;font-size:1.05rem;flex-shrink:0}
.testi-meta .ta-name{font-weight:700;color:#fff;font-size:.95rem}
.testi-meta .ta-loc{font-size:.82rem;color:rgba(255,255,255,.6)}

/* ---------- FAQ ---------- */
.faq-list{max-width:820px;margin:0 auto;display:flex;flex-direction:column;gap:14px}
.faq-item{background:#fff;border:1px solid var(--border);border-radius:var(--radius-md);overflow:hidden;transition:box-shadow .2s,border-color .2s}
.faq-item.active{box-shadow:var(--shadow-md);border-color:transparent}
.faq-question{width:100%;display:flex;align-items:center;justify-content:space-between;gap:16px;padding:20px 22px;font-weight:700;font-size:1.02rem;text-align:left;color:var(--text)}
.faq-question .faq-ico{width:30px;height:30px;border-radius:50%;background:var(--surface-2);color:var(--primary);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:transform .25s,background .2s,color .2s}
.faq-question .faq-ico svg{width:16px;height:16px}
.faq-item.active .faq-ico{background:var(--primary);color:#fff;transform:rotate(45deg)}
.faq-answer{max-height:0;overflow:hidden;transition:max-height .3s ease}
.faq-answer-inner{padding:0 22px 22px;color:var(--text-secondary);font-size:.97rem}

/* ---------- CTA ---------- */
.cta-dark{position:relative;background:var(--primary);color:#fff;overflow:hidden}
.cta-dark::before{content:none}
.cta-dark::after{content:none}
.cta-content{position:relative;z-index:2;text-align:center;max-width:680px;margin:0 auto}
.cta-content h2{color:#fff;margin-bottom:16px}
.cta-content p{color:rgba(255,255,255,.85);font-size:1.1rem;margin-bottom:28px}
.cta-actions{display:flex;flex-wrap:wrap;gap:14px;justify-content:center}

/* CTA with form */
.cta-band{position:relative;background:var(--dark);color:#fff;overflow:hidden}
.cta-band-bg{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;opacity:.16;z-index:0}
.cta-band::before{content:"";position:absolute;inset:0;background:linear-gradient(105deg,rgba(13,13,13,.94),rgba(13,13,13,.78));z-index:1}
.cta-form-grid{position:relative;z-index:2;display:grid;grid-template-columns:1fr;gap:44px;align-items:center}
@media(min-width:1024px){.cta-form-grid{grid-template-columns:1.05fr .95fr;gap:60px}}
.cta-form-grid .cfg-text h2{color:#fff;margin-bottom:16px}
.cta-form-grid .cfg-text p{color:rgba(255,255,255,.78);margin-bottom:24px}
.cfg-contact{display:flex;flex-direction:column;gap:16px;margin-top:8px}
.cfg-contact .ci{display:flex;align-items:center;gap:14px}
.cfg-contact .ci-ico{width:44px;height:44px;border-radius:12px;background:rgba(255,255,255,.1);display:flex;align-items:center;justify-content:center;color:var(--accent);flex-shrink:0}
.cfg-contact .ci-ico svg{width:20px;height:20px}
.cfg-contact .ci-label{font-size:.78rem;color:rgba(255,255,255,.6);text-transform:uppercase;letter-spacing:.06em}
.cfg-contact .ci-val{font-weight:700;color:#fff;font-size:1rem}
.cta-form{background:#fff;border-radius:var(--radius-lg);padding:30px 28px;box-shadow:var(--shadow-lg)}
.cta-form h3{color:var(--text);font-size:1.3rem;margin-bottom:6px}
.cta-form .cf-sub{color:var(--text-secondary);font-size:.9rem;margin-bottom:20px}

/* ---------- Forms ---------- */
.form-group{margin-bottom:16px}
.form-row{display:grid;grid-template-columns:1fr;gap:16px}
@media(min-width:560px){.form-row{grid-template-columns:1fr 1fr}}
.form-label{display:block;font-weight:700;font-size:.86rem;color:var(--text);margin-bottom:7px}
.form-label .req{color:var(--accent)}
.form-control{width:100%;padding:12px 15px;border:1.5px solid var(--border);border-radius:var(--radius-sm);background:#fff;color:var(--text);font-size:.95rem;transition:border-color .15s,box-shadow .15s}
.form-control::placeholder{color:var(--text-muted)}
.form-control:focus{border-color:var(--primary);box-shadow:0 0 0 3px rgba(77,108,119,.14)}
textarea.form-control{resize:vertical;min-height:110px}
select.form-control{appearance:none;background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%2351636a' stroke-width='2.5'%3E%3Cpath d='M6 9l6 6 6-6'/%3E%3C/svg%3E");background-repeat:no-repeat;background-position:right 13px center;background-size:17px;padding-right:40px}
.form-success{display:none;text-align:center;padding:30px 20px;background:var(--secondary);border-left:4px solid var(--accent-dark);border-radius:var(--radius-sm)}
.form-success.show{display:block}
.form-success .fs-ico{width:56px;height:56px;border-radius:50%;background:var(--accent);color:var(--text);display:flex;align-items:center;justify-content:center;margin:0 auto 16px}
.form-success .fs-ico svg{width:28px;height:28px}
.form-success h4,.form-success .fs-title{font-size:1.2rem;margin-bottom:8px;font-family:var(--font-display);font-weight:700;letter-spacing:-.02em;line-height:1.14;color:var(--text)}
/* PRE-FOOTER LEAD FORM — injected on every page by renderFooterForm() so no page is
   conversion-dead. A LIGHT band (the footer below is dark) so it never forms an
   adjacent-dark-bands pair, with dark text overriding the dark-band .cfg-text defaults. */
.footer-cta-band{background:var(--surface-2);border-top:1px solid var(--border)}
.footer-cta-band .cfg-text h2{color:var(--text)}
.footer-cta-band .cfg-text p{color:var(--text-secondary)}
.footer-cta-band .cfg-text a{color:var(--primary);font-weight:700}
/* Override white-text defaults when cta-form-grid lives inside a light .surface band (About page) */
.section.surface .cta-form-grid .cfg-text h2{color:var(--text)}
.section.surface .cta-form-grid .cfg-text p{color:var(--text-secondary)}
.form-note{font-size:.8rem;color:var(--text-muted);margin-top:6px}
/* Form CHOICE chips — the canonical multi/single-select control INSIDE A FORM (e.g. "Services
   interested in: LTL / FTL / Expedited …"). Self-contained: needs NO extra markup, keeps the
   NATIVE checkbox/radio VISIBLE + clickable (accent-colored), and the whole chip highlights when
   checked via :has(). Use THIS in forms — NOT .filter-check (that's the catalog sidebar and is
   invisible without a .fc-box span). Markup:
     <div class="form-check-grid">
       <label class="form-check"><input type="checkbox" name="services" value="LTL"><span>LTL</span></label> …
     </div>  (use type="radio" for single-select). */
.form-check-grid{display:grid;grid-template-columns:repeat(auto-fit,minmax(132px,1fr));gap:10px;margin-top:8px}
.form-check{display:flex;align-items:center;gap:10px;padding:11px 14px;border:1.5px solid var(--border);border-radius:var(--radius-md);background:#fff;cursor:pointer;font-size:.93rem;color:var(--text-secondary);transition:border-color .15s,background .15s,color .15s;-webkit-user-select:none;user-select:none}
.form-check:hover{border-color:var(--primary);color:var(--text)}
.form-check input{width:18px;height:18px;flex-shrink:0;margin:0;accent-color:var(--primary);cursor:pointer}
.form-check:has(input:checked){border-color:var(--primary);background:var(--secondary);color:var(--text);font-weight:700}
/* Safety net: a .filter-check MISUSED in a form (no .fc-box span) must NOT hide its native input
   into an invisible, un-selectable control — the real "can't select the LTL/FTL" defect. Only hide
   the native box when the custom .fc-box replacement is actually present. */
.filter-check:not(:has(.fc-box)) input{position:static;opacity:1;width:18px;height:18px;accent-color:var(--primary);cursor:pointer}

/* ---------- Contact ---------- */
.contact-layout{display:grid;grid-template-columns:1fr;gap:40px}
@media(min-width:1024px){.contact-layout{grid-template-columns:1.2fr .8fr;gap:56px}}
.contact-card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:28px 26px;margin-bottom:22px}
.contact-card h3{font-size:1.15rem;margin-bottom:6px;display:flex;align-items:center;gap:9px}
.contact-card h3 .cc-tag{font-size:.7rem;font-weight:700;color:var(--primary);background:var(--secondary);padding:3px 9px;border-radius:var(--radius-pill);text-transform:uppercase;letter-spacing:.05em}
.contact-item{display:flex;align-items:flex-start;gap:13px;padding:11px 0;border-bottom:1px solid var(--surface)}
.contact-item:last-child{border-bottom:none}
.contact-icon{width:42px;height:42px;border-radius:11px;background:var(--secondary);color:var(--primary);display:flex;align-items:center;justify-content:center;flex-shrink:0}
.contact-icon svg{width:19px;height:19px}
.contact-item .ci-label{font-size:.78rem;color:var(--text-muted);text-transform:uppercase;letter-spacing:.05em}
.contact-item .ci-val{font-weight:700;color:var(--text);font-size:.98rem}
.contact-item .ci-val a:hover{color:var(--primary)}
.quick-response{background:var(--primary);color:#fff;border-radius:var(--radius-lg);padding:24px 26px}
.quick-response h4{color:#fff;font-size:1.05rem;margin-bottom:8px;display:flex;align-items:center;gap:9px}
.quick-response h4 svg{width:20px;height:20px;color:var(--accent)}
.quick-response p{color:rgba(255,255,255,.84);font-size:.92rem}
.map-embed{border-radius:var(--radius-lg);overflow:hidden;border:1px solid var(--border);height:300px}
.map-embed iframe{width:100%;height:100%;border:0;display:block}

/* ---------- Catalog (all-services) ---------- */
.catalog-layout{display:grid;grid-template-columns:1fr;gap:30px}
@media(min-width:1024px){.catalog-layout{grid-template-columns:260px 1fr;gap:40px}}
.filter-panel{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:24px 22px}
@media(min-width:1024px){.filter-panel{position:sticky;top:calc(var(--header-total) + 20px)}}
.filter-panel h4{font-size:1.05rem;margin-bottom:6px}
.filter-panel .fp-sub{font-size:.85rem;color:var(--text-muted);margin-bottom:18px}
.filter-group{margin-bottom:20px}
.filter-group .fg-title{font-size:.78rem;font-weight:700;letter-spacing:.08em;text-transform:uppercase;color:var(--text-muted);margin-bottom:11px}
.filter-check{display:flex;align-items:center;gap:10px;padding:7px 0;cursor:pointer;font-size:.93rem;color:var(--text-secondary)}
.filter-check input{position:absolute;opacity:0;width:0;height:0}
.filter-check .fc-box{width:20px;height:20px;border:1.5px solid var(--border);border-radius:5px;display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:background .15s,border-color .15s}
.filter-check .fc-box svg{width:13px;height:13px;color:#fff;opacity:0;transition:opacity .15s}
.filter-check input:checked + .fc-box{background:var(--primary);border-color:var(--primary)}
.filter-check input:checked + .fc-box svg{opacity:1}
.filter-check:hover{color:var(--text)}
.filter-toggle-btn{display:flex;align-items:center;justify-content:center;gap:9px;width:100%;margin-bottom:18px;padding:13px;border:1.5px solid var(--border);border-radius:var(--radius-pill);font-weight:700;color:var(--text)}
.filter-toggle-btn svg{width:18px;height:18px}
@media(min-width:1024px){.filter-toggle-btn{display:none}}
.catalog-count{font-size:.9rem;color:var(--text-muted);margin-bottom:18px}
.catalog-grid{display:grid;grid-template-columns:1fr;gap:22px}
@media(min-width:640px){.catalog-grid{grid-template-columns:repeat(2,1fr)}}
.catalog-card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:26px 24px;transition:transform .2s,box-shadow .2s,border-color .2s;display:flex;flex-direction:column;height:100%}
.catalog-card:hover{transform:translateY(-4px);box-shadow:var(--shadow-md);border-color:transparent}
.catalog-card .cat-tag{display:inline-block;align-self:flex-start;font-size:.72rem;font-weight:700;color:var(--primary);background:var(--secondary);padding:4px 11px;border-radius:var(--radius-pill);margin-bottom:14px}
.catalog-card .cat-ico{width:48px;height:48px;border-radius:12px;background:var(--secondary);color:var(--primary);display:flex;align-items:center;justify-content:center;margin-bottom:14px}
.catalog-card .cat-ico svg{width:24px;height:24px}
.catalog-card h3{font-size:1.1rem;margin-bottom:8px}
.catalog-card p{font-size:.9rem;flex:1}
.catalog-card .card-link{margin-top:14px}
.filter-empty{display:none;text-align:center;padding:50px 20px;color:var(--text-muted)}
.filter-empty.show{display:block}

/* ---------- Detail grid + sidebar ---------- */
.detail-grid{display:grid;grid-template-columns:1fr;gap:34px}
/* min-width:0 lets a wide child (e.g. a .table-wrap/.data-table with min-width:440px)
   scroll INSIDE its own box instead of forcing the whole grid — and the page — wider
   than the viewport on mobile. Grid items default to min-width:auto (= content min),
   which is the #1 cause of mobile horizontal scroll here. */
.detail-grid>*{min-width:0}
@media(min-width:1024px){.detail-grid{grid-template-columns:2fr 1fr;gap:44px;align-items:start}}
.detail-card{background:#fff;border:1px solid var(--border);border-radius:var(--radius-lg);padding:30px 28px;margin-bottom:24px}
.detail-card h2{font-size:1.5rem;margin-bottom:14px}
.detail-card h3{font-size:1.15rem;margin:22px 0 12px}
.detail-card p{margin-bottom:14px}
.feature-list{display:grid;grid-template-columns:1fr;gap:13px;margin:18px 0}
@media(min-width:560px){.feature-list{grid-template-columns:1fr 1fr}}
.feature-list li{display:flex;align-items:flex-start;gap:10px;font-size:.94rem;color:var(--text-secondary)}
.feature-list li svg{width:19px;height:19px;color:var(--accent-dark);flex-shrink:0;margin-top:2px}
.app-grid{display:grid;grid-template-columns:1fr;gap:14px;margin-top:8px}
@media(min-width:560px){.app-grid{grid-template-columns:1fr 1fr}}
.app-item{display:flex;gap:13px;padding:16px;background:var(--surface);border-radius:var(--radius-md)}
.app-item .ai-ico{width:40px;height:40px;border-radius:10px;background:#fff;color:var(--primary);display:flex;align-items:center;justify-content:center;flex-shrink:0;box-shadow:var(--shadow-sm)}
.app-item .ai-ico svg{width:20px;height:20px}
.app-item h4{font-size:.98rem;margin-bottom:3px}
.app-item p{font-size:.85rem;margin:0}
.sidebar-cta{position:sticky;top:calc(var(--header-total) + 20px);background:var(--primary);color:#fff;border-radius:var(--radius-lg);padding:28px 26px}
.sidebar-cta h3{color:#fff;font-size:1.2rem;margin-bottom:10px}
.sidebar-cta p{color:rgba(255,255,255,.84);font-size:.92rem;margin-bottom:18px}
.sidebar-cta .sc-list{display:flex;flex-direction:column;gap:12px;margin-bottom:22px}
.sidebar-cta .sc-list li{display:flex;align-items:center;gap:10px;font-size:.92rem;color:rgba(255,255,255,.9)}
.sidebar-cta .sc-list svg{width:18px;height:18px;color:var(--accent);flex-shrink:0}
.sidebar-cta .sc-phone{display:flex;align-items:center;gap:10px;margin-top:14px;padding-top:16px;border-top:1px solid rgba(255,255,255,.18);font-size:.92rem;color:rgba(255,255,255,.84)}
.sidebar-cta .sc-phone a{font-weight:700;color:#fff;font-size:1.15rem}

/* product hero grid (service detail top) */
.product-hero-grid{display:grid;grid-template-columns:1fr;gap:40px;align-items:center;position:relative;z-index:2}
@media(min-width:1024px){.product-hero-grid{grid-template-columns:1.05fr .95fr;gap:56px}}
.product-visual{position:relative}
.product-visual img{width:100%;border-radius:var(--radius-lg);box-shadow:var(--shadow-lg);aspect-ratio:4/3;object-fit:cover}
.product-meta{display:grid;grid-template-columns:repeat(3,1fr);gap:14px;margin:26px 0}
.product-meta-item{background:rgba(255,255,255,.08);border:1px solid rgba(255,255,255,.14);border-radius:var(--radius-md);padding:15px 14px;text-align:center}
.product-meta-item .pm-num{font-size:1.25rem;font-weight:700;color:var(--accent)}
.product-meta-item .pm-label{font-size:.74rem;color:rgba(255,255,255,.7);margin-top:3px}
.delivery-note{display:inline-flex;align-items:center;gap:9px;font-size:.88rem;color:rgba(255,255,255,.82);margin-top:6px}
.delivery-note svg{width:17px;height:17px;color:var(--accent)}

/* ---------- Related ---------- */
.related-grid{display:grid;grid-template-columns:1fr;gap:18px}
/* auto-fit so 3-item AND 4-item related rows both fill the row evenly instead of
   stranding a lone 4th card on its own line (repeat(3,1fr) orphaned the 4th). */
@media(min-width:640px){.related-grid{grid-template-columns:repeat(auto-fit,minmax(230px,1fr))}}
.related-card{display:flex;align-items:center;gap:14px;background:#fff;border:1px solid var(--border);border-radius:var(--radius-md);padding:18px 20px;transition:transform .2s,box-shadow .2s,border-color .2s}
.related-card:hover{transform:translateY(-3px);box-shadow:var(--shadow-md);border-color:transparent}
.related-card .rc-ico{width:42px;height:42px;border-radius:11px;background:var(--secondary);color:var(--primary);display:flex;align-items:center;justify-content:center;flex-shrink:0}
.related-card .rc-ico svg{width:21px;height:21px}
.related-card h4{font-size:.97rem;margin-bottom:2px}
.related-card p{font-size:.8rem;margin:0;color:var(--text-muted)}

/* ---------- Photo strip ---------- */
.photo-strip{display:grid;grid-template-columns:repeat(2,1fr);gap:10px}
@media(min-width:768px){.photo-strip{grid-template-columns:repeat(4,1fr)}}
.photo-strip img{width:100%;aspect-ratio:1;object-fit:cover;border-radius:var(--radius-md)}

/* ---------- Value props (icon row) ---------- */
.value-row{display:grid;grid-template-columns:1fr;gap:20px}
@media(min-width:640px){.value-row{grid-template-columns:repeat(2,1fr)}}
@media(min-width:1024px){.value-row{grid-template-columns:repeat(4,1fr)}}
.value-item{text-align:center;padding:8px}
.value-item .vi-ico{width:60px;height:60px;border-radius:50%;background:var(--secondary);color:var(--primary);display:flex;align-items:center;justify-content:center;margin:0 auto 16px}
.value-item .vi-ico svg{width:28px;height:28px}
.value-item h3{font-size:1.05rem;margin-bottom:7px}
.value-item p{font-size:.9rem}

/* ---------- Timeline ---------- */
.timeline{max-width:760px;margin:0 auto;position:relative;padding-left:38px}
.timeline::before{content:"";position:absolute;left:11px;top:8px;bottom:8px;width:2px;background:var(--border)}
.timeline-item{position:relative;padding-bottom:32px}
.timeline-item:last-child{padding-bottom:0}
.timeline-dot{position:absolute;left:-38px;top:2px;width:24px;height:24px;border-radius:50%;background:var(--primary);border:4px solid var(--surface);box-shadow:0 0 0 1px var(--border)}
.timeline-year{font-size:.8rem;font-weight:700;letter-spacing:.06em;color:var(--primary);margin-bottom:5px}
.timeline-item h3{font-size:1.1rem;margin-bottom:6px}
.timeline-item p{font-size:.93rem}

/* ---------- Footer ---------- */
.site-footer{background:var(--dark);color:rgba(255,255,255,.7);margin-top:auto}
.footer-top{padding:62px 0 44px}
.footer-grid{display:grid;grid-template-columns:1fr;gap:38px}
@media(min-width:640px){.footer-grid{grid-template-columns:repeat(2,1fr)}}
@media(min-width:1024px){.footer-grid{grid-template-columns:1.4fr 1fr 1fr 1.2fr}}
/* The real art is the wordmark + tagline lockup (864×87) — far wider than it is tall, so the
   WIDTH is capped and the height follows the aspect ratio. Driving height instead would force
   a ~457px-wide box that overflows this column (or distorts the art once max-width clamped it). */
.footer-logo{height:auto;width:100%;max-width:300px;margin-bottom:16px;background:#fff;padding:8px 12px;border-radius:10px}
/* The default white chip suits a dark/colored logo on the dark footer. A LIGHT/white logo
   on a white chip is the exact "invisible logo" failure — initLogoContrast() tags it
   .logo-chip-dark so it sits directly on the dark footer instead. (dark logo keeps the chip.)
   We ship the WHITE-ink art, so .logo-chip-dark is also hard-coded in the markup: that makes
   the correct state the default (no white-chip flash, and it survives JS/canvas failure).
   initLogoContrast() recomputes the same class from the art, so the two agree. */
.footer-logo.logo-chip-dark{background:transparent;padding:0;border-radius:0}
.footer-about{font-size:.92rem;line-height:1.7;margin-bottom:18px;max-width:340px}
/* Footer CTA sits between the about paragraph and the social row; .btn is inline-flex, so it
   needs its own bottom margin to clear .footer-social. */
.footer-cta{margin-bottom:20px}
.footer-social{display:flex;gap:10px}
.footer-social a{width:38px;height:38px;border-radius:10px;background:rgba(255,255,255,.08);display:flex;align-items:center;justify-content:center;color:rgba(255,255,255,.78);transition:background .2s,color .2s}
.footer-social a:hover{background:var(--accent);color:var(--text)}
.footer-social svg{width:18px;height:18px}
.footer-col h4,.footer-col .footer-heading{color:#fff;font-size:.95rem;font-weight:700;letter-spacing:.03em;margin-bottom:18px}
.footer-col ul{display:flex;flex-direction:column;gap:11px}
.footer-col ul li a{font-size:.91rem;color:rgba(255,255,255,.66);transition:color .15s,padding-left .15s}
.footer-col ul li a:hover{color:var(--accent);padding-left:3px}
.footer-contact-item{display:flex;gap:11px;margin-bottom:15px;font-size:.9rem;align-items:center}
.footer-contact-item svg{width:17px;height:17px;color:var(--accent);flex-shrink:0}
.footer-contact-item .fci-label{color:rgba(255,255,255,.5);font-size:.76rem;text-transform:uppercase;letter-spacing:.05em}
.footer-contact-item a:hover,.footer-contact-item .fci-val:hover{color:#fff}
.footer-contact-item .fci-val{color:rgba(255,255,255,.82);font-weight:700}
.footer-bottom{border-top:1px solid rgba(255,255,255,.1);padding:20px 0}
.footer-bottom-inner{display:flex;flex-direction:column;gap:10px;align-items:center;text-align:center;font-size:.84rem;color:rgba(255,255,255,.55)}
@media(min-width:768px){.footer-bottom-inner{flex-direction:row;justify-content:space-between;text-align:left}}
.footer-bottom a{color:rgba(255,255,255,.55)}
.footer-bottom a:hover{color:var(--accent)}
.footer-legal{display:flex;gap:18px}

/* ==========================================================================
   Slick / futuristic layer
   ========================================================================== */

/* Scroll progress bar */
.scroll-progress{position:fixed;top:0;left:0;height:3px;width:0;background:var(--accent);z-index:1200;box-shadow:none;transition:width .08s linear}

/* Video hero. THE STACK BUG: the static fallback <img class="hero-dark-bg"> comes AFTER
   the <video> in the DOM, and both defaulted to z-index:0 — so the image painted ON TOP
   of the video and the video was never visible (a real shipped bug; the editor "added the
   video" but it stayed hidden under the still). Explicit, fallback-preserving stack for
   video heroes: fallback img 0 → video 1 → scrim ::before 2 → content 3. (.hero-dark
   sets no stacking context, so negative z-index would hide the img behind the dark bg —
   don't use it here.) */
.hero-video .hero-bg-video{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;z-index:1;opacity:0;transition:opacity .9s ease;filter:saturate(.85) brightness(.5)}
.hero-video .hero-bg-video.ready{opacity:1}
.hero-video .hero-dark-bg{z-index:0}     /* fallback stays UNDER the video (still visible if the video fails) */
.hero-video::before{z-index:2;will-change:transform;transform:translateZ(0)}           /* readability scrim sits ABOVE the video */
.hero-video .container{z-index:3}        /* hero copy sits above the scrim */

/* v3: the coloured "aurora" glow and the animated grid overlay are both removed. The hero is a
   real photograph under a flat neutral-black scrim — nothing tinted, nothing animated over it. */
.hero-dark::after{content:none}
.hero-grid-lines{display:none}

/* Card glow + lift on hover */
.card:hover,.cat-card:hover,.img-card:hover,.retention-card:hover,.catalog-card:hover{box-shadow:0 14px 34px rgba(13,13,13,.10),0 0 0 1px var(--silver)}
.svc-card,.cat-card,[data-tilt]{transition:transform .25s cubic-bezier(.2,.7,.3,1),box-shadow .25s ease,border-color .25s ease;transform-style:preserve-3d;will-change:transform}

/* Pulsing / glowing CTA */
.btn-glow{position:relative;animation:btn-pulse 2.8s ease-in-out infinite}
@keyframes btn-pulse{0%,100%{box-shadow:0 0 0 0 rgba(179,33,27,.45)}50%{box-shadow:0 0 0 10px rgba(179,33,27,0)}}
.btn-glow:hover{animation-play-state:paused}

/* Animated underline accent under section h2 */
.section-header h2{position:relative;display:inline-block}
.section-header h2::after{content:"";position:absolute;left:50%;bottom:-12px;transform:translateX(-50%);width:54px;height:3px;border-radius:3px;background:linear-gradient(90deg,var(--accent),var(--primary));opacity:.9}
.section-header.left h2::after{left:0;transform:none}
.section.dark .section-header h2::after,.process .section-header h2::after{background:var(--accent)}

/* Brand marquee */
.brand-marquee{padding:38px 0;border-top:1px solid var(--border);border-bottom:1px solid var(--border);background:var(--surface)}
.brand-marquee .bm-label{text-align:center;font-size:.78rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;color:var(--text-muted);margin-bottom:22px}
.brand-strip{display:flex;overflow:hidden;-webkit-mask-image:linear-gradient(90deg,transparent,#000 8%,#000 92%,transparent);mask-image:linear-gradient(90deg,transparent,#000 8%,#000 92%,transparent)}
.brand-track{display:flex;gap:22px;align-items:center;width:max-content;animation:brand-scroll 42s linear infinite}
.brand-track:hover{animation-play-state:paused}
.brand-item{height:108px;min-width:184px;display:flex;align-items:center;justify-content:center;padding:0 34px;background:#fff;border:1px solid var(--border);border-radius:16px;flex-shrink:0;box-shadow:var(--shadow-sm)}
.brand-item img{height:56px;width:auto;max-width:150px;object-fit:contain;opacity:.9;filter:grayscale(1);transition:opacity .25s,filter .25s,transform .25s}
.brand-item:hover img{opacity:1;filter:none;transform:scale(1.06)}
/* text fallback for a client with no available logo mark — reads as a wordmark in the same card */
.brand-item .brand-text{font-family:var(--font-display);font-weight:700;font-size:1.12rem;letter-spacing:-.01em;color:var(--text-muted);white-space:nowrap}
@keyframes brand-scroll{from{transform:translateX(0)}to{transform:translateX(-50%)}}

/* Stat pop on reveal */
.stat-num{transition:transform .3s ease}
.stat-item.in .stat-num{animation:stat-pop .5s ease}
@keyframes stat-pop{0%{transform:scale(.8);opacity:0}100%{transform:scale(1);opacity:1}}

/* Glassy lift for hero ticker numbers */
.hero-ticker>div{transition:transform .3s ease}
.hero-ticker>div:hover{transform:translateY(-4px)}

@media(prefers-reduced-motion:reduce){
  .hero-dark::after,.hero-grid-lines,.btn-glow,.brand-track,.scroll-progress{animation:none!important}
}

/* ---------- Contrast safety: dark bands legible BY CONSTRUCTION ----------
   Every dark-background section/panel/card carries .on-dark (the marker). The
   built-in dark classes are aliased in as a safety net so a forgotten marker
   still self-heals. These rules set a legible LIGHT default for EVERY text
   descendant AND icon, regardless of element type or component class — so a
   brand-new dark band (awards/credentials/stats grid) is readable without being
   named here. Accent/primary stay (they read fine on dark); :where() keeps
   specificity low so a deliberate per-component color still wins.            */
.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar{color:#fff}
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar) :where(h1,h2,h3,h4,h5,h6,strong,b,dt,.stat-num){color:#fff}
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar) :where(p,li,dd,blockquote,span,small,figcaption,label,.stat-label,.cert-sub,.section-header p){color:rgba(255,255,255,.78)}
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar) :where(svg,.icon,i){color:#fff}
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar) .eyebrow{color:#fff;background:rgba(255,255,255,.14)}
/* icons that intentionally use the accent on dark keep it (higher specificity below wins) */
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar) .trust-pill svg,
.sidebar-cta .sc-list svg,.footer-contact-item svg{color:var(--silver)}

/* ---------- Quote FAB ---------- */
.quote-fab{position:fixed;right:22px;bottom:22px;z-index:1090;display:inline-flex;align-items:center;gap:10px;background:var(--accent);color:#fff;font-weight:700;font-size:.95rem;padding:14px 22px;border-radius:var(--radius-pill);box-shadow:0 8px 24px rgba(13,13,13,.30);transition:transform .2s,box-shadow .2s;animation:fab-breathe 3.4s ease-in-out infinite}
.quote-fab:hover{transform:translateY(-3px) scale(1.02);box-shadow:0 16px 38px rgba(20,40,46,.34);animation-play-state:paused}
.quote-fab svg{width:19px;height:19px}
@keyframes fab-breathe{0%,100%{box-shadow:0 8px 24px rgba(13,13,13,.30)}50%{box-shadow:0 8px 24px rgba(179,33,27,.55)}}
@media(max-width:560px){.quote-fab{right:16px;bottom:16px;width:56px;height:56px;padding:0;justify-content:center;border-radius:50%}.quote-fab-label{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0,0,0,0)}}

/* ---------- Modal ---------- */
.modal-overlay{position:fixed;inset:0;z-index:1100;background:rgba(20,40,46,.6);backdrop-filter:blur(4px);display:none;align-items:flex-start;justify-content:center;padding:40px 16px;overflow-y:auto}
.modal-overlay.active{display:flex}
.modal{background:#fff;border-radius:var(--radius-lg);max-width:560px;width:100%;box-shadow:var(--shadow-lg);animation:modal-in .25s ease}
@keyframes modal-in{from{opacity:0;transform:translateY(18px)}to{opacity:1;transform:translateY(0)}}
.modal-header{display:flex;align-items:flex-start;justify-content:space-between;gap:16px;padding:24px 26px 0}
.modal-header h3{font-size:1.35rem;margin-bottom:5px}
.modal-header p{font-size:.9rem}
.modal-close{width:38px;height:38px;border-radius:50%;background:var(--surface);color:var(--text);display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:background .15s}
.modal-close:hover{background:var(--border)}
.modal-close svg{width:20px;height:20px}
.modal-body{padding:20px 26px 28px}
.modal-success{display:none;text-align:center;padding:36px 26px}
.modal-success.show{display:block}
.modal-success .ms-ico{width:64px;height:64px;border-radius:50%;background:var(--accent);color:var(--text);display:flex;align-items:center;justify-content:center;margin:0 auto 18px}
.modal-success .ms-ico svg{width:32px;height:32px}
.modal-success h3,.modal-success .ms-title{margin-bottom:8px;font-family:var(--font-display);font-weight:700;letter-spacing:-.02em;line-height:1.14;color:var(--text);font-size:1.35rem}

/* ---------- Reveal animation ---------- */
.reveal{opacity:0;transform:translateY(24px);transition:opacity .6s ease,transform .6s ease}
.reveal.in{opacity:1;transform:none}
@media(prefers-reduced-motion:reduce){.reveal{opacity:1;transform:none;transition:none}.brand-track,.quote-fab{animation:none}}

/* ==========================================================================
   Mobile optimizations
   ========================================================================== */
@media(max-width:767px){
  .section{padding:56px 0}
  .section-sm{padding:40px 0}
  .section-lg{padding:64px 0}
  .section-header{margin-bottom:34px}
  .hero-pad{padding:96px 0 64px}
  .hero-pad-sm{padding:96px 0 52px}
  .hero-fullscreen{min-height:auto;padding:110px 0 64px}
  .footer-top{padding:46px 0 32px}
  .cta-form-grid{gap:34px}
  .stat-grid{padding:38px 0;gap:26px 14px}
  .split-media .badge-float{left:50%;transform:translateX(-50%);bottom:-26px}
}
@media(max-width:639px){
  .product-meta{grid-template-columns:1fr 1fr}
  .card{padding:24px 20px}
  .cat-card,.catalog-card,.detail-card,.cta-form{padding:24px 20px}
  .hero-ticker{gap:28px}
  .hero-ticker .ht-num{font-size:1.6rem}
  .faq-question{padding:16px 18px;font-size:.96rem}
  .trust-pill{font-size:.84rem;padding:9px 14px}
}
@media(max-width:479px){
  .section{padding:48px 0}
  .btn{white-space:normal;text-align:center}
  .btn-lg{padding:15px 24px}
  .hero-dark h1{font-size:1.95rem}
  .hero-actions .btn{width:100%}
  .product-meta{grid-template-columns:1fr}
  .ind-card{flex-basis:220px}
  .stat-num{font-size:1.7rem}
  .modal-body{padding:16px 18px 22px}
  .modal-header{padding:18px 18px 0}
}

/* ==========================================================================
   Spacing floor — every top-level section breathes, even in a free-flowing layout.
   .section / .section-sm / .section-lg / .hero-* / .brand-marquee all set their own
   padding at class-specificity and KEEP it (a class beats this element-only rule);
   this only rescues a <section> whose class forgot vertical padding, so no section
   can ever render flush with zero spacing around it.
   ========================================================================== */
main > section{padding-block:56px}

/* ==========================================================================
   Band-separation safety net (deterministic — does NOT depend on the build
   alternating correctly). When two adjacent sections share the same tone they
   visually merge into one cramped wall ("no spacing"); give the second a hairline
   so every band reads as its own surface even in a free-flowing layout.
   ========================================================================== */
/* light + light (white→white) */
.section:not(.surface):not(.dark):not(.process):not(.cta-band):not(.cta-dark)
  + .section:not(.surface):not(.dark):not(.process):not(.cta-band):not(.cta-dark){border-top:1px solid var(--border)}
/* tint + tint (surface / brand-marquee both use the tinted surface) */
.section.surface + .section.surface,
.section.surface + .brand-marquee,
.brand-marquee  + .section.surface,
.brand-marquee  + .brand-marquee{border-top:1px solid var(--border)}
/* dark + dark — a faint light hairline keeps the seam visible without a harsh line */
.hero-dark + .section.dark,        .hero-dark + .section.process,
.section.dark + .section.dark,     .section.dark + .section.process,
.section.process + .section.dark,  .section.process + .section.process,
.section.dark + .section.cta-band, .section.cta-band + .section.dark,
.section.process + .section.cta-band{border-top:1px solid rgba(255,255,255,.10)}

/* ==========================================================================
   Card safety net — cards must be a <div>, NEVER an <a>, and must NEVER nest an
   <a class="cc-foot"> inside an <a> (illegal nested anchors → the browser ejects
   the inner link, it becomes a stray grid cell, and the whole card grid collapses
   into a vertical full-width mess — a real shipped defect).
   To make the WHOLE card clickable, keep it a <div> and let the single .cc-foot
   link stretch over the card via this overlay. No anchor wrapping needed.
   ========================================================================== */
.cat-card,.img-card,.related-card{position:relative}
.cat-card .cc-foot,.img-card .cc-foot,.img-card .ic-body .cc-foot{position:static}
.cat-card .cc-foot::after,.img-card .cc-foot::after{content:"";position:absolute;inset:0;z-index:1}

/* Defensive: if a build uses a `.cc-media` image box inside a card (the canonical
   image card is `.img-card > .ic-media`, but `.cc-media` was improvised with NO
   css and rendered images at full intrinsic size, blowing the grid apart), still
   constrain it to a fixed-ratio cover box so it can never balloon. */
.cc-media{aspect-ratio:16/10;overflow:hidden;border-radius:var(--radius-md);margin-bottom:18px;position:relative}
.cc-media img{width:100%;height:100%;object-fit:cover;display:block}

/* Last-ditch: a card-footer link that got ejected to be a DIRECT child of a grid
   (the nested-anchor bug) must not sit in a card column and shove everything out of
   alignment — drop it onto its own full-width row instead of interleaving the cards. */
.grid-2 > .cc-foot,.grid-3 > .cc-foot,.grid-4 > .cc-foot{grid-column:1/-1}

/* ==========================================================================
   CTA / button breathing room. A button or actions row that follows content in a
   body column (e.g. the "See the math" button pinned flush under a comparison
   table) must never sit jammed against the element above it.
   ========================================================================== */
.split-body > .btn,.split-body > .hero-actions,.split-body > .btn-row,
.cta-content > * + .btn,.cta-content > * + .hero-actions{margin-top:24px}
.split-body > * + .btn,.detail-card > * + .btn,.sidebar-cta > * + .btn{margin-top:22px}

/* ==========================================================================
   TABLES — for genuinely tabular content (comparison / spec / pricing). Use a REAL
   <table class="data-table"> wrapped in <div class="table-wrap"> (the wrap scrolls
   horizontally on small screens so columns never crush). NEVER fake a table by
   splitting a sentence or key-value data across mis-sized grid/flex columns.
   ========================================================================== */
.table-wrap{width:100%;overflow-x:auto;-webkit-overflow-scrolling:touch;margin:10px 0 24px;border:1px solid var(--border);border-radius:var(--radius-md)}
.data-table,.compare-table{width:100%;border-collapse:collapse;font-size:.95rem;min-width:440px}
.data-table th,.data-table td,.compare-table th,.compare-table td{padding:13px 18px;text-align:left;vertical-align:top;border-bottom:1px solid var(--border)}
.data-table thead th,.compare-table thead th{background:var(--surface);color:var(--text);font-weight:700;font-size:.82rem;letter-spacing:.04em;text-transform:uppercase;white-space:nowrap}
.data-table tbody tr:last-child td,.compare-table tbody tr:last-child td{border-bottom:0}
.data-table tbody tr:nth-child(even),.compare-table tbody tr:nth-child(even){background:var(--surface)}
.data-table td:first-child,.compare-table td:first-child{font-weight:700;color:var(--text)}
.data-table .td-yes{color:var(--accent-dark);font-weight:700}
.data-table .td-no{color:var(--text-muted)}
/* On a dark band the table inherits .on-dark light text; tint the header/zebra for contrast. */
.on-dark .table-wrap{border-color:rgba(255,255,255,.16)}
.on-dark .data-table th,.on-dark .data-table td,.on-dark .compare-table th,.on-dark .compare-table td{border-bottom-color:rgba(255,255,255,.14)}
.on-dark .data-table thead th,.on-dark .compare-table thead th{background:rgba(255,255,255,.08);color:#fff}
.on-dark .data-table tbody tr:nth-child(even),.on-dark .compare-table tbody tr:nth-child(even){background:rgba(255,255,255,.05)}

/* ==========================================================================
   Trust / "backed by" bar — keep it from rendering as a jumbled plain-text list.
   Items are spaced pills; an EMPTY item must not leave a ghost gap.
   ========================================================================== */
.trust-pills{display:flex;flex-wrap:wrap;align-items:center;justify-content:center;gap:14px 22px}
.trust-pills :empty{display:none}
.trust-label{display:block;text-align:center}

/* ============================================================================
   SIGNATURE / DESIGN-PACK LAYER — opt-in, VETTED, responsive + contrast-safe.
   This is the toolkit for making a build DISTINCTIVE and design-heavy (see SKILL
   "Design ceiling"). It EXTENDS the baseline; it never replaces it. Using these
   classes is NOT "improvising CSS" — they are part of the shipped baseline, so you
   reach for them instead of hand-rolling a section's internals. Each is
   self-contained, mobile-safe, and degrades gracefully. Decorative glow/mesh/grid
   layers sit BEHIND content (z-index) and are pointer-events:none. Pair every
   dark/over-media band with .on-dark so text + icons stay light (contrast rule).
   Push these on fitting clients (tech, premium, modern, creative); keep the
   restrained baseline for trust-forward/industrial ones. Never at the cost of
   contrast or responsiveness.
   ============================================================================ */

/* --- Decorative DARK-BAND backgrounds: futuristic glow / mesh / grid / scanlines.
   Add to a `.section.dark` / `.hero-dark` / `.on-dark` band; content sits above. --- */
.bg-aurora{position:relative;overflow:hidden;isolation:isolate}
.bg-aurora::before{content:"";position:absolute;inset:-40% -15% auto -15%;height:95%;z-index:-1;pointer-events:none;
  background:radial-gradient(55% 55% at 18% 20%,color-mix(in srgb,var(--accent) 42%,transparent),transparent 70%),
             radial-gradient(50% 50% at 82% 12%,color-mix(in srgb,var(--primary) 60%,transparent),transparent 72%);
  filter:blur(64px);opacity:.65}
.bg-grid{position:relative;overflow:hidden;isolation:isolate}
.bg-grid::before{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;opacity:.45;
  background-image:linear-gradient(color-mix(in srgb,var(--accent) 14%,transparent) 1px,transparent 1px),
                   linear-gradient(90deg,color-mix(in srgb,var(--accent) 14%,transparent) 1px,transparent 1px);
  background-size:46px 46px;
  -webkit-mask-image:radial-gradient(72% 60% at 50% 28%,#000,transparent 76%);
          mask-image:radial-gradient(72% 60% at 50% 28%,#000,transparent 76%)}
.bg-glow{position:relative;overflow:hidden;isolation:isolate}
.bg-glow::before{content:"";position:absolute;left:50%;top:-20%;width:70vw;height:70vw;max-width:760px;max-height:760px;
  transform:translateX(-50%);z-index:-1;pointer-events:none;border-radius:50%;opacity:.5;filter:blur(90px);
  background:radial-gradient(circle,color-mix(in srgb,var(--accent) 55%,transparent),transparent 65%)}

/* --- BENTO grid: an asymmetric feature grid (a wide/tall lead tile + smaller tiles)
   instead of a flat row of identical cards. Children are normal .cat-card/.img-card/.glass. --- */
.bento{display:grid;gap:18px;grid-template-columns:1fr}
@media(min-width:768px){
  .bento{grid-template-columns:repeat(3,1fr);grid-auto-rows:minmax(150px,auto)}
  .bento .bento-lg{grid-column:span 2;grid-row:span 2}
  .bento .bento-wide{grid-column:span 2}
  .bento .bento-tall{grid-row:span 2}
}

/* --- GLASS card (glassmorphism) — only on dark / over-media bands (carry .on-dark). --- */
.glass{background:rgba(255,255,255,.06);border:1px solid rgba(255,255,255,.14);border-radius:var(--radius-lg);
  -webkit-backdrop-filter:blur(14px) saturate(140%);backdrop-filter:blur(14px) saturate(140%);
  box-shadow:0 10px 44px rgba(0,0,0,.28);padding:28px 24px}

/* --- Editorial DISPLAY type, gradient + outline headline words. --- */
.display-xl{font-size:clamp(2.6rem,8vw,5.8rem);font-weight:700;letter-spacing:-.03em;line-height:1.02}
.display-lg{font-size:clamp(2.1rem,5.5vw,3.8rem);font-weight:700;letter-spacing:-.025em;line-height:1.06}
.text-gradient{background:linear-gradient(100deg,var(--accent),var(--primary));-webkit-background-clip:text;background-clip:text;color:transparent}
.text-stroke{-webkit-text-stroke:1.4px currentColor;color:transparent}   /* outline word for editorial heroes */
.eyebrow-line{display:inline-flex;align-items:center;gap:12px;font-weight:700;font-size:.8rem;letter-spacing:.14em;text-transform:uppercase;color:var(--text-muted)}
.eyebrow-line::before{content:"";width:34px;height:2px;background:var(--primary)}  /* minimalist line-label alt to the pill chip */

/* --- SPLIT-SCREEN hero: media on one side, content on the other (alt to the full-bleed hero). --- */
.hero-split{display:grid;grid-template-columns:1fr;min-height:auto}
.hero-split .hs-media{position:relative;overflow:hidden;min-height:44vh}
.hero-split .hs-media>img,.hero-split .hs-media>video{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
.hero-split .hs-body{display:flex;flex-direction:column;justify-content:center;padding:120px 0 64px}
@media(min-width:900px){
  .hero-split{grid-template-columns:1.04fr .96fr;min-height:92vh}
  .hero-split .hs-media{min-height:0}
  .hero-split .hs-body{padding:96px 64px 96px 0}
}

/* --- ANGLED / soft-curve section divider — breaks the flat band-on-band stack.
   Use sparingly (one or two per page) and only on a band with ample vertical padding. --- */
.section-angled{clip-path:polygon(0 0,100% 2.6vw,100% 100%,0 calc(100% - 2.6vw))}
.section-curve{border-top-left-radius:48px 26px;border-top-right-radius:48px 26px;overflow:hidden}

/* --- MARQUEE strip: a moving row of CAPSULE chips (duplicate the track once for a seamless loop).
   ⛔ HARD CONSTRAINT: every phrase is its own `.hm-pill` — a padded, bordered capsule with real
   spacing between items. The old giant bare-text marquee shipped as an unreadable run-on word blur
   and is BANNED. Never put bare text directly in `.hm-track`. Pauses on hover. --- */
.headline-marquee{overflow:hidden;white-space:nowrap;width:100%;padding:6px 0}
.headline-marquee .hm-track{display:inline-flex;gap:16px;align-items:center;width:max-content;
  padding-right:16px;animation:hm-scroll 36s linear infinite}
.headline-marquee .hm-pill{display:inline-flex;align-items:center;gap:10px;padding:11px 24px;
  border-radius:999px;border:1px solid var(--border);background:var(--surface);
  font-weight:700;font-size:1.02rem;letter-spacing:.01em;line-height:1;color:var(--text)}
/* Icons on a LIGHT pill must never be raw --accent — a light client accent (cyan/yellow)
   on near-white --surface drops below 2:1 and the QA probe blocks it as an invisible band.
   Blend the accent toward --text so it stays brand-tinted but always readable; the dark
   override below restores light icons on dark sections. */
.headline-marquee .hm-pill svg,.headline-marquee .hm-pill .icon{width:1.05em;height:1.05em;color:color-mix(in srgb,var(--accent) 55%,var(--text))}
:is(.on-dark,.section.dark,.hero-dark) .headline-marquee .hm-pill{
  background:rgba(255,255,255,.08);border-color:rgba(255,255,255,.2);color:#fff}
:is(.on-dark,.section.dark,.hero-dark) .headline-marquee .hm-pill svg,
:is(.on-dark,.section.dark,.hero-dark) .headline-marquee .hm-pill .icon{color:#fff}
.headline-marquee .hm-dot{color:var(--graphite);font-weight:700}
:is(.on-dark,.section.dark,.hero-dark) .headline-marquee .hm-dot{color:rgba(255,255,255,.6)}
.headline-marquee:hover .hm-track{animation-play-state:paused}
@keyframes hm-scroll{from{transform:translateX(0)}to{transform:translateX(-50%)}}

/* --- Accent KICKER rule under a stat / feature, and a hairline "tech" border. --- */
.kicker-rule{width:46px;height:3px;border-radius:3px;background:linear-gradient(90deg,var(--accent),var(--primary));margin:14px 0 0}
.edge-glow{border:1px solid color-mix(in srgb,var(--accent) 34%,transparent);box-shadow:0 0 0 1px color-mix(in srgb,var(--accent) 10%,transparent),0 14px 50px rgba(0,0,0,.18)}

@media(prefers-reduced-motion:reduce){
  .headline-marquee .hm-track{animation:none}
}
/* Mobile: kill the angled clip (it eats content at small sizes) and calm big type. */
@media(max-width:639px){
  .section-angled{clip-path:none}
  .hero-split .hs-body{padding:104px 0 56px}
}
/* AUTO-REPAIR: any explicit multi-column grid — INCLUDING a hand-written inline
   `style="display:grid;grid-template-columns:repeat(3,1fr)"` — collapses to a single
   column on phones. A stylesheet `!important` beats a non-important inline declaration,
   so this neutralises the #1 cause of mobile horizontal scroll (responsive_hscroll)
   regardless of how the section was authored. */
@media(max-width:600px){
  [style*="grid-template-columns"]{grid-template-columns:1fr !important}
}
/* AUTO-REPAIR: a .cta-form is always a WHITE card. When it sits inside an on-dark band
   (.cta-band / .cta-dark / .on-dark …), the band's white-text cascade turned the form's
   labels, helper text and input text white-on-white — an invisible form. This higher-
   specificity rule restores dark text inside the white card. (Same dark-cascade-into-a-
   light-child defect that hit .process; .cta-form is the reliably-white one we can target.) */
:is(.on-dark,.section.dark,.hero-dark,.process,.cta-dark,.cta-band,.sidebar-cta,.quick-response,.trust-bar,.stat-bar) .cta-form
  :where(h1,h2,h3,h4,h5,h6,p,label,span,small,strong,b,li,dd,dt,.form-label,.form-note,input,textarea,select){color:var(--text)}
/* AUTO-REPAIR: buttons inside the white .cta-form must use on-LIGHT styling. A .btn-outline
   defaults to white text + faint-white border (built for dark bands) — invisible on the
   white card. Force dark ink + a visible border so the form's buttons are always visible. */
.cta-form .btn-outline{color:var(--text);border-color:var(--border)}
/* …EXCEPT .btn-primary, which is a solid RED fill, not a white surface — dark ink on red
   is the wrong repair. Aug 19 revision: every AVAS request button is red background,
   white text, and this is the one rule that was breaking that inside the form card. */
.cta-form .btn-primary{color:#fff}
.cta-form :where(.btn,.btn-primary,.btn-outline) span{color:inherit}

/* AUTO-REPAIR: tolerate the FAQ class-name variants the builder sometimes emits
   (.faq-q / .faq-a / .faq-icon) instead of the canonical .faq-question / .faq-answer /
   .faq-ico, so the accordion still styles + collapses. Paired with a JS selector that
   binds both spellings. */
.faq-q{width:100%;display:flex;align-items:center;justify-content:space-between;gap:16px;
  padding:20px 22px;font-weight:700;font-size:1.02rem;text-align:left;color:var(--text);cursor:pointer}
.faq-q .faq-icon{width:30px;height:30px;border-radius:50%;background:var(--secondary);color:var(--primary);
  display:flex;align-items:center;justify-content:center;flex-shrink:0;transition:transform .25s,background .2s,color .2s}
.faq-q .faq-icon svg{width:16px;height:16px}
.faq-item.active .faq-icon{background:var(--accent);color:var(--text);transform:rotate(45deg)}
.faq-a{max-height:0;overflow:hidden;transition:max-height .3s ease;color:var(--text-secondary);
  font-size:.97rem;padding:0 22px}
.faq-a > :last-child{margin-bottom:22px}
/* AUTO-REPAIR: tolerate the process-section variant the builder sometimes emits (.ps-num for
   the number circle, and a bare .process with steps not wrapped in .process-grid) so a
   hand-rolled "How It Works" still styles instead of shipping as an unstyled stack. */
.process .ps-num,.ps-num{width:54px;height:54px;border-radius:50%;border:2px solid var(--accent);
  color:var(--accent);display:flex;align-items:center;justify-content:center;font-weight:700;font-size:1.2rem;margin-bottom:18px}
.process > .container > .process-step{display:inline-block}
@media(min-width:768px){.process .process-step + .process-step{margin-top:0}}

/* ABOUT page (/about/) — Jason Vargas bio headshot is a square 800x800 source. Override the
   default 4/3 .split-media crop so the real photo renders square and uncropped, not distorted. */
.split-media img.about-founder-photo{aspect-ratio:1/1;object-position:center center}

/* ---- HOME (index.html): FAQ 2-column layout ----
   v2 asks for ONE unified question list split visually into two columns (half left,
   half right), collapsing to a single column on mobile. Implemented as a grid on the
   single .faq-list so every .faq-item / .faq-question / .faq-answer hook is preserved
   for the existing accordion JS. grid-auto-flow:column + 6 explicit rows puts Q1-6 in
   the left column and Q7-12 in the right, matching the client's document order.
   align-items:start keeps each card at its natural height so an open answer doesn't
   stretch its neighbour. */
.faq-list.faq-2col{
  display:grid;
  grid-auto-flow:column;
  grid-template-columns:1fr 1fr;
  grid-template-rows:repeat(6,auto);
  align-items:start;
  column-gap:24px;
  row-gap:14px;
  max-width:1040px;
}
@media(max-width:767px){
  .faq-list.faq-2col{grid-auto-flow:row;grid-template-columns:1fr;grid-template-rows:none}
}

/* --- Page: /how-you-gain-proof/ --- */
/* Base `p` carries no margin, so the two stacked lede paragraphs in the
   Roadmap section header need explicit separation. */
.hygp-lede p + p{margin-top:14px}
/* "What Changes As a Result" closer: constrain the bullet list to a readable
   measure and centre it, matching .faq-list / .cta-content. */
.hygp-outcomes{max-width:820px;margin:0 auto}

/* AVAS page (/avas/) — "The Findings" statistics block.
   Reuses Home's .section.dark + .stat-grid pattern for the four-across number row.
   These rules only style the definitions BELOW that row: the client specified a single
   vertical stack (explicitly NOT four columns), each definition using the full width. */
.avas-findings-defs{max-width:820px;margin:44px auto 0;display:grid;grid-template-columns:1fr;gap:24px}
.avas-findings-defs .affd-item{padding-top:24px;border-top:1px solid rgba(255,255,255,.14)}
.avas-findings-defs .affd-item:first-child{padding-top:0;border-top:0}
.avas-findings-defs dt{font-family:var(--font-display);font-weight:700;font-size:1.02rem;letter-spacing:-.01em;margin-bottom:6px}
.avas-findings-defs dd{margin:0;font-size:.98rem;line-height:1.65}
@media(max-width:767px){
  .avas-findings-defs{margin-top:32px;gap:20px}
  .avas-findings-defs .affd-item{padding-top:20px}
  .avas-findings-defs dt{font-size:.96rem}
}

/* Proof — Gore-Tex page (/proof-gore-tex/) — the one case study.
   The narrative + Jason's two supplied rain-room photos. Scoped to .gt-* only.
   Deliberately NO aspect-ratio on these images: one photo is landscape (2030x1248),
   one is portrait (946x1264). The global `img{max-width:100%;height:auto}` reset plus
   width:100% keeps each at its true ratio — unlike .split-media img, whose 4/3 crop
   would cut the portrait demo shot in half. */
.gt-case{max-width:820px;margin:0 auto}
.gt-narrative{border-left:4px solid var(--accent);padding-left:28px}
.gt-narrative p{font-size:1.1rem;line-height:1.7;margin-bottom:14px}
.gt-narrative p:last-child{margin-bottom:0}
.gt-lede{font-family:var(--font-display);font-size:1.5rem;font-weight:700;line-height:1.4;color:#fff;margin-bottom:22px}
.gt-figure{margin:34px 0 0}
.gt-figure img{width:100%;border-radius:var(--radius-lg);border:1px solid rgba(255,255,255,.1)}
.gt-figure-portrait{margin:0;max-width:300px;margin-inline:auto}
.gt-closing{font-family:var(--font-display);font-size:1.24rem;font-weight:700;line-height:1.45;color:#fff;margin:0}
@media(min-width:768px){
  .gt-figure-portrait{margin-inline:0}
}
@media(max-width:767px){
  .gt-narrative{padding-left:20px}
  .gt-lede{font-size:1.28rem}
  .gt-narrative p{font-size:1.02rem}
  .gt-figure{margin-top:26px}
  .gt-closing{font-size:1.1rem}
}
/* These two sections lost their .split-media (they held stock images that
   misrepresented this case study). .split goes 1fr 1fr at >=1024px, which would leave
   a single remaining child stranded in a half-width column beside dead space — so pin
   the prose to one centred, readable column (the 820px measure used site-wide).
   .split.gt-prose (0,2,0) outranks the .split media-query rule regardless of order. */
.split.gt-prose{grid-template-columns:1fr;max-width:820px;margin:0 auto;gap:0}

/* --- Page: /how-you-gain-proof/ (contrast fix) ---
   The Roadmap steps are now a <table class="data-table"> inside the dark
   .section.process.on-dark (previously .process-step divs, whose <h3> picked up
   #fff from the .on-dark heading rule). `.data-table td:first-child` is the only
   rule that sets a td colour and it hard-codes var(--text) (#0A0A18) — near-black
   ink on the near-black --dark (#07071A) panel, i.e. an invisible Step column.
   The sibling .on-dark overrides cover thead/borders/striping but miss this one.
   (0,3,1) beats the (0,2,1) base rule, so order is not load-bearing. */
:is(.on-dark,.section.dark,.process,.cta-dark) :is(.data-table,.compare-table):not(.roadmap-table) td:first-child{color:#fff}
/* ...except the Roadmap table, which the final revision moves onto a white field inside the
   same black section, so its Step column goes back to black ink. */

/* --- Page: /how-you-gain-proof/ --- Roadmap section closing paragraph.
   The client's copy places this paragraph AFTER the step table, closing the
   Roadmap section and leading into "What Gets Built". It sits on the .process
   dark band, so colour is inherited from the .on-dark rules above; these rules
   only give it the same centred 680px measure and 1.08rem size as .section-header p. */
.hygp-roadmap-close{max-width:680px;margin:44px auto 0;text-align:center;font-size:1.08rem}

/* ---------- /the-proof-gap/ — copy strip (client v2) ----------
   The client supplied no hero subhead and no sidebar copy for this page, so both were removed.
   These rules restore the spacing those elements used to provide; no other page uses them.
   The hero dropped .hero-fullscreen (its 88vh min-height left a near-empty band once the
   invented subhead went), so .pg-hero must supply its own top padding to clear the
   position:fixed header (--header-total 108px) — .hero-pad-sm's 96px alone let the H1
   slide under it on mobile. */
.pg-hero{padding:168px 0 92px}
@media(max-width:767px){
  .pg-hero{padding:142px 0 64px}
}
.pg-hero .hero-content h1{margin-bottom:30px}
.pg-lede{max-width:820px;margin:0 auto}
.pg-lede p{font-size:1.12rem}

/* ---------- /about/ — copy strip (client v2) ----------
   v2 supplies no hero subhead, no section subheads and no card CTA labels for About,
   so those were removed. These rules re-tidy the spacing the removed elements used to
   provide. Scoped to body.page-about; no other page is affected. */
.page-about .section-header h2:only-child{margin-bottom:0}
.page-about .cat-card p:last-child{margin-bottom:0}

/* --- Page: /proof-gore-tex/ (strip to the client's v2 copy) ---
   v2 supplies no eyebrow and no hero subhead for this page, so the invented ones
   were removed and the H1 now carries the hero band on its own. The .hero-sub that
   used to sit under the headline contributed the 30px of air before .hero-actions;
   with it gone the CTA crowds the H1 at .hero-dark h1's 18px. Restore that rhythm
   and hold the headline to a display measure so it breaks across two lines rather
   than running as one thin line across the 760px .hero-content. Scoped to .gt-hero,
   which exists only on this page. */
.gt-hero h1{margin-bottom:34px;max-width:15ch}
@media(max-width:767px){
  .gt-hero h1{margin-bottom:26px;max-width:none}
}
/* This page now carries exactly two photos, and the hero backdrop is the same
   rain-room shot that appears as a full figure in the body a screen below. At the
   base brightness(.62) the truck and its "KNOW WHAT'S INSIDE" wrap stay legible
   through the ::before scrim's thin right edge (.55 alpha), so the identical photo
   reads twice. Sink it to a texture: the body figure stays the only place the
   photo is actually presented. Scoped to .gt-hero-band; this page only. */
.gt-hero-band .hero-dark-bg{filter:saturate(.32) brightness(.34)}

/* ============================================================
   AVAS page (/avas/) — copy-strip tidy.
   The page now publishes only the client's v2 copy, so several
   sections lost invented scaffolding. These rules keep the
   remaining markup composed. Scoped to /avas/ only.
   ============================================================ */

/* Hero: the client supplied no subhead and no eyebrow for this page, so the
   hero is now just the H1 + the client's two CTA labels. .hero-fullscreen's
   88vh would leave a near-empty screen, so the hero drops to .hero-pad-sm.
   But the header is fixed and overlays the hero (--header-total:108px), and
   .hero-pad-sm's 120px top left the H1 with 11px of clearance — it read as if
   it were colliding with the nav. Supply our own top padding to clear the
   header properly, matching /the-proof-gap/'s .pg-hero rhythm, and give the
   lone H1 breathing room above the CTAs. */
.avas-hero{padding:168px 0 92px}
.avas-hero h1{margin-bottom:30px}
@media(max-width:767px){
  .avas-hero{padding:142px 0 64px}
}

/* "Why SEO Alone Isn't Enough" is a heading + one paragraph — all the copy the
   client wrote for it. Rendered as a centred statement band; it is the last
   thing in its section, so drop .section-header's 48px bottom margin. */
.section-header.avas-statement{margin-bottom:0}

/* "How AVAS Works": the client supplies five UNLABELLED paragraphs, so the
   invented step <h3> titles are gone and .process-step is now number + text.
   Pull the paragraph up under the numeral to close the gap the h3 left. */
.process-grid.cols-5 .process-step .process-num{margin-bottom:14px}

/* The Findings definitions: the client asked for a single vertical stack in
   which "each definition should use the full available width" — so the stack
   spans the container instead of the earlier 820px measure. */
.avas-findings-defs{max-width:none}

/* "What Makes AVAS Different" + "What You Get" are two equal-weight content
   cards, not the main+sidebar pairing .detail-grid's 2fr/1fr was built for —
   and the client's "What You Get" is the longer of the two. Even the columns,
   and drop the trailing margin now that each column holds a single card. */
@media(min-width:1024px){
  .detail-grid.avas-two-col{grid-template-columns:1fr 1fr}
}
.detail-grid.avas-two-col .detail-card{margin-bottom:0;height:100%}

/* footer form band — the pre-footer lead-capture band injected by renderFooterForm().
   The band publishes only the client's sanctioned "Request an AVAS™ Report" label, so there is
   no editorial column to sit beside the form: the old .cta-form-grid two-column split would
   strand a lone heading next to a tall form. Single centered column instead — heading titles
   the band, form directly below, both capped to the form's comfortable reading measure. */
.footer-cta-band .ffb-inner{max-width:660px;margin:0 auto}
.footer-cta-band .ffb-title{color:var(--text);text-align:center;margin-bottom:28px}

/* ============================================================
   Research & Resources page (/research-resources/) — hero fit.
   The hero holds only the H1 (the client's v2 copy for this page
   supplies no eyebrow, subhead or hero CTA), so .hero-fullscreen's
   min-height:88vh left a near-empty band before the downloads.
   Dropped it; the hero now sizes to its content. The header is
   position:fixed and overlays the hero (body gets
   .has-transparent-header, --header-total:108px), so this hero must
   supply its own top padding to clear it — .hero-pad-sm's 120px/96px
   alone leaves the H1 grazing the nav. Matches the .pg-hero /
   .avas-hero rhythm. Scoped to .rr-hero; this page only.
   ============================================================ */
.rr-hero{padding:168px 0 92px}
@media(max-width:767px){
  .rr-hero{padding:142px 0 64px}
}

/* ============================================================
   /how-you-gain-proof/ — hero sizing.
   The client's v2 copy for this page supplies no eyebrow and no hero
   subhead, so the invented ones were removed and the hero is now just
   the H1 plus the client's two CTA labels. .hero-fullscreen's 88vh
   min-height left a near-empty band around that content, so the hero
   drops to .hero-pad-sm and sizes to what it holds. The header is
   position:fixed and overlays the hero (--header-total:108px), so
   supply our own top padding to clear it — .hero-pad-sm's 120px/96px
   alone leaves the H1 grazing the nav. Matches the .pg-hero /
   .avas-hero / .rr-hero rhythm. Scoped to .hygp-hero; this page only. */
.hygp-hero{padding:168px 0 92px}
.hygp-hero h1{margin-bottom:30px}
@media(max-width:767px){
  .hygp-hero{padding:142px 0 64px}
}

/* ---------- /proof-gore-tex/ — hero band (client v2 copy strip) ----------
   v2 gives this page a headline and six narrative beats: no eyebrow, no hero
   subhead. The hero is therefore just the H1 + the client's own CTA label, and
   .hero-fullscreen's 88vh min-height stretched that to a 792px near-empty band
   at >=768px. The hero drops to .hero-pad-sm, matching /the-proof-gap/'s
   .pg-hero and /avas/'s .avas-hero. Those pages then supply their own top
   padding because the header is position:fixed and overlays the hero
   (--header-total 108px) — .hero-fullscreen's mobile 110px left this H1 exactly
   1px below the header, reading as a collision. Same 168/142 rhythm as the two
   sibling stripped heroes. Scoped to .gt-hero-band; this page only. */
.gt-hero-band{padding:168px 0 92px}
@media(max-width:767px){
  .gt-hero-band{padding:142px 0 64px}
}

/* ============================================================
   Page: /about/ — header clearance + founder photo aspect
   ============================================================ */

/* Hero: the client supplies no eyebrow and no hero subhead for About, so the hero
   is just the H1 ("About", the page name) plus the client's two CTA labels. The
   header is position:fixed and overlays the hero (--header-total:108px), and
   .hero-pad-sm's 120px/96px top padding alone leaves the H1 grazing the nav —
   at 390px its 96px sits ABOVE the 108px header bottom, so "About" renders behind
   the header. About was the last page still on bare .hero-pad-sm; give it the same
   clearance and rhythm as .pg-hero / .avas-hero / .rr-hero / .hygp-hero.
   Scoped to .ab-hero; this page only. */
.ab-hero{padding:168px 0 92px}
.ab-hero h1{margin-bottom:30px}
@media(max-width:767px){
  .ab-hero{padding:142px 0 64px}
}

/* Founder photo: images/jason-vargas.jpg is the client's real 800x800 bio photo, so
   it must render square and uncropped. The rule above (.split-media img.about-founder-photo)
   already beats .split-media img's 4/3 crop, but the sitewide guard
   `main img:not(…){max-height:560px;object-fit:cover}` still applies — at (0,6,2) no
   practical page-scoped selector out-specifies it. Between 768px and 1023px .split is
   still one column, so the photo is 720px wide; aspect-ratio:1/1 asks for 720px of
   height, the 560px guard clamps it, and object-fit:cover crops Jason's face to a
   720x560 landscape. Rather than fight the guard, cap the photo's WIDTH at that same
   560px: the square then always fits inside the clamp and stays uncropped at every
   breakpoint, centred in its column. */
.split-media img.about-founder-photo{display:block;max-width:560px;margin-inline:auto}

/* AVAS page (/avas/) — "The Findings": keep the four statistics on ONE horizontal row.
   copy_v2: "Display the four statistics in one horizontal row." The shared .stat-grid is
   `flex-wrap:wrap` with `flex:0 1 160px` and a 40px column gap, so four items need
   4x160+3x40 = 760px. The container is only 720px at 768px wide, so the row silently broke
   into 2+2 from 768px up to ~1180px. Scoped to .avas-findings so Home's own reuse of this
   same block ("Built from the Operator's Seat") is untouched.
   `flex-wrap:nowrap` alone fixes it: the items shrink below the 160px basis only in the
   narrow band where they must, and Home's 30px/40px gap is left untouched so the block keeps
   the client's "Keep the same dark background, white type, dimensions, spacing" at desktop.
   NOT applied below 768px: measured at 390px, four columns are 73px wide and the client's
   own numbers overflow them ("1,500+" needs 95px). Since the type scale must stay identical
   to Home's, the numbers cannot be shrunk to compensate — so the phone keeps the 2x2 wrap,
   which renders every number intact. */
@media(min-width:768px){
  .avas-findings .stat-grid{flex-wrap:nowrap}
  .avas-findings .stat-grid .stat-item{min-width:0}
}

/* Downloads band: the client's v2 button labels for this page are long
   ("Download New Front Door to the Internet (PDF)"). .btn is white-space:nowrap
   above 479px, so that label sets each card's min-content width (~410px). Grid
   items default to min-width:auto, and .grid-2 goes 2-up at 640px — so between
   640px and ~1000px the two cards cannot shrink into their 1fr tracks and the
   whole page scrolled sideways (measured: doc 862px vs 768px viewport).
   Let the tracks shrink, and let the label wrap — the same treatment .btn
   already gets at <=479px. Above ~1024px the label still fits on one line, so
   the desktop rendering is unchanged. Scoped to .rr-downloads; this page only. */
.rr-downloads > .cat-card{min-width:0}
.rr-downloads .btn{white-space:normal;text-align:center}

/* Below 768px the four items fall back to a 2x2 grid rather than the shared .stat-grid's
   flex wrap. Reason: the 160px flex basis + gap needs 334px, so at 360px (a common phone)
   the shared rule fits only ONE item per row and the block degrades into a 4-row vertical
   list. A fixed 2x2 keeps the statistics reading as a row-based unit at every phone width
   and leaves every number intact. Scoped to .avas-findings; Home's copy of the block is
   unaffected. */
@media(max-width:767px){
  .avas-findings .stat-grid{display:grid;grid-template-columns:1fr 1fr;justify-content:stretch}
  .avas-findings .stat-grid .stat-item{flex:none;min-width:0}
}

/* ---- Post-v2 deploy-gate fixes (footer legibility, FAB/footer overlap, mobile topbar) ---- */
/* Footer <p> was inheriting the dark --text-secondary via the global p{} rule → dark-on-dark. */
.site-footer p,.site-footer .footer-about{color:rgba(255,255,255,.72)}
/* FAB tucks away while the footer is in view so it never sits over the legal links. */
.quote-fab{transition:transform .2s,box-shadow .2s,opacity .25s ease,visibility .25s ease}
.quote-fab.fab-tucked{opacity:0;visibility:hidden;transform:translateY(24px);pointer-events:none;animation:none}
/* Utility topbar: keep the phone on one line and shed the long email before it clips (<480px). */
.topbar a{white-space:nowrap}
@media(max-width:479px){.topbar-right a[href^="mailto"]{display:none}}

/* ==========================================================================
   V3 DESIGN SYSTEM LAYER — "Evidence Communications — Website Content & Build Guide"
   Everything below implements the sitewide rules from that document:
   left-justified editorial layout, two weights, black/silver/graphite with red as
   single-point emphasis, minimal white header, print-style square corners.
   ========================================================================== */

/* ---- All copy left-justified (build guide: "All copy left-justified") ---- */
.section-header,
.section-header.label-below{max-width:760px;margin:0 0 48px;text-align:left;align-items:flex-start}
.cta-content{text-align:left;margin:0;max-width:760px}
.stat-grid>*,.stat-item{text-align:left}
.brand-marquee .bm-label{text-align:left}
.hygp-roadmap-close{margin-left:0;text-align:left}
.footer-cta-band .ffb-inner{margin:0}
.footer-cta-band .ffb-title{text-align:left}
.hero-content.center{margin:0;text-align:left}

/* Thin editorial rule under section headings — black on light, white on dark. Never red:
   red is reserved for one point of emphasis per section, not repeated furniture. */
.section-header h2::after{left:0;transform:none;width:44px;height:2px;border-radius:0;background:var(--primary);opacity:1}
.section.dark .section-header h2::after,.process .section-header h2::after,
.on-dark .section-header h2::after,.cta-dark .section-header h2::after{background:#fff}

/* ---- Type: heavy + tight-tracked, two weights only ---- */
h1,h2,h3,h4,h5,h6{font-weight:700;letter-spacing:-.028em}
h1{letter-spacing:-.035em}
strong,b{font-weight:700}
em,i{font-style:italic}          /* italic is the sanctioned secondary emphasis tool */
.stat-num,.ht-num,.bf-num,.display-xl,.display-lg{letter-spacing:-.035em}

/* ---- Inline prose links: black with an underline. Never blue, never red. ---- */
.split-body p a,.pg-lede p a,.detail-card p a,.section-header p a,
.rr-body p a,.gt-body p a,.prose a,.faq-answer-inner a{
  color:var(--primary);text-decoration:underline;text-underline-offset:3px;text-decoration-thickness:1px}
.split-body p a:hover,.prose a:hover,.faq-answer-inner a:hover{text-decoration-thickness:2px}

/* ---- Statistics: large, bold, black. Weight comes from scale, not colour. ---- */
.stat-num .text-accent,.hero-ticker .ht-num .text-accent{color:inherit}
.on-dark .stat-num,.section.dark .stat-num{color:#fff}

/* ---- Hero photo rotation (Ken Burns) ---------------------------------------
   Six stills, slow pan/zoom, crossfaded. Desaturated and darkened so the hero
   copy stays legible over every frame. Replaces the old montage video. --- */
.hero-kb{position:absolute;inset:0;z-index:0;overflow:hidden;background:var(--dark)}
.hero-kb img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;opacity:0;
  filter:saturate(.3) brightness(.62) contrast(1.06);
  animation:kb-cycle 42s linear infinite both;animation-delay:calc(var(--i) * 7s);will-change:transform,opacity}
@keyframes kb-cycle{
  0%    {opacity:0;transform:scale(1.04) translate3d(0,0,0)}
  1.8%  {opacity:1}
  15%   {opacity:1}
  16.7% {opacity:0;transform:scale(1.13) translate3d(-1.1%,-.9%,0)}
  100%  {opacity:0;transform:scale(1.13) translate3d(-1.1%,-.9%,0)}
}
.hero-kb img:nth-child(even){animation-name:kb-cycle-alt}
@keyframes kb-cycle-alt{
  0%    {opacity:0;transform:scale(1.13) translate3d(1%,.8%,0)}
  1.8%  {opacity:1}
  15%   {opacity:1}
  16.7% {opacity:0;transform:scale(1.04) translate3d(0,0,0)}
  100%  {opacity:0;transform:scale(1.04) translate3d(0,0,0)}
}
@media(prefers-reduced-motion:reduce){
  .hero-kb img{animation:none;opacity:0;transform:none}
  .hero-kb img:first-child{opacity:1}
}

/* ---- Client logo strip: ONE continuous loop, all logos at a consistent scale ----
   Single track carrying the 12 logos twice. The trailing gap makes the -50% wrap land
   exactly on the duplicate of item 1, so there is no seam and no pair of logos
   colliding at the join (the Lego / General Motors overlap). --- */
.brand-marquee{padding:34px 0;background:var(--bg);border-top:1px solid var(--border);border-bottom:1px solid var(--border)}
.brand-marquee .bm-label{color:var(--graphite);margin-bottom:20px}
.brand-strip{-webkit-mask-image:linear-gradient(90deg,transparent,#000 5%,#000 95%,transparent);mask-image:linear-gradient(90deg,transparent,#000 5%,#000 95%,transparent)}
.brand-track{--bm-gap:64px;gap:var(--bm-gap);padding-right:var(--bm-gap);animation-duration:56s}
.brand-item{height:auto;min-width:0;padding:0;background:none;border:0;border-radius:0;box-shadow:none;
  width:120px;display:flex;align-items:center;justify-content:center;flex-shrink:0}
/* One optical box for every mark: 120 x 44. object-fit:contain does the rest, so a wide
   wordmark and a square roundel carry the same visual weight instead of the square
   logos rendering twice the size of the wordmarks. */
.brand-item img{height:44px;width:120px;max-width:120px;object-fit:contain;object-position:center;
  filter:grayscale(1);opacity:.62;transition:opacity .25s,filter .25s;transform:none}
.brand-item:hover img{opacity:1;filter:grayscale(1);transform:none}
/* Square/roundel marks read heavier than wordmarks at the same box height — trim them so the
   whole strip sits on one optical baseline. */
.brand-item img[src*="lego"],.brand-item img[src*="general-motors"],
.brand-item img[src*="gore-tex"],.brand-item img[src*="playstation"]{height:36px}

/* ---- Buttons: red = the one primary action per section; black = secondary ---- */
.btn{border-radius:0;letter-spacing:.01em}
.btn-dark{background:var(--primary);color:#fff;border-color:var(--primary)}
.btn-dark:hover{background:#000;border-color:#000;color:#fff}
.btn-outline-dark{background:transparent;color:var(--primary);border-color:var(--primary)}
.btn-outline-dark:hover{background:var(--primary);color:#fff}
.btn-outline{border-color:rgba(255,255,255,.6)}

/* ---- Header: minimal, white, no utility bar (applies to every page) ---- */
.site-header{background:#fff;backdrop-filter:none;-webkit-backdrop-filter:none;border-bottom:1px solid var(--border)}
.site-header .topbar{display:none}
.header-inner{height:var(--header-h)}
.nav-link{border-radius:0;font-weight:400}
.nav-link:hover,.nav-link[aria-current="page"]{color:var(--primary);background:none}
.nav-link[aria-current="page"]{font-weight:700}
.nav-link[aria-current="page"]::after{transform:scaleX(1)}
.header-phone{display:none}   /* the phone number lives in the footer; the header keeps one action */

/* ---- Footer (build guide): black background, no CTA button, no tagline line,
        social icons in graphite. ---- */
.site-footer .footer-cta{display:none}
.site-footer .footer-about{display:none}
.footer-social a{border-radius:0;background:none;color:var(--silver)}
.footer-social a:hover{background:none;color:#fff}
.footer-social a svg{color:var(--graphite)}
.footer-social a:hover svg{color:#fff}
.footer-bottom-inner{align-items:flex-start;text-align:left}
@media(min-width:768px){.footer-bottom-inner{flex-direction:row;justify-content:space-between;align-items:center}}

/* ---- Cards: flat, square, silver-ruled. No lavender tint, no coloured squares. ---- */
.cat-card{background:var(--bg);border:1px solid var(--border);border-radius:0}
.card:hover,.cat-card:hover,.img-card:hover,.retention-card:hover,.catalog-card:hover{
  box-shadow:none;border-color:var(--primary)}
.cat-card h3{font-weight:700;color:var(--text)}
.cat-card .cc-foot{color:var(--primary);font-weight:700;text-decoration:underline;text-underline-offset:4px;text-decoration-thickness:1px}
.cat-card .cc-foot:hover{text-decoration-thickness:2px}
.cat-card .cc-foot svg{color:var(--graphite)}
/* .cards-plain — short cards with no icon and no rule, per the AVAS "What AVAS Is" note. */
.cards-plain .cat-card{border:0;padding-left:0;padding-right:0;background:none}
.cards-plain .cat-card .cc-icon{display:none}
.cards-plain .cat-card:hover{border-color:transparent}

/* ---- Plain black round bullets (How You Gain Proof: "plain black round bullet,
        not a checkmark or dash") ---- */
.bullet-list{display:flex;flex-direction:column;gap:14px;list-style:none;margin:20px 0 26px}
.bullet-list li{position:relative;padding-left:24px;color:var(--text-secondary)}
.bullet-list li::before{content:"";position:absolute;left:2px;top:.62em;width:7px;height:7px;border-radius:50%;background:var(--primary)}
.bullet-list li::after{content:none}
.on-dark .bullet-list li::before,.section.dark .bullet-list li::before{background:#fff}
.bullet-list li strong,.bullet-list li b{color:var(--text);font-weight:700}

/* ---- Editorial multi-column text grid (build guide: "editorial multi-column text
        grids (two or three columns), closer to a print layout") ---- */
.col-grid{display:grid;gap:40px}
.col-grid-2{grid-template-columns:1fr}
.col-grid-3{grid-template-columns:1fr}
@media(min-width:760px){.col-grid-2{grid-template-columns:1fr 1fr}}
@media(min-width:900px){.col-grid-3{grid-template-columns:repeat(3,1fr)}}
.col-grid > * > h3{font-size:1.06rem;font-weight:700;margin-bottom:6px}
.col-grid p{margin-bottom:12px}

/* ---- Plain track-record columns (About): column header bold black, stat headline
        bold black, body paragraph regular. No card, no icon tile, no colour. ---- */
.track-cols{border-top:2px solid var(--primary);padding-top:0}
.track-cols .tc-col{padding-top:26px;border-top:1px solid var(--border)}
@media(min-width:900px){
  .track-cols .tc-col{border-top:0;padding-top:26px;padding-right:32px}
  .track-cols .tc-col + .tc-col{border-left:1px solid var(--border);padding-left:32px}
}
.track-cols .tc-org{font-size:1.18rem;font-weight:700;color:var(--text);letter-spacing:-.02em;margin-bottom:14px}
.track-cols .tc-stat{font-size:1.9rem;font-weight:700;color:var(--text);letter-spacing:-.035em;line-height:1.05;margin-bottom:12px}
.track-cols .tc-body{font-size:.98rem;font-weight:400;color:var(--text-secondary);line-height:1.7;margin:0}
.track-lead{font-size:1.9rem;font-weight:700;letter-spacing:-.035em;color:var(--text);margin-bottom:6px}
.track-lead-label{font-size:.95rem;color:var(--text-secondary);margin-bottom:40px}

/* ---- Surfaces: silver, never lavender ---- */
.section.surface,.footer-cta-band{background:var(--surface)}
.data-table tbody tr:nth-child(even),.compare-table tbody tr:nth-child(even){background:var(--surface)}
.data-table thead th,.compare-table thead th{background:var(--surface-2)}
.data-table .td-yes{color:var(--text)}
.detail-card,.form-success,.form-check,.modal-card{border-radius:0}
.form-control{border-radius:0}
.form-success{background:var(--surface);border-left:4px solid var(--primary)}

/* ---- The 3.4x badge: the one red figure in its section ---- */
.split-media .badge-float{border-radius:0;border:1px solid var(--border);box-shadow:none}

/* ---- Cited statistics are never hyperlinked (build guide, sitewide). Source is
        attributed by name in the copy instead. ---- */
.stat-source{display:block;font-size:.8rem;color:var(--text-muted);margin-top:6px}
.on-dark .stat-source,.hero-dark .stat-source{color:rgba(255,255,255,.6)}

/* ---- What Proof Looks Like (Gore-Tex) hero ---------------------------------
   The tour-truck photo was being cover-cropped down its vertical centre, so only the
   roof and the mountain wrap showed. The truck body sits at roughly 40–96% of the
   frame height, so the crop is biased low and the band is given enough height for the
   whole vehicle graphic to read. Tint is the sitewide neutral black — no olive. */
.gt-hero-band{min-height:62vh;display:flex;align-items:center}
.gt-hero-band .hero-dark-bg{object-position:50% 72%;filter:saturate(.28) brightness(.44)}
@media(max-width:767px){.gt-hero-band{min-height:52vh}}

/* Three short stacked lines: "What Does" / "Proof" / "Look Like?" */
.gt-h1{display:flex;flex-direction:column;line-height:1.02}
.gt-h1 span{display:block}

/* ---- How You Gain Proof: STEP / WHAT HAPPENS roadmap table ----
   Black background, white text, red accent line — the one point of red in the section. */
.roadmap-table{border-top:3px solid var(--accent)}
.roadmap-table thead th{background:transparent;border-bottom:1px solid rgba(255,255,255,.28)}

/* ---- Warm-to-cool colour pass for photography shot under warm light, so it sits in the
        black / silver / graphite system instead of fighting it. ---- */
.img-cool{filter:saturate(.34) contrast(1.06) brightness(.97)}

/* ==========================================================================
   V3 — polish pass after visual review
   ========================================================================== */

/* Hero scrim was crushing the lower half of the photo into flat black. Keep the copy
   legible but let the photograph read as a photograph across the whole band. */
.hero-dark::before{background:linear-gradient(100deg,rgba(13,13,13,.86) 0%,rgba(13,13,13,.62) 46%,rgba(13,13,13,.34) 100%)}
.hero-kb img{filter:saturate(.3) brightness(.72) contrast(1.06)}
/* A short bottom fade keeps the hero statistics readable over a bright frame. */
.hero-fullscreen::after{content:"";position:absolute;left:0;right:0;bottom:0;height:42%;z-index:1;
  pointer-events:none;background:linear-gradient(to top,rgba(13,13,13,.72),transparent)}
.hero-dark .container{z-index:2}

/* Square/roundel marks need a touch more height than a diamond-tight 36px to match the
   optical weight of the wordmarks beside them. */
.brand-item img[src*="lego"],.brand-item img[src*="general-motors"],
.brand-item img[src*="gore-tex"],.brand-item img[src*="playstation"]{height:40px}

/* The 3.4x callout was wrapping to four cramped lines inside a 130px label. */
.split-media .badge-float{padding:18px 24px;gap:18px;background:#fff}
.split-media .badge-float .bf-label{max-width:190px;line-height:1.45}

/* Gore-Tex narrative rule: silver, not red. The red on this page is the word "Proof" in
   the hero — a vertical accent bar would be red doing a second, decorative job. */
.gt-narrative{border-left:3px solid var(--silver)}
.gt-figure img{border-radius:0;border:1px solid rgba(255,255,255,.14)}
/* Let the tour-truck hero read at a normal exposure — it is the evidence on this page. */
.gt-hero-band .hero-dark-bg{filter:saturate(.3) brightness(.58)}

/* Footer wordmark: no baked-in tagline lockup, so it needs no chip padding. */
.footer-logo{max-width:260px;margin-bottom:22px}

/* The pre-footer lead form band is left-aligned like the rest of the page. */
.footer-cta-band .cfg-form{max-width:660px}

/* Left-justify the editorial lede blocks that were still centre-constrained. */
.pg-lede,.hygp-outcomes,.gt-case{margin-left:0;margin-right:0}

/* Push the warm pipe-inspection frame fully into the black / silver / graphite system. */
.img-cool{filter:grayscale(.84) contrast(1.06) brightness(.98)}

/* Download cards: buttons align on a common baseline instead of floating mid-card. */
.rr-downloads > .cat-card{display:flex;flex-direction:column}
.rr-downloads > .cat-card .btn{margin-top:auto}

/* A wrapped two-line eyebrow should not render as a stadium lozenge on narrow screens. */
@media(max-width:520px){.hero-label{border-radius:2px}}

/* Every hero photograph gets the same treatment as the home rotation: desaturated toward
   cool and darkened, so no single frame (e.g. the teal glass on the Contact skyline)
   introduces a colour outside the black / silver / graphite system. */
.hero-dark-bg{filter:saturate(.32) brightness(.6) contrast(1.04)}

/* ==========================================================================
   FINAL REVISION — Website Revision Instructions + Addendum 1
   Every rule below implements a numbered instruction from the client's revision
   documents. Section headings quote the instruction being satisfied.
   ========================================================================== */

/* ---- SITEWIDE: header logo "modestly" larger, proportions untouched --------
   The lockup is 861x56 — a 15.4:1 wordmark — so its displayed size is governed by WIDTH.
   The old rule capped it at 200px wide inside a 42px-tall box, which just letterboxed it:
   raising `height` changed nothing on screen. These caps grow the mark ~20% and let
   `height:auto` hold the proportions exactly. Values stay inside the header fit-guard's
   budget at every width, so the desktop nav never collapses to a hamburger. */
.site-header .logo-img{height:auto;width:auto;max-width:250px;max-height:46px}
.site-header.header-tight .logo-img{max-width:232px}
@media(min-width:1024px) and (max-width:1279px){.site-header .logo-img,
  .site-header.header-tight .logo-img{max-width:196px}}
@media(max-width:767px){.site-header .logo-img{max-width:216px}}

/* ---- SITEWIDE: footer — the complete supplied lockup WITH the tagline, then the
        telephone icon + number directly beneath it on one conventional tel: link. --- */
.footer-logo.footer-logo-tagline{max-width:290px;margin-bottom:16px}
.footer-phone-line{display:inline-flex;align-items:center;gap:9px;margin-bottom:18px;
  font-size:1rem;font-weight:700;color:#fff;letter-spacing:.01em}
.footer-phone-line svg{width:17px;height:17px;color:var(--silver);flex-shrink:0}
.footer-phone-line:hover{color:var(--accent)}
.footer-phone-line:hover svg{color:var(--accent)}

/* ---- SITEWIDE: the approved paragraph under the final AVAS CTA -------------- */
.ffb-note{margin:18px 0 0;font-size:.86rem;line-height:1.65;color:var(--text-secondary);
  border-top:1px solid var(--border);padding-top:16px}

/* ---- HOME: Statistics band moves from black to white. Black numbers, black copy,
        red only as the hairline rule above each figure. --------------------- */
.stat-band{background:#fff;padding:64px 0;border-bottom:1px solid var(--border)}
.stat-band .sb-grid{display:grid;grid-template-columns:1fr;gap:40px}
@media(min-width:760px){.stat-band .sb-grid{grid-template-columns:1fr 1fr;gap:64px}}
.stat-band .sb-item{border-top:3px solid var(--accent);padding-top:22px}
.stat-band .sb-num{font-family:var(--font-display);font-size:clamp(3rem,7vw,4.6rem);font-weight:700;
  line-height:1;letter-spacing:-.04em;color:var(--text);margin-bottom:14px}
.stat-band .sb-label{font-size:1.02rem;line-height:1.6;color:var(--text);max-width:46ch;margin:0}
.stat-band .sb-source{font-size:.82rem;color:var(--text-muted);margin:10px 0 0}
@media(max-width:767px){.stat-band{padding:46px 0}}

/* ---- HOME: "Experience Includes" — all nine marks resized to one optical scale.
   Aug 19 revision. The previous pass tuned heights by eye and drifted badly: with a
   120px-wide box and object-fit:contain, the wide wordmarks were WIDTH-constrained and
   collapsed (Bridgestone rendered ~15px tall) while the two square marks stayed at their
   full set height (Gore-Tex 62px) — a 4x spread that read as random sizing.
   Fixed here by normalising on optical AREA rather than height: each mark's height is
   set to k / ratio^0.42 (k≈54, ratio = the source artwork's width:height), which lands
   every logo on roughly the same amount of ink inside one uniform 200x56 cell. --------- */
.brand-item{width:200px;height:64px}
.brand-item img{width:auto;max-width:100%;max-height:100%;object-fit:contain}
/* square marks (1:1) — set slightly under the area target, since a solid roundel reads
   heavier than a wordmark that fills the same bounding box. */
.brand-item img[src*="gore-tex"],
.brand-item img[src*="general-motors"]{height:56px}
/* oval (2.8:1) */
.brand-item img[src*="ford"]{height:35px}
/* wordmarks, narrow → wide (4.2:1 … 8.8:1) */
.brand-item img[src*="jaguar"],
.brand-item img[src*="sac-wireless"]{height:28px}
.brand-item img[src*="kolcraft"]{height:25px}
.brand-item img[src*="kimberly-clark"]{height:21px}
.brand-item img[src*="bridgestone"],
.brand-item img[src*="fabtech-igm"]{height:20px}
@media(max-width:767px){
  .brand-item{width:170px;height:54px}
  .brand-item img[src*="gore-tex"],
  .brand-item img[src*="general-motors"]{height:46px}
  .brand-item img[src*="ford"]{height:29px}
  .brand-item img[src*="jaguar"],
  .brand-item img[src*="sac-wireless"]{height:23px}
  .brand-item img[src*="kolcraft"]{height:21px}
  .brand-item img[src*="kimberly-clark"]{height:18px}
  .brand-item img[src*="bridgestone"],
  .brand-item img[src*="fabtech-igm"]{height:17px}
}

/* ---- HOME: "How Evidence Communications Works" — gray becomes black, white
        headings and body copy, and the three cards stay white with black text. --- */
.how-ec-works{background:var(--dark)}
.how-ec-works .cat-card{background:#fff;border-color:#fff}
.how-ec-works .cat-card h3{color:var(--text)}
.how-ec-works .cat-card p{color:var(--text-secondary)}
.how-ec-works .cat-card .cc-icon svg{color:var(--graphite)}
.how-ec-works .cat-card .cc-foot{color:var(--text)}
.how-ec-works .cat-card:hover{border-color:var(--accent)}

/* ---- HOME + THE PROOF GAP: publication feature — the supplied cover shown whole,
        uncropped, in its own proportions, beside the description and button. --- */
.pub-feature-grid{display:grid;grid-template-columns:1fr;gap:34px;align-items:center}
@media(min-width:820px){.pub-feature-grid{grid-template-columns:minmax(0,280px) minmax(0,1fr);gap:56px}}
.pub-cover img{display:block;width:100%;height:auto;max-width:280px;max-height:none;
  object-fit:contain;border:1px solid rgba(255,255,255,.22);background:#fff}
.pub-body .eyebrow{margin-bottom:14px}
.pub-body h2{margin-bottom:14px}
@media(max-width:819px){.pub-cover img{max-width:210px}}

/* ---- RESEARCH & RESOURCES: two-tier hierarchy kept. The two featured publications
        show real cover art at a readable, proportional size (addendum items 4 + 6);
        the three supporting citations stay a smaller secondary row. ---------- */
.pub-cards{display:grid;grid-template-columns:1fr;gap:34px}
@media(min-width:900px){.pub-cards{grid-template-columns:1fr 1fr;gap:40px}}
.pub-card{display:grid;grid-template-columns:1fr;gap:24px;align-items:start;
  border:1px solid var(--border);background:#fff;padding:28px}
@media(min-width:560px){.pub-card{grid-template-columns:minmax(0,168px) minmax(0,1fr);gap:26px}}
.pub-card-cover{display:block}
.pub-card-cover img{display:block;width:100%;height:auto;max-width:168px;max-height:none;
  object-fit:contain;border:1px solid var(--border)}
.pub-card-cover:hover img{border-color:var(--accent)}
@media(max-width:559px){.pub-card-cover img{max-width:150px}}
.pub-card-body h3,.pub-card-body h2{font-size:1.16rem;line-height:1.28;margin-bottom:8px}
.pub-card-body .pub-subtitle{font-size:.95rem;font-weight:700;color:var(--text);
  line-height:1.45;margin-bottom:8px}
.pub-card-body .pub-attrib{font-size:.8rem;font-weight:700;letter-spacing:.08em;
  text-transform:uppercase;color:var(--text-muted);margin-bottom:14px}
.pub-card-body p{font-size:.93rem;margin-bottom:16px}
.pub-card-body .btn{margin-top:4px}
/* Supporting research: a clearly smaller secondary row, not a third featured card. */
.rr-supporting .section-header h2{font-size:1.5rem}
.rr-supporting .cat-card{padding:24px 22px}
.rr-supporting .cat-card h3{font-size:1.02rem;line-height:1.35}
.rr-supporting .cat-card p{font-size:.88rem}

/* ---- AVAS: the page's first appearance carries the full name --------------- */
.avas-h1{display:flex;flex-direction:column;gap:8px}
.avas-h1 .avas-h1-expand{font-size:clamp(1.05rem,2.4vw,1.5rem);font-weight:400;
  letter-spacing:-.01em;color:rgba(255,255,255,.82)}

/* ---- AVAS: "What Is AVAS?" cards are not clickable, so they must not lift,
        slide or tilt. A border change on hover is the whole interaction. ----- */
.cards-plain .cat-card,
.cat-card:not(:has(a)):not(:has(button)){transform:none!important;transition:border-color .2s ease}
.cards-plain .cat-card:hover,
.cat-card:not(:has(a)):not(:has(button)):hover{transform:none!important;box-shadow:none}

/* ---- AVAS: "What You Get" — approved paragraph above the three items, with
        breathing room after the third. --------------------------------------- */
.wyg-lede{margin-bottom:22px}
.check-list.wyg-list{margin-bottom:34px}
.check-list.wyg-list li{margin-bottom:4px}

/* ---- HOW YOU GAIN PROOF: the roadmap table sits on a white field inside the black
        section — black body text, black header row with white labels, thin rules,
        more vertical space, narrow Step column, wide What Happens column. ----- */
.roadmap-wrap{background:#fff;border:1px solid var(--border);margin-top:8px}
/* Every rule here is doubled up on .on-dark, because the surrounding black section's own
   table overrides (.on-dark .data-table thead th, …) are more specific than a bare
   .roadmap-table selector and would otherwise repaint this white table for a dark band. */
.roadmap-table,.on-dark .roadmap-table{border-top:0;width:100%;border-collapse:collapse;background:#fff}
.roadmap-table thead th,.on-dark .roadmap-table thead th{background:var(--primary);color:#fff;
  border-bottom:0;border-bottom-color:transparent;
  font-size:.78rem;font-weight:700;letter-spacing:.1em;text-transform:uppercase;
  padding:16px 22px;text-align:left;white-space:nowrap}
.roadmap-table tbody tr,.on-dark .roadmap-table tbody tr,
.roadmap-table tbody tr:nth-child(even),.on-dark .roadmap-table tbody tr:nth-child(even){background:#fff}
.roadmap-table tbody tr + tr td,.on-dark .roadmap-table tbody tr + tr td{border-top:1px solid var(--border)}
.roadmap-table tbody td,.on-dark .roadmap-table tbody td{padding:24px 22px;color:var(--text);
  vertical-align:top;font-size:.98rem;line-height:1.7;border-bottom:0;border-bottom-color:transparent}
.roadmap-table .rt-step,.on-dark .roadmap-table td.rt-step{width:26%;font-weight:700;
  letter-spacing:-.01em;color:var(--text)}
.roadmap-table .rt-what,.on-dark .roadmap-table td.rt-what{width:74%;color:var(--text-secondary)}
/* Mobile: stacked step cards, which read better than a squeezed two-column table. */
@media(max-width:719px){
  .roadmap-table thead{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0 0 0 0)}
  .roadmap-table,.roadmap-table tbody,.roadmap-table tr,.roadmap-table td{display:block;width:auto;min-width:0}
  .roadmap-table tbody tr,.on-dark .roadmap-table tbody tr{padding:20px 18px}
  .roadmap-table tbody tr + tr{border-top:1px solid var(--border)}
  .roadmap-table tbody tr + tr td,.on-dark .roadmap-table tbody tr + tr td{border-top:0}
  .roadmap-table tbody td,.on-dark .roadmap-table tbody td{padding:0;width:auto}
  .roadmap-table .rt-step,.on-dark .roadmap-table td.rt-step{font-size:1.02rem;margin-bottom:8px;width:auto}
  .roadmap-table .rt-what,.on-dark .roadmap-table td.rt-what{width:auto}
  .roadmap-table .rt-what::before{content:attr(data-label);display:block;font-size:.7rem;
    font-weight:700;letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);margin-bottom:5px}
}

/* ---- WHAT PROOF LOOKS LIKE: the client's conclusion line becomes an oversized pull
        quote. (The "truck runs smaller" rules that lived here are gone with the second
        truck photograph itself — removed in the Aug 19 revision.) ------------- */
.gt-pullquote-band{background:var(--dark);padding:104px 0}
@media(max-width:767px){.gt-pullquote-band{padding:64px 0}}
.gt-pullquote{margin:0;border:0;padding:0}
/* The measure must be set on the element that carries the display size — a ch limit on the
   blockquote would be computed against the 16px body size and break to one word per line. */
.gt-pullquote p{font-family:var(--font-display);font-weight:700;color:#fff;
  font-size:clamp(1.9rem,5.2vw,3.6rem);line-height:1.14;letter-spacing:-.03em;margin:0;
  max-width:17em;text-wrap:balance}
.gt-pullquote p .hl{color:var(--accent)}

/* ---- ABOUT: track-record columns now carry a role line under the company ---- */
.track-cols .tc-role{font-size:1.05rem;font-weight:700;color:var(--text);
  letter-spacing:-.01em;line-height:1.35;margin-bottom:12px}

/* ---- CONTACT: the Chicago skyline is removed. No replacement photography has been
        approved, so the hero is the sanctioned fallback — solid black, oversized
        white Helvetica, one restrained red accent. --------------------------- */
.contact-hero-solid{background:var(--dark);padding:150px 0 110px}
.contact-hero-solid::before,.contact-hero-solid::after{content:none}
.contact-hero-solid h1{font-size:clamp(3.2rem,9vw,6.4rem);letter-spacing:-.045em;line-height:1.02}
.contact-hero-solid h1 .hl{color:var(--accent)}
/* Measured so the closing word never lands on a line of its own. */
.contact-hero-solid .hero-sub{max-width:56ch;text-wrap:pretty}
.contact-hero-solid .hero-loc{margin:0;font-size:.95rem;color:rgba(255,255,255,.7)}
@media(max-width:767px){.contact-hero-solid{padding:110px 0 72px}}

/* ==========================================================================
   FINAL REVISION — image crops, checked on desktop, tablet and mobile
   Instruction: "Check image crops on desktop, tablet, and mobile" / "no heads cut off".
   ========================================================================== */

/* ---- HOME, scrolling photography ------------------------------------------
   Two changes, both asked for by name ("reposition or reduce scale"):
   1. The Ken Burns move was a 1.04 -> 1.13 zoom about the centre, so it ate 6% off
      every edge — that is what sliced the tops of heads. It is now a much smaller
      1.00 -> 1.06 zoom pinned to the TOP of the frame, so the top edge never crops.
   2. Each photograph carries its own framing (--ox/--oy) per breakpoint, because the
      band goes from 1.8:1 on desktop to 0.56:1 on a phone and the subjects move.
   --tox pins the zoom's horizontal anchor to whichever edge the people stand near. */
/* The sitewide `main img { max-height:560px }` guard was also catching the rotating hero
   stills, so on any hero taller than 560px the photograph stopped short and the rest of
   the band fell back to flat black. The hero rotation is a background layer, not content
   imagery — it must fill its band. The guard's selector carries six :not() classes, so
   !important is the only way to beat it without weakening the guard for real content. */
.hero-kb img{max-height:none!important;height:100%!important;
  object-position:var(--ox,50%) var(--oy,50%);transform-origin:var(--tox,50%) 0%}
@keyframes kb-cycle{
  0%    {opacity:0;transform:scale(1.00)}
  1.8%  {opacity:1}
  15%   {opacity:1}
  16.7% {opacity:0;transform:scale(1.06)}
  100%  {opacity:0;transform:scale(1.06)}
}
@keyframes kb-cycle-alt{
  0%    {opacity:0;transform:scale(1.06)}
  1.8%  {opacity:1}
  15%   {opacity:1}
  16.7% {opacity:0;transform:scale(1.00)}
  100%  {opacity:0;transform:scale(1.00)}
}
/* Desktop framing. --oy keeps every head clear of the top edge. */
.hero-kb img[src*="welder-mid-arc"]      {--ox:50%;--oy:0%; --tox:50%}
.hero-kb img[src*="cnc-control-panel"]   {--ox:47%;--oy:4%; --tox:50%}   /* man + woman at the lathe */
.hero-kb img[src*="robotics-programming"]{--ox:70%;--oy:6%; --tox:80%}
.hero-kb img[src*="welder-mask"]         {--ox:50%;--oy:0%; --tox:50%}   /* second welding photograph */
.hero-kb img[src*="roll-forming-line"]   {--ox:48%;--oy:36%;--tox:50%}   /* two women with the executive */
.hero-kb img[src*="machine-pair"]        {--ox:92%;--oy:6%; --tox:96%}   /* two men bending pipe */
/* No per-photo mobile re-framing: below 1024px the hero stacks into a 3/2 band (the
   stills' native ratio), so the desktop anchors above already frame the two 16:9
   frames and the rest crop nothing. */
/* Below 1024px the homepage hero STACKS, matching the interior pages (client flag,
   Aug 26: stills competing with the copy — and the flat-scrim overlay tried first read
   as text-on-black with the photography lost). The slideshow becomes its own vivid
   in-flow band under the fixed header — 3/2, the stills' native ratio, so four of the
   six frames crop nothing — with the interior bands' filter and no scrim; the copy sits
   on solid black beneath it. Desktop keeps the approved overlay + pan/zoom. The rotation
   stays an opacity-only crossfade on small screens: the 6% zoom judders on phone GPUs
   (sub-pixel scale steps read as shake). */
@media(max-width:1023px){
  .hero-dark.hero-fullscreen{min-height:0;display:block;padding:0 0 48px;background:var(--dark)}
  .hero-dark.hero-fullscreen::before{content:none}
  .hero-dark.hero-fullscreen > .hero-kb{position:relative;inset:auto;width:100%;height:auto;
    aspect-ratio:3/2;margin-top:var(--header-total)}
  .hero-kb img,.hero-kb img:nth-child(even){animation-name:kb-fade;transform:none;
    filter:saturate(.88) brightness(.96) contrast(1.02)}
  .hero-dark.hero-fullscreen > .container{padding-top:40px}
}
@keyframes kb-fade{
  0%    {opacity:0}
  1.8%  {opacity:1}
  15%   {opacity:1}
  16.7% {opacity:0}
  100%  {opacity:0}
}

/* ---- Page heroes (static background photographs) --------------------------
   These bands are wide and short (about 3.5:1 on desktop), so barely 40% of the
   frame height survives. Each is anchored on the head/hands/activity instead of
   the geometric centre, then re-anchored horizontally on a phone. */
.pg-hero .hero-dark-bg   {object-position:50% 0%}    /* head at the top edge, hands just below */
.avas-hero .hero-dark-bg {object-position:50% 8%}
.hygp-hero .hero-dark-bg {object-position:50% 10%}
.ab-hero .hero-dark-bg   {object-position:50% 34%}
.rr-hero .hero-dark-bg   {object-position:50% 40%}
.gt-hero-band{min-height:70vh}
/* The tour truck occupies y 40-98% of the frame; a bottom-anchored crop in a taller band is
   the only framing that keeps the roof AND the wheels. */
.gt-hero-band .hero-dark-bg{object-position:50% 100%}
@media(max-width:767px){
  .avas-hero .hero-dark-bg {object-position:88% 8%}
  .hygp-hero .hero-dark-bg {object-position:92% 10%}
}

/* Addendum item 6: the Research & Resources hero was magnified to the point where the
   photograph stopped reading. A taller band shows more of the frame at less scale. */
.rr-hero{padding:180px 0 116px}
@media(max-width:767px){.rr-hero{padding:142px 0 76px}}

/* ---- THE PROOF GAP hero -----------------------------------------------------
   The operator's head sits within the top ~1% of the source frame, so the crop is
   already flush to the top and no further headroom exists in the photograph. A
   slightly deeper band is what makes the person and the machine read as context
   rather than as a sliver. */
.pg-hero{padding:150px 0 104px}
@media(max-width:767px){.pg-hero{padding:118px 0 66px}}

/* ---- RESEARCH: the two featured cards align their buttons on one baseline ---- */
.pub-card-body{display:flex;flex-direction:column;height:100%}
.pub-card-body .btn{margin-top:auto;align-self:flex-start}

/* ---- HOW YOU GAIN PROOF: the two "What Gets Built" tables get the same stacked-card
        treatment as the Roadmap table on a phone. At 390px a 440px-min-width table
        scrolled sideways with the "Why It Matters" column clipped off screen. ------ */
@media(max-width:719px){
  .stack-table thead{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0 0 0 0)}
  .stack-table,.stack-table tbody,.stack-table tr,.stack-table td{display:block;width:auto;min-width:0}
  .stack-table tbody tr{padding:16px 0;border-bottom:1px solid var(--border)}
  .stack-table tbody tr:last-child{border-bottom:0}
  .stack-table tbody td{padding:0;border-bottom:0;width:auto}
  .stack-table td.st-a{font-size:1rem;font-weight:700;color:var(--text);margin-bottom:6px}
  .stack-table td.st-b{color:var(--text-secondary)}
  .stack-table td.st-b::before{content:attr(data-label);display:block;font-size:.7rem;font-weight:700;
    letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);margin-bottom:4px}
  .stack-table tbody tr:nth-child(even){background:none}
}

/* ==========================================================================
   AUG 19 REVISION
   ========================================================================== */

/* ---- SITEWIDE: page heroes -------------------------------------------------
   THE DEFECT: every page hero is a short, very wide band (~3.5:1 on desktop) with the
   photograph as an absolutely-positioned .hero-dark-bg behind the copy. Two consequences
   the client flagged:
     1. Desktop — barely 40% of the frame survives the crop, so each photo reads as a
        different, arbitrary sliver: "displaying inconsistently across the site".
     2. Mobile — the band gets shorter still while the copy gets taller, so the headline
        and button sit ON TOP of the photo: "text overlapping the photo instead of
        stacking cleanly".
   THE FIX: one shared treatment for every photographic hero.
     Desktop — a materially taller band (74vh, matching Home's 88vh / Contact's deep
     padding) so a real portion of each photograph is visible, with the copy centred.
     Mobile  — the hero STACKS: the photograph becomes a normal in-flow block at its own
     natural aspect ratio (nothing cropped, the whole scene visible) and the copy sits
     below it on solid black. Nothing overlaps anything.
   Scoped with :has(> .hero-dark-bg) so it reaches exactly the photographic heroes and
   leaves Home (.hero-kb slideshow) and Contact (solid black band) alone. ------------- */
.hero-dark:has(> .hero-dark-bg){min-height:74vh;display:flex;flex-direction:column;justify-content:center}

@media(max-width:767px){
  /* The stacked hero: photo block, then copy. The section's own top padding goes to 0 —
     the photo's margin-top is what clears the position:fixed header instead. */
  .hero-dark:has(> .hero-dark-bg){min-height:0;display:block;padding:0 0 40px;background:var(--dark)}
  /* The readability scrim exists only to keep copy legible ON the photo. Nothing sits on
     the photo any more, so it must go — otherwise it dims the whole stacked band. */
  .hero-dark:has(> .hero-dark-bg)::before{content:none}
  /* position:static returns the image to the flow; height:auto + no object-fit means the
     ENTIRE frame shows, uncropped, at its own ratio. object-position is inert here, so the
     per-page desktop crops below need no mobile counterparts. */
  .hero-dark:has(> .hero-dark-bg) > .hero-dark-bg{
    position:static;width:100%;height:auto;object-fit:fill;
    margin-top:var(--header-total);filter:saturate(.9)}
  .hero-dark:has(> .hero-dark-bg) > .container{padding-top:32px}
  /* The per-page top padding (142px) existed only to clear the fixed header over an
     absolutely-positioned photo. In the stacked layout it would open a black gap. */
  .pg-hero,.avas-hero,.hygp-hero,.ab-hero,.rr-hero,.gt-hero-band{padding:0 0 40px}
}

/* Desktop crops. With the taller band each photograph keeps its subject AND enough
   surrounding scene to read as a photograph rather than a sliver. */
/* The Proof Gap — the machinist's head sits at ~3% of the frame; anchor just below it. */
.pg-hero .hero-dark-bg   {object-position:50% 6%}
/* AVAS — the two monitor screens occupy y 43–90%. The old 8% anchor cropped them off
   entirely, which is what "both monitor screens fully visible" refers to. */
.avas-hero .hero-dark-bg {object-position:50% 58%}
/* How You Gain Proof — both men plus the pipe bender. */
.hygp-hero .hero-dark-bg {object-position:50% 25%}
/* About — a tight macro of the cutting head; centring it is what makes it legible. */
.ab-hero .hero-dark-bg   {object-position:50% 45%}
.rr-hero .hero-dark-bg   {object-position:50% 40%}

/* The deep one-off top paddings were sized for the old short band. The band now sizes
   itself, and the copy is vertically centred, so they only push the copy off-centre —
   a single clearance for the fixed header is all that is needed. */
@media(min-width:768px){
  .pg-hero,.avas-hero,.hygp-hero,.ab-hero,.rr-hero,.gt-hero-band{padding:var(--header-total) 0 0}
}

/* ---- HOME: the Gardner statistic. "More than" is part of the claim, so it rides with
        the figure at reduced size rather than being dropped from it. ---------------- */
.stat-band .sb-num-qual{display:block;font-family:var(--font-body);font-size:.9rem;
  font-weight:700;letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);
  line-height:1;margin-bottom:8px}
/* …and the 89% figure reserves the same strip of space, so the two numbers stay on one
   baseline instead of the qualifier shunting the Gardner figure down. */
.stat-band .sb-item:not(:has(.sb-num-qual)) .sb-num{margin-top:calc(.9rem + 8px)}

/* ---- WHAT PROOF LOOKS LIKE: the rain-room photograph moves up beside the opening line.
   The second truck photograph is gone (it duplicated the hero band), so the case study is
   now narrative + one photograph, and align-items:start is what puts the top of the photo
   level with "We didn't tell people Gore-Tex worked. We proved it." ------------------- */
.gt-figure-portrait{margin:0;max-width:none;margin-inline:0}
@media(min-width:820px){
  .gt-case{display:grid;grid-template-columns:minmax(0,1.55fr) minmax(0,1fr);
    grid-template-areas:"narrative portrait";column-gap:44px;align-items:start}
  .gt-narrative{grid-area:narrative}
  .gt-figure-portrait{grid-area:portrait}
}
@media(max-width:819px){
  .gt-figure-portrait{margin-top:30px;max-width:420px}
}

/* ---- CONTACT: the Jason photo + logo lockup is supporting detail, not the headline. It
        ran full-bleed at the foot of the sidebar and outweighed everything above it. --- */
.contact-lockup{padding:20px 22px}
.contact-lockup img{display:block;width:100%;max-width:280px;height:auto;
  border-radius:var(--radius-sm);margin-inline:auto}

/* ---- FOOTER, SITEWIDE: the lockup gets bigger, the phone line beneath it gets smaller,
        so the logo leads the column instead of competing with the number. ------------ */
.footer-logo.footer-logo-tagline{max-width:390px;margin-bottom:14px}
@media(max-width:1023px){.footer-logo.footer-logo-tagline{max-width:330px}}
.footer-phone-line{font-size:.86rem;font-weight:700;gap:7px;margin-bottom:16px}
.footer-phone-line svg{width:14px;height:14px}

/* ---- MOBILE QA, SITEWIDE: touch target sizes -------------------------------
   Found by the pre-launch mobile pass: on a phone the header logo link resolved to a
   179x14 hit area (the wordmark is a wide, thin lockup, so its natural height at mobile
   width is 14px) and every footer link to 17-23px tall. WCAG 2.5.8 asks for 24x24 CSS px
   minimum, and a 14px-tall tap target is genuinely hard to hit.
   The type sizes and the layout are untouched — only the hit area grows, and only on
   touch widths, so the approved desktop footer is unaffected. ---------------------- */
.site-header .logo{display:inline-flex;align-items:center;min-height:44px}

@media(max-width:1023px){
  /* Column link lists: padding absorbs most of the existing gap, so the footer grows by
     only a few pixels while each link becomes a comfortable 30px target. */
  .footer-col ul{gap:2px}
  .footer-col ul li a{display:inline-block;padding:7px 0;min-height:24px}
  /* Contact rows: the label + value pair is the target, so pad the row rather than the
     link, and keep the icon aligned to the top of it. */
  .footer-contact-item{align-items:flex-start;margin-bottom:12px}
  .footer-contact-item svg{margin-top:3px}
  .footer-contact-item .fci-val{display:inline-block;padding:4px 0;min-height:24px}
  /* The phone line under the logo stays visually small (as instructed) but gains a
     comfortable hit area around it. */
  .footer-phone-line{padding:5px 0;min-height:26px}
  .footer-legal{gap:10px 18px;flex-wrap:wrap}
  .footer-legal a{display:inline-block;padding:5px 0;min-height:24px}
  /* Contact page sidebar cards — the LinkedIn link had the same 18px-tall problem. */
  .contact-card > a{display:inline-block;padding:4px 0;min-height:24px}
}

/* ==========================================================================
   AUG 20 REVISION
   ========================================================================== */

/* ---- SITEWIDE: page heroes still collided on tablets ------------------------
   THE DEFECT (client, re-reported): "on every page with a header image the image and the
   copy are colliding on mobile, text sitting on top of the photo instead of stacking
   below it." The Aug 19 stacking fix was correct but its breakpoint was too narrow: it
   only ran below 768px, so every width from 768px up still got the desktop OVERLAY —
   iPad portrait (768/810/834px), iPad landscape (1024px+) and every phone held sideways.
   Measured in both Chromium and WebKit: at 390/430/640 the hero stacked; at 768/820/900
   the <h1> sat inside the photograph's box.
   THE FIX: stack at every width where this site is already in its mobile skin. The
   hamburger drawer takes over below 1024px (`@media(min-width:1024px){.mobile-toggle
   {display:none}}`), so 1024px is the site's own mobile boundary and the hero now uses it.
   Also pinned with an explicit .hero-photo class alongside :has() — :has() is fine in
   current Chrome/Safari, but this hero is the one thing on the site that must not fail
   in an older in-app browser, and a plain class cannot fail. ------------------------- */
.hero-dark.hero-photo,
.hero-dark:has(> .hero-dark-bg){min-height:74vh;display:flex;flex-direction:column;justify-content:center}

@media(max-width:1023px){
  .hero-dark.hero-photo,
  .hero-dark:has(> .hero-dark-bg){min-height:0;display:block;padding:0 0 40px;background:var(--dark)}
  .hero-dark.hero-photo::before,
  .hero-dark:has(> .hero-dark-bg)::before{content:none}
  .hero-dark.hero-photo > .hero-dark-bg,
  .hero-dark:has(> .hero-dark-bg) > .hero-dark-bg{
    position:static;width:100%;height:auto;object-fit:fill;
    margin-top:var(--header-total);filter:saturate(.9)}
  .hero-dark.hero-photo > .container,
  .hero-dark:has(> .hero-dark-bg) > .container{padding-top:32px}
  .pg-hero,.avas-hero,.hygp-hero,.ab-hero,.rr-hero,.gt-hero-band{padding:0 0 40px}
  /* .gt-hero-band carries its own min-height:70vh, which would re-open the black gap the
     stacked layout exists to remove. */
  .gt-hero-band{min-height:0}
}

/* The overlay treatment (deep padding to clear the fixed header) belongs only to the
   widths that actually still overlay. */
@media(min-width:1024px){
  .pg-hero,.avas-hero,.hygp-hero,.ab-hero,.rr-hero,.gt-hero-band{padding:var(--header-total) 0 0}
}

/* ---- THE PROOF GAP: hero composition ---------------------------------------
   Client: "I would like to see the person at the drill press centered vertically.
   Currently, too much of the bottom of the photo is featured."
   Measured against the source frame (2400x1601): the operator runs from y≈1% (the crown of
   his head is all but flush with the top edge) to y≈65%, so his centre of mass is y≈33%.
   Everything below 65% is machine bed and chip conveyor — the "bottom of the photo" the
   client is reading as dead weight.
   Desktop: the band shows 62% of the frame height, so anchoring at 0% both stops the old
   6% anchor slicing the top of his head AND drops the lowest 38% of machine bed. His
   centre then lands at 53% of the band — vertically centred, with the small bias upward
   that keeps his head off the top edge.
   Mobile: the stacked photo previously ran the WHOLE uncropped frame, which is where the
   surplus bottom third was most obvious. Cropping the band to 15:7 shows the frame's top
   70% only, putting his y≈33% centre at 47% of the band. Scoped to this page — the other
   stacked heroes are framed as the client approved them. */
.pg-hero .hero-dark-bg{object-position:50% 0%}
@media(max-width:1023px){
  .hero-dark.pg-hero > .hero-dark-bg,
  .hero-dark:has(> .hero-dark-bg).pg-hero > .hero-dark-bg{
    aspect-ratio:15/7;height:auto;object-fit:cover;object-position:50% 0%}
}

/* ---- HOME: the 3.4x badge stopped being a badge on a phone ------------------
   Client: "the 3.4x stat is overlapping the entire photo of the engineer at the laptop
   instead of sitting cleanly above or below it."
   The badge is position:absolute over the photo. That reads as a badge while it stays
   small, but its label is a full sentence, so as the column narrows the label wraps and
   the badge grows while the photo shrinks. Measured coverage of the photo: 5% at 820px,
   10% at 640px, 31% at 430px, 45% at 390px, 54% at 360px — and at phone widths the label
   was also clipped by the bottom of the card.
   THE FIX: below 640px the badge leaves the overlay and becomes a normal card directly
   BELOW the photo, exactly as asked. Above 640px the float is 10% or less and stays. */
@media(max-width:639px){
  .split-media .badge-float{position:static;transform:none;margin-top:14px;
    border-radius:var(--radius-md);box-shadow:var(--shadow-md);border:1px solid var(--border);
    align-items:center;gap:16px;padding:16px 18px}
  .split-media .badge-float .bf-label{max-width:none}
}

/* ---- WHAT PROOF LOOKS LIKE: the rain-room photograph grows 4% ---------------
   Client: "increase the size of the rain room photo by 3 to 5 percent. No change to its
   position." The photo is the right-hand column of .gt-case, so its width is set by the
   grid ratio, not by the figure. At 1.55fr/1fr the photo took 1/2.55 = 39.2% of the
   track space; 1.45fr/1fr takes 1/2.45 = 40.8%. 40.8/39.2 = 1.04 — a 4% increase at every
   viewport width, with the column order, the gap and the alignment untouched. */
@media(min-width:820px){
  .gt-case{grid-template-columns:minmax(0,1.45fr) minmax(0,1fr)}
}

/* ---- AVAS: the lockup is a title, not a sentence ----------------------------
   Client: two stacked lines, "AVAS(tm)" over "The AI Visibility Assessment System", and no
   full stop. The comma and the period are removed in the markup; this keeps the second
   line reading as a subtitle rather than as a second heading. */
.avas-h1 .avas-h1-expand{display:block}

/* ---- AVAS CTA note sits ABOVE the button ------------------------------------
   Client: "add the AVAS CTA supporting paragraph directly above the request button, not
   below". renderFooterForm() in js/main.js now emits .ffb-note before the submit button;
   the spacing flips with it. */
.ffb-note{margin:0 0 18px}

/* ---- THE PROOF GAP: the new hero subhead + standfirst -----------------------
   Client copy, added above the download button. The subhead is a deck under the H1, so it
   is set at heading weight but well below H1 size — it must not compete with "The Proof
   Gap" — and the standfirst below it is body copy at the hero's reading size.
   .pg-hero .hero-content h1 carried a 30px bottom margin that existed to space the H1 off
   the button when nothing sat between them; the deck supplies that rhythm now. */
.pg-hero .hero-content h1{margin-bottom:14px}
.pg-hero-subhead{font-family:var(--font-display);font-size:clamp(1.12rem,2.1vw,1.42rem);
  font-weight:700;line-height:1.3;letter-spacing:-.01em;color:#fff;max-width:40ch;
  margin:0 0 14px;text-wrap:balance}
.pg-hero-standfirst{font-size:1.02rem;line-height:1.6;color:rgba(255,255,255,.82);
  max-width:58ch;margin:0 0 30px;text-wrap:pretty}
@media(max-width:1023px){
  .pg-hero-subhead{max-width:none;font-size:1.16rem;margin-bottom:10px}
  .pg-hero-standfirst{font-size:.98rem;margin-bottom:26px}
}

/* ---- AVAS: header standfirst above the request button ----------------------
   Client: place this copy in the hero, where the photograph currently reads,
   directly above the red “Request an AVAS Report” button. Matches the Proof Gap
   standfirst rhythm so the H1 → deck → CTA spacing stays even. */
.avas-hero h1{margin-bottom:16px}
.avas-hero-standfirst{font-size:1.02rem;line-height:1.6;color:rgba(255,255,255,.82);
  max-width:58ch;margin:0 0 30px;text-wrap:pretty}
@media(max-width:1023px){
  .avas-hero-standfirst{font-size:.98rem;margin-bottom:26px}
}

/* ---- AUG 23: Home overlay stays; interior heroes STACK at every width ------
   Client: homepage Ken Burns stills stay UNDERNEATH the copy — that overlay is
   approved. Interior pages were still overlaying title/copy on the photograph
   (on desktop always; on tablet whenever stacking didn't win), so the header
   read as a darkened poster with type sitting on the subject. Composition off.

   Interior photographic heroes now separate the two layers everywhere:
     photograph as its own in-flow band (consistent cinematic crop, cover-framed
     on the subject, no scrim — the photo is allowed to read as a photo)
     copy on solid black underneath.
   Home (.hero-fullscreen / .hero-kb) and Contact (no photo) are not touched. */
.hero-dark.hero-photo,
.hero-dark:has(> .hero-dark-bg){
  min-height:0;
  display:block;
  padding:0 0 48px;
  background:var(--dark)}
.hero-dark.hero-photo::before,
.hero-dark:has(> .hero-dark-bg)::before{content:none}
.hero-dark.hero-photo > .hero-dark-bg,
.hero-dark:has(> .hero-dark-bg) > .hero-dark-bg{
  position:static;
  width:100%;
  height:auto;
  aspect-ratio:8/3;
  object-fit:cover;
  margin-top:var(--header-total);
  filter:saturate(.88) brightness(.96) contrast(1.02)}
.hero-dark.hero-photo > .container,
.hero-dark:has(> .hero-dark-bg) > .container{padding-top:40px}
.pg-hero,.avas-hero,.hygp-hero,.ab-hero,.rr-hero,.gt-hero-band{
  padding:0 0 48px;min-height:0}
/* Per-page framing — same anchors the client already approved, now applied to
   a real photograph band instead of an overlay crop. */
.pg-hero .hero-dark-bg{object-position:50% 0%}
.avas-hero .hero-dark-bg{object-position:50% 58%}
.hygp-hero .hero-dark-bg{object-position:50% 25%}
.ab-hero .hero-dark-bg{object-position:50% 45%}
.rr-hero .hero-dark-bg{object-position:50% 40%}
.gt-hero-band .hero-dark-bg{object-position:50% 100%;filter:saturate(.72) brightness(.92)}
@media(max-width:1023px){
  .hero-dark.hero-photo > .hero-dark-bg,
  .hero-dark:has(> .hero-dark-bg) > .hero-dark-bg,
  .hero-dark.pg-hero > .hero-dark-bg,
  .hero-dark:has(> .hero-dark-bg).pg-hero > .hero-dark-bg{
    aspect-ratio:16/9;height:auto;object-fit:cover}
  .avas-hero .hero-dark-bg{object-position:88% 8%}
  .hygp-hero .hero-dark-bg{object-position:92% 10%}
}
