/* ============================================================================
   Radio Archive — styles
   Modern, dependency-free CSS: custom-property tokens, oklch, fluid clamp(),
   Grid/Flex, logical properties, native nesting.
   ========================================================================== */

/* --- Self-hosted fonts -----------------------------------------------------
   Drop the woff2 files into /assets/fonts/ (see README). Until then the
   system fallback stack renders. Do NOT re-add Google Fonts. */
@font-face { font-family: "Manrope"; font-weight: 500; font-display: swap; src: url("../fonts/manrope-500.woff2") format("woff2"); }
@font-face { font-family: "Manrope"; font-weight: 600; font-display: swap; src: url("../fonts/manrope-600.woff2") format("woff2"); }
@font-face { font-family: "Manrope"; font-weight: 700; font-display: swap; src: url("../fonts/manrope-700.woff2") format("woff2"); }
@font-face { font-family: "Manrope"; font-weight: 800; font-display: swap; src: url("../fonts/manrope-800.woff2") format("woff2"); }
@font-face { font-family: "IBM Plex Sans"; font-weight: 400; font-display: swap; src: url("../fonts/ibm-plex-sans-400.woff2") format("woff2"); }
@font-face { font-family: "IBM Plex Sans"; font-weight: 500; font-display: swap; src: url("../fonts/ibm-plex-sans-500.woff2") format("woff2"); }
@font-face { font-family: "IBM Plex Sans"; font-weight: 600; font-display: swap; src: url("../fonts/ibm-plex-sans-600.woff2") format("woff2"); }
@font-face { font-family: "IBM Plex Mono"; font-weight: 500; font-display: swap; src: url("../fonts/ibm-plex-mono-500.woff2") format("woff2"); }
@font-face { font-family: "IBM Plex Mono"; font-weight: 600; font-display: swap; src: url("../fonts/ibm-plex-mono-600.woff2") format("woff2"); }

/* --- Design tokens --------------------------------------------------------- */
:root {
  /* The site is dark-only (no light theme) — this tells the browser to skin
     native form controls (the FM sample <audio> players, scrollbars, etc.)
     dark by default too, instead of the stark light-UI bar it'd otherwise
     render regardless of the page's own colors. */
  color-scheme: dark;
  --bg: oklch(0.22 0.01 90);
  --bg-alt: oklch(0.19 0.008 90);
  --bg-black: oklch(0.08 0.004 90);
  --surface: oklch(0.22 0.01 90);
  --text: oklch(0.95 0.005 90);
  --text-muted: oklch(0.75 0.008 90);
  --text-soft: oklch(0.85 0.008 90);
  --accent-blue: oklch(0.68 0.16 245);
  --accent-cyan: oklch(0.78 0.12 195);
  --grad: linear-gradient(90deg, var(--accent-blue), var(--accent-cyan));
  --btn-ink: oklch(0.14 0.01 90);
  --link-hover: oklch(0.78 0.16 245);
  --pulse: oklch(0.6 0.19 25);
  --border: oklch(1 0 0 / 0.12);
  --border-strong: oklch(1 0 0 / 0.18);
  --hairline: oklch(1 0 0 / 0.1);

  --font-head: "Manrope", system-ui, -apple-system, "Segoe UI", sans-serif;
  --font-body: "IBM Plex Sans", system-ui, -apple-system, "Segoe UI", sans-serif;
  --font-mono: "IBM Plex Mono", ui-monospace, "SF Mono", Menlo, monospace;

  --gutter: clamp(20px, 4vw, 44px);
  --radius-pill: 999px;
  --radius-card: 16px;
  --content-max: 960px; /* shared max content width (page columns + map align to this) */
}

/* --- Reset / base ---------------------------------------------------------- */
*, *::before, *::after { box-sizing: border-box; }
body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font-body);
  font-size: 16px;
  line-height: 1.6;
  /* Sticky footer: fill the viewport, let <main> grow, footer sits at bottom. */
  display: flex;
  flex-direction: column;
  min-height: 100vh;
  min-height: 100dvh;
  -webkit-font-smoothing: antialiased;
}
#main-content { flex: 1 0 auto; }
a { color: var(--accent-blue); text-decoration: none; transition: color 0.2s; }
h1, h2, h3 { font-family: var(--font-head); margin: 0; }
img, svg { max-width: 100%; }

.arrow-nudge { display: inline-block; transition: transform 0.2s ease; }
a:hover .arrow-nudge { transform: translateX(4px); }

:where(a, button, .mobile-menu-link):focus-visible {
  outline: 2px solid var(--accent-cyan);
  outline-offset: 3px;
  border-radius: 2px;
}

.skip-link {
  position: absolute;
  inset-inline-start: 8px;
  inset-block-start: -48px;
  background: var(--accent-blue);
  color: var(--btn-ink);
  padding: 10px 16px;
  border-radius: 6px;
  font: 700 14px var(--font-body);
  z-index: 200;
  transition: inset-block-start 0.2s;
}
.skip-link:focus { inset-block-start: 8px; }

.eyebrow {
  font: 600 11px var(--font-mono);
  letter-spacing: 0.12em;
  color: var(--accent-blue);
  margin: 0 0 16px;
}
.eyebrow-left { text-align: start; margin-block: 56px 16px; }
.eyebrow-center { text-align: center; margin-bottom: 8px; }

/* --- Header ---------------------------------------------------------------- */
.site-header {
  position: sticky;
  top: 0;
  z-index: 110;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 20px;
  padding: 16px var(--gutter);
  background: var(--surface);
  border-bottom: 1px solid var(--hairline);
}
.wordmark { display: flex; align-items: center; flex: none; }
.ra-logo { display: block; height: 34px; width: auto; }

