/* =========================================================================
   FLOW — Enterprise operating system for AI
   styles.css

   Table of contents
   1.  Self-hosted fonts (@font-face)
   2.  Design tokens (custom properties)
   3.  Reset & base
   4.  Keyframe animations
   5.  Layout helpers
   6.  Site header / navigation
   7.  Hero
   8.  Ocean column (shared zone chrome)
   9.  Trust strip + statement
   10. Feature blocks (4)
   11. Architecture layers
   12. Live console
   13. Capabilities explorer (pick-list + detail panel)
   14. Why Flow (comparison) + Employees grid
   15. How it works (wire diagram)
   15b. About Indnord
   16. FAQ
   17. Final CTA
   18. Contact
   19. Footer
   20. Marine snow particles
   21. Responsive — tablet (<=860px)
   22. Responsive — mobile (<=720px)
   23. Responsive — small phones (<=520px)
   ========================================================================= */


/* =========================================================================
   1. SELF-HOSTED FONTS
   Subsetted woff2 files live in /assets/fonts. unicode-range lets the
   browser fetch only the subset a glyph actually needs.
   ========================================================================= */

/* IBM Plex Mono — 400 */
@font-face {
  font-family: 'IBM Plex Mono';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/ibm-plex-mono-400-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'IBM Plex Mono';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/ibm-plex-mono-400-latin.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;
}
/* IBM Plex Mono — 500 */
@font-face {
  font-family: 'IBM Plex Mono';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url('assets/fonts/ibm-plex-mono-500-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'IBM Plex Mono';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url('assets/fonts/ibm-plex-mono-500-latin.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;
}

/* Instrument Sans — variable weight 400..600, single file per subset */
@font-face {
  font-family: 'Instrument Sans';
  font-style: normal;
  font-weight: 400 600;
  font-stretch: 100%;
  font-display: swap;
  src: url('assets/fonts/instrument-sans-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Instrument Sans';
  font-style: normal;
  font-weight: 400 600;
  font-stretch: 100%;
  font-display: swap;
  src: url('assets/fonts/instrument-sans-latin.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;
}

/* Instrument Serif — italic 400 */
@font-face {
  font-family: 'Instrument Serif';
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/instrument-serif-italic-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Instrument Serif';
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/instrument-serif-italic-latin.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;
}
/* Instrument Serif — normal 400 */
@font-face {
  font-family: 'Instrument Serif';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/instrument-serif-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Instrument Serif';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('assets/fonts/instrument-serif-latin.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;
}

/* Schibsted Grotesk — variable weight 400..800, single file per subset */
@font-face {
  font-family: 'Schibsted Grotesk';
  font-style: normal;
  font-weight: 400 800;
  font-display: swap;
  src: url('assets/fonts/schibsted-grotesk-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Schibsted Grotesk';
  font-style: normal;
  font-weight: 400 800;
  font-display: swap;
  src: url('assets/fonts/schibsted-grotesk-latin.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;
}

/* Dancing Script — the cursive brand wordmark, latin subset only (the logo is
   just "Flow"). Self-hosted like every other face here; no CDN at runtime. */
@font-face {
  font-family: 'Dancing Script';
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url('assets/fonts/dancing-script-700-latin.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;
}


/* =========================================================================
   2. DESIGN TOKENS
   ========================================================================= */
:root {
  /* families */
  --font-sans:  'Instrument Sans', system-ui, sans-serif;
  --font-serif: 'Instrument Serif', Georgia, serif;
  --font-grotesk: 'Schibsted Grotesk', sans-serif;
  --font-mono:  'IBM Plex Mono', monospace;
  --font-brand: 'Dancing Script', cursive;

  /* core palette */
  --bg:            #04121f;
  --red:           #E15451;
  --cyan:          #7FE9F0;
  --cyan-dim:      #5FC7DA;
  --sky:           #8FD8E6;
  --steel:         #6FB6C8;
  --ok:            #7FE9C0;
  --warn:          #E6C575;

  /* text */
  --text:          #EAF3F6;
  --text-soft:     #DCEBF0;
  --text-mut:      #9FC0CC;
  --text-head:     #ECF6F9;
  --text-faint:    #6E8A97;

  /* layout — wider container so content hugs the sides on large screens
     instead of leaving big empty margins (was 1240px). */
  --maxw:          1440px;
  --gutter:        32px;
}


/* =========================================================================
   3. RESET & BASE
   ========================================================================= */
* { margin: 0; padding: 0; box-sizing: border-box; }

html {
  scroll-behavior: smooth;
  /* Chrome's scroll anchoring compensates for the data-reveal translateY as
     sections animate in during an anchor scroll, dragging the landing ~22px
     short. Layout is kept stable by other means (realizeZones in app.js), so
     anchoring has nothing legitimate to correct here. */
  overflow-anchor: none;
  /* Every in-page nav link lands 90px from the top so the fixed 72px header
     never covers the section heading. Set once on the scroll container so all
     anchors (#platform, #why-flow, #employees, #how, #faq, #contact) share the
     same offset — don't re-declare scroll-margin-top per section. */
  scroll-padding-top: 90px;
  height: auto;
  min-height: 100%;
  overflow-x: hidden;
  -webkit-text-size-adjust: 100%;
  /* Dark UI surfaces (scrollbars, the email input, form focus rings) across all
     engines — pairs with the color-scheme meta for pre-CSS paint. */
  color-scheme: dark;
}

body {
  min-height: 100vh;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font-sans);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  overflow-x: hidden;
}

a { color: #CFE7EC; text-decoration: none; }
a:hover { color: var(--cyan); }
::selection { background: #0E7C8B; color: #fff; }
input, button { font-family: inherit; }
img { display: block; max-width: 100%; }
h1, h2, h3 { font-weight: 400; }

/* Scroll-reveal: only hide when JS is available (html.js), so the page
   degrades gracefully to fully-visible without scripting. JS adds .is-visible. */
.js [data-reveal] {
  opacity: 0;
  transform: translateY(22px);
  transition: opacity .7s ease, transform .7s ease;
}
.js [data-reveal].is-visible { opacity: 1; transform: none; }


/* =========================================================================
   4. KEYFRAME ANIMATIONS
   ========================================================================= */
@keyframes osaaiPulse   { 0%,100% { opacity: 1; }   50% { opacity: .35; } }
@keyframes marineDrift  { 0% { transform: translate(0,0); } 25% { transform: translate(7px,12px); } 50% { transform: translate(-5px,22px); } 75% { transform: translate(6px,10px); } 100% { transform: translate(0,0); } }
@keyframes marineTwinkle{ 0%,100% { opacity: .12; } 50% { opacity: .6; } }


/* =========================================================================
   5. LAYOUT HELPERS
   ========================================================================= */
.container {
  max-width: var(--maxw);
  margin: 0 auto;
  padding: 0 var(--gutter);
  width: 100%;
}
.eyebrow {
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: .16em;
  text-transform: uppercase;
  color: var(--cyan-dim);
}
.section-title {
  margin-top: 20px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2rem, 4.4vw, 3.3rem);
  line-height: 1.06;
  letter-spacing: -.03em;
  color: var(--text-head);
}


/* =========================================================================
   6. SITE HEADER / NAVIGATION
   ========================================================================= */
.site-header {
  position: fixed;
  top: 0; left: 0; right: 0;
  z-index: 50;
  background: transparent;
  border-bottom: 1px solid rgba(255,255,255,0);
  transition: background .3s ease, border-color .3s ease;
}
.site-header.is-scrolled {
  background: rgba(4,18,31,.95);
  border-bottom: 1px solid rgba(127,233,240,.1);
}
.site-header__inner {
  max-width: var(--maxw);
  margin: 0 auto;
  padding: 0 var(--gutter);
  height: 72px;
  display: flex;
  align-items: center;
  justify-content: space-between;
}
/* The wordmark is live text set in the cursive brand face (Dancing Script). It's
   sized large to read as a logo, and line-height:1 keeps its tall ascenders and
   descenders from bloating the 72px nav row. `cursive` is the load fallback. */
.site-logo {
  font-family: var(--font-brand);
  font-weight: 700;
  font-size: 52px;
  line-height: 1;
  color: var(--red);
}
.site-nav {
  display: flex;
  align-items: center;
  /* Six links at the full 38px gap overflow the 72px row and wrap between the
     tablet breakpoint and roughly 1100px, colliding with the wordmark. The gap
     closes over that band only — it reaches its designed 38px by 1100px and
     holds there, so wide screens are untouched. `white-space` keeps the two-word
     labels on one line while the gap tightens. */
  gap: clamp(14px, 38px - (1100px - 100vw) * 0.12, 38px);
}
.site-nav a { white-space: nowrap; }
.site-nav a {
  font-size: 14.5px;
  font-weight: 500;
  color: var(--text-soft);
}
.site-header.is-scrolled .site-nav a { color: #AEC9D2; }
.site-nav a:hover { color: var(--cyan); }
.header-actions {
  display: flex;
  align-items: center;
  gap: 22px;
}
.btn-demo {
  display: inline-flex;
  align-items: center;
  height: 40px;
  padding: 0 20px;
  color: #fff;
  border-radius: 6px;
  font-weight: 600;
  font-size: 14px;
  letter-spacing: .01em;
  background-color: var(--red);
}
.btn-demo:hover { color: #fff; }

/* Hamburger toggle — hidden on desktop, shown on phones */
.nav-toggle {
  display: none;
  flex-direction: column;
  justify-content: center;
  gap: 5px;
  width: 42px;
  height: 42px;
  padding: 0;
  background: none;
  border: 1px solid rgba(127,233,240,.28);
  border-radius: 8px;
  cursor: pointer;
}
.nav-toggle span {
  display: block;
  width: 20px;
  height: 2px;
  margin: 0 auto;
  background: #EAF3F6;
  transition: transform .3s ease, opacity .3s ease;
}


/* =========================================================================
   7. HERO
   ========================================================================= */
.hero {
  position: relative;
  min-height: 100vh;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  background-color: #241A10;
}
.hero__bg {
  position: absolute;
  inset: 0;
  z-index: 0;
  overflow: hidden;
}
.hero__bg-inner {
  position: absolute;
  inset: 0;
  transform: translateX(11%) translateY(8%) scale(1.24);
  transform-origin: center;
}
.hero__img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  filter: saturate(1.08) contrast(1.04) brightness(0.92);
}
/* two hero overlays */
.hero__overlay-side {
  position: absolute;
  inset: 0;
  z-index: 1;
  pointer-events: none;
  background: linear-gradient(102deg, rgba(9,13,16,.82) 0%, rgba(9,13,16,.66) 24%, rgba(9,13,16,.32) 50%, rgba(9,13,16,.06) 74%, rgba(9,13,16,0) 100%);
}
.hero__overlay-bottom {
  position: absolute;
  inset: 0;
  z-index: 1;
  pointer-events: none;
  background: linear-gradient(to top, #0a2036 0%, rgba(10,32,54,0) 34%);
}

/* iceberg metaphor annotations */
.hero-annote {
  display: block;
  position: absolute;
  z-index: 2;
  top: 120px;
  bottom: 0;
  right: 56px;
  width: 300px;
  pointer-events: none;
  text-align: right;
  height: 900px;
}
.annote-tip  { position: absolute; top: 14px;  right: 0; width: 100%; }
.annote-deep { position: absolute; top: 220px; right: 0; width: 100%; }
.annote-kicker {
  font-family: var(--font-grotesk);
  font-size: 15px;
  letter-spacing: .22em;
  text-transform: uppercase;
  text-shadow: 0 1px 3px rgba(2,12,22,.95);
  font-weight: 700;
}
.annote-kicker.is-visible-tip  { color: var(--sky); }
.annote-kicker.is-hidden-deep  { color: var(--red); }
.annote-lead {
  margin-top: 7px;
  font-family: var(--font-serif);
  font-style: italic;
  font-size: 1.5rem;
  line-height: 1.15;
  color: #fff;
  text-shadow: 0 1px 3px rgba(2,12,22,.95), 0 3px 16px rgba(2,12,22,.85);
}
.annote-tip .annote-body {
  margin-top: 4px;
  font-size: 13.5px;
  color: #E4F1F5;
  text-shadow: 0 1px 3px rgba(2,12,22,.95), 0 2px 10px rgba(2,12,22,.8);
}
.annote-deep .annote-body {
  margin-top: 6px;
  font-size: 13.5px;
  line-height: 1.5;
  color: #E4F1F5;
  text-shadow: 0 1px 3px rgba(2,12,22,.95), 0 2px 10px rgba(2,12,22,.8);
}

/* hero content column
   The column is bottom-aligned, so it used to be the proof band that held the
   copy up off the foot of the viewport. That band now lives down by the
   architecture section, so the padding stands in for it and keeps the headline
   at the same height it has always sat at. */
.hero__content {
  position: relative;
  z-index: 2;
  max-width: var(--maxw);
  margin: 0 auto;
  width: 100%;
  padding: 0 var(--gutter) 317px;
  pointer-events: none;
}
.hero__copy { max-width: 720px; padding-top: 200px; }
.hero__eyebrow-row {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 30px;
}
.hero__eyebrow-dash {
  display: block;
  width: 34px;
  height: 1.5px;
  background-color: var(--red);
}
.hero__eyebrow-text {
  font-family: var(--font-grotesk);
  font-size: 15px;
  font-weight: 700;
  color: var(--sky);
  text-shadow: 0 1px 3px rgba(0,0,0,.15);
  letter-spacing: 0;
}
.hero__title {
  font-family: var(--font-grotesk);
  font-weight: 600;
  color: #fff;
  font-size: clamp(2.6rem, 6vw, 5.1rem);
  line-height: 1.02;
  letter-spacing: -.03em;
  text-wrap: balance;
}
/* "People & AI" reads in the same grotesk face as the rest of the headline —
   the colour accents stay, but no serif/italic emphasis. */
.hero__title .serif-emph {
  font-family: var(--font-grotesk);
  font-style: normal;
  font-weight: 600;
}
.hero__title .word-people { color: #8FD8E6; font-weight: 600; }
.hero__title .word-amp {
  color: #FAFEFF;
  font-family: var(--font-grotesk);
  font-style: normal;
}
.hero__title .word-ai { color: var(--red); font-weight: 600; }
.hero__lead {
  margin-top: 26px;
  font-size: 16px;
  line-height: 1.5;
  color: var(--text);
  max-width: 540px;
}
/* `.hero__content` has `pointer-events: none` so the fixed-offset iceberg
   annotations underneath stay clickable. Re-enable pointer events on the CTA
   itself so it can actually be clicked. */
.hero__cta {
  pointer-events: auto;
  margin-top: 28px;
}


/* =========================================================================
   8. OCEAN COLUMN (twilight -> midnight -> abyss)
   ========================================================================= */
.ocean {
  position: relative;
  margin-top: -1px;
  background: linear-gradient(180deg, #0a2036 0%, #072338 9%, #04121f 34%, #03101b 50%, #020c16 68%, #01080f 100%);
}
.zone {
  position: relative;
  overflow: hidden;
  background: transparent;
}
/* Twilight opens on a full-height screen (see .zone__screen) that centres its
   own content, so the zone contributes no top padding of its own. */
.zone--twilight { padding: 0 0 116px; }
.zone--midnight { padding: 116px 0 116px; }
.zone--abyss    { padding: 116px 0 0; }

/* The statement is the first thing you reach after the hero and gets a screen of
   its own, but it's only ~220px of type — a full 100vh here left it stranded in
   dead air. Sized so it still reads as its own beat with the colour blocks just
   breaking the bottom edge, which gives the eye a reason to keep going.
   min-height (not height) so it still grows if the content outruns a short
   viewport instead of overlapping what follows. */
.zone__screen {
  min-height: 50vh;
  display: flex;
  flex-direction: column;
  justify-content: center;
  /* Once the statement grew past min-height the centring air vanished and it sat
     ~20px off both the hero and the cards. Padding holds that gap open whether
     the content is short enough to be centred or tall enough to set the height. */
  padding: 88px 0;
}

/* Scroll performance (esp. Firefox / non-Chromium): each of these zones layers
   a full-height ~4MP AVIF banner (CSS filter + gradient mask) over an animated
   particle field. Skip rendering + painting them while off-screen so scrolling
   doesn't pay for the filtered banner every frame. `contain-intrinsic-size:
   auto …` reserves scroll height (remembering the real size after first paint),
   so the scrollbar doesn't jump. Unsupported browsers ignore it and render as
   before. The abyss zone is intentionally excluded — its wire diagram is drawn
   from live geometry and must stay measurable. */
.zone--twilight,
.zone--midnight {
  content-visibility: auto;
}
/* Reserve close-to-real heights while skipped (`auto` then remembers the exact
   size after first paint). A shared low-ball estimate (1200px) shifted every
   anchor target below by thousands of px when a zone first rendered mid-scroll,
   which is what made nav clicks land short. */
.zone--twilight { contain-intrinsic-size: auto 3970px; }
.zone--midnight { contain-intrinsic-size: auto 1320px; }

/* per-zone image banners
   Rendered as <img decoding="async"> so the ~4MP AVIFs decode off the main
   thread and never stall the scroll when they enter the viewport. */
.zone__banner {
  position: absolute;
  inset: 0;
  z-index: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: center;
  pointer-events: none;
  /* Promote to its own layer so the expensive filter + mask rasterizes
     once into a texture instead of re-painting on every scroll frame. */
  transform: translateZ(0);
}
.zone__banner--twilight {
  object-position: center 96%;
  filter: brightness(1.32) contrast(1.05) saturate(1.1);
  -webkit-mask-image: linear-gradient(180deg, transparent 0%, transparent 40%, #000 60%, #000 88%, transparent 100%);
          mask-image: linear-gradient(180deg, transparent 0%, transparent 40%, #000 60%, #000 88%, transparent 100%);
}
.zone__banner--midnight {
  object-position: center 45%;
  filter: brightness(1.32) contrast(1.05) saturate(1.1);
  -webkit-mask-image: linear-gradient(180deg, transparent 0%, #000 16%, #000 86%, transparent 100%);
          mask-image: linear-gradient(180deg, transparent 0%, #000 16%, #000 86%, transparent 100%);
}
.zone__banner--abyss {
  top: auto;
  inset: auto 0 0 0;
  height: min(600px, 60vh);
  object-position: center 88%;
  filter: brightness(1.5) contrast(1.06) saturate(1.1);
  -webkit-mask-image: linear-gradient(180deg, transparent 0%, #000 78%, #000 100%);
          mask-image: linear-gradient(180deg, transparent 0%, #000 78%, #000 100%);
}
/* per-zone tint overlays */
.zone__tint { position: absolute; inset: 0; z-index: 1; pointer-events: none; }
.zone__tint--twilight { background: linear-gradient(180deg, rgba(7,20,34,0) 0%, rgba(7,20,34,.34) 42%, rgba(6,20,34,.42) 66%, rgba(4,18,31,.1) 100%); }
.zone__tint--midnight { background: linear-gradient(180deg, rgba(4,18,31,0) 0%, rgba(3,14,24,.38) 40%, rgba(2,12,22,.44) 66%, rgba(2,12,22,.12) 100%); }
.zone__tint--abyss    { background: radial-gradient(90% 44% at 50% 100%, rgba(23,120,150,.16), rgba(1,8,15,0) 70%); }

.zone__inner {
  position: relative;
  z-index: 2;
  max-width: var(--maxw);
  margin: 0 auto;
  padding: 0 var(--gutter);
}
.zone--abyss .zone__inner { position: relative; z-index: 2; max-width: none; padding: 0; }


/* =========================================================================
   9. PROOF BAND (STATS + TRUST STRIP) + STATEMENT
   ========================================================================= */
/* The numbers and the logos they refer to are one claim, so they share a single
   bar: "100+" opens it, the marks run through the middle, "7 frameworks" closes
   it. These stats began life in the hero and kept the `hero__` prefix long after
   they left it — they're named for where they live now. */
.proof { margin-top: 120px; }
/* flex-shrink: 0 so the numbers keep their line and it's the logo run between
   them that gives up width first. */
.proof__stat {
  flex-shrink: 0;
  text-align: center;
}
.proof__stat-big {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: clamp(1.6rem, 2.4vw, 2.1rem);
  color: #fff;
  letter-spacing: -.02em;
}
.proof__stat-label {
  margin-top: 6px;
  font-size: 13.5px;
  color: #9FC0CC;
  line-height: 1.35;
}

.trust-strip {
  display: flex;
  align-items: center;
  gap: 40px;
  flex-wrap: wrap;
  padding: 20px 26px;
  border: 1px solid rgba(127,233,240,.14);
  border-radius: 14px;
  background: rgba(6,24,40,.45);
  -webkit-backdrop-filter: blur(6px);
          backdrop-filter: blur(6px);
}
.trust-strip__list {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 24px 40px;
  flex-wrap: wrap;
  flex: 1;
  padding: 0 8px;
}
.trust-strip__logo {
  height: 42px;
  width: auto;
  object-fit: contain;
  opacity: .88;
  transition: opacity .2s ease;
}
.trust-strip__logo:hover { opacity: 1; }
/* Logos shipped as their own rounded tiles (LangGraph, LangChain) carry a bit
   of built-in padding — give them a touch more height so the mark inside
   matches the free-standing marks visually. */
.trust-strip__logo--tile { height: 48px; }
/* The OpenAI mark is solid black on transparent — invert it to white so it
   reads on the dark twilight panel like the other marks. */
.trust-strip__logo--openai { filter: invert(1); }

/* Number / logos / number needs ~904px of content width to hold one line. Below
   that the logo run is the flex item that gives, and it collapses into a tall
   vertical column with the closing number stranded beside it — so stack the three
   parts instead. This breakpoint is the component's own min width, not a device
   tier, which is why it sits here rather than with the tablet rules in §21. */
@media (max-width: 960px) {
  .trust-strip {
    flex-direction: column;
    gap: 22px;
  }
  .proof__stat { width: 100%; }
  .trust-strip__list {
    width: 100%;
    justify-content: center;
    gap: 20px 32px;
  }
}

/* No top margin: the statement is centred by .zone__screen, so any margin here
   only pushes it off-centre and widens the gap under the hero. */
/* 900 not 840: the full form sets one line at ~837px, which left almost no slack
   before a lone "Workforce" dropped to a second line under a fallback font. The
   body copy has its own narrower measure, so this only buys the title room. */
.statement {
  max-width: 1120px;
  margin: 0 auto;
  text-align: center;
}
.statement__title {
  margin-top: 22px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2.4rem, 5.2vw, 4rem);
  line-height: 1.06;
  letter-spacing: -.01em;
  text-wrap: balance;
  color: var(--text-head);
}
.statement__title .flow-cap { color: var(--red); font-weight: 700; }
/* Several paragraphs, not the single line this used to hold. A wide measure lets
   the lead sit on one line; a tighter top margin keeps the beats close together
   without merging into a single grey slab. */
.statement__body {
  margin-top: 16px;
  font-size: 1.12rem;
  line-height: 1.65;
  color: var(--text-mut);
  max-width: 1040px;
  margin-left: auto;
  margin-right: auto;
}
/* The opening line states the category the rest of the section explains, so it
   sits a step above the supporting paragraphs. */
.statement__body--lead { font-size: 1.25rem; }


/* =========================================================================
   10. FEATURE BLOCKS (4)
   ========================================================================= */
.blocks {
  /* The statement's screen already ends in centring air, so this margin stacks
     on top of it — kept modest so the two don't compound into a big gap. */
  margin-top: 40px;
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 20px;
}
.block {
  position: relative;
  display: flex;
  flex-direction: column;
  min-height: 420px;
  padding: 32px 28px;
  border-radius: 16px;
  overflow: hidden;
  color: #fff;
  box-shadow: 0 30px 70px -46px rgba(0,0,0,.8);
  transition: opacity .7s ease, transform .7s ease, box-shadow .3s ease;
}
.block:hover {
  color: #fff;
  transform: translateY(-4px);
  box-shadow: 0 40px 90px -40px rgba(23,162,184,.4);
}
.block[data-reveal].is-visible:hover { transform: translateY(-4px); }
/* A light-to-dark ramp read left to right. The two endpoints are the original
   three-card palette's brightest and darkest; --3 was inserted between them so
   the fourth card extends the ramp instead of restating it. */
.block--1 { background: linear-gradient(158deg, #17A2B8, #0E7C8B); }
.block--2 { background: linear-gradient(158deg, #0E8FA6, #0A5666); }
.block--3 { background: linear-gradient(158deg, #0C5566, #06323D); }
.block--4 { background: linear-gradient(158deg, #0B3A47, #052730); }
.block__title {
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: 1.5rem;
  line-height: 1.14;
  letter-spacing: -.01em;
  max-width: 96%;
}
.block__icon-wrap {
  flex: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 24px 0;
}
.block__icon { width: 104px; height: 104px; position: relative; }
/* Card icons are external PNGs (512×512 black line art on a white ground).
   `invert(1)` flips the artwork to white and `mix-blend-mode: screen` drops
   the white background against the teal gradient, so the icons read as clean
   white line art on the card. All four use plain white for visual
   consistency (card 4's old inline SVG used the teal accent stroke). */
.block__img {
  width: 100%;
  height: 100%;
  object-fit: contain;
  display: block;
  filter: invert(1);
  mix-blend-mode: screen;
}
.block__sub {
  font-size: 15px;
  line-height: 1.5;
  max-width: 100%;
}
.block--1 .block__sub { color: rgba(255,255,255,.82); }
.block--2 .block__sub { color: rgba(255,255,255,.86); }
.block--3 .block__sub { color: rgba(255,255,255,.82); }
.block--4 .block__sub { color: rgba(220,235,240,.78); }

/* Four cards need ~1180px before the serif titles start breaking into slivers.
   Like the trust strip's 960px rule, this is the component's own min width
   rather than a device tier, so it lives with the component. Below the tablet
   breakpoint §21 takes over and drops these to a single column. */
@media (max-width: 1180px) {
  .blocks { grid-template-columns: repeat(2, 1fr); }
}


/* =========================================================================
   11. ARCHITECTURE LAYERS
   ========================================================================= */
.architecture { margin-top: 140px; }
.architecture__head {
  max-width: 760px;
  margin: 0 auto;
  text-align: center;
}
.architecture__title {
  margin-top: 20px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2rem, 4.4vw, 3.3rem);
  line-height: 1.06;
  letter-spacing: -.03em;
  color: var(--text-head);
}
.architecture__title .flow-cap { color: var(--red); }
.arch-stack {
  margin-top: 64px;
  display: grid;
  grid-template-columns: 1fr;
  gap: 0;
  max-width: 820px;
  margin-left: auto;
  margin-right: auto;
}
.arch-layer {
  padding: 30px 34px;
  border-radius: 12px;
  -webkit-backdrop-filter: blur(4px);
          backdrop-filter: blur(4px);
}
.arch-layer--plain {
  background: rgba(255,255,255,.03);
  border: 1px solid rgba(255,255,255,.1);
}
.arch-layer--highlight {
  background: linear-gradient(120deg, rgba(23,162,184,.18), rgba(23,162,184,.05));
  border: 1px solid rgba(95,199,218,.42);
}
.arch-layer__row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 20px;
  flex-wrap: wrap;
}
.arch-layer__kicker {
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: .14em;
  text-transform: uppercase;
}
.arch-layer__title {
  margin-top: 8px;
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.4rem;
  letter-spacing: -.02em;
}
.arch-layer__meta {
  font-size: 14px;
  text-align: right;
  max-width: 340px;
}
.arch-layer--plain     .arch-layer__kicker { color: var(--steel); }
.arch-layer--plain     .arch-layer__title  { color: #EAF3F6; }
.arch-layer--plain     .arch-layer__meta   { color: #8FB0BB; }
.arch-layer--highlight .arch-layer__kicker { color: var(--cyan); }
.arch-layer--highlight .arch-layer__title  { color: #fff; }
.arch-layer--highlight .arch-layer__meta   { color: #CFE7EC; }
.arch-arrow {
  display: flex;
  justify-content: center;
  padding: 14px 0;
}
.arch-arrow span {
  font-family: var(--font-mono);
  color: #4F8497;
  font-size: 20px;
}


/* =========================================================================
   12. LIVE CONSOLE
   ========================================================================= */
.console__head { max-width: 760px; }
.console__head .section-title { text-wrap: balance; letter-spacing: -.03em; }
.console {
  margin-top: 52px;
  border-radius: 16px;
  overflow: hidden;
  background: rgba(6,22,36,.82);
  -webkit-backdrop-filter: blur(10px);
          backdrop-filter: blur(10px);
  box-shadow: 0 50px 110px -50px rgba(0,0,0,.9);
  border: 1px solid rgba(127,233,240,.16);
}
.console__bar {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 16px 22px;
  border-bottom: 1px solid rgba(255,255,255,.08);
}
.console__dot {
  width: 11px; height: 11px;
  border-radius: 50%;
  background: #2E4A54;
}
.console__path {
  margin-left: 14px;
  font-family: var(--font-mono);
  font-size: 12.5px;
  color: var(--steel);
}
.console__live {
  margin-left: auto;
  display: inline-flex;
  align-items: center;
  gap: 7px;
  font-family: var(--font-mono);
  font-size: 12px;
  color: var(--ok);
}
.console__live-dot {
  width: 7px; height: 7px;
  border-radius: 50%;
  background: var(--ok);
  animation: osaaiPulse 2s ease-in-out infinite;
}
.console__tabs {
  display: flex;
  gap: 8px;
  padding: 16px 22px;
  flex-wrap: wrap;
  border-bottom: 1px solid rgba(255,255,255,.06);
}
.console__tab {
  height: 36px;
  padding: 0 16px;
  border-radius: 7px;
  font-size: 13.5px;
  font-weight: 500;
  cursor: pointer;
  background: rgba(255,255,255,.05);
  color: #CFE4E9;
  border: 1px solid rgba(255,255,255,.12);
  transition: background .2s ease, color .2s ease, border-color .2s ease;
}
.console__tab.is-active {
  background: #0E7C8B;
  color: #fff;
  border-color: #0E7C8B;
}
.console__rows { padding: 10px 12px 18px; }
.console-row {
  display: flex;
  align-items: center;
  gap: 16px;
  padding: 16px;
  border-radius: 10px;
  transition: background .2s ease;
}
.console-row:hover { background: rgba(255,255,255,.03); }
.console-row__dot {
  width: 9px; height: 9px;
  border-radius: 50%;
  flex-shrink: 0;
}
.console-row__main { flex: 1; min-width: 0; }
.console-row__title { font-weight: 600; font-size: 15px; color: #EAEFF1; }
.console-row__sub {
  margin-top: 3px;
  font-size: 13px;
  color: var(--steel);
  font-family: var(--font-mono);
}
.console-row__tag {
  flex-shrink: 0;
  padding: 5px 11px;
  border-radius: 20px;
  font-size: 12px;
  font-weight: 500;
}
/* status tones (shared by console + employees) */
.tone-ok   .console-row__dot,   .tone-ok-dot   { background: var(--ok); }
.tone-warn .console-row__dot,   .tone-warn-dot { background: var(--warn); }
.tag-ok   { background: rgba(127,233,192,.14); color: var(--ok); }
.tag-warn { background: rgba(230,197,117,.16); color: var(--warn); }


/* =========================================================================
   13. CAPABILITIES EXPLORER (pick-list + detail panel)
   Twelve capabilities as a narrow index on the left and one large detail
   panel on the right; app.js swaps which panel carries `.is-active` in
   response to hover/focus/click on the matching `.cap-pick__btn`.

   Base tones (`.cap--teal` / `--deep` / `--ink` / `--glass`) are reused on
   the detail panels — same gradients that the previous card grid used.
   ========================================================================= */
.capabilities { margin-top: 140px; }
.capabilities__head { max-width: 760px; }
.capabilities__head .section-title { text-wrap: balance; }

/* ---- Base (no-JS + small screens): plain card grid fallback ----
   The pick-list drives nothing without app.js, so we hide it and let every
   panel render as a card. That keeps the content usable and crawlable when
   JS is disabled, and — via the ≤860px override below — gives phones the
   same simple stack instead of a two-column split that would not fit. */
.cap-explorer { margin-top: 64px; }
/* The hint line lives beside the list, so hide the column rather than the
   list alone — otherwise "hover a capability" survives into the grid
   fallback, where there is nothing to hover. */
.cap-explorer__side { display: none; }
.cap-explorer__detail {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 22px;
}
.cap-detail {
  position: relative;
  overflow: hidden;
  padding: 32px 30px;
  min-height: 230px;
  border-radius: 16px;
  box-shadow: 0 24px 50px -34px rgba(0,0,0,.7);
  display: flex;
  flex-direction: column;
  /* Title first, description under it: the panel is read top-down, so the
     capability's name is the first thing the eye lands on. */
  justify-content: flex-start;
}

/* ---- JS-enabled desktop: two-column pick-list + sticky detail panel ----
   The `.js` class is added inline in <head> before first paint (see
   index.html), so the split appears without a flash of card-grid layout. */
.js .cap-explorer {
  display: grid;
  /* The list is deliberately narrow: it is an index, not a card wall. */
  grid-template-columns: minmax(260px, 340px) 1fr;
  gap: 48px;
  align-items: start;
}
.js .cap-explorer__side { display: block; }
.js .cap-pick {
  display: flex;
  flex-direction: column;
  gap: 6px;
  list-style: none;
}
/* The detail column sticks so hovering entries near the top of the list
   never leaves the panel scrolled off-screen. `top: 96px` clears the fixed
   site header. */
.js .cap-explorer__detail {
  display: block;
  position: sticky;
  top: 96px;
}
/* Only the active panel renders. A generous min-height keeps the sticky
   column the same size no matter which panel is showing, so swapping
   entries never nudges surrounding layout. */
.js .cap-detail { display: none; min-height: 420px; padding: 48px 52px; }
.js .cap-detail__icon { opacity: .2; }
.js .cap-detail.is-active { display: flex; animation: capDetailIn .26s ease both; }
@keyframes capDetailIn {
  from { opacity: 0; transform: translateY(8px); }
  to   { opacity: 1; transform: none; }
}
@media (prefers-reduced-motion: reduce) {
  .js .cap-detail.is-active { animation: none; }
}

/* ---- Pick-list buttons ---- */
.cap-pick__item { display: block; }
.cap-pick__btn {
  width: 100%;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 13px 16px;
  border: 1px solid rgba(127,233,240,.12);
  border-radius: 11px;
  background: rgba(255,255,255,.035);
  color: var(--text-mut);
  font-family: var(--font-grotesk);
  font-size: 14.5px;
  letter-spacing: -.005em;
  text-align: left;
  cursor: pointer;
  transition: background-color .18s ease, color .18s ease, border-color .18s ease, transform .18s ease;
}
.cap-pick__btn:hover  { color: var(--text-head); border-color: rgba(127,233,240,.28); }
.cap-pick__btn:focus-visible { outline: 2px solid var(--cyan); outline-offset: 2px; }
/* Active row adopts the teal accent so the list reads as a selection, and
   the arrow points at the panel it is driving. */
.cap-pick__btn.is-active {
  background: linear-gradient(158deg, #17A2B8, #0C6C7D);
  border-color: rgba(255,255,255,.14);
  color: #fff;
  transform: translateX(4px);
}
.cap-pick__arrow {
  font-size: 18px;
  line-height: 1;
  opacity: 0;
  transition: opacity .18s ease;
}
.cap-pick__btn.is-active .cap-pick__arrow { opacity: .9; }
@media (prefers-reduced-motion: reduce) {
  .cap-pick__btn,
  .cap-pick__arrow { transition: none; }
}
.cap-pick__hint {
  margin-top: 18px;
  font-family: var(--font-mono);
  font-size: 10.5px;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: rgba(159,192,204,.55);
}

/* ---- Detail panel ---- */
/* Bottom-right, out of the title's way now that the copy starts at the top. */
.cap-detail__icon {
  position: absolute;
  bottom: -8%;
  right: -4%;
  width: 58%;
  max-width: 380px;
  /* Faint by default: in the card grid the description runs across the
     watermark, and anything stronger competes with it. The roomier explorer
     panel lifts it again below. */
  opacity: .12;
  pointer-events: none;
}
.cap-detail__icon svg {
  width: 100%;
  height: auto;
  fill: none;
  stroke: currentColor;
  stroke-width: 4;
  stroke-linecap: round;
  stroke-linejoin: round;
}
.cap-detail__title {
  position: relative;
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: clamp(1.6rem, 3vw, 2.3rem);
  line-height: 1.1;
  letter-spacing: -.02em;
}
.cap-detail__body {
  position: relative;
  margin-top: 14px;
  max-width: 46ch;
  font-size: 16px;
  line-height: 1.55;
}

/* ---- Palette (shared with the old grid; body colour re-attached to the
   detail body element that replaced .cap__body) ---- */
.cap--teal  { background: linear-gradient(158deg, #17A2B8, #0C6C7D); color: #fff; border: 1px solid rgba(255,255,255,.06); }
.cap--deep  { background: linear-gradient(158deg, #0E7F94, #0A5061); color: #fff; border: 1px solid rgba(255,255,255,.06); }
.cap--ink   { background: linear-gradient(158deg, #0B3140, #06202b); color: #EAF3F6; border: 1px solid rgba(127,233,240,.12); }
.cap--glass { background: rgba(255,255,255,.045);                    color: #EAF3F6; border: 1px solid rgba(127,233,240,.12); }
.cap--teal  .cap-detail__body,
.cap--deep  .cap-detail__body { color: rgba(255,255,255,.82); }
.cap--ink   .cap-detail__body { color: rgba(220,235,240,.72); }
.cap--glass .cap-detail__body { color: #9DBAC6; }


/* =========================================================================
   14. WHY FLOW (comparison) + EMPLOYEES GRID
   ========================================================================= */
.whyflow { margin-bottom: 150px; }
/* Intro copy is centred and given a wide measure so lines like "…hire Digital
   Employees" don't break mid-phrase. The table below keeps its own left align. */
.whyflow__head {
  max-width: 960px;
  margin-inline: auto;
  text-align: center;
}
.whyflow__title {
  margin-top: 20px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2rem, 4.4vw, 3.3rem);
  line-height: 1.06;
  letter-spacing: -.03em;
  color: var(--text-head);
}
/* The emphasised word in the headline picks up the same serif italic the rest
   of the page uses for accents, in cyan rather than a heavier weight. */
.whyflow__title em { font-style: italic; color: var(--cyan); }

.whyflow__lede {
  margin-top: 28px;
  max-width: 960px;
  margin-inline: auto;
  display: flex;
  flex-direction: column;
  gap: 12px;
  font-size: 16px;
  line-height: 1.6;
  color: var(--text-mut);
  text-align: center;
}
/* "FLOW changes that." — the pivot line, lifted out of the muted body copy. */
.whyflow__turn {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.15rem;
  color: var(--text-head);
}

/* Comparison table. Desktop renders as a real two-column table; below the
   mobile breakpoint each row restacks into label/value pairs (see section 22). */
.compare {
  margin: 56px auto 0;
  max-width: 960px;
  border: 1px solid rgba(127,233,240,.12);
  border-radius: 12px;
  overflow: hidden;
  -webkit-backdrop-filter: blur(4px);
          backdrop-filter: blur(4px);
}
/* fixed layout so both columns are exactly half-width regardless of content. */
.compare__table {
  width: 100%;
  table-layout: fixed;
  border-collapse: collapse;
  font-size: 15px;
}
.compare__table th,
.compare__table td {
  width: 50%;
  padding: 18px 24px;
  text-align: center;
  vertical-align: top;
  line-height: 1.5;
}
.compare__table thead th {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.05rem;
  letter-spacing: -.01em;
  color: var(--text-head);
  background: rgba(255,255,255,.035);
}
.compare__table tbody td { color: var(--text-mut); border-top: 1px solid rgba(255,255,255,.07); }
/* The FLOW column is the payoff side: highlighted tint + brighter text, so the
   eye reads left-problem / right-answer without needing a caption. */
.compare__col--flow { color: var(--cyan) !important; }
.compare__table th.compare__col--flow,
.compare__table td:last-child {
  background: rgba(127,233,240,.05);
  border-left: 1px solid rgba(127,233,240,.12);
}
.compare__table td:last-child { color: var(--text-soft); }

/* "FLOW" and "Digital Employees" pick up the red brand accent, matching the
   header wordmark. */
.whyflow__brand { color: var(--red); }
.whyflow__close {
  margin-top: 40px;
  max-width: 900px;
  margin-inline: auto;
  text-align: center;
  font-family: var(--font-serif);
  font-size: clamp(1.25rem, 2.4vw, 1.75rem);
  line-height: 1.4;
  letter-spacing: -.01em;
  color: var(--text-head);
}


/* =========================================================================
   14b. EMPLOYEES GRID
   ========================================================================= */

.employees__head {
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  gap: 24px;
  flex-wrap: wrap;
  max-width: 100%;
}
.employees__head-copy { max-width: 640px; }
.employees__title {
  margin-top: 20px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2rem, 4.4vw, 3.3rem);
  line-height: 1.06;
  letter-spacing: -.03em;
  color: var(--text-head);
}
/* Shared: the "crossed-out word" device, used by the employees headline and the
   statement body. Scoped to nothing in particular so both can reach it. */
.strike {
  color: #5C7A86;
  text-decoration: line-through 2px rgba(95,199,218,.7);
}
.employees__viewall {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  font-weight: 600;
  font-size: 15px;
  color: #CFE7EC;
  white-space: nowrap;
}
.employees__viewall span { font-family: var(--font-mono); color: var(--cyan-dim); }
.emp-grid {
  margin-top: 56px;
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 20px;
}
.emp {
  background: rgba(255,255,255,.035);
  border: 1px solid rgba(127,233,240,.1);
  border-radius: 12px;
  padding: 28px 26px;
  display: flex;
  flex-direction: column;
  -webkit-backdrop-filter: blur(4px);
          backdrop-filter: blur(4px);
  transition: opacity .6s ease, transform .6s ease, border-color .3s ease;
}
.emp:hover { border-color: rgba(127,233,240,.34); }
.emp__status-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
}
.emp__status {
  padding: 4px 11px;
  border-radius: 20px;
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: .02em;
}
.emp__status--available { background: rgba(127,233,192,.16); color: var(--ok); }
.emp__status--dev       { background: rgba(230,197,117,.18); color: var(--warn); }
.emp__role {
  margin-top: 18px;
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.25rem;
  letter-spacing: -.01em;
  color: var(--text-head);
}
.emp__body {
  margin-top: 10px;
  font-size: 14.5px;
  line-height: 1.55;
  color: var(--text-mut);
  flex: 1;
}
.emp__connects {
  margin-top: 20px;
  padding-top: 16px;
  border-top: 1px solid rgba(255,255,255,.08);
  font-family: var(--font-mono);
  font-size: 12px;
  color: var(--text-faint);
}


/* =========================================================================
   15. HOW IT WORKS (wire diagram)
   ========================================================================= */
/* `.how` now opens the abyss zone (moved above #why-flow), so its top rhythm
   comes from the zone's own 116px padding — matching `.whyflow`, which also
   sits at margin-top: 0 as a zone-opener. */
.how { margin-top: 0; }
.how__head {
  text-align: center;
  /* Tightened from 96px: the demo below scales to fit one screen, so keep the
     heading close to it. */
  margin-bottom: 28px;
}
/* Stepper — five labels between the "How it works" heading and the demo
   iframe. Rendered as an <ol> so the counter reads to AT; a thin connector
   line runs behind the row, and each label carries a numbered dot rendered
   from `counter(step)`. app.js toggles `.is-active` on the pressed button
   in sync with the demo phase. */
.how-steps {
  list-style: none;
  counter-reset: step;
  margin: 28px 0 32px;
  padding: 0;
  display: flex;
  justify-content: center;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px 22px;
  position: relative;
}
/* Connector line sits behind the dots. Absolute so gaps between items don't
   collapse it. Same faint cyan as the other abyss-zone dividers. */
.how-steps::before {
  content: "";
  position: absolute;
  left: 8%;
  right: 8%;
  top: 50%;
  height: 1px;
  background: rgba(127,233,240,.18);
  z-index: 0;
  pointer-events: none;
}
.how-steps__item {
  counter-increment: step;
  position: relative;
  z-index: 1;
}
.how-steps__btn {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  background: transparent;
  border: 0;
  padding: 8px 12px;
  border-radius: 999px;
  font-family: var(--font-mono);
  font-size: 11.5px;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--text-faint);
  cursor: pointer;
  transition: color .15s ease, background-color .15s ease;
}
/* Numbered dot before each label. Uses the item's counter so DOM order and
   visible order stay in lockstep. Filled on the active step. */
.how-steps__btn::before {
  content: counter(step);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  border-radius: 50%;
  border: 1px solid rgba(127,233,240,.35);
  background: rgba(4,18,31,.85);
  color: var(--text-faint);
  font-family: var(--font-mono);
  font-size: 10.5px;
  letter-spacing: 0;
}
.how-steps__btn:hover { color: #fff; }
.how-steps__btn:focus-visible {
  outline: 2px solid var(--cyan);
  outline-offset: 2px;
}
.how-steps__btn.is-active { color: var(--cyan); }
.how-steps__btn.is-active::before {
  background: var(--cyan);
  color: #04121F;
  border-color: var(--cyan);
}
.how__title {
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2.2rem, 4.6vw, 3.4rem);
  line-height: 1.06;
  letter-spacing: -.01em;
  color: var(--text-head);
}
/* "See it in action" embed — the standalone flow-in-action.html loaded in an
   iframe so its animation stays byte-identical. app.js listens for a postMessage
   from the frame and sets its height, so there is no inner scrollbar. The
   860px start height only limits first-paint jump before JS sizes it. */
/* Neutral top margin: the stepper now sits between the heading and the demo,
   so the old -40px pull-up would drag the iframe over the stepper (that was
   the overlap reviewers flagged). Spacing above the iframe now comes from
   `.how-steps` margin below it. */
.fia-embed-wrap { margin-top: 0; }
.fia-embed {
  display: block;
  width: 100%;
  /* First-paint height mirrors app.js's budget (max(380, innerHeight - 130), and
     the demo never exceeds 860). Starting at a fixed 860px meant the frame shrank
     once the demo posted its real height, shifting the FAQ/CTA anchors below it
     mid-scroll. */
  height: clamp(380px, calc(100vh - 130px), 860px);
  border: 0;
  overflow: hidden;
  /* Matches the demo's default (light) base tone so the letterbox margins that
     appear when it scales down to fit the screen blend in. The demo re-tints
     its own <body> when switched to dark, so this only covers first paint. */
  background: #dcefef;
  color-scheme: light;
}

.wire {
  position: relative;
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: clamp(24px, 5vw, 72px);
  max-width: 1080px;
  margin: 0 auto;
}
.wire__svg {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  pointer-events: none;
  z-index: 0;
  overflow: visible;
}
.wire__col-title {
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: 1.7rem;
  margin-bottom: 24px;
  color: var(--text-head);
}
.wire__col-title--right { text-align: right; }
.wire__list {
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.wire-node {
  position: relative;
  z-index: 1;
  padding: 16px 20px;
  border: 1px solid rgba(127,233,240,.16);
  border-radius: 10px;
  font-family: var(--font-grotesk);
  font-weight: 500;
  font-size: 1.02rem;
  background: rgba(255,255,255,.03);
  color: var(--text-soft);
  transition: opacity .5s ease, transform .5s ease;
}
.wire-node.wire-right { text-align: right; }
.js .wire-node.wire-left  { opacity: 0; transform: translateX(-14px); }
.js .wire-node.wire-right { opacity: 0; transform: translateX(14px); }
.js .wire-node.wire-left.is-visible,
.js .wire-node.wire-right.is-visible { opacity: 1; transform: none; }
.wire__hub {
  position: relative;
  z-index: 2;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  width: clamp(150px, 20vw, 220px);
  height: clamp(150px, 20vw, 220px);
  border-radius: 50%;
  background: radial-gradient(circle at 50% 40%, rgba(23,162,184,.24), rgba(2,12,22,0) 68%);
  border: 1px solid rgba(95,199,218,.34);
  text-align: center;
  padding: 24px;
  box-shadow: 0 0 60px -10px rgba(23,162,184,.4);
  transition: opacity .8s ease;
}
.js .wire__hub { opacity: 0; }
.js .wire__hub.is-visible { opacity: 1; }
.wire__hub-orbit {
  position: absolute;
  inset: -56px;
  border-radius: 50%;
  border: 1.5px dashed rgba(225,84,81,.5);
  pointer-events: none;
}
.wire__hub-oversight {
  position: absolute;
  left: 50%;
  bottom: calc(100% - 2px);
  transform: translateX(-50%);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 5px;
  pointer-events: none;
  white-space: nowrap;
}
.wire__hub-oversight span {
  font-family: var(--font-mono);
  font-size: 10px;
  letter-spacing: .16em;
  text-transform: uppercase;
  color: #F0908D;
}
.wire__hub-kicker {
  font-family: var(--font-mono);
  font-size: 10.5px;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--cyan);
}
.wire__hub-name {
  margin-top: 10px;
  font-family: var(--font-serif);
  font-size: 1.5rem;
  line-height: 1.05;
  color: var(--red);
}
.wire__hub-tag {
  margin-top: 8px;
  font-size: 12px;
  color: #8FB0BB;
  line-height: 1.4;
}


/* =========================================================================
   15b. ABOUT INDNORD
   Numbered 15b rather than renumbering 16-23: this section landed between two
   existing ones, and shifting every number below it would churn the table of
   contents above, the table in README.md and every comment that cites one.
   ========================================================================= */
.about { margin-top: 150px; }
/* Same 960px centred measure as `.whyflow__head` / `.whyflow__lede`: this is the
   page's established treatment for a centred intro, and a narrower column here
   would read as a different kind of section rather than the same one. The card
   grid below deliberately keeps the full container width, exactly as
   `.cap-explorer` does. */
.about__head,
.about__lede,
.about__what,
.about__close {
  max-width: 960px;
  margin-inline: auto;
  text-align: center;
}
.about__lede {
  margin-top: 28px;
  display: flex;
  flex-direction: column;
  gap: 12px;
  font-size: 16px;
  line-height: 1.6;
  color: var(--text-mut);
}
/* The pivot line, lifted out of the muted body copy — same treatment as
   `.whyflow__turn`, which does the same job for "FLOW changes that." */
.about__turn {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.15rem;
  color: var(--text-head);
}
.about__what { margin-top: 64px; }
.about__what-title {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.15rem;
  letter-spacing: -.01em;
  color: var(--text-head);
}
.about__what-lede {
  margin-top: 12px;
  font-size: 16px;
  line-height: 1.6;
  color: var(--text-mut);
}
/* auto-fit rather than a fixed count: five items sit in one row on a wide
   screen and reflow to 3 / 2 / 1 on their own, so the shared breakpoint rules
   that collapse `.cap-explorer__detail` don't need a fifth special case. */
.about__grid {
  /* 64px above the cards, matching `.cap-explorer`, so the two card sections
     on the page breathe identically. */
  margin-top: 64px;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
  gap: 22px;
  list-style: none;
}
.about__card {
  padding: 28px 26px;
  border-radius: 16px;
  background: rgba(255,255,255,.045);
  border: 1px solid rgba(127,233,240,.12);
  color: #EAF3F6;
  text-align: left;
  box-shadow: 0 24px 50px -34px rgba(0,0,0,.7);
  transition: transform .3s ease, box-shadow .3s ease;
}
.about__card:hover {
  transform: translateY(-4px);
  box-shadow: 0 34px 64px -30px rgba(23,162,184,.34);
}
.about__card-title {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.15rem;
  letter-spacing: -.01em;
  color: var(--text-head);
}
.about__card-body {
  margin-top: 9px;
  font-size: 14px;
  line-height: 1.5;
  color: #9DBAC6;
}
.about__close {
  margin-top: 64px;
  display: flex;
  flex-direction: column;
  gap: 12px;
  font-size: 16px;
  line-height: 1.6;
  color: var(--text-mut);
}
/* Matches the serif italic the other section headlines use for emphasis. */
.about__close em { font-style: italic; color: var(--cyan); font-weight: 600; }
.about__motto {
  margin-top: 10px;
  font-family: var(--font-mono);
  font-size: 13px;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--cyan);
}


/* =========================================================================
   16. FAQ
   ========================================================================= */
.faq {
  margin-top: 150px;
  max-width: 900px;
  margin-left: auto;
  margin-right: auto;
}
.faq__head { margin-bottom: 48px; }
.faq__title {
  margin-top: 20px;
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2rem, 4.4vw, 3rem);
  line-height: 1.06;
  letter-spacing: -.03em;
  color: var(--text-head);
}
.faq__list { border-top: 1px solid rgba(255,255,255,.12); }
.faq-item { border-bottom: 1px solid rgba(255,255,255,.12); }
.faq-item__q {
  width: 100%;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 20px;
  padding: 26px 4px;
  background: none;
  border: none;
  cursor: pointer;
  text-align: left;
}
.faq-item__q-text {
  font-family: var(--font-grotesk);
  font-weight: 600;
  font-size: 1.2rem;
  letter-spacing: -.01em;
  color: var(--text-head);
}
.faq-item__icon {
  flex-shrink: 0;
  font-family: var(--font-mono);
  font-size: 22px;
  color: var(--cyan-dim);
  transition: transform .3s ease;
  transform: rotate(0deg);
}
.faq-item.is-open .faq-item__icon { transform: rotate(45deg); }
.faq-item__a {
  max-height: 0;
  overflow: hidden;
  transition: max-height .4s ease;
}
.faq-item.is-open .faq-item__a { max-height: 320px; }
.faq-item__a p {
  padding: 0 4px 28px;
  font-size: 1.02rem;
  line-height: 1.6;
  color: var(--text-mut);
  max-width: 680px;
}


/* =========================================================================
   17. FINAL CTA
   ========================================================================= */
.cta {
  margin-top: 40px;
  padding: 130px 0 120px;
  position: relative;
  background: transparent;
}
.cta__inner {
  max-width: 820px;
  margin: 0 auto;
  padding: 0 var(--gutter);
  text-align: center;
  position: relative;
  z-index: 1;
}
.cta__eyebrow-row {
  display: inline-flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 26px;
}
.cta__eyebrow-dash { display: block; width: 34px; height: 1.5px; background: #0E7C8B; }
.cta__eyebrow-text {
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--cyan);
}
.cta__title {
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: clamp(2.2rem, 5vw, 3.8rem);
  line-height: 1.04;
  letter-spacing: -.03em;
  text-wrap: balance;
  color: #fff;
}
.cta__title i { color: var(--red); font-style: italic; }
.cta__body {
  margin-top: 22px;
  font-size: 1.15rem;
  line-height: 1.55;
  color: #B7D3DB;
  max-width: 560px;
  margin-left: auto;
  margin-right: auto;
}
.cta__form {
  margin-top: 40px;
  display: flex;
  gap: 12px;
  max-width: 480px;
  margin-left: auto;
  margin-right: auto;
  flex-wrap: wrap;
  justify-content: center;
}
/* One control per row. The rows come from each child claiming a whole flex
   line, not from restyling the form — the 480px cap, the auto side margins and
   the wrap/centre behaviour above are what hold the CTA composition in place.
   `.cta__status` sets its own `flex-basis: 100%` further down. */
.cta__field,
.cta__fieldset,
.cta__submit { flex-basis: 100%; }
/* `.cta__inner` centres its text, which would turn a label sitting above a
   full-width field into a caption rather than a label. */
.cta__field { text-align: left; }
.cta__label {
  display: block;
  margin-bottom: 8px;
  font-family: var(--font-mono);
  font-size: 11px;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: #7F9AA6;
}
.cta__input {
  /* Explicit width rather than `flex: 1`: the inputs sit inside `.cta__field`
     wrappers now, so they are no longer flex items of the form and flex sizing
     on them would simply be ignored. */
  width: 100%;
  height: 52px;
  padding: 0 18px;
  border-radius: 8px;
  border: 1px solid rgba(127,233,240,.2);
  background: rgba(255,255,255,.05);
  color: #fff;
  font-size: 15px;
  outline: none;
}
.cta__input::placeholder { color: #7F9AA6; }
/* Borrows `.cta__input` for its chrome, so the fixed 52px height has to be
   undone or `rows="3"` would render as a one-line box. Resize is vertical only:
   dragging it wider would push it out of the 480px column. `font-family` is set
   here because the reset in §3 covers `input, button` but not `textarea`. */
.cta__textarea {
  height: auto;
  min-height: 96px;
  padding: 14px 18px;
  line-height: 1.5;
  font-family: inherit;
  resize: vertical;
}
/* Browsers give a fieldset a border and an intrinsic `min-width: min-content`
   that refuses to shrink — the latter would push the group past the column's
   480px. Padding and margin are already zeroed by the `*` reset in §3. */
.cta__fieldset {
  min-width: 0;
  border: 0;
  text-align: left;
}
/* <legend> ignores `display: flex` and has a padding model of its own, so it is
   left as a plain block with only its type set. Brighter than `.cta__label`
   because it is a question to answer, not a caption on a field. */
.cta__legend {
  margin-bottom: 12px;
  font-size: 15px;
  line-height: 1.4;
  color: #B7D3DB;
}
/* One column, though five options would fit in two: in two columns the right
   option's checkbox lands mid-row, where it reads as belonging to the label on
   its left. */
.cta__choices {
  display: flex;
  flex-direction: column;
  gap: 10px;
}
.cta__choice {
  display: flex;
  align-items: flex-start;
  gap: 10px;
}
.cta__checkbox {
  /* D3: keep the native control and only tint it — it arrives with keyboard,
     screen-reader, form-reset and High Contrast behaviour already correct. The
     unchecked box takes dark chrome from the page-level `color-scheme: dark`
     (§3), so it doesn't sit on this panel as a light square. */
  accent-color: var(--cyan);
  width: 17px;
  height: 17px;
  /* Aligns with the first line of the label, not the top of its box. */
  margin: 2px 0 0;
  flex: none;
  cursor: pointer;
}
.cta__choice-label {
  font-size: 15px;
  line-height: 1.4;
  color: #B7D3DB;
  cursor: pointer;
}
.cta__submit {
  height: 52px;
  padding: 0 28px;
  border: none;
  border-radius: 8px;
  background: #0E7C8B;
  color: #fff;
  font-weight: 600;
  font-size: 15px;
  cursor: pointer;
  white-space: nowrap;
}
.cta__submit:disabled { opacity: .6; cursor: default; }
.cta__input:disabled { opacity: .6; }
/* A successful submit disables the checkboxes too, so they have to dim with the
   rest — otherwise the one part of the form still looking live is the part the
   user is most likely to reread. */
.cta__checkbox:disabled { opacity: .6; cursor: default; }
.cta__checkbox:disabled + .cta__choice-label { opacity: .6; cursor: default; }
/* `:focus-visible` rather than `:focus`, so clicking a control with a mouse
   doesn't leave a ring behind it. The outline has to be restored explicitly
   because `.cta__input` clears it above; the textarea inherits this via that
   same class. */
.cta__input:focus-visible,
.cta__checkbox:focus-visible,
.cta__submit:focus-visible {
  outline: 2px solid var(--cyan);
  outline-offset: 2px;
}
/* Honeypot. Pulled out of the layout entirely rather than `display:none`, which
   some bots detect and skip; `aria-hidden` + `tabindex="-1"` on the element keep
   it away from assistive tech and the tab order. */
.cta__trap {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  border: 0;
  overflow: hidden;
  clip: rect(0 0 0 0);
  clip-path: inset(50%);
  white-space: nowrap;
}
/* Takes the full row under the input + button. Removed from the flex flow while
   empty so the CTA renders at its original height until there's something to
   say — an empty flex item would still contribute the 12px row gap. */
.cta__status {
  flex-basis: 100%;
  font-size: 14px;
  line-height: 1.4;
  color: var(--text-mut);
}
.cta__status:empty { display: none; }
.cta__status--ok    { color: var(--ok); }
.cta__status--error { color: var(--red); }

/* ---- CTA modal --------------------------------------------------------
   The form lives in a native <dialog> opened by `.cta__open`. Native for the
   same reason the checkboxes are (D3): showModal() arrives with the focus
   trap, Escape-to-close, background inerting and top-layer stacking already
   correct, and a hand-built overlay has to re-earn all four.

   `has-modal` is set by app.js only after it confirms showModal() exists. Until
   then — no JS, or a browser without <dialog> — the rules below unwind the
   dialog back into an ordinary block so the form still renders inline under the
   CTA copy, and the trigger button stays hidden rather than sitting there dead.
   ------------------------------------------------------------------------ */
html:not(.has-modal) .cta__open { display: none; }
html:not(.has-modal) .cta-modal {
  display: block;
  position: static;
  max-width: none;
  border: 0;
  padding: 0;
  background: none;
  color: inherit;
}
html:not(.has-modal) .cta-modal__close { display: none; }
html:not(.has-modal) .cta-modal__title { display: none; }
html:not(.has-modal) .cta-modal__panel { padding: 0; border: 0; background: none; }

.cta__open { margin-top: 40px; }

.cta-modal {
  width: 100%;
  max-width: 520px;
  padding: 0;
  border: 0;
  background: transparent;
  /* The UA centres a modal dialog with `margin: auto`; keep it and add the
     gutter so the panel never touches the edge on a small screen. */
  margin: auto;
  /* Six fields and a five-option group are taller than a short viewport — a
     laptop in landscape, or any phone once the keyboard is up. The dialog
     scrolls internally rather than letting the panel run off-screen, which it
     would do silently because the page behind it is scroll-locked. */
  max-height: calc(100vh - 32px);
  max-height: calc(100dvh - 32px);
  overflow-y: auto;
  overscroll-behavior: contain;
}
.cta-modal::backdrop {
  background: rgba(2, 12, 18, .74);
}
.cta-modal__panel {
  position: relative;
  padding: 34px 30px 30px;
  border-radius: 14px;
  border: 1px solid rgba(127,233,240,.18);
  /* Opaque, unlike the CTA section behind it: the panel sits over whatever the
     page had scrolled to, so it cannot borrow that as its background. */
  background: #071A24;
  box-shadow: 0 24px 60px rgba(0,0,0,.5);
}
.cta-modal__title {
  font-family: var(--font-serif);
  font-weight: 400;
  font-size: 1.8rem;
  line-height: 1.15;
  letter-spacing: -.02em;
  color: #fff;
  /* Clears the close button, which is absolutely positioned in the corner. */
  padding-right: 34px;
  text-align: left;
}
/* The form's own top margin is sized for the CTA section, not a panel. */
.cta-modal .cta__form { margin-top: 22px; }
.cta-modal__close {
  position: absolute;
  top: 14px;
  right: 14px;
  width: 34px;
  height: 34px;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: var(--text-mut);
  font-size: 22px;
  line-height: 1;
  cursor: pointer;
}
.cta-modal__close:hover { color: #fff; background: rgba(255,255,255,.06); }
.cta-modal__close:focus-visible {
  outline: 2px solid var(--cyan);
  outline-offset: 2px;
}
/* The page behind a modal must not scroll under it. Set by app.js on open. */
html.modal-open, body.modal-open { overflow: hidden; }


/* =========================================================================
   18. CONTACT
   ========================================================================= */
.contact { padding: 110px 0 120px; }
.contact__grid {
  max-width: var(--maxw);
  margin: 0 auto;
  padding: 0 var(--gutter);
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: clamp(40px, 6vw, 90px);
  align-items: start;
}
.contact__lead {
  margin-top: 22px;
  font-size: 1.08rem;
  line-height: 1.6;
  color: var(--text-mut);
  max-width: 440px;
}
.contact__rows {
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.contact-row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 24px;
  padding: 22px 0;
  border-top: 1px solid rgba(255,255,255,.12);
}
.contact-row__label {
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--text-faint);
}
.contact-row__value {
  font-family: var(--font-grotesk);
  font-weight: 500;
  font-size: 1.15rem;
  color: var(--text-head);
  letter-spacing: -.01em;
  text-align: right;
}


/* =========================================================================
   19. FOOTER
   ========================================================================= */
.site-footer {
  background: transparent;
  color: #fff;
  padding: 76px 0 44px;
  position: relative;
  overflow: hidden;
}
.site-footer__cols {
  display: grid;
  grid-template-columns: 1.6fr 1fr 1fr;
  gap: 40px;
}
/* Brand row reads "Flow by Indnord": the cursive Flow wordmark, a small "by",
   and the parent Indnord logo — so the footer credits Indnord as the maker. */
.site-footer__brand {
  display: flex;
  align-items: center;
  gap: 14px;
  font-family: var(--font-brand);
  font-weight: 700;
  font-size: 2.2rem;
  line-height: 1;
}
/* Match the header wordmark: the cursive brand face in red. */
.site-footer__wordmark { color: var(--red); }
/* The connective word takes the Indnord indigo, so it belongs to the mark it
   points at. #5A46DA is the indigo of "Ind" as the logo actually renders: the
   source art is #403393, and this is that colour after the
   brightness(1.4) saturate(1.1) applied to the logo below — a filter this text
   does not inherit, so the value is baked in here to match. Family and weight
   are inherited from `.site-footer__brand`; kept well under 2.2rem so the word
   still reads smaller than the two marks it joins. */
.site-footer__by {
  font-size: 1.25rem;
  color: #5A46DA;
}
/* The Indnord mark sits straight on the dark footer — no backdrop plate.
   Its wordmark runs indigo → blue → cyan with an orange swirl, and the indigo
   end is too dark to read at ~1.8:1 against this background, so the whole mark
   is lifted instead of being boxed. brightness(1.4) clears the darks without
   pushing the orange into yellow (1.7 does); the light saturate keeps the
   cyan end from washing out as it brightens. */
.site-footer__indnord {
  display: inline-flex;
  align-items: center;
  filter: brightness(1.4) saturate(1.1);
}
.site-footer__indnord img {
  height: 42px;
  width: auto;
  display: block;
}
.site-footer__about {
  margin-top: 16px;
  font-size: 14px;
  line-height: 1.6;
  color: var(--text-faint);
  max-width: 280px;
}
.footer-col__head {
  font-family: var(--font-mono);
  font-size: 11.5px;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: #4F6B78;
}
.footer-col__links {
  margin-top: 18px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}
.footer-col__links a { font-size: 14.5px; color: #AEC9D2; }
.footer-col__links a:hover { color: var(--cyan); }
.site-footer__bottom {
  margin-top: 56px;
  padding-top: 26px;
  border-top: 1px solid rgba(255,255,255,.09);
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 20px;
  flex-wrap: wrap;
}
.site-footer__copy { font-size: 13px; color: #4F6B78; }
.site-footer__legal {
  font-size: 13px;
  color: #4F6B78;
  font-family: var(--font-mono);
}


/* =========================================================================
   20. MARINE SNOW PARTICLES
   ========================================================================= */
.snow {
  position: absolute;
  inset: 0;
  z-index: 1;
  pointer-events: none;
  overflow: hidden;
  /* Isolate the animated particle field's paint from the rest of the zone. */
  contain: layout paint style;
}
.snow span {
  position: absolute;
  border-radius: 50%;
}


/* =========================================================================
   21. RESPONSIVE — TABLET (<=860px)
   Collapse the multi-column content grids while keeping the desktop
   composition (hero unchanged, cards simply reflow).
   ========================================================================= */
@media (max-width: 860px) {
  .blocks,
  .emp-grid { grid-template-columns: 1fr; }

  /* Capabilities: below tablet the two-column split falls back to a card
     grid — the pick-list is an index, and an index sitting above the thing
     it indexes is just repetition. Every panel is visible again so the
     content is browsable without hover/tap gating on a small screen. */
  .js .cap-explorer { display: block; }
  .js .cap-explorer__side { display: none; }
  .js .cap-explorer__detail {
    position: static;
    display: grid;
    grid-template-columns: 1fr;
  }
  /* Back to card proportions: the 420px/48px sizing exists for the sticky
     desktop panel and would leave each fallback card mostly empty space. */
  .js .cap-detail { display: flex; min-height: 230px; padding: 32px 30px; }
  .js .cap-detail__icon { opacity: .12; }

  /* Tablet tier: keep the card grids at two columns down to ~620px so the
     composition stays closer to desktop and the scroll doesn't get very long.
     (The big feature blocks stay single-column as full-width statements.) */
  @media (min-width: 620px) {
    .cap-explorer__detail,
    .js .cap-explorer__detail,
    .emp-grid { grid-template-columns: 1fr 1fr; }
  }

  .site-footer__cols { grid-template-columns: 1fr 1fr; gap: 28px; }

  /* how-it-works: KEEP the wired hub-and-spoke diagram (SVG connectors,
     flowing dots, orbit ring) — just scale it down so it fits. */
  .wire {
    gap: clamp(12px, 3.2vw, 44px);
    max-width: 560px;
  }
  .wire__hub {
    width: clamp(104px, 24vw, 150px);
    height: clamp(104px, 24vw, 150px);
    padding: 14px;
  }
  .wire__hub-orbit { inset: -22px; }
  .wire__hub-name { font-size: 1.15rem; }
  .wire__hub-tag  { font-size: 10px; }
  .wire-node {
    padding: 11px 12px;
    font-size: clamp(.82rem, 3.1vw, 1rem);
  }
  .wire__col-title,
  .wire__col-title--right { font-size: 1.25rem; margin-bottom: 18px; }

  /* ---- HERO (tablet): the fixed-offset annotation no longer lined up with
     the waterline here. Mirror the tuned mobile composition instead — drop the
     desktop zoom/pan transform so the whole iceberg frames centred, keep the
     headline in a left column, and anchor the annotations proportionally so the
     "visible 10% / hidden 90%" pair straddles the surface. (≤720px refines
     these further.) ---- */
  .hero__bg-inner { transform: none; }
  .hero__img { object-position: 50% 44%; }
  .hero__copy { padding-top: 124px; }
  .hero__eyebrow-row { max-width: 58%; align-items: flex-start; }
  .hero__title { max-width: 58%; }
  .hero__lead { max-width: 460px; }

  .hero-annote {
    top: 22%;
    right: 28px;
    bottom: auto;
    width: clamp(180px, 27vw, 240px);
    height: auto;
  }
  .annote-tip  { top: 0; }
  .annote-deep { top: 168px; }
  .annote-kicker { font-size: 11px; letter-spacing: .16em; }
  .annote-lead { font-size: 1.05rem; margin-top: 4px; }
  .annote-tip .annote-body,
  .annote-deep .annote-body { font-size: 11.5px; margin-top: 3px; line-height: 1.4; }

  /* nav: the five inline links no longer fit comfortably — collapse them
     into the tap-to-open dropdown menu from tablet down. */
  .nav-toggle { display: inline-flex; }
  .site-nav {
    position: absolute;
    top: 72px;
    left: 0;
    right: 0;
    display: none;
    flex-direction: column;
    align-items: stretch;
    gap: 0;
    padding: 6px var(--gutter) 14px;
    background: rgba(4,18,31,.97);
    border-bottom: 1px solid rgba(127,233,240,.12);
    -webkit-backdrop-filter: blur(8px);
            backdrop-filter: blur(8px);
  }
  .site-header.nav-open .site-nav { display: flex; }
  .site-nav a {
    padding: 15px 2px;
    font-size: 16px;
    border-bottom: 1px solid rgba(255,255,255,.06);
  }
  .site-nav a:last-child { border-bottom: none; }
  .site-header.nav-open .nav-toggle span:nth-child(1) { transform: translateY(7px) rotate(45deg); }
  .site-header.nav-open .nav-toggle span:nth-child(2) { opacity: 0; }
  .site-header.nav-open .nav-toggle span:nth-child(3) { transform: translateY(-7px) rotate(-45deg); }
}


/* =========================================================================
   22. RESPONSIVE — MOBILE (<=720px)
   Preserve the hero composition; tame oversized vertical rhythm and
   gutters so nothing overflows or clips.
   ========================================================================= */
@media (max-width: 720px) {
  :root { --gutter: 20px; }

  .site-logo { font-size: 40px; }

  /* The demo form used to be re-stacked here — one row of email + button at
     desktop, a column on phones. It now has a label, five checkboxes and a
     textarea, so every child claims a full flex line at every width (§17) and
     the overrides that used to live here (`flex-direction: column` on the form,
     and the `flex: none` that stopped `flex: 1` collapsing the field height in
     a column container) would only restate what §17 already does. Deleted
     rather than left contradicting it; the fields, fieldset and textarea are
     already full-width and stacked by the time this breakpoint applies, and
     nothing in the group needs narrowing further. */

  /* The panel keeps a gutter on both sides rather than going edge-to-edge:
     full-bleed would put the close button against the screen edge. */
  .cta-modal { max-width: calc(100vw - 32px); }
  .cta-modal__panel { padding: 30px 20px 24px; }
  .cta-modal__title { font-size: 1.5rem; }

  /* ---- COMPARISON TABLE: a two-column table is too wide for a phone, so
     restack each row into stacked cells. The header row is hidden and each
     cell prints its own label from data-label. ---- */
  .whyflow { margin-bottom: 110px; }
  .compare__table thead { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); }
  .compare__table,
  .compare__table tbody,
  .compare__table tr,
  .compare__table td { display: block; width: 100%; }
  .compare__table tr { border-top: 1px solid rgba(255,255,255,.08); }
  .compare__table tr:first-child { border-top: 0; }
  .compare__table td { width: 100%; border-top: 0; padding: 14px 20px; text-align: left; }
  .compare__table td:last-child { border-left: 0; }
  .compare__table td::before {
    content: attr(data-label);
    display: block;
    margin-bottom: 4px;
    font-family: var(--font-mono);
    font-size: 11px;
    letter-spacing: .1em;
    text-transform: uppercase;
    color: var(--text-faint);
  }

  /* ---- HERO: keep the desktop composition (headline on the LEFT,
     annotations on the RIGHT at the waterline) — just scale the type down
     so the two columns sit side by side without colliding. ---- */

  /* image: drop the desktop framing transform so the full above/below-water
     iceberg shows, centred, like desktop */
  .hero__bg-inner { transform: none; }
  .hero__img { object-position: 50% 43%; }

  .hero__copy { padding-top: 92px; }
  /* keep the eyebrow + headline inside the LEFT column so they never cross
     into the right-hand annotations */
  .hero__eyebrow-row { max-width: 55%; align-items: flex-start; }
  .hero__eyebrow-text { font-size: 11px; letter-spacing: .12em; }
  .hero__eyebrow-dash { margin-top: 7px; }
  .hero__title {
    max-width: 55%;
    font-size: clamp(1.3rem, 5.7vw, 1.95rem);
    line-height: 1.12;
  }
  .hero__lead { font-size: 13px; max-width: 100%; }
  /* Mirror of the desktop stand-in padding (see section 7) — the band the hero
     copy used to rest on was shorter at this width, so its stand-in is too. */
  .hero__content { padding-bottom: 182px; }

  /* annotations: right column, straddling the waterline (same intent as
     desktop — visible tip above, hidden mass below), scaled down */
  .hero-annote {
    top: 23%;
    right: 12px;
    bottom: auto;
    width: 40%;
    max-width: 148px;
    height: auto;
  }
  /* position the visible-tip while keeping the hidden-90% block near the
     waterline: the deep block's top offset counter-balances the container's
     top so the hidden mass holds its absolute position at the surface */
  .annote-tip  { top: 0; }
  .annote-deep { top: 132px; }
  .annote-kicker { font-size: 9px; letter-spacing: .1em; }
  .annote-lead { font-size: .82rem; line-height: 1.12; margin-top: 3px; }
  .annote-tip .annote-body,
  .annote-deep .annote-body { font-size: 9.5px; line-height: 1.3; margin-top: 2px; }

  /* how-it-works: nudge the hub bigger and lift the "Human oversight" label
     clear so it no longer overlaps "Control plane" */
  .wire__hub {
    width: clamp(124px, 34vw, 150px);
    height: clamp(124px, 34vw, 150px);
    padding: 10px;
  }
  .wire__hub-orbit { inset: -16px; }
  .wire__hub-kicker { font-size: 9px; letter-spacing: .12em; }
  .wire__hub-name { font-size: 1rem; margin-top: 5px; }
  .wire__hub-tag { font-size: 9px; margin-top: 5px; }
  .wire__hub-oversight { bottom: calc(100% + 6px); }
  .wire__hub-oversight span { font-size: 8.5px; }
  .wire-node { font-size: clamp(.78rem, 3vw, .95rem); padding: 10px 11px; }

  /* zone vertical rhythm */
  .zone--twilight { padding: 0 0 60px; }
  .zone--midnight { padding: 60px 0; }
  .zone--abyss    { padding: 60px 0 0; }

  .architecture,
  .capabilities { margin-top: 72px; }
  /* `.how` opens the abyss zone at every width now — the zone padding sets
     the rhythm above it. */
  .how { margin-top: 0; }
  /* Let the five step labels wrap onto two rows instead of overflowing; the
     connector line hides on wrap so it never floats between rows. */
  .how-steps { gap: 6px 14px; }
  .how-steps::before { display: none; }
  .how-steps__btn { font-size: 11px; letter-spacing: .1em; padding: 6px 10px; }
  .faq { margin-top: 72px; }
  .cta { padding: 68px 0; }
  .contact { padding: 68px 0; }

  /* single-column contact + wider stat scaling */
  .contact__grid { grid-template-columns: 1fr; }

  /* footer collapses to a single column */
  .site-footer__cols { grid-template-columns: 1fr 1fr; }
}


/* =========================================================================
   23. RESPONSIVE — SMALL PHONES (<=520px)
   ========================================================================= */
@media (max-width: 520px) {
  .proof__stat-big { font-size: 1.5rem; }

  .site-footer__cols { grid-template-columns: 1fr; gap: 32px; }
  .site-footer__bottom { flex-direction: column; align-items: flex-start; gap: 10px; }
  /* Wordmark + "by" + logo can crowd a phone gutter — let the row wrap. */
  .site-footer__brand { flex-wrap: wrap; gap: 10px; }

  .employees__head { flex-direction: column; align-items: flex-start; }
}


/* =========================================================================
   Reduced motion
   ========================================================================= */
@media (prefers-reduced-motion: reduce) {
  * { scroll-behavior: auto; }
  [data-reveal] { opacity: 1 !important; transform: none !important; transition: none; }
  .snow { display: none; }
}


/* =========================================================================
   Firefox scroll performance  (`.is-firefox`, set pre-paint in index.html)
   Gecko is the outlier for the two most scroll-expensive things on this page,
   so we trim them for Firefox only — Chromium/Safari keep the full look:

     1. `backdrop-filter`: unlike Blink, Gecko can't cache the blurred backdrop,
        so every frosted panel re-blurs whatever is behind it on every scroll
        frame. Drop the blur; lean on slightly more opaque fills instead.
     2. Marine snow: a field of infinite `transform`/opacity animations that
        Gecko largely runs on the main thread (Blink offloads them to the
        compositor). This is the dominant cause of the sustained scroll jank,
        so the field is hidden in Firefox (and skipped in app.js so it never
        even builds). The flowing wire-diagram dots are likewise skipped.
   ========================================================================= */
.is-firefox .trust-strip {
  -webkit-backdrop-filter: none;
          backdrop-filter: none;
  background: rgba(6,24,40,.74);
}
.is-firefox .console {
  -webkit-backdrop-filter: none;
          backdrop-filter: none;
  background: rgba(6,22,36,.95);
}
.is-firefox .arch-layer,
.is-firefox .emp,
.is-firefox .site-header.nav-open .site-nav {
  -webkit-backdrop-filter: none;
          backdrop-filter: none;
}
.is-firefox .snow { display: none; }
/* Reveal-on-scroll fully disabled in Firefox (content shown up-front by app.js);
   zero the transition so nothing animates in. */
.is-firefox [data-reveal] {
  opacity: 1 !important;
  transform: none !important;
  transition: none !important;
}

/* THE big one for above-the-fold scroll. The hero photo and the two full-height
   zone banners each carry a CSS `filter`; WebRender re-rasterizes that filtered
   surface as it scrolls past, which is the jank you feel from the hero down to
   the Employees section (the abyss banner is small, so it's fine). Drop the
   filters in Firefox — the imagery looks a touch flatter but scrolls cleanly.
   `content-visibility` is reverted here too: Gecko's implementation forces
   per-scroll layout on exactly these zones (Blink's doesn't), so plain
   rendering scrolls better in Firefox. */
.is-firefox .hero__img { filter: none; }
.is-firefox .zone__banner { filter: none; }
.is-firefox .zone--twilight,
.is-firefox .zone--midnight {
  content-visibility: visible;
  contain-intrinsic-size: auto;
}
