/* NorthOps flagship homepage (8 Nov 2026).
   System: neutral full-bleed tiles separated by a 12px gutter, Inter / Inter Display (optical sizing),
   pill actions in NorthOps blue, one scroll-linked hero object. Homepage only; other routes keep northops-glass.css. */

@font-face{
  font-family:"Inter";
  font-style:normal;
  font-display:swap;
  font-weight:100 900;
  src:url(/assets/fonts/inter-latin-opsz-normal.woff2) format("woff2-variations"),
      url(/assets/fonts/inter-latin-opsz-normal.woff2) format("woff2");
  unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;
}

:root{
  --ink:#1d1d1f;
  --ink-2:#424245;
  --ink-3:#6e6e73;
  --paper:#ffffff;
  --mist:#f5f5f7;
  --night:#111113;
  --night-2:#1d1d1f;
  --on-night:#f5f5f7;
  --on-night-2:#a1a1a6;
  --blue:#1f5fd1;
  --blue-hover:#1a55bd;
  --blue-press:#164aa6;
  --blue-on-night:#5b9cff;
  --hair:rgba(0,0,0,.12);
  --hair-night:rgba(255,255,255,.16);
  --gutter:12px;
  --side:max(22px, env(safe-area-inset-left));
  --col:1024px;
  --ease:cubic-bezier(.4,0,.6,1);
  --ease-out:cubic-bezier(.16,1,.3,1);
  --shadow:3px 5px 30px rgba(0,0,0,.18);
  --font:"Inter",-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,"Helvetica Neue",Arial,sans-serif;
  color-scheme:light;
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;text-size-adjust:100%;scroll-padding-top:64px}
@media (prefers-reduced-motion:no-preference){html{scroll-behavior:smooth}}
body{margin:0;background:var(--paper);color:var(--ink);font-family:var(--font);font-size:17px;line-height:1.47;
  letter-spacing:-.011em;font-optical-sizing:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;
  text-rendering:optimizeLegibility;overflow-x:clip}