/* Logo bars — an equalizer-style hover animation. Each <rect>'s corner
   radius makes CSS transform:scaleY() the simplest way to grow/shrink it
   without hand-animating height/y per bar; transform-box:fill-box makes
   "center" mean the bar's own vertical midpoint regardless of its position,
   so no per-bar origin math is needed. Five keyframe variants (amplitude +
   timing) are spread across the 14 bars via :nth-child so they move out of
   phase, like a real audio meter, rather than bouncing in lockstep. */
.ra-logo-bar { transform-box: fill-box; transform-origin: center; }
.wordmark:hover .ra-logo-bar,
.wordmark:focus-visible .ra-logo-bar {
  animation-iteration-count: infinite;
  animation-timing-function: ease-in-out;
}
@keyframes ra-eq-a { 0%, 100% { transform: scaleY(0.55); } 50% { transform: scaleY(1.3); } }
@keyframes ra-eq-b { 0%, 100% { transform: scaleY(1.2); } 50% { transform: scaleY(0.6); } }
@keyframes ra-eq-c { 0%, 100% { transform: scaleY(0.7); } 50% { transform: scaleY(1.4); } }
@keyframes ra-eq-d { 0%, 100% { transform: scaleY(1.3); } 50% { transform: scaleY(0.5); } }
@keyframes ra-eq-e { 0%, 100% { transform: scaleY(0.85); } 50% { transform: scaleY(1.2); } }
.wordmark:hover .ra-logo-bar:nth-child(5n+1), .wordmark:focus-visible .ra-logo-bar:nth-child(5n+1) { animation-name: ra-eq-a; animation-duration: 0.9s; animation-delay: -0.1s; }
.wordmark:hover .ra-logo-bar:nth-child(5n+2), .wordmark:focus-visible .ra-logo-bar:nth-child(5n+2) { animation-name: ra-eq-b; animation-duration: 1.15s; animation-delay: -0.4s; }
.wordmark:hover .ra-logo-bar:nth-child(5n+3), .wordmark:focus-visible .ra-logo-bar:nth-child(5n+3) { animation-name: ra-eq-c; animation-duration: 0.8s; animation-delay: -0.6s; }
.wordmark:hover .ra-logo-bar:nth-child(5n+4), .wordmark:focus-visible .ra-logo-bar:nth-child(5n+4) { animation-name: ra-eq-d; animation-duration: 1.3s; animation-delay: -0.2s; }
.wordmark:hover .ra-logo-bar:nth-child(5n+5), .wordmark:focus-visible .ra-logo-bar:nth-child(5n+5) { animation-name: ra-eq-e; animation-duration: 1s; animation-delay: -0.75s; }
.header-right { display: flex; align-items: center; gap: 20px; }

.desktop-nav-links {
  display: flex;
  align-items: center;
  gap: clamp(16px, 3vw, 32px);
  font: 500 16px var(--font-body);
  color: var(--text);
}
.nav-link { color: var(--text); }
.nav-link:hover { color: var(--link-hover); }

/* Product dropdown (pure CSS) */
.product-nav { position: relative; display: inline-flex; align-items: center; gap: 8px; }
.product-nav-label {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  border: none;
  background: none;
  padding: 0;
  font: inherit;
  color: inherit;
  cursor: pointer;
}
.caret-icon {
  display: inline-block;
  width: 10px;
  height: 6px;
  background: currentColor;
  clip-path: polygon(0 0, 100% 0, 50% 100%);
  transition: transform 0.2s ease;
}
.product-dropdown {
  position: absolute;
  top: 100%;
  inset-inline-start: 0;
  padding-top: 12px;
  min-width: 220px;
  z-index: 10;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.18s ease;
}
.product-nav:hover .product-dropdown,
.product-nav:focus-within .product-dropdown { opacity: 1; pointer-events: auto; }
.product-dropdown-inner {
  background: var(--surface);
  border: 1px solid var(--border-strong);
  border-radius: 10px;
  overflow: hidden;
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.4);
}
.product-dropdown-inner a {
  display: block;
  padding: 12px 16px;
  color: var(--text);
  font: 500 16px var(--font-body);
  transition: background 0.18s ease;
}
.product-dropdown-inner a + a { border-top: 1px solid var(--border-strong); }
.product-dropdown-inner a:hover { background: var(--grad); color: var(--btn-ink); }

.product-nav:hover .product-nav-label,
.product-nav:focus-within .product-nav-label {
  background: var(--grad);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.product-nav:hover .caret-icon,
.product-nav:focus-within .caret-icon { transform: rotate(180deg); background: var(--accent-cyan); }

/* --- Buttons --------------------------------------------------------------- */
.btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 14px 24px;
  border-radius: var(--radius-pill);
  font: 600 14px var(--font-body);
  white-space: nowrap;
  cursor: pointer;
  transition: background 0.2s, filter 0.2s, transform 0.2s, box-shadow 0.2s;
}
.btn-ghost {
  border: 1px solid oklch(0.68 0.16 245 / 0.5);
  color: var(--accent-blue);
  background: transparent;
}
.btn-ghost:hover { background: oklch(0.68 0.16 245 / 0.08); }
.btn-primary {
  border: 0;
  background: var(--grad);
  color: var(--btn-ink);
  font-weight: 700;
}
.btn-primary:hover {
  filter: brightness(1.18);
  transform: translateY(-2px) scale(1.02);
  box-shadow: 0 8px 24px oklch(0.68 0.16 245 / 0.4);
}

/* Header contact button + mobile contact button (email shortcode output) */
.contact-btn {
  padding: 10px 20px;
  background: var(--grad);
  color: var(--btn-ink);
  border-radius: var(--radius-pill);
  font: 700 14px var(--font-body);
  white-space: nowrap;
  transition: filter 0.2s, transform 0.2s;
}
.contact-btn:hover { filter: brightness(1.15); transform: translateY(-1px); }

/* --- Hamburger ------------------------------------------------------------- */
.hamburger-btn {
  display: none;
  flex-direction: column;
  gap: 4px;
  align-items: center;
  justify-content: center;
  padding: 4px;
  background: none;
  border: none;
  cursor: pointer;
}
.hamburger-btn span {
  width: 20px;
  height: 2px;
  border-radius: 1px;
  background: var(--grad);
}
.hamburger-btn .bar-top,
.hamburger-btn .bar-bottom { transition: transform 0.3s ease; }
.hamburger-btn .bar-mid { transition: opacity 0.2s ease; }
.hamburger-btn[aria-expanded="true"] .bar-top { transform: translateY(6px) rotate(45deg); }
.hamburger-btn[aria-expanded="true"] .bar-mid { opacity: 0; }
.hamburger-btn[aria-expanded="true"] .bar-bottom { transform: translateY(-6px) rotate(-45deg); }