img{display:block;max-width:100%;height:auto}
a{color:var(--blue);text-decoration:none;text-underline-offset:.18em;text-decoration-thickness:1px}
a:hover{text-decoration:underline}
::selection{background:#cfe0ff;color:var(--ink)}
.t-night ::selection{background:#2b4f8f;color:#fff}
input,textarea,select{caret-color:var(--blue)}
:focus-visible{outline:2px solid var(--blue);outline-offset:3px;border-radius:6px}
.t-night :focus-visible{outline-color:var(--blue-on-night)}
h1,h2,h3,p{margin:0}
h1,h2,h3{font-weight:600;text-wrap:balance}
p{text-wrap:pretty}
.sr-only{position:absolute!important;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;border:0}

.skip{position:absolute;left:12px;top:-60px;z-index:1000;background:var(--ink);color:#fff;padding:12px 18px;border-radius:980px;font-size:15px}
.skip:focus{top:10px;text-decoration:none}

/* ---------- type ---------- */
.d-hero{font-size:clamp(40px,7.2vw,80px);line-height:1.04;letter-spacing:-.035em;font-weight:650}
.d-1{font-size:clamp(34px,5.2vw,56px);line-height:1.07;letter-spacing:-.03em}
.d-2{font-size:clamp(28px,3.4vw,40px);line-height:1.1;letter-spacing:-.022em}
.d-3{font-size:clamp(21px,2vw,24px);line-height:1.17;letter-spacing:-.015em}
.lead{font-size:clamp(19px,1.9vw,24px);line-height:1.33;letter-spacing:-.012em;font-weight:400;color:var(--ink-2)}
.t-night .lead{color:var(--on-night-2)}
.small{font-size:14px;line-height:1.43;letter-spacing:-.006em;color:var(--ink-3)}
.t-night .small{color:var(--on-night-2)}
.num{font-variant-numeric:tabular-nums}

/* ---------- buttons ---------- */
.btns{display:flex;flex-wrap:wrap;gap:14px 17px;align-items:center}
.btns.center{justify-content:center}
.btn{display:inline-flex;align-items:center;justify-content:center;gap:8px;min-height:44px;padding:11px 22px;border-radius:980px;
  border:1px solid transparent;font:inherit;font-size:17px;line-height:1.18;letter-spacing:-.016em;font-weight:500;white-space:nowrap;
  cursor:pointer;text-decoration:none!important;transition:background-color .24s var(--ease),color .24s var(--ease),border-color .24s var(--ease),transform .1s ease-out}
.btn:active{transform:scale(.97)}
.btn-primary{background:var(--blue);color:#fff}
.btn-primary:hover{background:var(--blue-hover)}
.btn-primary:active{background:var(--blue-press)}
.btn-outline{background:transparent;color:var(--blue);border-color:currentColor}
.btn-outline:hover{background:var(--blue);border-color:var(--blue);color:#fff}
.t-night .btn-outline{color:var(--blue-on-night)}
.t-night .btn-outline:hover{background:var(--blue);border-color:var(--blue);color:#fff}
.btn-sm{min-height:32px;padding:6px 14px;font-size:14px;position:relative}
.btn-sm::after{content:"";position:absolute;left:0;right:0;top:50%;height:44px;transform:translateY(-50%)} /* 44px hit area */
.more{display:inline-flex;align-items:center;gap:4px;font-size:17px;font-weight:500;min-height:44px}
.more svg{width:12px;height:12px;flex:none;transition:transform .24s var(--ease)}
.more:hover svg{transform:translateX(3px)}
.t-night .more{color:var(--blue-on-night)}

/* ---------- nav ---------- */
.nav{position:sticky;top:0;z-index:600;height:52px;background:rgba(250,250,252,.82);
  -webkit-backdrop-filter:saturate(180%) blur(20px);backdrop-filter:saturate(180%) blur(20px);
  border-bottom:1px solid transparent;transition:border-color .24s var(--ease)}
.nav.is-scrolled{border-bottom-color:rgba(0,0,0,.08)}
.nav-in{max-width:calc(var(--col) + 2 * 22px);margin:0 auto;height:100%;padding:0 var(--side);display:flex;align-items:center;gap:20px}
.brand{display:inline-flex;align-items:center;gap:9px;color:var(--ink);font-weight:600;font-size:17px;letter-spacing:-.02em;min-height:44px;text-decoration:none!important}
.brand svg{width:24px;height:24px;flex:none}
.nav-links{display:flex;align-items:center;gap:2px;margin-left:auto}
.nav-link{display:inline-flex;align-items:center;gap:5px;min-height:44px;padding:0 11px;font:inherit;font-size:14px;letter-spacing:-.01em;
  color:rgba(0,0,0,.8);background:none;border:0;cursor:pointer;border-radius:8px;text-decoration:none!important;transition:color .24s var(--ease)}
.nav-link:hover{color:#000}
.nav-link svg{width:10px;height:10px;transition:transform .24s var(--ease)}
.nav-link[aria-expanded="true"] svg{transform:rotate(180deg)}
.dd{position:relative}
.nav-toggle{display:none;margin-left:auto;width:44px;height:44px;align-items:center;justify-content:center;background:none;border:0;cursor:pointer;color:var(--ink);border-radius:10px}
.nav-toggle svg{width:22px;height:22px}
.nav-toggle .i-close{display:none}
.nav-toggle[aria-expanded="true"] .i-open{display:none}
.nav-toggle[aria-expanded="true"] .i-close{display:block}

.mnav{position:fixed;inset:52px 0 0 0;z-index:590;background:#fafafc;overflow-y:auto;overscroll-behavior:contain;
  padding:18px var(--side) calc(32px + env(safe-area-inset-bottom))}
.mnav:not([hidden]){animation:mnav-in .32s var(--ease-out)}
@keyframes mnav-in{from{opacity:0;transform:translateY(-8px)}to{opacity:1;transform:none}}
.mnav ul{list-style:none;margin:0;padding:0}
.mnav li a{display:flex;align-items:center;min-height:52px;font-size:24px;font-weight:600;letter-spacing:-.02em;color:var(--ink);text-decoration:none!important;border-bottom:1px solid rgba(0,0,0,.08)}
.mnav .mnav-sub a,.mnav .mnav-demos a{font-size:17px;font-weight:400;min-height:48px;color:var(--ink-2)}
.mnav-label{margin:26px 0 4px;font-size:13px;color:var(--ink-3)}
.mnav .btns{margin-top:28px}
.mnav .btn{flex:1 1 100%}
body.menu-open{overflow:hidden}
/* round 6c fix: a backdrop-filter makes the header the containing block of the fixed phone menu, which clipped the open
   menu to the 52px header bar. While the menu is open the header goes solid and drops the filter, so the menu fills the screen. */
body.menu-open .nav{-webkit-backdrop-filter:none;backdrop-filter:none;background:rgb(250,250,252)}

@media (max-width:900px){
  .nav-links{display:none}
  .nav-toggle{display:inline-flex}
  /* round 13: no "Get a quote" in the top bar, so search takes the auto margin that pushes search + menu to the right */
  .nav-in > .ns-btn{order:1;margin-left:auto}
  .nav-in > .nav-toggle{order:2}
  .ns-btn ~ .nav-toggle{margin-left:-14px}
}
/* round 3: header search button (styles in search.css); it needs JS, so it is hidden without it */
html:not(.js) .ns-btn{display:none}
@media (min-width:901px){.nav-in > .ns-btn{margin-left:6px;margin-right:-6px}}
/* very narrow phones: tighter header gaps */
@media (max-width:360px){
  .nav-in{gap:4px;padding:0 14px}
  .nav-in > .ns-btn{margin-left:auto;width:36px}
  .ns-btn ~ .nav-toggle{margin-left:0;width:36px}
}

/* ---------- tiles ---------- */
main{display:block}
.tile{position:relative;margin-top:var(--gutter);overflow:clip}
.tile:first-child{margin-top:0}
.t-mist{background:var(--mist)}
.t-paper{background:var(--paper)}
.t-night{background:var(--night);color:var(--on-night)}
.wrap{max-width:calc(var(--col) + 2 * 22px);margin:0 auto;padding:0 var(--side)}
.wrap-wide{max-width:1240px;margin:0 auto;padding:0 var(--side)}
.pad{padding:clamp(64px,9vw,112px) 0}
.head{text-align:center;max-width:820px;margin:0 auto}
.head .lead{margin-top:14px}
.head .btns{margin-top:22px}

/* ---------- hero (round 5): soft neutral light, a small monochrome mark, and one example enquiry playing out around the copy ----------
   Background: a very faint top light and bottom shade over Apple-style mist, plus a 3% grain. Neutral, never blue-tinted. */
.hero{--hp:0;position:relative;background:
    radial-gradient(120% 70% at 50% -8%,rgba(255,255,255,.95) 0,rgba(255,255,255,.55) 38%,rgba(255,255,255,0) 70%),
    radial-gradient(90% 60% at 50% 112%,rgba(0,0,0,.045) 0,rgba(0,0,0,0) 70%),
    var(--mist);
  padding:clamp(28px,4vw,56px) 0 clamp(18px,2.4vw,28px);min-height:calc(100svh - 52px);display:flex;flex-direction:column;justify-content:center;overflow:clip}
.hero::before{content:"";position:absolute;inset:0;pointer-events:none;opacity:.035;mix-blend-mode:multiply;
  background:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='2' stitchTiles='stitch'/%3E%3CfeColorMatrix values='0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1.4 0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E") 0 0/160px 160px}
.hero-copy{position:relative;z-index:3;text-align:center;max-width:900px;margin:0 auto;padding:0 var(--side)}
.hero .d-hero{max-width:11ch;margin:0 auto}
.hero-copy .lead{max-width:540px;margin:18px auto 0}
.hero-copy .btns{margin-top:28px;justify-content:center}
.hero-facts{margin-top:18px;display:flex;flex-wrap:wrap;justify-content:center;gap:4px 18px;font-size:14px;color:var(--ink-3)}
.hero-facts li{display:inline-flex;align-items:flex-start;gap:7px;text-align:left}
.hero-facts svg{width:14px;height:14px;margin-top:3px;color:var(--blue);flex:none}
.hero-facts{list-style:none;padding:0}

/* the mark: the existing diamond-N line mark, small and monochrome, one quiet settle-in. No glow, no sheen. */
.logo-mark{width:clamp(34px,3vw,42px);aspect-ratio:1;margin:0 auto clamp(16px,2vw,24px);color:var(--ink)}
.logo-mark svg{display:block;width:100%;height:100%}

/* entrance: content is visible by default; .js only adds a short rise once on load */
@media (prefers-reduced-motion:no-preference){
  .js .enter{animation:rise .9s var(--ease-out) both}
  .js .enter-2{animation-delay:.08s}
  .js .enter-3{animation-delay:.16s}
  .js .enter-4{animation-delay:.26s}
  .js .logo-mark{animation:mark-in 1.1s var(--ease-out) both}
  .js .hx-card{animation:float-in 1.4s var(--ease-out) both}
  .js .hx-crm .hx-card{animation-delay:.15s}
  .js .hx-phone .hx-card{animation-delay:.3s}
  .js .hx-quote .hx-card{animation-delay:.45s}
  .js .hx-week .hx-card{animation-delay:.6s}
}
/* transform-only, so text and images paint at full opacity immediately (keeps LCP early) */
@keyframes rise{from{transform:translateY(12px)}to{transform:none}}
@keyframes mark-in{from{opacity:0;transform:translateY(6px) scale(.94)}to{opacity:1;transform:none}}
@keyframes float-in{from{translate:0 30px;scale:.97}to{translate:0 0;scale:1}}

.chrome{display:flex;align-items:center;gap:6px;height:clamp(22px,2.4cqw,32px);padding:0 clamp(8px,1.1cqw,14px);border-bottom:1px solid rgba(0,0,0,.07);
  background:#fafafa;border-radius:inherit;border-bottom-left-radius:0;border-bottom-right-radius:0}
.chrome i{width:clamp(6px,.7cqw,9px);height:clamp(6px,.7cqw,9px);border-radius:50%;background:#dcdce0;flex:none}
.chrome span{margin:0 auto;font-size:clamp(9px,.95cqw,12px);color:#5c5c61;letter-spacing:0;padding:2px 10px;border-radius:6px;background:#f0f0f2;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;max-width:60%}
.card-ui{padding:clamp(10px,1.4cqw,18px);font-size:clamp(9.5px,1.12cqw,14px);line-height:1.35;color:var(--ink)}
.card-ui header{display:flex;align-items:center;gap:8px;margin-bottom:clamp(8px,1cqw,12px)}
.card-ui .ico{display:inline-grid;place-items:center;width:clamp(20px,2.4cqw,30px);height:clamp(20px,2.4cqw,30px);border-radius:50%;background:#e8f0fe;color:var(--blue);flex:none}
.card-ui .ico svg{width:55%;height:55%}
.card-ui header b{font-weight:600;letter-spacing:-.01em;display:block}
.card-ui header small{display:block;color:var(--ink-3);font-size:.86em}
.card-ui dl{margin:0;display:grid;grid-template-columns:auto 1fr;gap:clamp(3px,.5cqw,6px) 10px}
.card-ui dt{color:var(--ink-3)}
.card-ui dd{margin:0;font-weight:500;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.card-ui footer{margin-top:clamp(8px,1cqw,12px);padding-top:clamp(7px,.9cqw,10px);border-top:1px solid rgba(0,0,0,.07);display:flex;align-items:center;gap:6px;color:#1b7f3b;font-weight:500}
.card-ui footer svg{width:1.1em;height:1.1em;flex:none}
/* Example labels: neutral dark glass, so blue stays reserved for actions */
.tag{display:inline-flex;align-items:center;gap:5px;padding:2px 9px;border-radius:980px;background:rgba(29,29,31,.84);color:#fff;font-size:12px;font-weight:600;letter-spacing:.01em;line-height:1.5;white-space:nowrap;
  -webkit-backdrop-filter:blur(8px);backdrop-filter:blur(8px);box-shadow:0 0 0 1px rgba(255,255,255,.14) inset}
.t-night .tag,.ex .tag{background:rgba(245,245,247,.92);color:#1d1d1f;box-shadow:none}
.card-ui .tag{margin-left:auto;font-size:max(9px,.82em);padding:1px 7px}
.urgent{color:#a1300f}

/* hero story cards (round 5). Each card is sized in cqw so it scales as a whole.
   .hx  = the positioned layer: mouse parallax (--mx/--my x depth --d) and the scroll hand-over (--hp, --gx/--gy) live here.
   .hx-card = the visible card: entrance and story states live here.
   Default (no JS, reduced motion) = the finished story: both bubbles, Tom's card in Booked, the notification showing. */
.hero-art{position:relative;z-index:1;width:min(1000px,calc(100% - 2 * var(--side)));height:clamp(330px,60vw,440px);margin:clamp(28px,4vw,44px) auto 0;pointer-events:none}
.hx{--d:1;--gx:0px;--gy:0px;position:absolute;container-type:inline-size;
  translate:calc(var(--mx,0) * var(--d) * 9px + var(--hp) * var(--gx)) calc(var(--my,0) * var(--d) * 6px + var(--hp) * var(--gy));
  scale:calc(1 - var(--hp) * .3);opacity:calc(1 - var(--hp) * var(--hp) * .95)}
.hx-card{border-radius:clamp(12px,5cqw,18px);background:rgba(255,255,255,.94);color:var(--ink);
  box-shadow:0 0 0 1px rgba(0,0,0,.05),0 1px 0 rgba(255,255,255,.8) inset,0 calc(10px + var(--d) * 14px) calc(30px + var(--d) * 26px) rgba(0,0,0,calc(.06 + var(--d) * .04));
  padding:4.8cqw;font-size:4.2cqw;line-height:1.3}
.mini-top{display:flex;align-items:center;gap:2.4cqw;margin-bottom:3.6cqw;font-size:4.6cqw}
.mini-top b{font-weight:600;letter-spacing:-.01em}
.mini-top .tag{margin-left:auto;font-size:3.6cqw;padding:.2cqw 2.4cqw}
.mini-top .orb{width:8cqw;height:8cqw}
/* round 6c (D17): the round 6b Ask North orb, so the whole site uses one orb (same recipe as .nc-orb in chat-widget.css,
   here so it shows without JS). Translucent graphite-silver sphere; a blurred low-saturation colour field turns slowly
   (::before) and a soft highlight drifts (::after). Transform-only; still under reduced motion and while the hero is paused. */
.orb{position:relative;display:block;flex:none;border-radius:50%;overflow:hidden;isolation:isolate;
  background:radial-gradient(circle at 40% 35%,#ececef 0%,#c9cad0 40%,#9a9ca4 75%,#7b7d85 100%);
  box-shadow:inset 0 0 0 .5px rgba(0,0,0,.14),inset 0 -4px 8px rgba(52,54,62,.22),0 3px 8px -3px rgba(0,0,0,.28)}
.orb::before,.orb::after{content:"";position:absolute;border-radius:50%;pointer-events:none}
.orb::before{inset:-20%;
  background:radial-gradient(circle at 28% 68%,rgba(176,168,214,.9) 0%,rgba(176,168,214,0) 42%),
    radial-gradient(circle at 74% 34%,rgba(146,196,200,.85) 0%,rgba(146,196,200,0) 40%),
    radial-gradient(circle at 66% 80%,rgba(214,170,186,.8) 0%,rgba(214,170,186,0) 38%),
    radial-gradient(circle at 36% 24%,rgba(120,122,132,.5) 0%,rgba(120,122,132,0) 36%);
  filter:blur(5px);opacity:.9;animation:orb-turn 14s linear infinite}
.orb::after{inset:0;
  background:radial-gradient(circle at 34% 27%,rgba(255,255,255,.9) 0%,rgba(255,255,255,.3) 20%,rgba(255,255,255,0) 42%),
    radial-gradient(circle at 50% 50%,rgba(255,255,255,0) 58%,rgba(70,72,80,.28) 100%);
  animation:orb-drift 9s ease-in-out infinite alternate}
@keyframes orb-turn{to{transform:rotate(360deg)}}
@keyframes orb-drift{0%{transform:translate(0,0) scale(1)}50%{transform:translate(4%,-3%) scale(1.04)}100%{transform:translate(-3%,4%) scale(.98)}}
/* in the hero the orb never loops (the story is JS-driven and pausable): it rests, and while North "thinks"
   (the sent beat, before the reply) it glows and its core pulses twice, as the Ask North header orb does */
.hero .orb::before,.hero .orb::after{animation:none}
.hero-art[data-beat="sent"] .orb{box-shadow:inset 0 0 0 .5px rgba(0,0,0,.1),inset 0 -3px 6px rgba(60,62,70,.14),0 0 0 3px rgba(214,212,226,.45),0 0 16px 3px rgba(186,184,204,.6)}
.hero-art[data-beat="sent"] .orb::after{animation:orb-think .4s ease-in-out 2 alternate}
@keyframes orb-think{from{transform:scale(.94)}to{transform:scale(1.08)}}
@media (prefers-reduced-motion:reduce){.orb::before,.orb::after{animation:none}}
.mini-dot{width:3cqw;height:3cqw;border-radius:50%;background:var(--ink)}

/* chat */
.hx-msgs{display:grid;gap:2.4cqw;align-content:start}
.hx-chat .bub{font-size:4.6cqw;line-height:1.32;padding:2.6cqw 3.8cqw;border-radius:4.6cqw;max-width:86%;transition:opacity .35s var(--ease),translate .45s var(--ease-out)}
.hx-chat .bub.me{justify-self:end;background:var(--blue);color:#fff;border-bottom-right-radius:1.4cqw}
.hx-chat .bub.bot{justify-self:start;background:#f0f0f2;color:var(--ink);border-bottom-left-radius:1.4cqw}
/* the typing dots share the reply's grid cell, so showing them never moves the input (no layout shift) */
.hx-chat .bub.me{grid-row:1}
.hx-chat .bub.bot,.hx-chat .bub.dots{grid-row:2;grid-column:1}
.hx-chat .bub.dots{visibility:hidden;display:flex;justify-self:start;align-self:start;gap:1.2cqw;background:#f0f0f2;padding:3.4cqw 3.8cqw}
.bub.dots i{width:1.8cqw;height:1.8cqw;border-radius:50%;background:#8e8e93}
.hx-input{display:flex;align-items:center;gap:2cqw;margin-top:3.6cqw;padding:1.8cqw 1.8cqw 1.8cqw 3.8cqw;border-radius:99px;background:#f5f5f7;
  box-shadow:inset 0 0 0 1px rgba(0,0,0,.06);font-size:4.2cqw;min-height:11cqw;color:var(--ink)}
.hx-typed{white-space:nowrap;overflow:hidden;min-width:0}
.hx-typed:empty{display:none}
.hx-ph{color:#8e8e93}
.hx-typed:not(:empty) + .hx-ph{display:none}
.hx-send{margin-left:auto;display:grid;place-items:center;width:7.4cqw;height:7.4cqw;border-radius:50%;background:#d2d2d7;color:#fff;flex:none;rotate:-90deg;transition:background-color .2s var(--ease)}
.hx-send svg{width:56%;height:56%}
.hx-chat.is-typing .hx-send{background:var(--blue)}
.hx-chat.is-typing .hx-typed::after{content:"";display:inline-block;width:1.5px;height:1.05em;margin-left:1px;vertical-align:-.15em;background:var(--blue)}

/* pipeline */
.mini-cols{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:2.6cqw}
.mini-cols > div{display:flex;flex-direction:column;gap:2cqw;min-width:0}
.mini-cols p{font-size:3.4cqw;color:var(--ink-3);font-weight:500}
.mc{display:block;position:relative;padding:2.2cqw 2.4cqw;border-radius:2.4cqw;background:#f2f2f5;font-size:3.4cqw;color:var(--ink-2);line-height:1.25}
.mc b{display:block;color:var(--ink);font-weight:600}
.mc.ghost{height:10cqw;background:#f7f7f9}
.mc.slot{padding:0;background:none;min-height:var(--mh,14.5cqw)}
/* round 16: with JS and motion, flagship.js sets --mh to the mover's measured height (about 17.2cqw at every size). When a CDN
   paints the first frame before the deferred script runs, the 14.5cqw fallback made the Booked cards jump ~9px; start from the
   same value instead. Reduced motion / no JS never set --mh and keep the 14.5cqw static frame. */
@media (prefers-reduced-motion:no-preference){.js .mc.slot{min-height:var(--mh,17.2cqw)}}
.mc.mover{display:grid;grid-template-columns:minmax(0,1fr);background:#e3f3ea;box-shadow:0 0 0 1px rgba(27,127,59,.16);z-index:2;
  translate:calc(var(--mv,2) * (100% + 2.6cqw)) var(--dy,0px);transition:translate .9s cubic-bezier(.5,0,.2,1),background-color .4s var(--ease),box-shadow .4s var(--ease),opacity .35s var(--ease),scale .35s var(--ease)}
.mc.mover b{grid-area:1/1}
.mv-a,.mv-b{grid-area:2/1;transition:opacity .3s var(--ease)}
.mv-a{opacity:0}
.mv-b{color:#1b7f3b;font-weight:500}

/* phone card (round 6d): a white card like the others. A large phone-style device (drawn in CSS, ours: no Apple assets) rises
   from the card's bottom edge, and the card's own edge crops it, so only the top half shows: thin bezel, a pill camera
   cut-out, status bar, the lock-screen date and time over a soft neutral wallpaper, and a large frosted "New job booked"
   banner that slides in. Two soft icons (a chat tile, a ringing bell) sit either side and pulse/ring once as it lands.
   Sizes: card-relative cqw (the .hx is the container); the device is its own container, so its insides scale with it.
   --dv = device width (share of the card), --vis = how much of the device shows (x its width), --pt = space above it. */
.hx-phone{--dv:58cqw;--vis:.75;--pt:5.2cqw}
.hx-phone .hx-card{position:relative;overflow:hidden;padding:0;height:calc(var(--pt) + var(--dv) * var(--vis));border-radius:clamp(12px,3cqw,18px)}
.hx-phone .hx-card > .tag{position:absolute;top:clamp(12px,2.4cqw,18px);right:clamp(12px,2.4cqw,18px);font-size:clamp(11px,1.7cqw,13px);padding:1px 9px;z-index:2}
/* Round 10 device: a current-generation Pro-style phone, drawn originally in CSS. Layers, outside in: a slim space-black
   titanium band (.95% of the width) with a soft edge highlight -> a very thin, even black glass bezel (--bz, ~1.5%) ->
   the screen. Corners are concentric (outer radius minus band = glass radius, as % of each box; minus bezel = screen) and, where the
   browser supports it, continuous-curve (corner-shape: superellipse); elsewhere they fall back to round. All sizes are
   shares of the device width: on .ph-dev itself via var(--dv) or %, inside it via its own cqw. The screen is its own size
   container, so the lock-screen content (island, clock, banner) scales with the glass, as in round 6d. 9:19.5 proportions. */
.ph-dev{--bz:1.55cqw;
  position:absolute;left:50%;top:var(--pt);width:var(--dv);margin-left:calc(var(--dv) / -2);aspect-ratio:9/19.5;container-type:inline-size;
  padding:calc(var(--dv) * .0095);border-radius:16.6% / 7.66%;
  background:linear-gradient(90deg,rgba(255,255,255,.2) 0,rgba(255,255,255,0) 4%,rgba(255,255,255,0) 96%,rgba(255,255,255,.16) 100%),
    linear-gradient(180deg,#8a8a8f 0,#4a4a4e 3.5%,#36363a 14%,#2c2c30 40%,#323236 100%);
  box-shadow:0 0 0 .5px rgba(0,0,0,.6),inset 0 0 0 .5px rgba(255,255,255,.34),inset 0 1px 0 rgba(255,255,255,.22),
    0 1px 2px rgba(0,0,0,.1),0 14px 30px -10px rgba(0,0,0,.26),0 34px 70px -18px rgba(0,0,0,.2)}
/* side buttons as slim metal bumps: action + volume up/down on the left, the side button on the right (top = share of height) */
.ph-btn{position:absolute;width:.85cqw;border-radius:.6cqw 0 0 .6cqw;
  background:linear-gradient(90deg,#26262a 0,#6e6e74 40%,#9a9aa0 55%,#3c3c40 100%);box-shadow:0 0 0 .5px rgba(0,0,0,.45)}
.ph-act{left:-.8cqw;top:17.6%;height:3.4%}
.ph-vup{left:-.8cqw;top:24.4%;height:6.4%}
.ph-vdn{left:-.8cqw;top:32.2%;height:6.4%}
.ph-side{right:-.8cqw;top:26%;height:10.4%;border-radius:0 .6cqw .6cqw 0;background:linear-gradient(90deg,#3c3c40 0,#9a9aa0 45%,#6e6e74 60%,#26262a 100%)}
.ph-screen{position:relative;height:100%;overflow:hidden;container-type:inline-size;border:var(--bz) solid #050506;border-radius:15.95% / 7.29%;
  display:flex;flex-direction:column;align-items:center;color:#fff;box-shadow:0 0 0 .5px rgba(0,0,0,.7);
  background:radial-gradient(70% 40% at 18% 4%,rgba(236,226,214,.55) 0,rgba(236,226,214,0) 70%),
    radial-gradient(80% 45% at 92% 30%,rgba(196,202,216,.6) 0,rgba(196,202,216,0) 70%),
    radial-gradient(90% 50% at 30% 62%,rgba(120,124,136,.65) 0,rgba(120,124,136,0) 72%),
    linear-gradient(170deg,#9a9a9f 0,#7d7f87 34%,#5d6069 70%,#44464e 100%)}
/* a soft glass sheen over the whole screen (decorative, never blocks anything) */
.ph-screen::after{content:"";position:absolute;inset:0;border-radius:inherit;pointer-events:none;
  background:linear-gradient(118deg,rgba(255,255,255,.1) 0,rgba(255,255,255,.03) 26%,rgba(255,255,255,0) 40%)}
@supports (corner-shape:superellipse(2)){
  .ph-dev{border-radius:19.4% / 8.95%;corner-shape:superellipse(1.5)}
  .ph-screen{border-radius:18.81% / 8.59%}
  .ph-screen,.ph-screen::after{corner-shape:superellipse(1.5)}
}
/* Dynamic Island-style pill: centred, with a faint lens glint on its right */
.ph-island{position:absolute;top:2.3cqw;left:50%;width:29.5cqw;height:8.6cqw;margin-left:-14.75cqw;border-radius:99px;z-index:1;
  background:radial-gradient(circle at calc(100% - 4.3cqw) 50%,#1d2333 0,#10131b 1.1cqw,#000 1.9cqw);box-shadow:0 0 0 .3px rgba(255,255,255,.06)}
.ph-status{align-self:stretch;display:flex;justify-content:flex-end;align-items:center;height:8.6cqw;margin:2.3cqw 6.6cqw 0;font-size:3.6cqw;font-weight:600;letter-spacing:-.01em}
.ph-status > span{display:flex}
.ph-sig{align-items:flex-end;gap:.7cqw;height:3.2cqw;margin-right:1.8cqw}
.ph-sig i{width:1.1cqw;border-radius:.4cqw;background:#fff}
.ph-sig i:nth-child(1){height:35%}.ph-sig i:nth-child(2){height:55%}.ph-sig i:nth-child(3){height:78%}.ph-sig i:nth-child(4){height:100%}
.ph-bat{position:relative;width:6.2cqw;height:3.1cqw;border-radius:1cqw;box-shadow:inset 0 0 0 .4cqw rgba(255,255,255,.6);
  background:linear-gradient(90deg,#fff 0 72%,transparent 72%) .8cqw .8cqw/4.6cqw 1.5cqw no-repeat}
.ph-bat::after{content:"";position:absolute;right:-1cqw;top:1cqw;width:.6cqw;height:1.1cqw;border-radius:0 .4cqw .4cqw 0;background:rgba(255,255,255,.6)}
.ph-clock{text-align:center;font-size:21cqw;font-weight:500;letter-spacing:-.03em;line-height:.96;color:#fff;margin-top:4.6cqw;font-variant-numeric:tabular-nums;
  text-shadow:0 1px 12px rgba(0,0,0,.12)}
.ph-clock small{display:block;font-size:4.6cqw;font-weight:500;letter-spacing:-.005em;line-height:1.2;color:rgba(255,255,255,.92);margin-bottom:1cqw}
/* the banner: frosted, large, readable at a glance */
.ph-note{align-self:stretch;display:flex;gap:3.2cqw;align-items:center;margin:5.4cqw 3.2cqw 0;padding:3.4cqw 4cqw 3.6cqw 3.4cqw;border-radius:6.4cqw;
  background:rgba(250,250,252,.8);-webkit-backdrop-filter:blur(18px) saturate(1.3);backdrop-filter:blur(18px) saturate(1.3);
  color:var(--ink);box-shadow:0 0 0 .5px rgba(255,255,255,.5) inset,0 6px 24px rgba(0,0,0,.14);
  transform-origin:50% 0;transition:opacity .4s var(--ease),translate .6s var(--ease-out),scale .6s var(--ease-out)}
.ph-ico{display:grid;place-items:center;width:11.4cqw;height:11.4cqw;border-radius:2.8cqw;background:#1d1d1f;color:#fff;flex:none}
.ph-ico svg{width:66%;height:66%}
.ph-txt{font-size:4.2cqw;line-height:1.28;letter-spacing:-.01em;color:var(--ink-2);min-width:0}
.ph-txt small{display:block;font-size:3.5cqw;color:#6e6e73;letter-spacing:0;margin-bottom:.3cqw}
.ph-txt b{display:block;color:var(--ink);font-weight:600;font-size:4.5cqw}
/* flanking icons: ours, monochrome; a soft grey chat tile (left) and a ringing bell (right) */
.pf{position:absolute;top:calc(var(--pt) + var(--dv) * .3);width:11cqw;aspect-ratio:1;display:block}
.pf svg{display:block;width:100%;height:100%;overflow:visible}
/* each icon is centred in the space beside the device */
.pf-chat{left:calc(25cqw - var(--dv) / 4 - 5.5cqw)}
.pf-bell{right:calc(25cqw - var(--dv) / 4 - 5.5cqw)}
.pf-tile{fill:#f2f2f5;stroke:rgba(0,0,0,.06);stroke-width:1}
.pf-chat svg{filter:drop-shadow(0 6px 14px rgba(0,0,0,.08))}
.pf-bub{fill:#1d1d1f}
.pf-dot{fill:#fff}
.pf-badge{position:absolute;top:-8%;right:-8%;width:24%;aspect-ratio:1;border-radius:50%;background:var(--blue);box-shadow:0 0 0 2px #fff;transition:scale .35s var(--ease-out),opacity .3s var(--ease)}
.pf-b{fill:#3a3a3e;transform-origin:32px 12px}
.pf-waves{transform-origin:32px 32px;fill:none;stroke:#a1a1a6;stroke-width:2.4;stroke-linecap:round;transition:opacity .4s var(--ease)}

/* quote (round 6, round 11): it opens on an example text thread asking for a quote (below); when the lead lands the thread
   swipes left and the quote slides in showing "Quote sent · £120", then "Quote accepted" as the lead moves to Booked */
.q-ico{display:grid;place-items:center;width:8cqw;height:8cqw;border-radius:50%;background:#1d1d1f;color:#fff;font-size:4.6cqw;font-weight:600}
.q-body{display:grid}
.q-real{grid-area:1/1}
.q-row{display:flex;align-items:baseline;justify-content:space-between;gap:3cqw;font-size:4.4cqw;color:var(--ink-2);line-height:1.3}
.q-row b{display:block;color:var(--ink);font-weight:600}
.q-row strong{font-size:7.4cqw;font-weight:600;letter-spacing:-.02em;color:var(--ink)}
.q-st{display:grid;margin-top:3cqw}
.q-sent,.q-ok{grid-area:1/1;justify-self:start;display:inline-flex;align-items:center;gap:1.6cqw;padding:1cqw 3.4cqw;border-radius:99px;font-size:4cqw;font-weight:500;
  transition:opacity .35s var(--ease),scale .35s var(--ease-out)}
.q-sent{background:#f0f0f2;color:var(--ink-2);opacity:0}
.q-ok{background:#e3f3ea;color:#1b7f3b}
.q-ok svg{width:4.4cqw;height:4.4cqw}
/* round 11: the opening thread. Our own simple message style (neutral grey in, near-black out; no app's logo, colours or UI),
   the same size as the quote card and laid exactly over it. It only exists while the story runs (data-beat): with no JS or
   reduced motion the finished quote shows, as before. Swipe and slide use `transform`, which the cards' entrance
   (float-in on translate/scale) leaves free. */
.q-thread{position:absolute;inset:0;flex-direction:column}
.hero-art:not([data-beat]) .q-thread{display:none}
.qt-av{display:grid;place-items:center;width:8cqw;height:8cqw;border-radius:50%;background:#e8e8ed;color:var(--ink-2);font-size:3.4cqw;font-weight:600;letter-spacing:.02em}
.qt-msgs{display:grid;gap:2cqw;margin-top:auto}
.qt-msgs p{max-width:88%;font-size:4cqw;line-height:1.3;padding:2cqw 3.4cqw;border-radius:4.2cqw;transition:opacity .35s var(--ease),translate .45s var(--ease-out)}
.qt-in{justify-self:start;background:#f0f0f2;color:var(--ink);border-bottom-left-radius:1.4cqw}
/* the dots share the reply's grid cell, so the card never changes size */
.qt-dots,.qt-out{grid-row:2;grid-column:1;justify-self:end;border-bottom-right-radius:1.4cqw}
.qt-out{background:#1d1d1f;color:#fff}
.qt-msgs .qt-dots{display:flex;align-self:end;gap:1.2cqw;padding:2.8cqw 3.4cqw;background:#f0f0f2;opacity:0}
.qt-dots i{width:1.6cqw;height:1.6cqw;border-radius:50%;background:#8e8e93}

/* this week's bookings (round 6): Thursday gains a green block when Tom P. is booked, and the total goes 6 -> 7 */
.wk{display:flex;align-items:flex-end;justify-content:space-between;gap:4cqw}
.wk-n{display:grid;grid-template-columns:auto;line-height:1;font-size:15cqw;font-weight:600;letter-spacing:-.03em}
.wk-a,.wk-b{grid-area:1/1;transition:opacity .35s var(--ease),translate .45s var(--ease-out)}
.wk-a{opacity:0}
.wk-n small{grid-area:2/1;font-size:4.2cqw;font-weight:500;letter-spacing:0;color:var(--ink-3);margin-top:1.6cqw}
.wk-bars{display:flex;align-items:flex-end;gap:2.6cqw;height:26cqw}
.wk-bars span{display:flex;flex-direction:column;justify-content:flex-end;align-items:center;gap:.8cqw;width:7.4cqw;height:100%}
.wk-bars b{order:1}.wk-bars i{order:2}
.wk-bars em{order:3;font-style:normal;font-size:3.6cqw;color:var(--ink-3);line-height:1;margin-top:1.4cqw}
.wk-bars i,.wk-bars b{display:block;width:100%;height:calc(var(--v) * 8cqw);border-radius:1.6cqw;background:#d6d6dc}
.wk-bars b{height:8cqw;background:#34a061;transform-origin:50% 100%;transition:scale .55s var(--ease-out),opacity .3s var(--ease)}

/* story states (JS sets data-beat on #hero-story; no attribute = the finished frame above) */
.hero-art[data-beat] .bub.me,.hero-art[data-beat] .bub.bot{opacity:0;translate:0 2cqw}
.hero-art[data-beat] .mc.mover{opacity:0;scale:.92;--dy:-3cqw;--mv:0}
.hero-art[data-beat] .mc.mover{background:#fff;box-shadow:0 0 0 1px rgba(0,0,0,.06),0 0 0 .9cqw rgba(31,95,209,.18),0 4px 12px rgba(0,0,0,.08)}
.hero-art[data-beat] .mv-a{opacity:1}
.hero-art[data-beat] .mv-b{opacity:0}
.hero-art[data-beat] .ph-note{opacity:0;translate:0 -14cqw;scale:.94}
/* round 6 cards: quote and week reset to their waiting state, then step on with the same beats */
.hero-art[data-beat] .q-sent{opacity:1}
.hero-art[data-beat] .q-ok{opacity:0;scale:.92}
/* round 11: idle -> reply the thread shows (dots on "sent", the business replies on "reply"); on "lead" it swipes left and
   fades, and the quote card slides in from the right; on "out" the quote fades and the thread fades back in place for the loop */
.hero-art[data-beat] .q-thread{display:flex;opacity:1;transform:none;transform-origin:50% 100%;transition:opacity .45s var(--ease)}
.hero-art[data-beat] .hx-quote > .hx-card:not(.q-thread){opacity:0;transform:translateX(12%);transition:opacity .45s var(--ease),transform 0s .45s}
.hero-art[data-beat] .qt-out{opacity:0;translate:0 2cqw}
.hero-art[data-beat="sent"] .qt-dots{opacity:1}
.hero-art[data-beat="reply"] .qt-out{opacity:1;translate:0 0}
.hero-art[data-beat="lead"] .q-thread,.hero-art[data-beat="move"] .q-thread,.hero-art[data-beat="booked"] .q-thread,.hero-art[data-beat="note"] .q-thread{
  opacity:0;transform:translateX(-70%) rotate(-6deg);transition:transform .6s cubic-bezier(.4,0,.7,1),opacity .4s .15s var(--ease)}
.hero-art[data-beat="lead"] .qt-out,.hero-art[data-beat="move"] .qt-out,.hero-art[data-beat="booked"] .qt-out,.hero-art[data-beat="note"] .qt-out{opacity:1;translate:0 0}
.hero-art[data-beat="lead"] .hx-quote > .hx-card:not(.q-thread),.hero-art[data-beat="move"] .hx-quote > .hx-card:not(.q-thread),
.hero-art[data-beat="booked"] .hx-quote > .hx-card:not(.q-thread),.hero-art[data-beat="note"] .hx-quote > .hx-card:not(.q-thread){
  opacity:1;transform:none;transition:opacity .45s .2s var(--ease),transform .6s .2s var(--ease-out)}
/* keep "accepted" while the quote fades out on "out" (it is hidden until the next "lead") */
.hero-art[data-beat="out"] .q-sent{opacity:0}
.hero-art[data-beat="out"] .q-ok{opacity:1;scale:1}
.hero-art[data-beat] .wk-a{opacity:1}
.hero-art[data-beat] .wk-b{opacity:0;translate:0 3cqw}
.hero-art[data-beat] .wk-thu b{scale:1 0;opacity:0}
.hero-art[data-beat="move"] .q-sent,.hero-art[data-beat="booked"] .q-sent,.hero-art[data-beat="note"] .q-sent{opacity:0}
.hero-art[data-beat="move"] .q-ok,.hero-art[data-beat="booked"] .q-ok,.hero-art[data-beat="note"] .q-ok{opacity:1;scale:1}
.hero-art[data-beat="booked"] .wk-a,.hero-art[data-beat="note"] .wk-a{opacity:0;translate:0 -3cqw}
.hero-art[data-beat="booked"] .wk-b,.hero-art[data-beat="note"] .wk-b{opacity:1;translate:0 0}
.hero-art[data-beat="booked"] .wk-thu b,.hero-art[data-beat="note"] .wk-thu b{scale:1;opacity:1}
.hero-art[data-beat="booked"] .wk-thu b{transition-delay:.25s}
.hero-art[data-beat="out"] .wk-thu b{opacity:0}
.hero-art[data-beat="sent"] .bub.me,.hero-art[data-beat="reply"] .bub.me,.hero-art[data-beat="lead"] .bub.me,.hero-art[data-beat="move"] .bub.me,.hero-art[data-beat="booked"] .bub.me,.hero-art[data-beat="note"] .bub.me,
.hero-art[data-beat="reply"] .bub.bot,.hero-art[data-beat="lead"] .bub.bot,.hero-art[data-beat="move"] .bub.bot,.hero-art[data-beat="booked"] .bub.bot,.hero-art[data-beat="note"] .bub.bot{opacity:1;translate:0 0}
.hero-art[data-beat="sent"] .bub.dots{visibility:visible}
.hero-art[data-beat="lead"] .mc.mover{opacity:1;scale:1;--dy:0px}
.hero-art[data-beat="move"] .mc.mover{opacity:1;scale:1;--mv:2;--dy:0px;box-shadow:0 0 0 1px rgba(0,0,0,.06),0 8px 22px rgba(0,0,0,.14)}
.hero-art[data-beat="booked"] .mc.mover,.hero-art[data-beat="note"] .mc.mover{opacity:1;scale:1;--mv:2;--dy:0px;background:#e3f3ea;box-shadow:0 0 0 1px rgba(27,127,59,.16)}
.hero-art[data-beat="booked"] .mv-a,.hero-art[data-beat="note"] .mv-a{opacity:0}
.hero-art[data-beat="booked"] .mv-b,.hero-art[data-beat="note"] .mv-b{opacity:1}
.hero-art[data-beat="note"] .ph-note{opacity:1;translate:0 0;scale:1}
/* the loop's last beat fades everything back out gently */
.hero-art[data-beat="out"] .mc.mover{--mv:2;--dy:0px;scale:1;background:#e3f3ea;box-shadow:0 0 0 1px rgba(27,127,59,.16)}
.hero-art[data-beat="out"] .mv-a{opacity:0}
.hero-art[data-beat="out"] .mv-b{opacity:1}
.hero-art[data-beat="out"] .ph-note{translate:0 -6cqw;scale:1}
/* round 6d: the flanking icons wake when the banner lands: the chat tile pulses once and shows a dot, the bell rings once */
.hero-art[data-beat] .pf-badge{scale:0;opacity:0}
.hero-art[data-beat] .pf-waves{opacity:0}
.hero-art[data-beat="note"] .pf-badge{scale:1;opacity:1;transition-delay:.2s}
.hero-art[data-beat="note"] .pf-waves{opacity:1;transition-delay:.15s}
@media (prefers-reduced-motion:no-preference){
  .hero-art[data-beat="note"] .pf-chat svg{animation:pf-pulse .9s .1s var(--ease-out) both}
  .hero-art[data-beat="note"] .pf-b{animation:pf-ring 1.2s .05s ease-out both}
  .hero-art[data-beat="note"] .pf-waves{animation:pf-wave 1.2s .1s var(--ease-out) both}
}
@keyframes pf-pulse{0%{scale:1}35%{scale:1.1}100%{scale:1}}
@keyframes pf-ring{0%{rotate:0deg}12%{rotate:16deg}26%{rotate:-13deg}40%{rotate:9deg}54%{rotate:-6deg}68%{rotate:3deg}82%,100%{rotate:0deg}}
@keyframes pf-wave{0%{opacity:0;scale:.86}40%{opacity:1}100%{opacity:1;scale:1}}
.hero-art[data-beat="idle"] .mc.mover,.hero-art[data-beat="typing"] .mc.mover{transition:none}
@media (prefers-reduced-motion:reduce){.hx,.hx *{transition:none!important}}

/* layout (round 6d), phones and tablets: the side columns step aside (display:contents) and the cards stack under the copy
   in story order. Tablets: chat and pipeline side by side, the phone card centred below. Phones: one clean column, every card
   full width. The quote and week cards are desktop-only, to keep small screens calm. */
.hx-side{display:contents}
.hx-quote,.hx-week{display:none}
.hero-art{height:auto;display:flex;flex-wrap:wrap;justify-content:center;align-items:stretch;gap:32px;width:min(860px,calc(100% - 2 * var(--side)));margin-top:56px}
.hx-side .hx,.hx-phone{position:relative}
.hx-chat,.hx-crm{flex:1 1 0;min-width:0;max-width:418px}
.hx-chat .hx-card,.hx-crm .hx-card{height:100%}
.hx-phone{flex:0 0 100%;max-width:700px;z-index:3}
@media (max-width:640px){
  .hero-art{flex-direction:column;flex-wrap:nowrap;align-items:stretch;gap:32px}
  .hx-chat,.hx-crm,.hx-phone{flex:none;width:100%;max-width:none}
  /* the device takes most of the card so the banner reads at phone size; the side icons step out */
  .hx-phone{--dv:86cqw;--vis:.9;--pt:13cqw}
  .ph-txt{font-size:5.2cqw}.ph-txt small{font-size:4.4cqw}.ph-txt b{font-size:5.6cqw}
  .ph-ico{width:13cqw;height:13cqw}
  .ph-note{margin-left:2.6cqw;margin-right:2.6cqw}
  .pf{display:none}
}

.hero-foot{position:relative;z-index:3;display:flex;align-items:center;justify-content:center;gap:4px;padding:14px var(--side) 0}
@media (max-width:1239px){.hero{padding-bottom:64px}}
.stage-note{text-align:center}
.hero-play{flex:none;display:inline-grid;place-items:center;width:44px;height:44px;padding:0;border:0;background:none;color:var(--ink);cursor:pointer}
.hero-play span{display:grid;place-items:center;width:26px;height:26px;border-radius:50%;background:rgba(0,0,0,.06);transition:background-color .24s var(--ease)}
.hero-play:hover span{background:rgba(0,0,0,.12)}
.hero-play svg{width:10px;height:10px}
.hero-play .i-play,.hero-play[data-paused] .i-pause{display:none}
.hero-play[data-paused] .i-play{display:block}
html:not(.js) .hero-play,.hero-play[hidden]{display:none}
/* scroll cue: a quiet chevron that bobs twice when the page settles, then rests */
.hero-cue{position:absolute;left:50%;bottom:clamp(6px,1.4vh,14px);z-index:3;display:grid;place-items:center;width:44px;height:44px;margin-left:-22px;border-radius:50%;
  color:var(--ink-3);opacity:calc(1 - var(--hp) * 4)}
.hero-cue svg{width:20px;height:20px}
.hero-cue:hover{color:var(--ink)}
@media (prefers-reduced-motion:no-preference){.js .hero-cue svg{animation:cue 2.4s 1.6s var(--ease) 2 both}}
@keyframes cue{0%,100%{translate:0 0}40%{translate:0 5px}70%{translate:0 0}}

/* wide screens (round 6d): an Apple-style stage around the centred copy, on one rhythm.
   Row 1: the chat and the pipeline sit beside the headline, same width and height, tops level with the mark.
   Row 2: the quote (left) and this week's bookings (right), same size, tops level with the phone card's top.
   Centre: the half-phone card, the largest piece, 48px+ under the ticks. The example-data note sits on the phone card's
   bottom line at the left; the bottom-right corner stays clear for the fixed Ask North button.
   Gutters: --e at the screen edges; 48px+ from every card to the copy; 32px+ between cards. The device width (--dw)
   follows the viewport's width and height, so short screens shrink the stage instead of cropping it; when a screen is
   too short even so, the hero grows and the phone card rises from its bottom (the crop is always the card's own edge).
   --cw = phone card width, --ch = its height (5.2 + 58 x .75 = 48.7% of its width), --qw = row 2 width (height = half). */
@media (min-width:1240px){
  .hero{--e:clamp(28px,2.8vw,64px);--fb:60px;--dw:clamp(300px,min(29vw,calc(48vh - 44px)),460px);--cw:calc(var(--dw) / .58);--ch:calc(var(--cw) * .487);
    --qw:min(calc(50vw - var(--cw) / 2 - 32px - var(--e)),330px);
    justify-content:flex-start;padding:clamp(18px,2.6vh,52px) 0 var(--fb)}
  .hero .d-hero{font-size:min(80px,7.2vw,max(56px,8.6vh))}
  .logo-mark{margin-bottom:clamp(12px,1.8vh,22px)}
  .hero-copy .lead{margin-top:clamp(12px,1.8vh,18px)}
  .hero-copy .btns{margin-top:clamp(18px,2.8vh,28px)}
  .hero-facts{margin-top:clamp(12px,1.8vh,18px)}
  /* spare height on tall screens is shared evenly above the copy and between the ticks and the phone card */
  .hero-copy{margin-top:auto}
  .hero-art{position:static;display:block;width:auto;height:auto;margin:auto 0 0;padding-top:48px}
  .hx-side{position:absolute;top:0;bottom:0;display:flex;flex-direction:column;justify-content:space-between;
    padding:clamp(18px,2.6vh,52px) 0 calc(var(--fb) + var(--ch) - var(--qw) / 2)}
  .hx-l{left:var(--e);align-items:flex-start}
  .hx-r{right:var(--e);align-items:flex-end}
  .hx-quote,.hx-week{display:block}
  /* row 1: 48px clear of the headline's box (566px at 80px) */
  .hx-chat,.hx-crm{flex:none;width:min(calc(50vw - 283px - 48px - var(--e)),400px,52vh);max-width:none}
  .hx-chat .hx-card,.hx-crm .hx-card{height:78cqw}
  .hx-chat .hx-card{display:flex;flex-direction:column}
  .hx-chat .hx-input{margin-top:auto}
  .hx-chat .hx-msgs{margin-bottom:3.6cqw}
  /* row 2: 32px clear of the phone card */
  .hx-quote,.hx-week{width:var(--qw)}
  .hx-quote .hx-card,.hx-week .hx-card{height:50cqw;display:flex;flex-direction:column}
  .hx-quote .q-body,.hx-week .wk{margin-top:auto}
  .hx-phone{width:var(--cw);max-width:none;margin:0 auto}
  .hero-foot{position:absolute;left:var(--e);bottom:var(--fb);width:var(--qw);padding:0;justify-content:flex-start;align-items:flex-end;text-align:left}
  .hero-foot .stage-note{text-align:left}
  .hero-cue{bottom:4px}
}

/* ---------- flagship: example CRM (round 5: mirrors the /demo/ app, six tabs, one enquiry threaded through) ----------
   This file holds only the frame: the section, the sticky scroll passage, the device's unfold (--o), the captions and the
   pause control. The app inside is styled by /assets/crm.css (loaded without blocking first paint) and animated by
   /assets/crm-story.js (fetched as the section approaches). Defaults = the finished, static Dashboard (reduced motion, no JS). */
.crm{margin-top:var(--gutter);background:var(--paper);padding:clamp(64px,9vw,112px) 0 clamp(40px,5vw,64px)}
.crm-head{text-align:center;max-width:820px;margin:0 auto;padding:0 var(--side)}
.crm-head .eyebrow{margin-bottom:16px}
.crm-head .lead{margin-top:14px}
.crm-head .btns{margin-top:24px}
.crm-scroll{position:relative;margin-top:clamp(32px,4vw,52px)}
.crm-sticky{display:flex;flex-direction:column;align-items:center;justify-content:center;gap:clamp(14px,2vw,26px);padding:0 var(--side)}
.crm-device{--o:1;--v0:1;--v1:0;--v2:0;--v3:0;--v4:0;--v5:0;
  position:relative;width:min(1120px,100%);aspect-ratio:16/10;container-type:inline-size;
  transform:perspective(2200px) rotateX(calc((1 - var(--o)) * 16deg)) scale(calc(.84 + .16 * var(--o)));transform-origin:50% 100%}
/* round 16: until /assets/crm.css (non-blocking) applies, the unstyled app inside is ~5800px tall and the aspect-ratio box grew to
   fit it, so the sticky frame centred a giant device whose shadow covered the viewport; when crm.css landed after the first frame
   (seen on the Cloudflare preview only) it snapped back = CLS 0.75-1.0. min-height:0 keeps the box at its aspect ratio from the
   first frame; crm.css restores min-height:auto, so the loaded layout is exactly as before. */
.crm-device{min-height:0}
.crm-device::before{content:"";position:absolute;top:4%;bottom:0;left:3%;right:3%;transform:scaleX(calc(1 - (1 - var(--o)) * .64));border-radius:24px;box-shadow:0 30px 80px rgba(0,0,0,.2);opacity:var(--o)}
.crm-ctl{display:flex;align-items:flex-start;gap:clamp(8px,1.6vw,20px);width:min(1120px,100%)}
.crm-steps{flex:1;min-width:0;list-style:none;margin:0;padding:0;display:grid;grid-template-columns:repeat(6,minmax(0,1fr));gap:12px clamp(12px,1.6vw,22px)}
.crm-steps button{display:block;width:100%;min-height:44px;padding:12px 0 0;text-align:left;font:inherit;color:inherit;background:none;border:0;cursor:pointer;position:relative;border-top:1px solid var(--hair)}
.crm-steps button::before{content:"";position:absolute;left:0;right:0;top:-2px;height:3px;border-radius:3px;background:var(--ink);transform:scaleX(0);transform-origin:0 50%;transition:transform .45s var(--ease-out)}
.crm-steps button[aria-current="step"]::before{transform:scaleX(1)}
.crm-steps b{display:block;font-size:15px;font-weight:600;letter-spacing:-.015em}
.crm-steps span{display:block;margin-top:3px;font-size:13px;line-height:1.38;color:var(--ink-3)}
.crm-steps button[aria-current="step"] span{color:var(--ink-2)}
.crm-play{flex:none;display:inline-grid;place-items:center;width:44px;height:44px;margin-top:4px;padding:0;border:0;background:none;color:var(--ink);cursor:pointer}
.crm-play span{display:grid;place-items:center;width:30px;height:30px;border-radius:50%;background:rgba(0,0,0,.07);transition:background-color .24s var(--ease)}
.crm-play:hover span{background:rgba(0,0,0,.13)}
.crm-play svg{width:12px;height:12px}
.crm-play .i-play,.crm-play[data-paused] .i-pause{display:none}
.crm-play[data-paused] .i-play{display:block}
html:not(.js) .crm-play,.crm-play[hidden]{display:none}
.crm-note{text-align:center;max-width:760px;margin:clamp(24px,3vw,36px) auto 0;padding:0 var(--side)}
.crm-now{display:none}

/* the sticky, scroll-driven version: only with JS, motion allowed and room to show it */
@media (prefers-reduced-motion:no-preference) and (min-height:561px){
  .js .crm-scroll{height:250vh}
  .js .crm-sticky{position:sticky;top:52px;height:calc(100svh - 52px)}
  .js .crm-device{width:min(1120px,100%,calc((100svh - 52px - 190px) * 1.6));will-change:transform}
}
@media (max-width:1023px){
  .crm-steps{grid-template-columns:repeat(3,minmax(0,1fr))}
}
/* small screens: the app goes portrait (4:5); captions become a 3 x 2 grid of titles, and the current one's line shows below (.crm-now, filled by JS) */
@media (max-width:640px){
  .crm-device{aspect-ratio:4/5}
  .crm-steps{gap:0 12px}
  .crm-steps button{padding:8px 0 9px;min-height:40px;border-top:0;border-bottom:1px solid var(--hair)}
  .crm-steps button::before{top:auto;bottom:-2px}
  .crm-steps b{font-size:14px;color:var(--ink-3);transition:color .3s var(--ease)}
  .crm-steps button[aria-current="step"] b{color:var(--ink)}
  .crm-steps span{display:none}
  .crm-play{margin-top:0}
  .js .crm-now{display:block;width:100%;min-height:2.8em;margin:-4px 0 0;font-size:14px;line-height:1.4;color:var(--ink-2)}
}
@media (prefers-reduced-motion:no-preference) and (min-height:561px) and (max-width:640px){
  .js .crm-scroll{height:240vh}
  .js .crm-device{width:min(100%,calc((100svh - 52px - 200px) * .8))}
  .js .crm-sticky{gap:12px}
}

/* ---------- services ---------- */
.web-tile{padding:clamp(64px,9vw,104px) 0 0}
.web-tile .head{max-width:760px}
.web-price{margin-top:22px;display:flex;flex-wrap:wrap;justify-content:center;align-items:baseline;gap:6px 10px}
.web-price strong{font-size:clamp(28px,3vw,36px);letter-spacing:-.02em;font-weight:600}
.web-price span{color:var(--on-night-2);font-size:15px}
.packages{list-style:none;margin:36px auto 0;padding:0;display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:1px;max-width:900px;
  background:var(--hair-night);border-top:1px solid var(--hair-night);border-bottom:1px solid var(--hair-night)}
.packages li{background:var(--night);padding:18px 18px 20px}
.packages b{display:block;font-size:17px;font-weight:600}
.packages span{display:block;margin-top:4px;font-size:14px;color:var(--on-night-2);line-height:1.43}
.web-shot{position:relative;margin:clamp(44px,6vw,72px) auto 0;width:min(1240px,calc(100% - 2 * var(--side)));padding-bottom:0}
@media (prefers-reduced-motion:no-preference){
  .js .reveal{transform:translateY(56px) scale(.95);transform-origin:50% 0;transition:transform 1.6s var(--ease-out)}
  .js .reveal .phone{translate:0 40px;transition:translate 1.6s .15s var(--ease-out)}
  .js .reveal.in{transform:none}
  .js .reveal.in .phone{translate:0 0}
}
.web-shot .frame{border-radius:14px 14px 0 0;overflow:hidden;background:#1d1f25;box-shadow:0 -1px 0 rgba(255,255,255,.08) inset}
.web-shot .frame img{width:100%;aspect-ratio:1200/750}
.web-shot .phone{position:absolute;right:-1%;bottom:8%;width:19%;border-radius:18px;overflow:hidden;border:5px solid #23262d;box-shadow:0 20px 40px rgba(0,0,0,.45)}
.web-shot .phone img{aspect-ratio:390/780}
.web-shot .chrome .tag{margin-left:auto;font-size:11px}
.web-shot .chrome span{margin:0 0 0 auto}
.web-shot .frame .chrome{background:#24272e;border-bottom-color:rgba(255,255,255,.06)}
.web-shot .frame .chrome i{background:#3a3e47}
.web-shot .frame .chrome span{background:#2e323a;color:#a1a1a6}

.grid-2{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:var(--gutter);margin-top:var(--gutter)}
.promo{background:var(--mist);padding:clamp(44px,5vw,56px) clamp(24px,4vw,48px) 0;display:flex;flex-direction:column;align-items:center;text-align:center;min-height:clamp(520px,48vw,620px);overflow:clip}
.promo .d-2{max-width:16ch}
.promo p.sub{margin-top:10px;font-size:clamp(17px,1.5vw,19px);line-height:1.32;color:var(--ink-2);max-width:34ch}
.price{margin-top:14px;font-size:15px;line-height:1.47;color:var(--ink-2);max-width:40ch}
.price strong{color:var(--ink);font-weight:600}
.promo .btns{margin-top:18px;justify-content:center}
.promo .art{margin-top:auto;padding-top:28px;width:100%;display:flex;justify-content:center}
.not{margin-top:12px;font-size:14px;color:var(--ink-3);max-width:40ch}
.not svg{display:inline-block;width:14px;height:14px;vertical-align:-2px;margin-right:6px}

/* chat art */
.chat{width:min(340px,92%);background:#fff;border-radius:18px 18px 0 0;box-shadow:var(--shadow);padding:14px 14px 18px;text-align:left;font-size:14px;line-height:1.38}
.chat-h{display:flex;align-items:center;gap:8px;font-weight:600;padding-bottom:10px;border-bottom:1px solid rgba(0,0,0,.06);margin-bottom:12px}
.chat-h .orb{width:28px;height:28px}
.chat-h .tag{margin-left:auto}
.bub{max-width:84%;padding:8px 12px;border-radius:16px;margin-top:8px}
.bub.me{margin-left:auto;background:var(--blue);color:#fff;border-bottom-right-radius:5px}
.bub.bot{background:var(--mist);border-bottom-left-radius:5px}
/* call art */
.callsheet{width:min(340px,92%);background:#fff;border-radius:18px 18px 0 0;box-shadow:var(--shadow);text-align:left}
.callsheet .card-ui{font-size:14px;padding:16px}
.callsheet .card-ui .ico{width:32px;height:32px}
.callsheet .card-ui .tag{font-size:12px}
/* toolkit art */
.sheet{width:min(440px,96%);border-radius:12px 12px 0 0;overflow:hidden;box-shadow:var(--shadow);background:#fff}
.sheet{position:relative}
.sheet img{width:100%;aspect-ratio:800/500;object-fit:cover;object-position:top left}
.sheet img[width="900"]{aspect-ratio:900/588}
.sheet .tag{position:absolute;right:10px;top:10px}
/* round 9: on the Practical automation card the tag sits above the picture, clear of it (the image corner is rounded instead of clipped by the sheet) */
.art:has(> .sheet > img[width="900"] + .tag){padding-top:40px}
.sheet:has(> img[width="900"] + .tag){overflow:visible}
.sheet > img[width="900"]{border-radius:12px 12px 0 0}
.sheet > img[width="900"] + .tag{top:auto;bottom:calc(100% + 8px);right:0}
.price-note{max-width:760px;margin:28px auto 0;text-align:center}

/* ---------- examples: Apple-style carousel (round 3) ----------
   Big image cards that nearly fill the screen, neighbours peeking at both edges, a caption row inside each card,
   and under it only a row of small dots plus a pause button. The track is a native horizontal scroll-snap row,
   so touch swiping is the browser's own and the page never scrolls for you. Without JS it is simply a swipeable row.
   JS adds looping (two inert clones each side), autoplay every 5 s (pauses on hover, focus, touch, offscreen, hidden
   tab, the pause button and reduced motion) and the dot progress fill. */
.ex-tile{padding:clamp(20px,2.4vw,36px) 0 clamp(56px,7vw,96px)}
.car{--sw:min(88cqw,calc((100svh - 150px) * 2));--ar:2/1;--gap:16px;position:relative;container-type:inline-size}
@supports not (height:1svh){.car{--sw:min(88cqw,calc((100vh - 150px) * 2))}}
.car-track{position:relative;display:flex;gap:var(--gap);overflow-x:auto;scroll-snap-type:x mandatory;
  padding:0 calc((100cqw - var(--sw)) / 2);scrollbar-width:none;overscroll-behavior-x:contain}
.car-track::-webkit-scrollbar{display:none}
.car-track.is-anim{scroll-snap-type:none}
.car-slide{flex:0 0 var(--sw);scroll-snap-align:center;scroll-snap-stop:always}
.ex{position:relative;display:flex;flex-direction:column;justify-content:flex-end;aspect-ratio:var(--ar);border-radius:clamp(14px,1.6vw,22px);overflow:hidden;background:var(--night-2);
  color:#fff;text-decoration:none!important;isolation:isolate;clip-path:inset(0 round clamp(14px,1.6vw,22px))}
.ex-img,.ex-img img{position:absolute;inset:0;width:100%;height:100%}
.ex-img img{object-fit:cover;object-position:50% 0;transition:transform .9s var(--ease-out)}
.ex:hover .ex-img img{transform:scale(1.015)}
/* a soft scrim under the caption so the text reads on light and dark sites alike */
.ex::after{content:"";position:absolute;inset:auto 0 0 0;height:min(46%,340px);z-index:1;pointer-events:none;
  background:linear-gradient(to top,rgba(5,7,12,.94) 0,rgba(5,7,12,.86) 34%,rgba(5,7,12,.5) 66%,rgba(5,7,12,0) 100%);
  -webkit-backdrop-filter:blur(18px);backdrop-filter:blur(18px);-webkit-mask-image:linear-gradient(to top,#000 50%,transparent);mask-image:linear-gradient(to top,#000 50%,transparent)}
.ex .tag{position:absolute;left:clamp(14px,1.6vw,22px);top:clamp(14px,1.6vw,22px)}
.ex-cap{z-index:2;display:flex;align-items:center;gap:clamp(14px,1.6vw,22px);
  padding:0 clamp(18px,3.6cqw,56px) clamp(18px,3.2cqw,48px)}
.ex-go{flex:none;display:inline-flex;align-items:center;min-height:44px;padding:0 22px;border-radius:980px;background:#fff;color:#1d1d1f;
  font-size:17px;font-weight:500;letter-spacing:-.01em;transition:background-color .24s var(--ease)}
.ex:hover .ex-go{background:#e8e8ed}
.ex-txt{min-width:0;max-width:72ch;font-size:clamp(15px,1.45cqw,19px);line-height:1.35;letter-spacing:-.01em;color:rgba(255,255,255,.92);text-shadow:0 1px 12px rgba(0,0,0,.35)}
.ex-txt h3,.ex-txt p{display:inline;font-size:inherit;line-height:inherit;margin:0}
.ex-txt h3{font-weight:600;color:#fff;letter-spacing:-.01em}
.ex-txt h3::after{content:" \00B7"}
/* the card is clipped to its rounded shape, so its focus ring is drawn inside the edge */
.ex:focus-visible{outline:none}
.ex:focus-visible::before{content:"";position:absolute;inset:0;z-index:3;border-radius:inherit;pointer-events:none;box-shadow:inset 0 0 0 3px var(--blue-on-night),inset 0 0 0 5px #fff}

/* controls: centred dots with a small pause button to their right (kept clear of the fixed chat button in the corner) */
.car-ctl{position:relative;display:flex;align-items:center;justify-content:center;gap:clamp(12px,2vw,28px);width:var(--sw);margin:clamp(14px,1.6vw,22px) auto 0;min-height:44px}
.car-dots{display:flex;align-items:center;justify-content:center}
.car-dot{display:inline-grid;place-items:center;width:24px;height:44px;padding:0;border:0;background:none;cursor:pointer;transition:width .5s var(--ease-out)}
.car-dot i{position:relative;display:block;width:8px;height:8px;border-radius:99px;background:rgba(245,245,247,.42);overflow:hidden;
  transition:width .5s var(--ease-out),background-color .3s var(--ease)}
.car-dot:hover i{background:rgba(245,245,247,.7)}
.car-dot[aria-current="true"]{width:52px}
.car-dot[aria-current="true"] i{width:40px;background:rgba(245,245,247,.42)}
/* the active dot fills over the 5 s dwell while autoplay runs, and is simply solid when it doesn't */
.car-dot[aria-current="true"] i::after{content:"";position:absolute;inset:0;border-radius:inherit;background:var(--on-night);transform-origin:0 50%}
.car.is-running .car-dot[aria-current="true"] i::after{animation:car-fill var(--dwell,5000ms) linear both}
@keyframes car-fill{from{transform:scaleX(0)}to{transform:scaleX(1)}}
.car-play{display:inline-grid;place-items:center;width:44px;height:44px;padding:0;border:0;background:none;color:var(--on-night);cursor:pointer}
.car-play span{display:grid;place-items:center;width:30px;height:30px;border-radius:50%;background:rgba(245,245,247,.16);transition:background-color .24s var(--ease)}
.car-play:hover span{background:rgba(245,245,247,.26)}
.car-play svg{width:12px;height:12px}
.car-play .i-play,.car-play[data-paused] .i-pause{display:none}
.car-play[data-paused] .i-play{display:block}
/* without JS the cards stay a native swipeable row; the dots and pause need JS, so they are not shown */
html:not(.js) .car-ctl{display:none}

.ex-note{margin-top:22px;text-align:center}
/* tablets and landscape phones: a little taller than 2:1, still capped by the screen height */
@media (max-width:1068px){
  .car{--ar:16/9;--sw:min(90cqw,calc((100svh - 120px) * 16 / 9));--gap:12px}
  .ex-go{font-size:15px;padding:0 18px}
}
/* phones: tall cards, nearly full width; the caption stacks above the button */
@media (max-width:640px){
  .car{--ar:780/1120;--sw:88cqw;--gap:10px}
  .ex-cap{flex-direction:column;align-items:flex-start;gap:12px;padding:0 20px 22px}
  .ex-cap .tag{position:static;order:0}
  .ex-txt{order:1;font-size:15px}
  .ex-go{order:2}
  .ex::after{height:66%;background:linear-gradient(to top,rgba(5,7,12,.95) 0,rgba(5,7,12,.88) 45%,rgba(5,7,12,.5) 75%,rgba(5,7,12,0) 100%)}
  .car-dot{width:24px}
  .car-dot[aria-current="true"]{width:44px}
  .car-dot[aria-current="true"] i{width:32px}
}

/* ---------- process ---------- */
.steps{list-style:none;margin:clamp(40px,5vw,56px) 0 0;padding:0;display:grid;grid-template-columns:repeat(5,minmax(0,1fr));gap:0;counter-reset:s;position:relative}
.steps::before{content:"";position:absolute;left:10%;right:10%;top:21px;height:1px;background:rgba(0,0,0,.14)}
.steps li{position:relative;text-align:center;padding:0 10px}
.steps .n{position:relative;display:grid;place-items:center;width:44px;height:44px;margin:0 auto 16px;border-radius:50%;background:#fff;border:1px solid rgba(0,0,0,.14);
  font-weight:600;font-size:15px;font-variant-numeric:tabular-nums;color:var(--ink)}
.steps li:first-child .n{background:var(--blue);border-color:var(--blue);color:#fff}
.steps h3{font-size:17px;letter-spacing:-.012em}
.steps p{margin-top:6px;font-size:14px;line-height:1.43;color:var(--ink-2)}
/* round 3b: the steps play through once (flagship.js adds .is-play; without it, as above, all five show).
   Future steps: grey circle, text hidden (opacity only, still in the DOM). Reached steps: blue circle, text shown.
   Current step: soft halo. The blue line runs along the grey one from circle to circle. Calm ease-out, no overshoot. */
.steps::after{content:"";position:absolute;left:10%;right:10%;top:20.5px;height:2px;border-radius:2px;background:var(--blue);
  transform-origin:0 50%;transform:scaleX(0);opacity:0;pointer-events:none}
.steps.is-play::after{opacity:1;transform:scaleX(var(--fill,0));transition:transform .65s var(--ease-out)}
.steps.is-play li{cursor:pointer}
.steps button.n{padding:0;font:inherit;font-weight:600;font-size:15px;font-variant-numeric:tabular-nums;cursor:pointer;-webkit-tap-highlight-color:transparent}
.steps.is-play .n{z-index:1;background:#fff;border-color:rgba(0,0,0,.14);color:var(--ink-3);
  transition:background-color .45s var(--ease),border-color .45s var(--ease),color .45s var(--ease),box-shadow .6s var(--ease-out)}
.steps.is-play li:first-child .n{background:#fff;border-color:rgba(0,0,0,.14);color:var(--ink-3)}
.steps.is-play li.is-done .n{background:var(--blue);border-color:var(--blue);color:#fff}
.steps.is-play li.is-on .n{box-shadow:0 0 0 7px rgba(31,95,209,.13)}
.steps.is-play li:not(.is-done):hover .n{border-color:rgba(0,0,0,.32);color:var(--ink)}
.steps.is-play li > div{opacity:0;transform:translateY(10px);transition:opacity .35s var(--ease),transform .35s var(--ease)}
.steps.is-play li.is-done > div{opacity:1;transform:none;transition:opacity .7s var(--ease) .12s,transform .9s var(--ease-out) .12s}
.steps.is-play li.is-done:not(.is-on) p{color:var(--ink-3);transition:color .6s var(--ease)}
.steps.is-play.is-end li.is-done p{color:var(--ink-2)}

/* ---------- about ---------- */
.about{display:grid;grid-template-columns:minmax(0,5fr) minmax(0,7fr);gap:clamp(32px,6vw,80px);align-items:center}
.about figure{margin:0}
.about figure{max-width:400px}
.about figure img{width:100%;aspect-ratio:1;object-fit:cover;border-radius:50%}
.about figcaption{margin-top:12px}
.about .d-1{margin-bottom:18px}
.about p + p{margin-top:14px}
.about p{color:var(--ink-2)}
.about .first{color:var(--ink);font-size:clamp(19px,1.8vw,21px);line-height:1.38}
.about ul{list-style:none;padding:0;margin:22px 0 0;display:flex;flex-wrap:wrap;gap:8px}
.about li{font-size:14px;padding:6px 12px;border-radius:980px;background:var(--mist);color:var(--ink-2)}

/* ---------- faq ---------- */
.faq{max-width:820px;margin:clamp(32px,4vw,48px) auto 0;border-top:1px solid var(--hair)}
.faq details{border-bottom:1px solid var(--hair)}
.faq summary{list-style:none;cursor:pointer;display:flex;align-items:center;justify-content:space-between;gap:20px;min-height:64px;padding:14px 0;font-size:19px;font-weight:600;letter-spacing:-.015em}
.faq summary::-webkit-details-marker{display:none}
.faq summary svg{width:16px;height:16px;flex:none;color:var(--ink-3);transition:transform .32s var(--ease)}
.faq details[open] summary svg{transform:rotate(45deg)}
.faq details p{padding:0 40px 22px 0;color:var(--ink-2)}
.faq summary:focus-visible{outline-offset:2px}

/* ---------- contact ---------- */
.contact{display:grid;grid-template-columns:minmax(0,5fr) minmax(0,6fr);gap:clamp(32px,6vw,72px);align-items:start}
.contact .lead{margin-top:16px}
.next{list-style:none;padding:0;margin:28px 0 0;display:grid;gap:14px}
.next li{display:grid;grid-template-columns:28px 1fr;gap:12px;align-items:start;color:var(--on-night-2);font-size:15px;line-height:1.47}
.next li b{display:block;color:var(--on-night);font-weight:600}
.next .n{display:grid;place-items:center;width:28px;height:28px;border-radius:50%;border:1px solid var(--hair-night);font-size:13px;font-weight:600;color:var(--on-night)}
.channels{list-style:none;padding:0;margin:32px 0 0;display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:10px}
.channels a{display:flex;align-items:center;gap:12px;min-height:60px;padding:10px 14px;border-radius:14px;background:var(--night-2);color:var(--on-night);text-decoration:none!important;transition:background-color .24s var(--ease)}
.channels a:hover{background:#1d222c}
.channels svg{width:20px;height:20px;flex:none;color:var(--blue-on-night)}
.channels b{display:block;font-size:15px;font-weight:600}
.channels span{display:block;font-size:13px;color:var(--on-night-2);word-break:break-word}
.form-card{background:#fff;color:var(--ink);border-radius:22px;padding:clamp(24px,3.4vw,40px)}
.form-card h3{font-size:24px;letter-spacing:-.02em}
.form-card > p{margin-top:6px;color:var(--ink-2);font-size:15px}
.fields{display:grid;grid-template-columns:1fr 1fr;gap:14px;margin-top:22px}
.field{display:flex;flex-direction:column;gap:6px}
.field.full{grid-column:1/-1}
.field label{font-size:14px;font-weight:500;color:var(--ink)}
.field label small{font-weight:400;color:var(--ink-3)}
.field input,.field select,.field textarea{font:inherit;font-size:17px;letter-spacing:-.01em;color:var(--ink);background:#fff;border:1px solid #d2d2d7;border-radius:12px;
  min-height:48px;padding:11px 14px;width:100%;transition:border-color .24s var(--ease),box-shadow .24s var(--ease)}
.field textarea{min-height:128px;resize:vertical;line-height:1.4}
.field select{appearance:none;-webkit-appearance:none;padding-right:40px;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 10'%3E%3Cpath d='M2 3.5l3 3 3-3' fill='none' stroke='%236e6e73' stroke-width='1.4' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 14px center;background-size:12px}
.field input:focus,.field select:focus,.field textarea:focus{outline:none;border-color:var(--blue);box-shadow:0 0 0 4px rgba(31,95,209,.18)}
.field input[aria-invalid="true"],.field textarea[aria-invalid="true"]{border-color:#c4321b}
.field ::placeholder{color:#6e6e73}
.hp{position:absolute;left:-9999px;width:1px;height:1px;overflow:hidden}
.form-foot{margin-top:18px;display:flex;flex-wrap:wrap;align-items:center;gap:14px 18px}
.form-foot .btn{min-width:180px}
.form-foot .btn[disabled]{opacity:.6;cursor:progress}
.privacy-line{font-size:13px;color:var(--ink-3);flex:1 1 220px}
.form-error{margin-top:12px;color:#b3261e;font-size:14px;font-weight:500;min-height:0}
.form-error:empty{display:none}
.form-success{display:none;padding:8px 0}
.form-success h3{font-size:24px}
.form-success p{margin-top:8px;color:var(--ink-2)}
.form-success:focus{outline:none}

/* ---------- footer ---------- */
.foot{background:var(--mist);margin-top:var(--gutter);font-size:12px;line-height:1.33;color:rgba(0,0,0,.56)}
.foot .wrap{padding-top:28px;padding-bottom:28px}
.foot-top{display:grid;grid-template-columns:minmax(0,1.3fr) repeat(3,minmax(0,1fr));gap:28px;padding-bottom:22px;border-bottom:1px solid rgba(0,0,0,.16)}
.foot h2{font-size:12px;font-weight:600;color:rgba(0,0,0,.88);margin-bottom:10px;letter-spacing:0}
.foot ul{list-style:none;padding:0;margin:0;display:grid;gap:0}
.foot li a{display:inline-flex;align-items:center;min-height:44px;color:rgba(0,0,0,.72)}
.foot li a:hover{color:#000}
.foot .brand{font-size:15px;min-height:0;margin-bottom:10px}
.foot .brand svg{width:20px;height:20px}
.foot p{max-width:42ch}
.foot p + p{margin-top:8px}
.social{display:flex;gap:6px;margin-top:12px}
.social a{display:inline-grid;place-items:center;width:44px;height:44px;border-radius:50%;color:rgba(0,0,0,.72)}
.social a:hover{background:rgba(0,0,0,.05);color:#000}
.social svg{width:18px;height:18px;fill:none;stroke:currentColor;stroke-width:1.6}
.legal{padding-top:16px;display:flex;flex-wrap:wrap;gap:6px 18px;justify-content:space-between}
.legal a{color:rgba(0,0,0,.72)}

/* ---------- responsive ---------- */
@media (max-width:1068px){
  .steps{grid-template-columns:repeat(5,minmax(0,1fr))}
}
@media (max-width:900px){
  .steps{grid-template-columns:1fr;gap:22px;max-width:520px;margin-left:auto;margin-right:auto}
  .steps::before{left:21px;right:auto;top:22px;bottom:22px;width:1px;height:auto}
  .steps::after{left:20.5px;right:auto;top:22px;bottom:22px;width:2px;height:auto;transform-origin:50% 0;transform:scaleY(0)}
  .steps.is-play::after{transform:scaleY(var(--fill,0))}
  .steps.is-play::before,.steps.is-play::after{bottom:var(--tail,22px)}
  .steps li{display:grid;grid-template-columns:44px 1fr;gap:16px;text-align:left;padding:0}
  .steps .n{margin:0}
  .steps p{margin-top:4px}
  .about{grid-template-columns:1fr}
  .about figure{max-width:360px}
  .contact{grid-template-columns:1fr}
  .foot-top{grid-template-columns:1fr 1fr}
  .foot-top > div:first-child{grid-column:1/-1}
}
@media (max-width:734px){
  :root{--gutter:12px}
  .grid-2{grid-template-columns:1fr}
  .promo{min-height:0}
  .packages{grid-template-columns:1fr;max-width:420px}
  .packages li{padding:14px 16px}
  .fields{grid-template-columns:1fr}
  .channels{grid-template-columns:1fr}
  .web-shot .phone{width:28%;right:2%;border-width:3px;border-radius:12px}
  .web-shot .chrome span{display:none}
}
@media (max-width:400px){
  .btns .btn{flex:1 1 100%}
  .hero-copy .btns .btn{flex:1 1 100%}
  .foot-top{grid-template-columns:1fr}
}

/* ---------- motion and transparency preferences ---------- */
@media (prefers-reduced-motion:reduce){
  *,*::before,*::after{animation-duration:.01ms!important;animation-iteration-count:1!important;transition-duration:.01ms!important}
  .ex:hover .ex-img img{transform:none}
  .car-play{display:none!important}
  .crm-device{will-change:auto}
  .crm-play,.crm-cursor{display:none!important}
}
@media (prefers-reduced-transparency:reduce){
  .nav,.mnav{background:#fbfbfd;-webkit-backdrop-filter:none;backdrop-filter:none}
}
@media (prefers-contrast:more){
  .nav{background:#fff;border-bottom-color:#000}
  .small,.hero-facts,.privacy-line{color:var(--ink-2)}
}
@media print{.steps li > div{opacity:1!important;transform:none!important}.nav,.mnav,.hero-art,.car-ctl,.nc-launch{display:none!important}.tile{margin:0}.crm-scroll{height:auto!important}.crm-sticky{position:static!important}}

/* chat widget inherits the page face here */
.nc-root{font-family:var(--font)}

/* Toolkit founding price: set data-founding="false" on the Toolkit tile after the 10th sale (same switch as the live site). */
[data-founding="true"] .std,[data-founding="false"] .fnd{display:none}

/* First viewport on short landscape phones and very narrow screens: keep the facts clear of the fixed chat button */
@media (max-height:500px) and (orientation:landscape){.hero-facts{padding-right:76px;padding-left:76px}}
@media (max-width:420px){.hero-facts{flex-direction:column;align-items:flex-start;width:max-content;max-width:100%;margin-left:auto;margin-right:auto}}

/* ---------- round 12: restored sections and How we work ----------
   Quiet, type-led blocks in the existing system: grey kicker, Inter Display headline, hairline grids, mist/white cards.
   No new colours; Apple-blue only on links and buttons. Static (no reveal motion), so nothing shifts while loading. */
.kicker{font-size:17px;font-weight:600;letter-spacing:-.012em;color:var(--ink-3);margin-bottom:10px}
.problems{list-style:none;margin:clamp(40px,5vw,56px) auto 0;padding:0;display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:1px;
  background:var(--hair);border-top:1px solid var(--hair);border-bottom:1px solid var(--hair)}
.problems li{background:var(--mist);padding:24px 22px 26px}
.problems .pb-n{display:block;font-size:13px;font-weight:600;font-variant-numeric:tabular-nums;color:var(--ink-3);letter-spacing:.02em}
.problems h3{margin-top:10px;font-size:19px;line-height:1.26;letter-spacing:-.015em}
.problems p{margin-top:8px;font-size:15px;line-height:1.47;color:var(--ink-2)}

.systems{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:var(--gutter);margin-top:clamp(40px,5vw,56px)}
.sys{background:var(--mist);border-radius:22px;padding:clamp(24px,2.6vw,32px);display:flex;flex-direction:column;text-align:left}
.sys-top{display:flex;align-items:center;justify-content:space-between;gap:10px}
.sys-ind{font-size:14px;font-weight:600;color:var(--ink-3)}
.sys h3{margin-top:14px;font-size:clamp(21px,2vw,24px);line-height:1.17;letter-spacing:-.018em}
.sys-d{margin-top:8px;font-size:15px;line-height:1.47;color:var(--ink-2)}
.sys dl{margin:18px 0 0;border-top:1px solid var(--hair)}
.sys dt{margin-top:12px;font-size:14px;font-weight:600;color:var(--ink)}
.sys dd{margin:2px 0 0;font-size:14px;line-height:1.43;color:var(--ink-2)}
.sys-for{margin-top:18px;padding-top:14px;border-top:1px solid var(--hair);font-size:14px;line-height:1.43;color:var(--ink-2)}
.sys-for b{display:block;font-weight:600;color:var(--ink);margin-bottom:2px}
.sys .more{margin-top:auto;padding-top:14px;font-size:15px}

.doors{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:var(--gutter);margin-top:clamp(44px,5.5vw,64px)}
.door{background:#fff;border-radius:22px;padding:clamp(24px,3vw,36px);text-align:left}
.door h3{font-size:clamp(21px,2vw,24px);line-height:1.17;letter-spacing:-.018em}
.door p{margin-top:8px;font-size:15px;line-height:1.47;color:var(--ink-2);max-width:44ch}
.door-links{list-style:none;padding:0;margin:12px 0 0}
.door .more{font-size:15px}
.door .btns{margin-top:18px}

@media (max-width:1068px){
  .systems{grid-template-columns:1fr;max-width:640px;margin-left:auto;margin-right:auto}
}
@media (max-width:900px){
  .problems{grid-template-columns:repeat(2,minmax(0,1fr))}
}
@media (max-width:734px){
  .problems{grid-template-columns:1fr;max-width:520px}
  .problems li{padding:18px 4px 20px}
  .doors{grid-template-columns:1fr}
}
@media (max-width:400px){
  .door .btns .btn{flex:1 1 100%}
}