/* --- Mobile menu ----------------------------------------------------------- */
.mobile-menu {
  position: fixed;
  inset: 0 0 auto 0;
  height: 100vh;
  min-height: 400px;
  background: #1a1a1a;
  z-index: 100;
  padding-top: 58px;
  display: flex;
  flex-direction: column;
  overflow: hidden auto;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.15s ease;
}
.mobile-menu.open { opacity: 1; pointer-events: auto; }
.mobile-menu-scroll { flex: 1 1 auto; display: flex; flex-direction: column; overflow: auto; }
.mobile-menu-heading {
  display: flex;
  align-items: center;
  min-height: 48px;
  padding: 0 24px;
  margin: 0;
  color: var(--text-muted);
  font: 700 32px var(--font-head);
}
.mobile-menu-link {
  display: flex;
  align-items: center;
  gap: 10px;
  min-height: 64px;
  padding: 0 24px;
  border-bottom: 1px solid var(--hairline);
  background: #1a1a1a;
  transition: background 0.15s ease;
}
.mobile-menu-link .gradient-text {
  font: 700 32px var(--font-head);
  background: var(--grad);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.mobile-menu-sublink {
  min-height: 0;
  padding: 18px 24px 18px 44px;
  border-bottom: 0;
}
.mobile-menu-sublink .gradient-text { font: 600 16px var(--font-body); background: var(--grad); -webkit-background-clip: text; background-clip: text; color: transparent; }
.mobile-menu-sublink:last-child { border-bottom: 1px solid var(--hairline); }
.mobile-menu-top { flex: 1; }
.submenu-icon { color: var(--accent-blue); font-size: 14px; }
.mobile-menu-link:hover { background: var(--grad); }
.mobile-menu-link:hover .gradient-text { background: none; -webkit-background-clip: unset; background-clip: unset; color: #000; }
.mobile-menu-link:hover .submenu-icon { color: #000; }
.mobile-contact-btn {
  flex-shrink: 0;
  margin: 24px;
  padding: 22px 24px;
  text-align: center;
  background: var(--grad);
  color: var(--btn-ink);
  border-radius: var(--radius-pill);
  font: 700 20px var(--font-body);
}

/* --- Hero ------------------------------------------------------------------ */
.hero {
  position: relative;
  padding: clamp(24px, 4vw, 44px) var(--gutter) 0;
  text-align: center;
}
.hero-inner { position: relative; z-index: 1; }
.badge {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin: 0 0 28px;
  padding: 7px 16px;
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-pill);
}
.pulse {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--pulse);
  animation: pulseDot 2.2s ease-in-out infinite;
}
.badge-text { font: 600 14px var(--font-mono); letter-spacing: 0.12em; color: var(--accent-blue); }
.hero h1 {
  margin: 0 auto 24px;
  max-width: 760px;
  font: 700 clamp(30px, 6vw, 48px) / 1.15 var(--font-head);
  letter-spacing: -0.015em;
}
.gradient {
  background: var(--grad);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.subhead {
  margin: 0 auto 24px;
  max-width: 600px;
  font-size: 16px;
  line-height: 1.65;
  color: #c0c0c0;
}
.quote {
  margin: 0 0 34px;
  font: italic 500 18px var(--font-body);
  color: #fff;
}
.hero-ctas { display: flex; flex-direction: column; align-items: center; gap: 16px; }
.hero-ctas-row { display: flex; justify-content: center; gap: 14px; flex-wrap: wrap; }

/* Hero waveform — canvas animation ported from the reference site (see
   assets/js/sine-wave.js); this wrapper just positions it as a full-bleed,
   faded-out hero background, same as the reference's "isBackground" mode. */
.waveform {
  position: absolute;
  inset: 0;
  z-index: 0;
  overflow: hidden;
  opacity: 0.8;
  pointer-events: none;
}
.waveform__canvas { display: block; width: 100%; height: 100%; }
.waveform__fade {
  position: absolute;
  inset: 0;
  background: linear-gradient(to bottom, transparent, oklch(1 0 0 / 0.05) 60%, var(--bg) 100%);
}

/* --- Mission --------------------------------------------------------------- */
.mission {
  position: relative;
  z-index: 1;
  padding: 96px var(--gutter) 80px;
}
.mission-card {
  max-width: var(--content-max);
  margin: 8px auto 0;
  padding: clamp(24px, 4vw, 40px) clamp(20px, 3vw, 32px);
  text-align: center;
  background: linear-gradient(135deg, #1c1c1c, #1a1a1aeb, #1c1c1c);
  backdrop-filter: blur(48px) saturate(200%);
  -webkit-backdrop-filter: blur(48px) saturate(200%);
  border: 1px solid #0a629b;
  border-radius: var(--radius-card);
  box-shadow: 0 24px 60px rgba(0, 0, 0, 0.35), inset 0 1px 0 oklch(1 0 0 / 0.45), inset 0 0 40px oklch(1 0 0 / 0.04);
}
/* Desktop only — extra horizontal breathing room so paragraph lines and the
   IQ-sampling graphic below them don't stretch edge-to-edge on wide screens.
   Mobile/tablet keep the clamp() above as-is. */
@media (min-width: 900px) {
  .mission-card { padding-inline: clamp(64px, 9vw, 140px); }
}
.mission-heading { font: 700 clamp(22px, 3vw, 28px) / 1.3 var(--font-head); }
.mission-flex { display: flex; gap: clamp(24px, 4vw, 48px); align-items: flex-start; text-align: start; }
/* min-width: 0, not a positive floor — mission-copy is the sole flex item
   here, and a fixed min-width (leftover from when the IQ graphic sat beside
   it in the same row) doesn't shrink on narrow phones, pushing text past
   the card's padding and border. */
.mission-copy { flex: 1 1 380px; min-width: 0; }
.mission-copy p { margin: 0 0 16px; line-height: 1.75; color: var(--text-soft); }
.link-accent { font: 700 14px var(--font-body); color: var(--accent-blue); }
.link-accent:hover { color: var(--link-hover); }
/* IQ-sampling graphic — the same reference-site "full band IQ sampling"
   pseudo-3D canvas animation: an I/Q helix projected inside a wireframe box.
   Sits full-width below the mission copy, not beside it, so it has room to
   be large. */
.iq-graphic {
  position: relative;
  width: 100%;
  margin-top: clamp(24px, 4vw, 40px);
  /* Fixed, not min-height: the canvas inside is sized in JS off this
     container's own clientHeight every resize. A min-height lets the
     container's height be driven by its content instead (auto-height flex
     column), so each resize reads back the height it just wrote and grows
     without bound — most visibly while dragging the window narrower. A
     fixed height breaks that feedback loop. */
  height: clamp(340px, 55vw, 560px);
  display: flex;
  flex-direction: column;
  overflow: hidden;
  border: 1px solid var(--border-strong);
  border-radius: 16px;
  background: oklch(0.16 0.02 250 / 0.6);
  backdrop-filter: blur(6px);
  -webkit-backdrop-filter: blur(6px);
}
.iq-graphic__title {
  margin: 16px 0 0;
  font: 500 13px/1.3 var(--font-mono);
  letter-spacing: 1px;
  color: var(--accent-cyan);
  text-align: center;
}
.iq-graphic__canvas { display: block; flex: 1 1 auto; width: 100%; }

/* --- Innovation ------------------------------------------------------------ */
.innovation {
  /* Same --bg as the hero/mission above, so the gray band reads as one
     continuous field down through this section — the hard break to black
     happens at Explore below, not here. */
  padding: 88px var(--gutter) 96px;
  background: var(--bg);
}
.innovation-heading {
  max-width: 640px;
  margin: 0 auto 48px;
  font: 700 clamp(24px, 3.2vw, 34px) / 1.3 var(--font-head);
  text-align: center;
}
.innovation-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 20px;
  max-width: var(--content-max);
  margin: 0 auto;
}
/* Glassmorphism, sized up to carry the weight of "this is the whole
   product" — the same #0a629b outline as .mission-card/.glass ties it
   visually to the Our Mission box above, and the index number gives it a
   spec-sheet/product-line feel. */
.innovation-link {
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: 32px;
  min-height: 260px;
  padding: 36px 30px 30px;
  border: 1px solid #0a629b;
  border-radius: var(--radius-card);
  background: linear-gradient(135deg, oklch(1 0 0 / 0.08), oklch(1 0 0 / 0.02));
  backdrop-filter: blur(20px) saturate(140%);
  -webkit-backdrop-filter: blur(20px) saturate(140%);
  box-shadow: inset 0 1px 0 oklch(1 0 0 / 0.1);
  color: inherit;
  transition: transform 0.25s, box-shadow 0.25s, background 0.25s;
}
.innovation-title { font: 700 clamp(20px, 2.2vw, 25px) / 1.3 var(--font-head); }
.innovation-link-cta { font: 700 15px var(--font-body); color: var(--accent-blue); transition: color 0.2s; }
.innovation-link:hover {
  transform: translateY(-6px);
  background: linear-gradient(135deg, oklch(1 0 0 / 0.12), oklch(1 0 0 / 0.05));
  box-shadow:
    inset 0 1px 0 oklch(1 0 0 / 0.1),
    0 24px 48px rgba(0, 0, 0, 0.4),
    0 0 48px oklch(0.68 0.16 245 / 0.25);
}
.innovation-link:hover .innovation-link-cta { color: var(--link-hover); }

/* --- Explore --------------------------------------------------------------- */
.explore { padding: 60px var(--gutter); text-align: center; background: var(--bg-black); }
.explore h2 { font: 700 25px var(--font-head); margin: 0 0 16px; }
.explore-body { margin: 0 auto 28px; max-width: 520px; line-height: 1.7; color: var(--text-muted); }
.explore-ctas { display: flex; justify-content: center; gap: 16px; flex-wrap: wrap; }

/* --- Contact banner + footer ----------------------------------------------- */
.contact-banner {
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-wrap: wrap;
  gap: 12px;
  padding: 28px var(--gutter);
  background: var(--grad);
}
.contact-banner-text { font: 700 14.5px var(--font-head); color: var(--btn-ink); }
.banner-email { font: 600 14px var(--font-mono); color: var(--btn-ink); }
.banner-email:hover { color: var(--btn-ink); filter: brightness(0.8); }

.site-footer {
  display: flex;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 8px;
  padding: 22px var(--gutter);
  font: 14px var(--font-body);
  color: var(--text-muted);
}
.footer-nav { display: flex; gap: 8px; flex-wrap: wrap; align-items: center; }
.footer-nav a { color: inherit; }
.footer-nav a:hover { color: var(--link-hover); }
.dot { color: var(--text-muted); }
.footer-meta { display: flex; align-items: center; flex-wrap: wrap; gap: 8px; }
.credit a { color: var(--accent-blue); }
.credit a:hover { color: var(--link-hover); }

/* --- Prose (inner pages) --------------------------------------------------- */
.prose {
  max-width: var(--content-max);
  margin: 0 auto;
  padding: clamp(48px, 8vw, 88px) var(--gutter);
}
.prose h1 { font: 700 clamp(30px, 5vw, 44px) / 1.15 var(--font-head); letter-spacing: -0.015em; margin: 0 0 24px; }
.prose h2 { font: 700 clamp(20px, 3vw, 26px) var(--font-head); margin: 40px 0 12px; }
.prose p { margin: 0 0 18px; line-height: 1.75; color: var(--text-soft); }
.prose a { color: var(--accent-blue); }
.prose a:hover { color: var(--link-hover); }

/* --- Demos (video embeds) --------------------------------------------------- */
.video-embed {
  position: relative;
  width: 100%;
  aspect-ratio: 16 / 9;
  margin-block: 24px 0;
  overflow: hidden;
  border: 1px solid var(--border-strong);
  border-radius: 12px;
  background: oklch(0.16 0.02 250 / 0.6);
}
.video-embed iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }
.video-embed--featured { box-shadow: 0 24px 48px rgba(0, 0, 0, 0.35); }
.demo-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  gap: 24px;
  margin-top: 28px;
}
.demo-card { margin: 0; }
.demo-card .video-embed { margin-block: 0; }
.demo-card figcaption {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: 8px;
  margin-top: 12px;
}
.demo-card__title { font: 600 15px var(--font-body); color: var(--text); }
.demo-card__year { font: 600 13px var(--font-mono); color: var(--text-muted); letter-spacing: 0.04em; }
@media (max-width: 640px) {
  .demo-grid { grid-template-columns: 1fr; }
}

/* --- Timeline (::: timeline block) ----------------------------------------- */
.timeline { margin-top: 28px; }
.timeline ul {
  list-style: none;
  margin: 0;
  padding: 0;
  position: relative;
}
/* Connecting line: one segment per gap, so the rail ends at the last dot (2026 · Q1) */
.timeline li:not(:last-child)::after {
  content: "";
  position: absolute;
  inset-inline-start: 8px;
  inset-block-start: 12px;
  inset-block-end: -12px;
  width: 2px;
  border-radius: 2px;
  background: var(--accent-blue);
  opacity: 0.5;
}
.timeline li {
  position: relative;
  padding-inline-start: 34px;
  padding-block: 0 26px;
  line-height: 1.65;
  color: var(--text-soft);
}
.timeline li:last-child { padding-bottom: 0; }
/* Node dot — solid light blue, stacked above the connecting line */
.timeline li::before {
  content: "";
  position: absolute;
  inset-inline-start: 0;
  inset-block-start: 3px;
  width: 18px;
  height: 18px;
  border-radius: 50%;
  background: oklch(0.8 0.12 240);
  box-shadow: 0 0 0 4px oklch(0.68 0.16 245 / 0.12);
  z-index: 1;
  transition: transform 0.2s ease, box-shadow 0.2s ease;
}
.timeline li:hover::before {
  transform: scale(1.12);
  box-shadow: 0 0 0 5px oklch(0.68 0.16 245 / 0.2);
}
/* Year label */
.timeline li strong {
  display: block;
  margin-bottom: 5px;
  font: 600 15px var(--font-mono);
  letter-spacing: 0.06em;
  color: var(--accent-blue);
}
@media (max-width: 480px) {
  .timeline li { padding-inline-start: 30px; }
  .timeline li::before { width: 16px; height: 16px; }
  .timeline li:not(:last-child)::after { inset-inline-start: 7px; }
}

/* --- About page cards ------------------------------------------------------ */
.glass,
.deboss {
  margin-block: 0 32px;
  padding: clamp(22px, 4vw, 34px);
  border-radius: var(--radius-card);
}
.glass > :first-child,
.deboss > :first-child { margin-top: 0; }
.glass > :last-child,
.deboss > :last-child { margin-bottom: 0; }

/* Glassmorphism — matches the homepage mission card */
.glass {
  background: linear-gradient(135deg, #1c1c1c, #1a1a1aeb, #1c1c1c);
  backdrop-filter: blur(48px) saturate(200%);
  -webkit-backdrop-filter: blur(48px) saturate(200%);
  border: 1px solid #0a629b;
  box-shadow:
    0 24px 60px rgba(0, 0, 0, 0.35),
    inset 0 1px 0 oklch(1 0 0 / 0.4),
    inset 0 0 40px oklch(1 0 0 / 0.04);
}
.glass p { font-size: 17px; color: var(--text); }

/* Feature card (::: card) — raised panel with fun gradient-diamond bullets */
.card {
  margin-block: 0 24px;
  padding: clamp(20px, 3vw, 28px);
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-card);
  background: oklch(0.24 0.01 90);
}
.card > :first-child { margin-top: 0; }
.card > :last-child { margin-bottom: 0; }
.card h2 { margin-block: 0 16px; }
.card ul { list-style: none; margin: 0; padding: 0; }
.card li {
  position: relative;
  padding-inline-start: 26px;
  margin-bottom: 12px;
  line-height: 1.6;
  color: var(--text-soft);
}
.card li:last-child { margin-bottom: 0; }
.card li::before {
  content: "";
  position: absolute;
  inset-inline-start: 0;
  /* Vertical center of the *first line*, not the whole (possibly wrapped)
     li — line-height is 1.6, so that's 0.8em down from the top. */
  top: 0.8em;
  width: 9px;
  height: 9px;
  border-radius: 2px;
  background: var(--grad);
  transform: translateY(-50%) rotate(45deg);
}
.card li strong { color: var(--text); }

/* --- Tabs (Samples page: FM Analog / HD Radio / AM Samples) ---------------- */
.tabs { margin-block: 28px; }
.tabs__list {
  position: relative;
  display: inline-flex;
  gap: 4px;
  padding: 4px;
  margin-bottom: 28px;
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-pill);
  background: var(--bg-alt);
}
.tabs__thumb {
  position: absolute;
  top: 4px;
  bottom: 4px;
  left: 4px;
  width: 0;
  border-radius: var(--radius-pill);
  background: var(--grad);
  /* No transition until tabs.js marks the list ready (after it's placed the
     thumb once) — otherwise it visibly grows from 0 on first paint instead
     of just appearing under the already-selected tab. */
}
.tabs__list.is-ready .tabs__thumb {
  transition: left 0.25s cubic-bezier(0.22, 1, 0.36, 1), width 0.25s cubic-bezier(0.22, 1, 0.36, 1);
}
.tabs__tab {
  position: relative;
  z-index: 1;
  padding: 10px 20px;
  border: 0;
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--text-muted);
  font: 600 14px var(--font-body);
  white-space: nowrap;
  cursor: pointer;
  transition: color 0.2s ease;
}
.tabs__tab[aria-selected="true"] { color: var(--btn-ink); }
.tabs__tab:hover:not([aria-selected="true"]) { color: var(--text); }
.tabs__panel:focus-visible { outline: 2px solid var(--accent-cyan); outline-offset: 4px; border-radius: 4px; }
.tabs__panel > :first-child { margin-top: 0; }
@media (max-width: 480px) {
  .tabs__list { display: flex; width: 100%; }
  .tabs__tab { flex: 1; padding: 10px 8px; font-size: 13px; }
}

/* --- FM sample station rows ({{fmSamples}} token) ---------------------------
   One row per station rather than a card grid — 31 stations as big padded
   cards ran long and mostly-empty; a row fits the same info in a fraction of
   the height and reads as a scannable list instead of a wall of tiles.
   .fm-card__head stacks the freq/call block and the format badge into one
   column (rather than splitting them into two via display:contents, as an
   earlier pass did) — a fixed-width format column kept overflowing on the
   longer labels ("News/Talk Public Radio", "Top 40/Contemporary Hit Radio"),
   which is what was throwing the later columns out of alignment. */
.fm-grid { display: flex; flex-direction: column; gap: 8px; margin-block: 28px; }
.fm-card {
  display: grid;
  grid-template-columns: 190px minmax(180px, 1fr) minmax(230px, 280px);
  grid-template-rows: auto auto;
  align-items: center;
  column-gap: 20px;
  padding: 12px 20px;
  border: 1px solid var(--border-strong);
  border-radius: 10px;
  background: oklch(0.24 0.01 90);
  transition: border-color 0.2s ease, background 0.2s ease, box-shadow 0.2s ease;
}
.fm-card:hover { border-color: var(--accent-blue); }
/* .is-playing is toggled by fm-samples.js on the card's play/pause/ended
   events, so it's still in sync if the sample is stopped some other way
   (another player starting, the tab losing focus, etc.) rather than just on
   the click that started it. */
.fm-card.is-playing {
  border-color: var(--accent-blue);
  background: oklch(0.68 0.16 245 / 0.1);
  box-shadow: 0 0 0 1px var(--accent-blue), 0 8px 24px oklch(0.68 0.16 245 / 0.25);
}
.fm-card__head { grid-row: 1; grid-column: 1; display: flex; flex-direction: column; align-items: flex-start; gap: 6px; }
.fm-card__id { grid-row: 1; grid-column: 2; }
.fm-card__id-line { display: flex; align-items: baseline; gap: 5px; }
.fm-card__freq {
  font: 800 19px var(--font-head);
  letter-spacing: -0.01em;
  background: var(--grad);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.fm-card__call { font: 600 12px var(--font-mono); color: var(--text-muted); }
/* HD Radio subchannel badge ("HD1"/"HD2"/…) — sits between the frequency and
   the call sign on the same baseline-aligned line. Absent (and never
   rendered) for plain FM/AM stations. */
.fm-card__hd { font: 700 11px var(--font-mono); color: var(--accent-cyan); }
.fm-card__format {
  padding: 4px 10px;
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-pill);
  font: 700 10px var(--font-mono);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--accent-cyan);
  /* Allowed to wrap (unlike the old side-by-side layout, which needed
     nowrap to avoid blowing out its own column) — this is what actually
     keeps a long format name from overflowing into neighboring columns. */
  white-space: normal;
  text-align: left;
}
/* .fm-card__brand/city/licensee are all <p> tags, and .prose p (base
   typography) outspecifies a bare single class selector — .fm-card qualifies
   these enough to actually win instead of silently falling back to prose's
   color/margin defaults. */
.fm-card .fm-card__brand { margin: 0; font: 600 15px var(--font-body); color: var(--text); }
/* Only present on HD Radio subchannels — the "what this feed actually is"
   line between the station name and the city (e.g. "America's Jazz and
   Blues Station"). */
.fm-card .fm-card__tagline { margin: 2px 0 0; font-size: 12px; font-style: italic; color: var(--text-muted); }
.fm-card .fm-card__city { margin: 2px 0 0; font-size: 12px; color: var(--text-muted); }
/* Spans both the head/id row and the licensee row below it, then centers
   itself in that full span — otherwise align-items:center only centers it
   against the (shorter) head/id row, leaving it visibly hugging the top of
   the card instead of the middle once the licensee line adds height below.
   Every cell in this grid is now placed explicitly (head/id/player/licensee
   all set their own grid-row/grid-column) rather than relying on
   auto-placement — a grid item with a definite row but an auto column (as
   player was) jumps the placement queue ahead of items that are auto on
   both axes, and grabbed column 1 out from under head. */
.fm-card__player { grid-row: 1 / 3; grid-column: 3; align-self: center; width: 100%; accent-color: var(--accent-blue); }
/* Its own row, spanning every column, below the title/player line. */
.fm-card .fm-card__licensee {
  grid-row: 2;
  grid-column: 1 / -1;
  margin: 14px 0 0;
  font-size: 11px;
  line-height: 1.4;
  color: oklch(0.55 0.01 90);
}

/* Below the row grid's minimum comfortable width, stack each station back
   into a compact card instead of squeezing three columns into one line. */
@media (max-width: 900px) {
  /* Head (channel + ID) and id (station name + location) sit opposite each
     other as a top row instead of stacking — everything else (format pill,
     player, licensee) still stacks full-width below that row. */
  .fm-card {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    align-items: flex-start;
    column-gap: 16px;
    row-gap: 10px;
    padding: 16px 18px;
  }
  .fm-card__freq { font-size: 22px; }
  .fm-card__id { text-align: right; }
  .fm-card__player,
  .fm-card__licensee {
    flex-basis: 100%;
  }
}

/* --- Coverage map ({{map}} token) ------------------------------------------ */
.us-map-block { display: flex; flex-direction: column; gap: 20px; margin-block: 36px; }
.us-map {
  width: 100%;
  padding: clamp(12px, 2vw, 22px);
  background: var(--bg-alt);
  border: 1px solid var(--border);
  border-radius: var(--radius-card);
}
.us-map__figure { position: relative; margin: 0; }
.us-map__svg { display: block; width: 100%; height: auto; }
/* touch-action only turns off once actually zoomed in (pannable) — setting
   it unconditionally would swallow the page-scroll swipe gesture any time a
   finger starts on the map at the default 1x view, where there's nothing to
   pan yet. */
.us-map__figure--zoomed .us-map__svg { cursor: grab; touch-action: none; }
.us-map__svg--dragging { cursor: grabbing; }
.us-map .state {
  fill: oklch(0.3 0.03 250);
  stroke: oklch(1 0 0 / 0.14);
  stroke-width: 0.75;
  stroke-linejoin: round;
}
.us-map__labels .state-label {
  fill: var(--text-muted);
  font: 500 12px var(--font-body);
  text-anchor: middle;
  pointer-events: none;
}
.us-map__labels .state-label--ext { text-anchor: start; }
.us-map__leaders .leader {
  fill: none;
  stroke: oklch(1 0 0 / 0.28);
  stroke-width: 1;
}

/* Pins: decorative + mouse-only (the state/city explorer box below the map
   is the real text equivalent for every user), so no focus states needed
   here. Teardrop marker,
   not a dot — .us-map__pin-body wraps the shape + hole so its fill-box
   bottom-center lands exactly on the pin's tip (the shape is authored with
   its point at local 0,0), letting the hover scale grow it from that tip
   instead of from the shape's own center. Every rule below triggers on
   EITHER :hover (a no-JS fallback) OR .is-active (set by map.js) — map.js
   also re-parents the hovered pin to the end of its group so it paints
   above its denser neighbors (SVG has no z-index of its own), and moving a
   :hover-matched node makes the browser drop that match, so .is-active is
   what actually keeps working once the reorder happens. */
.us-map__pin-body {
  transform-box: fill-box;
  transform-origin: 50% 100%;
  transition: transform 0.22s cubic-bezier(0.22, 1, 0.36, 1);
}
.us-map__pin:hover .us-map__pin-body,
.us-map__pin.is-active .us-map__pin-body { transform: scale(1.6); }
.us-map__pin-shape {
  fill: var(--accent-cyan);
  stroke: oklch(0.12 0.01 90);
  stroke-width: 0.75;
  transition: fill 0.18s ease;
}
.us-map__pin:hover .us-map__pin-shape,
.us-map__pin.is-active .us-map__pin-shape { fill: var(--accent-blue); }
.us-map__pin-hole { fill: var(--bg-alt); }

/* Tooltip: a rounded-rect card (built with a matching-width <rect> — see
   build-map.mjs, no canvas available at build time to measure real text) so
   the label always sits on a legible, sized background instead of bare text. */
.us-map__pin-tooltip {
  pointer-events: none;
  opacity: 0;
  transform: translateY(4px);
  transform-box: fill-box;
  transition: opacity 0.18s ease, transform 0.18s ease;
}
.us-map__pin-tooltip--below { transform: translateY(-4px); }
.us-map__pin:hover .us-map__pin-tooltip,
.us-map__pin.is-active .us-map__pin-tooltip { opacity: 1; transform: translateY(0); }
.us-map__pin-tooltip-bg {
  fill: var(--bg-alt);
  stroke: var(--border-strong);
  stroke-width: 1;
}
.us-map__pin-label {
  fill: var(--text);
  font: 600 13px var(--font-body);
  text-anchor: middle;
}

/* --- Zoom controls ---------------------------------------------------------- */
.us-map__zoom {
  position: absolute;
  inset-block-end: clamp(14px, 2.5vw, 26px);
  inset-inline-end: clamp(14px, 2.5vw, 26px);
  display: flex;
  flex-direction: column;
  gap: 10px;
  padding: 8px;
  border-radius: 16px;
  background: oklch(0.19 0.008 90 / 0.7);
  backdrop-filter: blur(6px);
  box-shadow: 0 6px 20px oklch(0 0 0 / 0.5);
}
.us-map__zoom-btn {
  display: grid;
  place-items: center;
  width: 46px;
  height: 46px;
  border: 0;
  border-radius: 10px;
  background: var(--grad);
  color: var(--btn-ink);
  font: 800 24px var(--font-body);
  line-height: 1;
  cursor: pointer;
  transition: filter 0.15s ease, transform 0.15s ease;
}
.us-map__zoom-btn:hover:not(:disabled) { filter: brightness(1.15); transform: scale(1.06); }
.us-map__zoom-btn:active:not(:disabled) { transform: scale(0.96); }
.us-map__zoom-btn:disabled {
  background: var(--surface);
  color: var(--text-muted);
  opacity: 0.5;
  cursor: default;
}

/* --- State/city explorer box ------------------------------------------------
   A native <select> is the accessibility fix here, not a bolt-on: every
   screen reader already knows how to announce and operate one, so listing
   the states with a pin as real <option>s (map.js just shows/hides the
   matching pre-rendered <ul> on change) covers keyboard and AT users for
   free, on top of being a genuinely useful lookup for sighted mouse/touch
   users too. */
.us-map__explorer {
  width: 100%;
  padding: clamp(16px, 2.5vw, 26px);
  background: var(--bg-alt);
  border: 1px solid var(--border);
  border-radius: var(--radius-card);
}
.us-map__explorer-label {
  display: block;
  margin-bottom: 10px;
  font: 600 12px var(--font-mono);
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--text-muted);
}
.us-map__state-select {
  width: 100%;
  max-width: 320px;
  padding: 12px 40px 12px 14px;
  border: 1px solid var(--border-strong);
  border-radius: 10px;
  background:
    url('data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" fill="none" stroke="%237a95b0" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M5 8l5 5 5-5"/></svg>')
      no-repeat right 12px center / 16px,
    var(--surface);
  color: var(--text);
  font: 500 15px var(--font-body);
  appearance: none;
  cursor: pointer;
  transition: border-color 0.15s ease;
}
.us-map__state-select:hover { border-color: var(--accent-blue); }
.us-map__state-select option { background: var(--surface); color: var(--text); }

.us-map__city-results { margin-top: 18px; }
.us-map__city-empty { margin: 0; color: var(--text-muted); font-size: 14px; }
.us-map__city-list {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
  gap: 8px 20px;
  margin: 0;
  padding: 0;
  list-style: none;
}
/* A class-based `display` declaration otherwise beats the UA stylesheet's
   [hidden] { display: none }, so every hidden list would render anyway. */
.us-map__city-list[hidden] { display: none; }
.us-map__city-list li {
  padding: 8px 0;
  border-bottom: 1px solid var(--hairline);
  color: var(--text-soft);
  font-size: 14px;
}

/* Debossed — pressed into the surface */
.deboss {
  margin-top: 40px;
  background: oklch(0.18 0.008 90);
  border: 1px solid oklch(0 0 0 / 0.35);
  box-shadow:
    inset 0 2px 6px rgba(0, 0, 0, 0.6),
    inset 0 -1px 0 oklch(1 0 0 / 0.05),
    0 1px 0 oklch(1 0 0 / 0.03);
}

/* --- WCAG 2.2: focus not obscured + target size (>=24px) ------------------- */
html { scroll-padding-block-start: 88px; scroll-behavior: smooth; }
.nav-link,
.product-nav-label { padding-block: 6px; }
.footer-nav a { padding-block: 6px; }
.banner-email { display: inline-block; padding-block: 6px; }

/* --- Animations ------------------------------------------------------------ */
@keyframes pulseDot { 0%, 100% { opacity: 0.4; } 50% { opacity: 1; } }

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.001ms !important;
  }
  html { scroll-behavior: auto; }
}

/* --- Responsive ------------------------------------------------------------ */
@media (max-width: 768px) {
  .desktop-nav-links { display: none; }
  .hamburger-btn { display: flex; }
  .innovation-grid { grid-template-columns: 1fr; }
  .site-footer { flex-direction: column; align-items: flex-start; gap: 16px; }
  .footer-nav { flex-direction: column; align-items: flex-start; gap: 10px; }
  .footer-nav .dot { display: none; }
  .contact-banner { flex-direction: column; justify-content: center; text-align: center; gap: 10px; }
  .contact-banner-text { font-size: 20px; }
  .banner-email { font-size: 17px; }
}
@media (min-width: 769px) {
  .mobile-menu { display: none; }
}
