/* =============================================================================
   TRUCKER TALK RADIO - styles.css
   Rugged · Elegant · Clean · Tough

   Matte black machined steel with ONE controlled amber machined edge.
   Restraint over glow. Editorial calm. Premium American work brand
   (Filson / Shinola / Red Wing / Peterbilt). Not a neon carnival.
   Amber is a CONTROLLED accent. Cyan is a RARE spark only (one ON AIR dot).
   Chrome/metal sparingly - essentially just the H1 wordmark. Matte over glossy.

   No frameworks, no libs. Mobile-first. Fluid clamp() type throughout.
   Fonts (Anton / Oswald 400·600·700 / Inter 400·500·600·700) are loaded by
   index.html's <link>. No @import here - that would be a redundant,
   render-blocking second fetch.

   Verified against the on-disk index.html + main.js (not assumptions):
   - The nav is <header id="site-nav"> with NO class → key on #site-nav.
   - The footer is <footer id="site-footer" class="site-footer"> → key on #site-footer.
   - <html> ships class="no-js"; main.js swaps it to "js" at boot
     (root.classList.remove('no-js'); add('js')). Reveals are gated on html.js,
     with an html:not(.js) / html.no-js safety net so content is NEVER trapped
     invisible if the script fails to run.
   - main.js sets CSS vars at runtime: --nav-h (nav height), and per-bar
     --bar-index / --bar-delay on each .soundwave .bar. CSS owns the @keyframes.
   - main.js sets INLINE transitionDelay on staggered .reveal children of
     episode-grid / platform-btns / topic-list / guest-list / social-links, so we
     add NO nth-child delays here (they would fight the JS).
   - main.js toggles: #site-nav.is-scrolled, #site-nav.nav-open,
     .nav-toggle[aria-expanded], html.nav-locked, .nav-links a.is-active
     (+ aria-current), .reveal.is-visible, .spotify-embed.is-loading/.is-loaded,
     .episode-card.is-focus. It also tabindex=-1 + .focus()es the target section
     on nav click → we suppress the stray outline on main > section:focus.
   - Mobile drawer breakpoint = max-width:859px to mirror the JS
     matchMedia('(min-width: 860px)') exactly (no off-by-one).
   - The iframe carries height="352"; we honor it so the embed is full-height.
   - .sr-only is used inside episode links in the HTML → defined here.
   - .nav-logo is an <a href="#">; the global anchor reset already clears its
     underline, so no per-element override is needed.
   ============================================================================= */

/* =============================================================================
   1. DESIGN TOKENS
   ============================================================================= */
:root {
  /* --- Surfaces - warm near-black charcoal, the dominant generous field --- */
  --bg:         #14100E;
  --bg-alt:     #1B1512;   /* alternating section background                   */
  --steel:      #23201C;   /* raised panels / cards - brushed matte steel feel */
  --steel-hi:   #2B2722;   /* card hover lift                                  */
  --steel-deep: #100C0A;   /* footer / deepest band                           */
  --line:       #3A342D;   /* hairline rules / keylines / borders             */
  --line-soft:  #2C2822;   /* quieter internal dividers                       */

  /* --- Accents - used sparingly. Amber is a machined edge, never a glow. --- */
  --amber:      #F5871F;   /* PRIMARY - CTAs, one keyline, one word emphasis   */
  --amber-hi:   #FF9A3C;   /* amber hover                                     */
  --amber-ink:  #140F0B;   /* text ON amber (near-black)                      */
  --amber-dim:  rgba(245, 135, 31, 0.12); /* very subtle fill, never a wash   */
  --cyan:       #37C6E0;   /* SECONDARY - a rare spark (the ON AIR live dot)   */

  /* --- Metal - chrome used sparingly, essentially just the wordmark --- */
  --chrome-1:   #EDEDEA;
  --chrome-2:   #9BA0A6;

  /* --- Type --- */
  --cream:      #F3ECDE;   /* primary text on dark                            */
  --muted:      #A9A196;   /* secondary / body text (muted, not glowing)      */
  --muted-dim:  #837C71;   /* tertiary / captions (kept high enough for AA)   */

  /* --- Brand platform tints (subtle, only on resting platform icons) --- */
  --spotify:    #1DB954;
  --iheart:     #C6002B;
  --apple:      #B86FE8;

  /* --- Fonts (loaded via the HTML <link>) --- */
  --font-display: "Anton", "Oswald", "Arial Narrow", sans-serif;
  --font-heavy:   "Oswald", "Arial Narrow", sans-serif;
  --font-body:    "Inter", system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;

  /* --- Rhythm & metrics - JS overwrites --nav-h at runtime; this is fallback --- */
  --nav-h:      72px;
  --maxw:       1200px;
  --gutter:     clamp(1.25rem, 5vw, 4.5rem);
  --section-y:  clamp(4.5rem, 10vw, 8.5rem);

  /* --- Motion --- */
  --ease:     cubic-bezier(0.22, 0.61, 0.36, 1);
  --ease-out: cubic-bezier(0.16, 1, 0.30, 1);
  --dur:      0.55s;

  /* --- Radius - machined, restrained, never pillowy --- */
  --r-sm: 2px;
  --r:    3px;
  --r-lg: 4px;

  color-scheme: dark;
}

/* =============================================================================
   2. RESET
   ============================================================================= */
*,
*::before,
*::after { box-sizing: border-box; }

* { margin: 0; }

html {
  -webkit-text-size-adjust: 100%;
  text-size-adjust: 100%;
  scroll-behavior: smooth;
  /* Offset native anchor jumps so targets clear the sticky nav */
  scroll-padding-top: calc(var(--nav-h) + 1rem);
  -webkit-tap-highlight-color: rgba(245, 135, 31, 0.18);
}

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
}

body {
  margin: 0;
  min-height: 100%;
  background-color: var(--bg);
  color: var(--cream);
  font-family: var(--font-body);
  font-size: clamp(1rem, 0.955rem + 0.2vw, 1.0625rem);
  line-height: 1.65;
  font-weight: 400;
  letter-spacing: 0.005em;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-rendering: optimizeLegibility;
  overflow-x: hidden;
}

/* Faint brushed-steel grain + a barely-there top-edge machined light.
   Pure CSS (no image request) so it stays Lighthouse-friendly. Fixed, matte,
   screen-blended, and behind everything - real content is lifted to z-index 1. */
body::before {
  content: "";
  position: fixed;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  opacity: 0.55;
  background:
    /* fine vertical brushed grain */
    repeating-linear-gradient(
      90deg,
      rgba(255, 255, 255, 0.012) 0px,
      rgba(255, 255, 255, 0.012) 1px,
      transparent 1px,
      transparent 3px
    ),
    /* soft top-edge machined light, tuned amber - barely there */
    radial-gradient(120% 60% at 50% -10%, rgba(245, 135, 31, 0.045), transparent 62%);
  mix-blend-mode: screen;
}

/* Keep real content above the texture layer */
header,
main,
footer { position: relative; z-index: 1; }

img,
picture,
svg,
iframe { display: block; max-width: 100%; }

img { height: auto; border-style: none; }

svg { fill: currentColor; }

/* Default anchor color = cream so nav / footer / body links inherit calmly and
   set their own accent where wanted (avoids amber-link bleed on inline links). */
a {
  color: var(--cream);
  text-decoration: none;
  transition: color 0.2s var(--ease);
}
a:hover { color: var(--amber-hi); }

/* Inline body-copy links (e.g. the Ready App link inside .hero-hosts) get the
   amber cue back plus an underline-on-hover so they still read as hyperlinks. */
.hero-hosts a,
.readyapp__intro a {
  color: var(--amber);
  border-bottom: 1px solid transparent;
  transition: color 0.2s var(--ease), border-color 0.2s var(--ease);
}
.hero-hosts a:hover,
.readyapp__intro a:hover {
  color: var(--amber-hi);
  border-bottom-color: var(--amber);
}

button {
  font: inherit;
  color: inherit;
  cursor: pointer;
  background: none;
  border: 0;
}

ul { list-style: none; padding: 0; }

:focus-visible {
  outline: 2px solid var(--amber);
  outline-offset: 3px;
  border-radius: var(--r-sm);
}
/* Suppress the ring on the JS-managed section focus target: main.js sets
   tabindex=-1 and .focus()es the section on nav click. */
main > section:focus,
main > section:focus-visible { outline: none; }

::selection {
  background: var(--amber);
  color: var(--amber-ink);
}

/* Visually-hidden but accessible (used by episode "Listen" links in the HTML) */
.sr-only {
  position: absolute !important;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip: rect(0, 0, 0, 0);
  white-space: nowrap;
  border: 0;
}

/* Matte scrollbar - WebKit + Firefox, no DOM cost */
::-webkit-scrollbar { width: 11px; height: 11px; }
::-webkit-scrollbar-track { background: var(--bg); }
::-webkit-scrollbar-thumb {
  background: var(--line);
  border: 2px solid var(--bg);
  border-radius: 7px;
}
::-webkit-scrollbar-thumb:hover { background: var(--muted-dim); }
* { scrollbar-width: thin; scrollbar-color: var(--line) var(--bg); }

/* Lock scroll when the mobile drawer is open (main.js adds html.nav-locked) */
html.nav-locked,
html.nav-locked body { overflow: hidden; }

/* =============================================================================
   3. SHARED LAYOUT PRIMITIVES
   ============================================================================= */
.section-inner,
.nav-inner,
.hero-inner,
.footer-inner {
  width: 100%;
  max-width: var(--maxw);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

main > section {
  padding-block: var(--section-y);
  position: relative;
}

/* Alternating steel field - assigned by ID (survives DOM reorders), matching
   the DOM contract exactly. Strong grid + dark negative space. */
#hero     { background: var(--bg); }
#listen   { background: var(--bg-alt); }
#episodes { background: var(--bg); }
#topics   { background: var(--bg-alt); }
#guests   { background: var(--bg); }
#readyapp { background: var(--bg-alt); }
#follow   { background: var(--bg); }

/* Recurring motif: ONE hairline rule at each section boundary after the hero,
   tipped with a single short amber machined edge on the left. Never a glow. */
main > section + section::before {
  content: "";
  position: absolute;
  top: 0;
  left: var(--gutter);
  right: var(--gutter);
  height: 1px;
  background: var(--line);
  pointer-events: none;
}
main > section + section::after {
  content: "";
  position: absolute;
  top: 0;
  left: var(--gutter);
  width: 56px;
  height: 1px;
  background: var(--amber);
  pointer-events: none;
}

/* =============================================================================
   4. TYPOGRAPHY - condensed display, generous tracking, real margins
   ============================================================================= */
h1, h2, h3, h4 {
  font-family: var(--font-display);
  font-weight: 400;              /* Anton is single-weight */
  line-height: 1.02;
  color: var(--cream);
  text-transform: uppercase;
  letter-spacing: 0.012em;
  font-kerning: normal;
  text-wrap: balance;
}

/* Section h2 - a short amber machined keyline sits above every heading.
   (The section-boundary amber tip and this keyline never stack because the h2
   is pushed down by its top padding, so each section reads as ONE clean edge.) */
main > section > .section-inner > h2 {
  position: relative;
  font-size: clamp(2.1rem, 1.5rem + 3.6vw, 3.75rem);
  letter-spacing: 0.016em;
  margin-bottom: 0.4rem;
  padding-top: 2.5rem;
  max-width: 24ch;
}
main > section > .section-inner > h2::before {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  width: 44px;
  height: 3px;
  background: var(--amber);
}

/* Section subtitle = the editorial eyebrow - uppercase tracked, muted */
.section-subtitle {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.18em;
  font-size: 0.78rem;
  color: var(--muted);
  margin-bottom: clamp(2.25rem, 5vw, 3.5rem);
  max-width: 56ch;
}

/* =============================================================================
   5. SITE NAV - sticky, matte, hairline underline, elevates on scroll.
   Keyed on #site-nav (the header carries an id, NOT a class).
   ============================================================================= */
#site-nav {
  position: sticky;
  top: 0;
  z-index: 100;
  background: rgba(20, 16, 14, 0.72);
  backdrop-filter: saturate(140%) blur(14px);
  -webkit-backdrop-filter: saturate(140%) blur(14px);
  border-bottom: 1px solid transparent;
  transition: background 0.3s var(--ease), border-color 0.3s var(--ease);
}
#site-nav.is-scrolled {
  background: rgba(18, 14, 12, 0.94);
  border-bottom-color: var(--line);
}
/* Solid fallback where backdrop-filter is unsupported */
@supports not ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
  #site-nav             { background: rgba(18, 14, 12, 0.97); }
  #site-nav.is-scrolled { background: rgba(18, 14, 12, 0.99); }
}

.nav-inner {
  display: flex;
  align-items: center;
  gap: clamp(1rem, 3vw, 2.5rem);
  height: var(--nav-h);
  min-height: 64px;
}

/* Logo lockup - "TTR" machined chip + full wordmark label */
.nav-logo {
  display: flex;
  align-items: center;
  gap: 0.7rem;
  cursor: pointer;
  user-select: none;
  flex: 0 0 auto;
  margin-right: auto;
}
.logo-text {
  font-family: var(--font-display);
  font-size: 1.5rem;
  line-height: 1;
  letter-spacing: 0.03em;
  color: var(--cream);
  padding: 0.28em 0.44em 0.2em;
  border: 1px solid var(--line);
  border-radius: var(--r-sm);
  /* very subtle machined-convex steel face */
  background: linear-gradient(180deg, var(--steel-hi), var(--steel));
  position: relative;
  transition: border-color 0.2s var(--ease);
}
/* the one machined amber edge on the chip - the site's recurring motif */
.logo-text::after {
  content: "";
  position: absolute;
  left: -1px;
  top: 20%;
  bottom: 20%;
  width: 2px;
  background: var(--amber);
  border-radius: 2px;
}
.nav-logo:hover .logo-text { border-color: var(--muted-dim); }
.logo-label {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  font-size: 0.72rem;
  color: var(--muted);
  white-space: nowrap;
  transition: color 0.2s var(--ease);
}
.nav-logo:hover .logo-label { color: var(--cream); }

/* Desktop nav links */
.nav-links {
  display: flex;
  align-items: center;
  gap: clamp(1.1rem, 2.2vw, 2rem);
}
.nav-links a {
  position: relative;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  font-size: 0.8rem;
  color: var(--muted);
  padding: 0.4rem 0;
  transition: color 0.2s var(--ease);
}
.nav-links a::after {
  content: "";
  position: absolute;
  left: 0;
  right: 100%;
  bottom: -2px;
  height: 2px;
  background: var(--amber);
  transition: right 0.28s var(--ease);
}
.nav-links a:hover,
.nav-links a:focus-visible { color: var(--cream); }
.nav-links a.is-active { color: var(--cream); }
.nav-links a:hover::after,
.nav-links a:focus-visible::after,
.nav-links a.is-active::after { right: 0; }
/* The underline already signals focus on nav links; drop the redundant ring */
.nav-links a:focus-visible { outline: none; }

/* Primary nav CTA - solid amber, crisp rectangle, not glowing */
.nav-cta {
  flex: 0 0 auto;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  font-size: 0.8rem;
  color: var(--amber-ink);
  background: var(--amber);
  padding: 0.7rem 1.25rem;
  border-radius: var(--r);
  border: 1px solid var(--amber);
  white-space: nowrap;
  transition: background 0.2s var(--ease), transform 0.2s var(--ease),
              border-color 0.2s var(--ease);
}
.nav-cta:hover {
  background: var(--amber-hi);
  border-color: var(--amber-hi);
  color: var(--amber-ink);
  transform: translateY(-1px);
}
.nav-cta:active { transform: translateY(0); }

/* Mobile toggle - hidden on desktop */
.nav-toggle {
  display: none;
  flex: 0 0 auto;
  width: 44px;
  height: 44px;
  padding: 11px 10px;
  border: 1px solid var(--line);
  border-radius: var(--r-sm);
  background: var(--steel);
  transition: border-color 0.2s var(--ease);
}
.nav-toggle:hover { border-color: var(--muted-dim); }
.nav-toggle span {
  display: block;
  width: 100%;
  height: 2px;
  background: var(--cream);
  border-radius: 2px;
  transition: transform 0.3s var(--ease), opacity 0.2s var(--ease),
              background 0.2s var(--ease);
}
.nav-toggle span + span { margin-top: 5px; }
.nav-toggle[aria-expanded="true"] span { background: var(--amber); }

/* =============================================================================
   6. HERO - editorial split: content left, cover art + soundwave right
   ============================================================================= */
.hero { overflow: hidden; }
.hero-inner {
  display: grid;
  grid-template-columns: 1fr;
  gap: clamp(2.5rem, 6vw, 4rem);
  align-items: center;
  padding-block: clamp(3rem, 8vw, 6rem);
}

.hero-content { max-width: 44rem; }

/* Wordmark - THE ONE brushed-metal gradient moment on the page.
   background-clip:text, restrained chrome sweep, no drop-shadow soup. The whole
   gradient is gated behind @supports so unsupporting browsers keep the solid
   --chrome-1 fill and never orphan into transparent text. */
.hero-wordmark {
  font-family: var(--font-display);
  font-size: clamp(3rem, 2rem + 9vw, 8.25rem);
  line-height: 0.9;
  letter-spacing: 0.004em;
  margin-bottom: 1.25rem;
  color: var(--chrome-1); /* solid fallback if background-clip is unsupported */
  text-wrap: balance;
}
@supports ((-webkit-background-clip: text) or (background-clip: text)) {
  .hero-wordmark {
    background: linear-gradient(
      180deg,
      var(--chrome-1) 0%,
      #d8dde2         40%,
      var(--chrome-2) 63%,
      #b6babf        100%
    );
    -webkit-background-clip: text;
    background-clip: text;
    -webkit-text-fill-color: transparent;
    color: transparent;
  }
}

.hero-tagline {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  font-size: clamp(1.05rem, 0.9rem + 1vw, 1.6rem);
  color: var(--cream);
  line-height: 1.2;
  margin-bottom: 0.85rem;
}
/* single amber machined rule under the tagline - the emphasis motif */
.hero-tagline::after {
  content: "";
  display: block;
  width: 64px;
  height: 3px;
  margin-top: 1rem;
  background: var(--amber);
  border-radius: 2px;
}

.hero-hosts {
  font-size: clamp(0.95rem, 0.9rem + 0.3vw, 1.05rem);
  color: var(--muted);
  letter-spacing: 0.02em;
  margin-bottom: 2.25rem;
  max-width: 46ch;
}
.hero-hosts strong {
  color: var(--cream);
  font-weight: 700;
}

.hero-cta-row {
  display: flex;
  flex-wrap: wrap;
  gap: 0.9rem;
}

/* -----------------------------------------------------------------------------
   6a. BUTTON SYSTEM - solid amber primary + ghost/outline secondary
   -------------------------------------------------------------------------- */
.hero-cta,
.readyapp__cta {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.09em;
  font-size: 0.9rem;
  padding: 0.95rem 1.65rem;
  border-radius: var(--r);
  border: 1px solid var(--amber);
  background: var(--amber);
  color: var(--amber-ink);
  transition: background 0.2s var(--ease), transform 0.2s var(--ease),
              border-color 0.2s var(--ease), color 0.2s var(--ease);
}
.hero-cta:hover,
.readyapp__cta:hover {
  background: var(--amber-hi);
  border-color: var(--amber-hi);
  color: var(--amber-ink);
  transform: translateY(-2px);
}
.hero-cta:active,
.readyapp__cta:active { transform: translateY(0); }

/* The inline Spotify glyph in the hero primary button */
.hero-cta-icon { flex: 0 0 auto; color: currentColor; }

/* ghost / outline secondary - hairline border, crisp, not glowing */
.hero-cta--secondary {
  background: transparent;
  color: var(--cream);
  border-color: var(--line);
}
.hero-cta--secondary:hover {
  background: transparent;
  color: var(--cream);
  border-color: var(--amber);
  transform: translateY(-2px);
}

/* Hero visual - cover art in a machined steel frame + calm equalizer */
.hero-visual {
  position: relative;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1.5rem;
  width: 100%;
}
.hero-image {
  width: min(370px, 80vw);
  height: auto;
  aspect-ratio: 1 / 1;
  object-fit: cover;
  border-radius: var(--r-lg);
  border: 1px solid var(--line);
  background: var(--steel);
  padding: 6px;
  /* single inset highlight from above - reads as a machined top edge, no glow */
  box-shadow:
    0 1px 0 rgba(255, 255, 255, 0.045) inset,
    0 24px 60px -34px rgba(0, 0, 0, 0.85);
  will-change: transform; /* anticipates JS parallax without repaints */
}

/* ON AIR status pill - the single rare cyan spark. Centered above the frame on
   mobile (frame is centered), re-anchored to the right edge on desktop (frame is
   right-aligned). The live dot rides just inside the pill's left padding. */
.hero-visual::before {
  content: "ON AIR";
  position: absolute;
  top: -0.55rem;
  left: max(0.5rem, calc(50% - min(180px, 39vw)));
  z-index: 2;
  display: inline-flex;
  align-items: center;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.22em;
  font-size: 0.62rem;
  color: var(--cream);
  background: var(--steel-deep);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 0.4rem 0.8rem 0.4rem 1.5rem;
}
.hero-visual::after {
  content: "";
  position: absolute;
  top: -0.05rem;
  left: calc(max(0.5rem, calc(50% - min(180px, 39vw))) + 0.72rem);
  z-index: 3;
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: var(--cyan);
  box-shadow: 0 0 0 0 rgba(55, 198, 224, 0.5);
  animation: onair 2.4s var(--ease) infinite;
}
@keyframes onair {
  0%   { box-shadow: 0 0 0 0 rgba(55, 198, 224, 0.5); }
  70%  { box-shadow: 0 0 0 7px rgba(55, 198, 224, 0); }
  100% { box-shadow: 0 0 0 0 rgba(55, 198, 224, 0); }
}

/* Calm equalizer - a considered signal, not a rave. CSS owns the @keyframes;
   main.js sets --bar-delay per bar and manages play/pause. Per-bar duration
   variation gives an organic wave that still holds up if JS never runs. */
.soundwave {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 5px;
  height: 42px;
  width: min(370px, 80vw);
}
.soundwave .bar {
  --bar-index: 0;
  --bar-delay: 0s;
  display: block;
  width: 4px;
  height: 12px;
  border-radius: 2px;
  background: linear-gradient(180deg, var(--amber-hi), var(--amber));
  transform-origin: center bottom;
  animation: eq 1.5s var(--ease) infinite;
  animation-delay: var(--bar-delay);
  opacity: 0.9;
}
/* Center bars taller - a natural, weighted EQ profile; per-bar duration
   variation keeps the wave from reading mechanical. */
.soundwave .bar:nth-child(1),
.soundwave .bar:nth-child(7) { height: 13px; opacity: 0.5;  animation-duration: 1.9s; }
.soundwave .bar:nth-child(2),
.soundwave .bar:nth-child(6) { height: 21px; opacity: 0.68; animation-duration: 1.6s; }
.soundwave .bar:nth-child(3),
.soundwave .bar:nth-child(5) { height: 31px; opacity: 0.82; animation-duration: 2s;   }
.soundwave .bar:nth-child(4) { height: 42px; opacity: 1;    animation-duration: 1.45s; }

@keyframes eq {
  0%, 100% { transform: scaleY(0.38); }
  50%      { transform: scaleY(1); }
}

/* Wide: hero becomes a true editorial split. Both the cover and the equalizer
   widen together so the soundwave stays flush under the frame. */
@media (min-width: 900px) {
  .hero-inner { grid-template-columns: 1.15fr 0.85fr; }
  .hero-visual { align-items: flex-end; }
  .hero-image  { width: min(400px, 100%); }
  .soundwave   { width: min(400px, 100%); }
  /* Re-anchor the ON AIR pill + dot to the right-aligned frame */
  .hero-visual::before { left: auto; right: 0; }
  .hero-visual::after  { left: auto; right: calc(min(400px, 100%) - 2.35rem); }
}

/* =============================================================================
   7. LISTEN - platform buttons + lazy Spotify embed
   ============================================================================= */
.platform-btns {
  display: flex;
  flex-wrap: wrap;
  gap: 0.9rem;
  margin-bottom: clamp(2.5rem, 6vw, 3.75rem);
}
.platform-btn {
  display: inline-flex;
  align-items: center;
  gap: 0.65rem;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  font-size: 0.85rem;
  color: var(--cream);
  background: var(--steel);
  border: 1px solid var(--line);
  border-radius: var(--r);
  padding: 0.85rem 1.4rem;
  transition: border-color 0.2s var(--ease), background 0.2s var(--ease),
              transform 0.2s var(--ease), color 0.2s var(--ease);
}
.platform-btn .platform-icon {
  flex: 0 0 auto;
  color: var(--muted);
  transition: color 0.2s var(--ease);
}
/* subtle brand tint on the resting icon - matte, not loud */
.platform-btn--spotify .platform-icon { color: var(--spotify); }
.platform-btn--iheart  .platform-icon { color: var(--iheart); }
.platform-btn--apple   .platform-icon { color: var(--apple); }
.platform-btn:hover {
  color: var(--cream);
  background: var(--steel-hi);
  border-color: var(--amber);
  transform: translateY(-2px);
}
.platform-btn:hover .platform-icon { color: var(--amber); }
.platform-btn:active { transform: translateY(0); }

/* Spotify embed - machined steel frame; graceful lazy states. The iframe ships
   with data-src and no src (0 height until JS swaps), so we reserve a min-height
   and show a placeholder toggled by .is-loading / .is-loaded. Once loaded, the
   iframe's height="352" attribute gives the player its full height. */
.spotify-embed {
  position: relative;
  border: 1px solid var(--line);
  border-radius: var(--r-lg);
  background: var(--steel);
  overflow: hidden;
  min-height: 232px;
  max-width: 720px;
}
.spotify-embed::before {
  content: "Loading player\2026";
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  font-size: 0.72rem;
  color: var(--muted-dim);
  opacity: 0;
  transition: opacity 0.3s var(--ease);
}
.spotify-embed.is-loading::before { opacity: 1; }
.spotify-embed.is-loaded::before  { display: none; }
.spotify-embed iframe.lazy-embed {
  width: 100%;
  min-height: 232px;
  height: 352px;
  border: 0;
  border-radius: var(--r-lg);
  position: relative;
  z-index: 1;
}
@media (max-width: 640px) {
  .spotify-embed iframe.lazy-embed { height: 232px; }
}

/* =============================================================================
   8. EPISODES - responsive CSS grid of matte steel cards
   ============================================================================= */
.episode-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(100%, 300px), 1fr));
  gap: 1.25rem;
  margin-bottom: clamp(2.25rem, 5vw, 3.25rem);
}

.episode-card {
  display: flex;
  flex-direction: column;
  gap: 0.4rem;
  position: relative;
  background: var(--steel);
  border: 1px solid var(--line);
  border-radius: var(--r-lg);
  padding: 1.6rem 1.5rem 1.5rem;
  overflow: hidden;
  transition: border-color 0.28s var(--ease), transform 0.28s var(--ease),
              background 0.28s var(--ease);
}
/* the recurring thin amber machined edge - a left rail revealed on hover/focus */
.episode-card::before {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  bottom: 0;
  width: 3px;
  background: var(--amber);
  transform: scaleY(0);
  transform-origin: top;
  transition: transform 0.3s var(--ease);
}
.episode-card:hover,
.episode-card.is-focus {
  border-color: var(--muted-dim);
  background: var(--steel-hi);
  transform: translateY(-3px);
}
.episode-card:hover::before,
.episode-card.is-focus::before { transform: scaleY(1); }

.episode-card__guest {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.14em;
  font-size: 0.72rem;
  color: var(--amber);
}
.episode-card__title {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: none;
  letter-spacing: 0.004em;
  font-size: clamp(1.12rem, 1.02rem + 0.4vw, 1.22rem);
  line-height: 1.22;
  color: var(--cream);
  margin: 0.2rem 0 0.35rem;
  text-wrap: pretty;
}
.episode-card__org {
  font-size: 0.85rem;
  color: var(--muted);
  margin-bottom: 0.35rem;
}
.episode-card__link {
  margin-top: auto;
  align-self: flex-start;
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  font-size: 0.78rem;
  color: var(--cream);
  padding-top: 0.65rem;
  transition: color 0.2s var(--ease);
}
.episode-card__link::after {
  content: "\2192"; /* → */
  color: var(--amber);
  transition: transform 0.2s var(--ease);
}
.episode-card__link:hover { color: var(--amber-hi); }
.episode-card__link:hover::after { transform: translateX(4px); }

/* See all - ghost/outline secondary */
.episodes-all {
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  font-size: 0.85rem;
  color: var(--cream);
  background: transparent;
  border: 1px solid var(--line);
  border-radius: var(--r);
  padding: 0.85rem 1.6rem;
  transition: border-color 0.2s var(--ease), color 0.2s var(--ease),
              transform 0.2s var(--ease);
}
.episodes-all::after {
  content: "\2192";
  color: var(--amber);
  transition: transform 0.2s var(--ease);
}
.episodes-all:hover {
  border-color: var(--amber);
  color: var(--cream);
  transform: translateY(-2px);
}
.episodes-all:hover::after { transform: translateX(4px); }

/* =============================================================================
   9. TOPICS - editorial numbered list with hairline dividers
   (a <ul>.topic-list of <li>.topic - no grid needed)
   ============================================================================= */
.topic-list {
  border-top: 1px solid var(--line);
  counter-reset: topic;
  max-width: 920px;
}
.topic {
  counter-increment: topic;
  position: relative;
  display: flex;
  align-items: baseline;
  gap: 1.2rem;
  padding: 1.4rem 0.25rem;
  border-bottom: 1px solid var(--line);
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.03em;
  font-size: clamp(1.15rem, 0.95rem + 1.4vw, 1.95rem);
  color: var(--cream);
  transition: color 0.25s var(--ease), padding-left 0.25s var(--ease);
}
.topic::before {
  content: counter(topic, decimal-leading-zero);
  font-family: var(--font-heavy);
  font-size: 0.85rem;
  letter-spacing: 0.1em;
  color: var(--amber);
  flex: 0 0 auto;
  align-self: center;
  min-width: 2.4ch;
}
/* a hairline amber machined edge slides in on hover - the motif again */
.topic::after {
  content: "";
  position: absolute;
  left: -0.75rem;
  top: 22%;
  bottom: 22%;
  width: 2px;
  background: var(--amber);
  opacity: 0;
  transition: opacity 0.2s var(--ease);
}
.topic:hover {
  color: #fff;
  padding-left: 0.85rem;
}
.topic:hover::after { opacity: 1; }

/* =============================================================================
   10. GUESTS - clean roster grid (the 1px gap + bg IS the hairline grid)
   ============================================================================= */
.guest-list {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(100%, 260px), 1fr));
  gap: 1px;
  background: var(--line);
  border: 1px solid var(--line);
  border-radius: var(--r-lg);
  overflow: hidden;
}
.guest {
  position: relative;
  display: flex;
  flex-direction: column;
  gap: 0.3rem;
  padding: 1.45rem 1.5rem;
  background: var(--steel);
  transition: background 0.2s var(--ease);
}
/* amber left edge revealed on hover - matches the card + chip motif */
.guest::before {
  content: "";
  position: absolute;
  left: 0;
  top: 0;
  bottom: 0;
  width: 3px;
  background: var(--amber);
  transform: scaleY(0);
  transform-origin: center;
  transition: transform 0.25s var(--ease);
}
.guest:hover { background: var(--steel-hi); }
.guest:hover::before { transform: scaleY(1); }
.guest-name {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.05em;
  font-size: 1.05rem;
  color: var(--cream);
}
.guest-org {
  font-size: 0.85rem;
  color: var(--muted);
  letter-spacing: 0.01em;
}

/* =============================================================================
   11. READY APP - the primary backlink, given real editorial weight.
   A faint, matte diamond-plate texture makes this band feel physically distinct.
   ============================================================================= */
.readyapp {
  position: relative;
  overflow: hidden;
}
.readyapp::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  opacity: 0.5;
  background-image:
    repeating-linear-gradient(45deg,  rgba(255,255,255,0.014) 0 2px, transparent 2px 22px),
    repeating-linear-gradient(-45deg, rgba(255,255,255,0.014) 0 2px, transparent 2px 22px);
}
.readyapp .section-inner {
  position: relative;
  z-index: 1;
  max-width: 800px;
}
.readyapp__intro {
  font-size: clamp(1.05rem, 0.98rem + 0.6vw, 1.3rem);
  line-height: 1.6;
  color: var(--cream);
  margin-bottom: 1rem;
  max-width: 62ch;
}
.readyapp__copy {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  font-size: 0.95rem;
  color: var(--muted);
  margin-bottom: 2.25rem;
}
.readyapp__cta { font-size: 0.95rem; padding: 1.05rem 2rem; }

/* =============================================================================
   12. FOLLOW - socials + guest inquiry
   ============================================================================= */
.social-links {
  display: flex;
  flex-wrap: wrap;
  gap: 0.9rem;
  margin-bottom: clamp(2.5rem, 6vw, 3.5rem);
}
.social-link {
  display: inline-grid;
  place-items: center;
  width: 52px;
  height: 52px;
  color: var(--muted);
  background: var(--steel);
  border: 1px solid var(--line);
  border-radius: var(--r);
  transition: color 0.2s var(--ease), border-color 0.2s var(--ease),
              background 0.2s var(--ease), transform 0.2s var(--ease);
}
.social-link svg { width: 22px; height: 22px; fill: currentColor; }
.social-link:hover {
  color: var(--cream);
  background: var(--steel-hi);
  border-color: var(--amber);
  transform: translateY(-2px);
}
.social-link:active { transform: translateY(0); }

.guest-inquiry {
  border-top: 1px solid var(--line);
  padding-top: clamp(2rem, 5vw, 2.85rem);
  max-width: 640px;
}
.guest-inquiry h3 {
  font-size: clamp(1.5rem, 1.1rem + 1.8vw, 2.3rem);
  margin-bottom: 0.55rem;
}
.guest-inquiry p {
  color: var(--muted);
  margin-bottom: 1rem;
}
.guest-inquiry-email {
  display: inline-block;
  font-family: var(--font-heavy);
  font-weight: 700;
  letter-spacing: 0.02em;
  font-size: clamp(1rem, 0.9rem + 0.8vw, 1.32rem);
  color: var(--amber);
  padding-bottom: 3px;
  border-bottom: 1px solid var(--line);
  transition: color 0.2s var(--ease), border-color 0.2s var(--ease);
  word-break: break-word;
}
.guest-inquiry-email:hover {
  color: var(--amber-hi);
  border-bottom-color: var(--amber-hi);
}

/* =============================================================================
   13. FOOTER - keyed on #site-footer (it also carries .site-footer)
   ============================================================================= */
#site-footer {
  background: var(--steel-deep);
  border-top: 1px solid var(--line);
  padding-block: clamp(3rem, 7vw, 5rem) 2rem;
  position: relative;
}
/* single amber accent line at the very top-left of the footer - closing motif */
#site-footer::before {
  content: "";
  position: absolute;
  top: -1px;
  left: 0;
  width: 56px;
  height: 1px;
  background: var(--amber);
}

.footer-inner {
  display: flex;
  flex-direction: column;
  gap: 2.5rem;
}

.footer-content {
  display: grid;
  grid-template-columns: 1fr;
  gap: 2.5rem;
  padding-bottom: 2.5rem;
  border-bottom: 1px solid var(--line-soft);
}
@media (min-width: 720px) {
  .footer-content { grid-template-columns: 1.6fr 1fr 1fr; gap: 3rem; }
}

.footer-branding h3 {
  font-size: clamp(1.3rem, 1.1rem + 1vw, 1.8rem);
  margin-bottom: 0.6rem;
  position: relative;
}
/* one small amber tick under the footer wordmark - the closing edge motif */
.footer-branding h3::after {
  content: "";
  display: block;
  width: 40px;
  height: 3px;
  margin-top: 0.7rem;
  background: var(--amber);
  border-radius: 2px;
}
.footer-branding p {
  color: var(--muted);
  font-size: 0.92rem;
  max-width: 34ch;
  line-height: 1.6;
}

.footer-links h4,
.footer-social h4 {
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  font-size: 0.72rem;
  color: var(--amber);
  margin-bottom: 1rem;
}
.footer-links ul,
.footer-social ul {
  display: flex;
  flex-direction: column;
  gap: 0.6rem;
}
.footer-links a,
.footer-social a {
  color: var(--muted);
  font-size: 0.92rem;
  transition: color 0.2s var(--ease);
}
.footer-links a:hover,
.footer-social a:hover { color: var(--cream); }

.footer-bottom {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding-top: 2rem;
}
.footer-ready {
  color: var(--muted);
  font-size: 0.95rem;
}
.footer-ready a {
  color: var(--cream);
  border-bottom: 1px solid var(--line);
  padding-bottom: 1px;
  transition: color 0.2s var(--ease), border-color 0.2s var(--ease);
}
.footer-ready a:hover {
  color: var(--amber-hi);
  border-bottom-color: var(--amber);
}
.copyright {
  color: var(--muted-dim);
  font-size: 0.78rem;
  letter-spacing: 0.03em;
}

/* =============================================================================
   14. REVEAL-ON-SCROLL - quiet fade / rise (main.js toggles .is-visible).
   Hidden state is gated on html.js so content is NEVER trapped invisible if the
   script fails to run. main.js sets inline transitionDelay on grid/list children
   for the stagger, so we add NO nth-child delays here (they would conflict).
   ============================================================================= */
html.js .reveal {
  opacity: 0;
  transform: translateY(22px);
  transition:
    opacity var(--dur) var(--ease-out),
    transform var(--dur) var(--ease-out);
  will-change: opacity, transform;
}
html.js .reveal.is-visible {
  opacity: 1;
  transform: translateY(0);
}
/* Safety net: absent the js class (pre-boot or script failure), show everything.
   Covers both the initial html.no-js state and the html:not(.js) case. */
html:not(.js) .reveal,
html.no-js .reveal {
  opacity: 1;
  transform: none;
  transition: none;
}

/* =============================================================================
   15. RESPONSIVE - mobile-first; enhance up
   ============================================================================= */

/* --- Mobile nav drawer (< 860px) - mirrors main.js matchMedia(min-width:860px).
   Drawer keyed to #site-nav.nav-open (the class main.js actually toggles). --- */
@media (max-width: 859px) {
  .nav-toggle { display: block; }
  .nav-cta    { display: none; }

  .nav-links {
    position: fixed;
    top: var(--nav-h);
    left: 0;
    right: 0;
    bottom: 0;
    flex-direction: column;
    align-items: flex-start;
    justify-content: flex-start;
    gap: 0.25rem;
    padding: 1.75rem var(--gutter) 3rem;
    background: rgba(16, 12, 10, 0.98);
    backdrop-filter: blur(18px) saturate(150%);
    -webkit-backdrop-filter: blur(18px) saturate(150%);
    border-top: 1px solid var(--line);
    /* Off-canvas until .nav-open */
    transform: translateX(100%);
    opacity: 0;
    visibility: hidden;
    pointer-events: none;
    transition: transform 0.34s var(--ease), opacity 0.3s var(--ease),
                visibility 0s linear 0.34s;
    overflow-y: auto;
    overscroll-behavior: contain;
  }

  #site-nav.nav-open .nav-links {
    transform: translateX(0);
    opacity: 1;
    visibility: visible;
    pointer-events: auto;
    transition: transform 0.34s var(--ease), opacity 0.3s var(--ease),
                visibility 0s linear 0s;
  }

  .nav-links a {
    width: 100%;
    font-size: 1.4rem;
    letter-spacing: 0.06em;
    padding: 1rem 0;
    border-bottom: 1px solid var(--line-soft);
    color: var(--cream);
  }
  .nav-links a::after { display: none; }
  .nav-links a.is-active { color: var(--amber); }

  /* Hamburger -> X. main.js sets BOTH #site-nav.nav-open and the toggle's
     aria-expanded="true"; keyed on both for resilience. */
  #site-nav.nav-open .nav-toggle span:nth-child(1),
  .nav-toggle[aria-expanded="true"] span:nth-child(1) {
    transform: translateY(7px) rotate(45deg);
  }
  #site-nav.nav-open .nav-toggle span:nth-child(2),
  .nav-toggle[aria-expanded="true"] span:nth-child(2) {
    opacity: 0;
  }
  #site-nav.nav-open .nav-toggle span:nth-child(3),
  .nav-toggle[aria-expanded="true"] span:nth-child(3) {
    transform: translateY(-7px) rotate(-45deg);
  }

  /* Tighten section headers a touch on small screens */
  main > section > .section-inner > h2 { padding-top: 2.1rem; }
}

/* --- Small phones: single-column comfort --- */
@media (max-width: 560px) {
  .logo-label { display: none; }
  .hero-cta,
  .platform-btn,
  .episodes-all,
  .readyapp__cta { width: 100%; justify-content: center; }
  .hero-cta-row,
  .platform-btns { flex-direction: column; }
  .footer-bottom { flex-direction: column; align-items: flex-start; }
  main > section > .section-inner > h2 { max-width: none; }
}

/* =============================================================================
   16. REDUCED MOTION - respect the user; disable all motion
   ============================================================================= */
@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.001ms !important;
    scroll-behavior: auto !important;
  }
  html.js .reveal { opacity: 1 !important; transform: none !important; }
  .soundwave .bar { animation: none !important; transform: scaleY(0.6) !important; }
  .hero-visual::after { animation: none !important; box-shadow: none !important; }
  .hero-image { transform: none !important; }
}

/* =============================================================================
   17. PRINT
   ============================================================================= */
@media print {
  body { background: #fff; color: #000; }
  body::before,
  #site-nav,
  .soundwave,
  .spotify-embed,
  .readyapp::after,
  .hero-visual::before,
  .hero-visual::after,
  .nav-toggle { display: none !important; }

  main > section + section::before,
  main > section + section::after { display: none !important; }

  a { color: #000; text-decoration: underline; }

  .hero-wordmark {
    -webkit-text-fill-color: #000 !important;
    color: #000 !important;
    background: none !important;
  }

  main > section { padding-block: 1.5rem; }
}

/* =============================================================================
   14. ENHANCEMENTS v2  (scroll progress, hero cue, Ready App download,
       Be-on-the-show form + Justin portrait, extra micro motion)
       Appended. Uses only existing tokens. Motion is gated by prefers-reduced.
   ============================================================================= */

/* ---- 14.0 shared motion tokens (scoped, additive) ---- */
:root {
  --lift: translateY(-3px);
  --dur-fast: 0.18s;
}

/* ---- 14.1 SCROLL PROGRESS RAIL ---- */
.scroll-progress {
  position: fixed;
  top: 0; left: 0; right: 0;
  height: 3px;
  z-index: 200;
  background: transparent;
  pointer-events: none;
}
.scroll-progress__bar {
  display: block;
  height: 100%;
  width: 0;
  transform-origin: left center;
  background: linear-gradient(90deg, var(--amber), var(--amber-hi));
  box-shadow: 0 0 0 1px rgba(0,0,0,0.15);
  transition: width 0.08s linear;
}

/* ---- 14.2 HERO SCROLL CUE ---- */
.hero-scroll-cue {
  position: absolute;
  left: 50%;
  bottom: clamp(1rem, 3vh, 2.25rem);
  transform: translateX(-50%);
  display: inline-flex;
  flex-direction: column;
  align-items: center;
  gap: 0.5rem;
  color: var(--muted);
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.24em;
  font-size: 0.62rem;
  opacity: 0.85;
  transition: opacity 0.4s var(--ease), color 0.2s var(--ease);
}
.hero-scroll-cue:hover { color: var(--cream); opacity: 1; }
.hero-scroll-cue.is-hidden { opacity: 0; pointer-events: none; }
.hero-scroll-cue__chevron {
  width: 12px; height: 12px;
  border-right: 2px solid currentColor;
  border-bottom: 2px solid currentColor;
  transform: rotate(45deg);
  animation: cue-bob 1.8s var(--ease) infinite;
}
@keyframes cue-bob {
  0%, 100% { transform: rotate(45deg) translate(0, 0); opacity: 0.55; }
  50%      { transform: rotate(45deg) translate(3px, 3px); opacity: 1; }
}

/* ---- 14.3 READY APP: widen, logo, actions, store badges, QR ---- */
.readyapp .section-inner { max-width: var(--maxw); }
.readyapp__grid {
  display: grid;
  grid-template-columns: minmax(0, 1.55fr) minmax(240px, 0.9fr);
  gap: clamp(2rem, 5vw, 4rem);
  align-items: center;
}
.readyapp__logo {
  height: clamp(38px, 5vw, 54px);
  width: auto;
  margin-bottom: 1.5rem;
  display: block;
}
.readyapp__intro { max-width: 58ch; }
.readyapp__actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 1rem 1.25rem;
}

.store-badges { display: inline-flex; flex-wrap: wrap; gap: 0.75rem; }
.store-badge {
  display: inline-flex;
  align-items: center;
  gap: 0.6rem;
  padding: 0.6rem 1rem;
  border: 1px solid var(--line);
  border-radius: var(--r);
  background: var(--steel);
  color: var(--cream);
  transition: border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease);
}
.store-badge:hover {
  border-color: var(--amber);
  background: var(--steel-hi);
  transform: var(--lift);
}
.store-badge:active { transform: translateY(0); }
.store-badge__glyph { flex: 0 0 auto; color: var(--cream); }
.store-badge__text {
  display: flex;
  flex-direction: column;
  line-height: 1.05;
  font-family: var(--font-heavy);
  font-weight: 700;
  letter-spacing: 0.02em;
  font-size: 0.98rem;
}
.store-badge__text small {
  font-family: var(--font-body);
  font-weight: 500;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  font-size: 0.56rem;
  color: var(--muted);
}

/* QR card. The QR SVG itself is dark modules on cream, so the card frame is cream. */
.qr-card {
  justify-self: end;
  width: min(280px, 100%);
  padding: 1.35rem 1.35rem 1.5rem;
  background: var(--steel);
  border: 1px solid var(--line);
  border-radius: var(--r-lg);
  text-align: center;
  position: relative;
}
.qr-card::before {
  content: "";
  position: absolute;
  top: 0; left: 0;
  width: 44px; height: 3px;
  background: var(--amber);
}
.qr-card__frame {
  background: var(--cream);
  border-radius: var(--r);
  padding: 12px;
  line-height: 0;
  margin-bottom: 1rem;
}
.qr-card__img { width: 100%; height: auto; display: block; }
.qr-card__label {
  font-family: var(--font-display);
  font-size: 1.15rem;
  letter-spacing: 0.03em;
  color: var(--cream);
  margin-bottom: 0.25rem;
}
.qr-card__sub { font-size: 0.82rem; color: var(--muted); line-height: 1.5; }

/* ---- 14.4 BE ON THE SHOW: Justin portrait + guest form ---- */
.beonshow { background: var(--bg-alt); }
.beonshow__grid {
  display: grid;
  grid-template-columns: minmax(0, 0.85fr) minmax(0, 1.15fr);
  gap: clamp(2rem, 5vw, 4rem);
  align-items: start;
}

.host-portrait { margin: 0; }
.host-portrait__frame {
  position: relative;
  border: 1px solid var(--line);
  border-radius: var(--r-lg);
  overflow: hidden;
  background: var(--steel);
  aspect-ratio: 1 / 1;
}
.host-portrait__frame::after {
  content: "";
  position: absolute;
  inset: 0;
  pointer-events: none;
  background: linear-gradient(180deg, transparent 55%, rgba(16,12,10,0.55) 100%);
}
.host-portrait__img {
  width: 100%; height: 100%;
  object-fit: cover;
  display: block;
  filter: saturate(1.02) contrast(1.02);
}
.host-portrait__onair {
  position: absolute;
  top: 0.85rem; left: 0.85rem;
  z-index: 2;
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  padding: 0.32rem 0.6rem;
  background: rgba(16,12,10,0.82);
  border: 1px solid var(--line);
  border-radius: 999px;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  font-size: 0.6rem;
  color: var(--cream);
}
.onair-dot {
  width: 8px; height: 8px;
  border-radius: 50%;
  background: var(--cyan);
  box-shadow: 0 0 0 0 rgba(55,198,224,0.6);
  animation: onair-pulse 2s var(--ease) infinite;
}
@keyframes onair-pulse {
  0%   { box-shadow: 0 0 0 0 rgba(55,198,224,0.55); }
  70%  { box-shadow: 0 0 0 7px rgba(55,198,224,0); }
  100% { box-shadow: 0 0 0 0 rgba(55,198,224,0); }
}
.host-portrait__cap {
  margin-top: 1rem;
  color: var(--muted);
  font-size: 0.95rem;
  line-height: 1.55;
}
.host-portrait__cap strong { color: var(--cream); display: block; margin-bottom: 0.15rem; }

.guest-form__lead {
  color: var(--cream);
  font-size: clamp(1rem, 0.95rem + 0.4vw, 1.18rem);
  line-height: 1.6;
  margin-bottom: 1.75rem;
  max-width: 54ch;
}
.guest-form__row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1rem;
}
.guest-field { display: block; margin-bottom: 1rem; }
.guest-field__label {
  display: block;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  font-size: 0.68rem;
  color: var(--muted);
  margin-bottom: 0.4rem;
}
.guest-field input,
.guest-field textarea {
  width: 100%;
  font-family: var(--font-body);
  font-size: 0.98rem;
  color: var(--cream);
  background: var(--bg);
  border: 1px solid var(--line);
  border-radius: var(--r);
  padding: 0.8rem 0.9rem;
  transition: border-color var(--dur-fast) var(--ease),
              box-shadow var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
  -webkit-appearance: none;
  appearance: none;
}
.guest-field textarea { resize: vertical; min-height: 108px; }
.guest-field input::placeholder,
.guest-field textarea::placeholder { color: var(--muted-dim); }
.guest-field input:focus,
.guest-field textarea:focus {
  outline: none;
  border-color: var(--amber);
  background: var(--steel);
  box-shadow: 0 0 0 3px var(--amber-dim);
}
.guest-field input:user-invalid,
.guest-field textarea:user-invalid { border-color: var(--iheart); }

.guest-form__actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 1rem;
  margin-top: 0.5rem;
}
.guest-form__submit {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  font-family: var(--font-heavy);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.09em;
  font-size: 0.95rem;
  padding: 0.95rem 2rem;
  border-radius: var(--r);
  border: 1px solid var(--amber);
  background: var(--amber);
  color: var(--amber-ink);
  cursor: pointer;
  transition: background var(--dur-fast) var(--ease),
              transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease);
}
.guest-form__submit:hover { background: var(--amber-hi); border-color: var(--amber-hi); transform: var(--lift); }
.guest-form__submit:active { transform: translateY(0); }
.guest-form__status {
  font-size: 0.9rem;
  color: var(--cyan);
  font-weight: 600;
}
.guest-form__status.is-error { color: var(--amber-hi); }
.guest-form__fallback {
  margin-top: 1.1rem;
  font-size: 0.85rem;
  color: var(--muted);
}
.guest-form__fallback a {
  color: var(--amber);
  border-bottom: 1px solid var(--line);
  transition: color var(--dur-fast) var(--ease), border-color var(--dur-fast) var(--ease);
}
.guest-form__fallback a:hover { color: var(--amber-hi); border-bottom-color: var(--amber-hi); }

/* ---- 14.5 EXTRA MICRO MOTION (restrained) ---- */
/* Episode cards: a touch more life on hover, amber edge tell. */
html.js .episode-card {
  transition: transform var(--dur-fast) var(--ease),
              border-color var(--dur-fast) var(--ease),
              background var(--dur-fast) var(--ease);
}
html.js .episode-card:hover {
  transform: var(--lift);
  border-color: var(--amber);
}
/* Platform buttons + primary CTAs get a subtle press feel. */
html.js .platform-btn { transition: transform var(--dur-fast) var(--ease), border-color var(--dur-fast) var(--ease), background var(--dur-fast) var(--ease); }
html.js .platform-btn:hover { transform: var(--lift); }
html.js .platform-btn:active { transform: translateY(0); }
/* Nav CTA quiet shine on hover. */
.nav-cta { position: relative; overflow: hidden; }
.nav-cta::after {
  content: "";
  position: absolute;
  top: 0; left: -120%;
  width: 60%; height: 100%;
  background: linear-gradient(100deg, transparent, rgba(255,255,255,0.18), transparent);
  transform: skewX(-18deg);
  transition: left 0.5s var(--ease);
}
.nav-cta:hover::after { left: 140%; }

/* Reveal: add a gentle directional variant for the new two-column blocks. */
html.js .reveal.reveal--right { transform: translateX(24px); }
html.js .reveal.reveal--right.is-visible { transform: none; }

/* ---- 14.6 RESPONSIVE (base pass; the mobile-opt armada refines further) ---- */
@media (max-width: 900px) {
  .readyapp__grid { grid-template-columns: 1fr; }
  .qr-card { justify-self: start; }
  .beonshow__grid { grid-template-columns: 1fr; }
  .host-portrait__frame { max-width: 360px; }
}
@media (max-width: 560px) {
  .guest-form__row { grid-template-columns: 1fr; gap: 0; }
  .store-badges { width: 100%; }
  .store-badge { flex: 1 1 auto; }
  .readyapp__actions { gap: 1rem; }
  .hero-scroll-cue { display: none; }
}

/* ---- 14.7 MOTION SAFETY: disable the new animations on request ---- */
@media (prefers-reduced-motion: reduce) {
  .hero-scroll-cue__chevron,
  .onair-dot { animation: none !important; }
  .scroll-progress__bar { transition: none !important; }
  .nav-cta::after { display: none !important; }
  html.js .episode-card:hover,
  html.js .platform-btn:hover,
  .store-badge:hover,
  .guest-form__submit:hover { transform: none !important; }
}


/* ---- 15. NEW STREAM: YouTube platform-button tint ---- */
.platform-btn--youtube .platform-icon { color: #FF0000; }

/* =============================================================================
   19. MOBILE OPTIMIZATION (merged lens layer: layout + touch-type + components
       + robustness). Append-only, wins by source order. Nothing above is
       rewritten. Tokens only, no new colors. No em dashes. Every rule is scoped
       inside a max-width, min-width, orientation, hover, pointer, @supports, or
       prefers-reduced-motion query so desktop is never regressed. Breakpoints
       reuse the existing set only (900 / 859 drawer / 720 / 640 / 560 / 430 /
       360) and the JS drawer matchMedia (max-width:859px). viewport-fit=cover is
       already set in index.html so env() insets are live; main.js already keys
       the drawer at max-width:859px. Grouped largest to smallest, then landscape,
       then reduced-motion. De-conflicted: the iOS 16px input fix lives once (859),
       safe-area insets live once, the hero is NOT re-split in landscape (that
       would desync the centered ON AIR pill math), and the QR card stays visible
       (store badges are the redundant download path).
   ============================================================================= */

/* ---- 19.0 GLOBAL OVERFLOW + WRAP GUARDS (ungated, safe everywhere) ---------
   Base sets overflow-x:hidden on BODY only, never on html. Close that gap with a
   clip on the html box, but assert overflow-y:visible so the browser cannot
   promote <html> to a scroll container (which would break the sticky #site-nav).
   Then force the real long-string offenders (email, urls, condensed titles) to
   wrap so a single token can never widen the page, and let grid/flex children
   shrink below content size so one long word inside a card cannot widen a track. */
html {
  overflow-x: clip;
  overflow-y: visible;
  max-width: 100%;
}

.hero-hosts,
.hero-hosts a,
.readyapp__intro,
.readyapp__intro a,
.readyapp__copy,
.section-subtitle,
.episode-card__title,
.episode-card__guest,
.episode-card__org,
.guest-name,
.guest-org,
.topic,
.host-portrait__cap,
.guest-form__lead,
.qr-card__sub,
.qr-card__label,
.footer-branding p,
.footer-ready,
main > section > .section-inner > h2 {
  overflow-wrap: break-word;
  word-break: break-word;
}

/* The email address must wrap at any character but never be hyphenated, which
   would corrupt the address. */
.guest-form__fallback,
.guest-form__fallback a[href^="mailto"],
.footer-social a[href^="mailto"] {
  overflow-wrap: break-word;
  word-break: break-all;
  hyphens: none;
  max-width: 100%;
}

/* Inputs and the textarea must respect their box, never force a wider row. */
.guest-field input,
.guest-field textarea {
  max-width: 100%;
  min-width: 0;
  box-sizing: border-box;
}

/* Grid/flex children may shrink below content size (no-overflow safety). */
.episode-card,
.guest,
.readyapp__lead,
.guest-form-wrap,
.host-portrait,
.store-badge,
.store-badge__text,
.footer-content > div { min-width: 0; }

/* Belt-and-suspenders viewport cap on the widest fixed-width elements. */
.spotify-embed,
.spotify-embed iframe.lazy-embed,
.qr-card,
.host-portrait__frame,
.readyapp__logo,
.store-badge { max-width: 100%; }

/* ---- 19.1 SAFE-AREA INSETS (notch + home indicator) -----------------------
   viewport-fit=cover is set in the HTML, so env(safe-area-inset-*) is live.
   max() means the inset only ever ADDS to the already generous clamped --gutter,
   never subtracts, so desktop (env()=0) and unsupporting browsers are untouched.
   One consolidated group: the sticky nav, section shells, hero, footer, the
   fixed drawer, the scroll-progress rail, and the section-boundary hairline and
   its amber machined tip (which live outside the padded containers). */
@supports (padding: max(0px)) {
  @media (max-width: 859px) {
    .nav-inner,
    .section-inner,
    .hero-inner,
    .footer-inner {
      padding-left:  max(var(--gutter), env(safe-area-inset-left));
      padding-right: max(var(--gutter), env(safe-area-inset-right));
    }

    /* Footer clears the home indicator on notched portrait. */
    #site-footer { padding-bottom: max(2rem, calc(1.25rem + env(safe-area-inset-bottom))); }

    /* Fixed scroll-progress rail respects side notches (full-bleed top by design). */
    .scroll-progress {
      padding-left:  env(safe-area-inset-left);
      padding-right: env(safe-area-inset-right);
    }

    /* Section-boundary hairline + amber tip use left:var(--gutter) in the base;
       realign so they never sit inside a side notch on a landscape device. */
    main > section + section::before {
      left:  max(var(--gutter), env(safe-area-inset-left));
      right: max(var(--gutter), env(safe-area-inset-right));
    }
    main > section + section::after {
      left: max(var(--gutter), env(safe-area-inset-left));
    }

    /* Fixed drawer is outside the padded shells: pad it so the last link and the
       scroll region clear the notch and the home indicator. */
    .nav-links {
      padding-left:  max(var(--gutter), env(safe-area-inset-left));
      padding-right: max(var(--gutter), env(safe-area-inset-right));
      padding-bottom: max(3rem, calc(2rem + env(safe-area-inset-bottom)));
    }

    /* JS-driven anchor jumps still land below the sticky bar on notched phones. */
    html { scroll-padding-top: calc(var(--nav-h) + 1rem + env(safe-area-inset-top)); }
  }

  /* Inset the fixed hero cue so it never hides under the home bar. */
  @media (max-width: 900px) {
    .hero-scroll-cue {
      bottom: max(clamp(1rem, 3vh, 2.25rem), env(safe-area-inset-bottom));
    }
  }
}

/* ---- 19.2 TABLET AND DOWN (<= 900px) --------------------------------------
   The two-column bands already collapse to one column here (readyapp +
   beonshow). Refine the stacked rhythm, center the QR card and portrait (base
   only sets justify-self:start / a bare max-width, which left-orphans them),
   and settle the logo + actions. */
@media (max-width: 900px) {
  /* Ready App: single column, lead then QR. */
  .readyapp__grid { gap: clamp(1.75rem, 6vw, 2.75rem); }
  .readyapp__logo { height: clamp(34px, 8vw, 46px); max-width: 260px; margin-bottom: 1.35rem; }
  .readyapp__actions { flex-direction: column; align-items: stretch; gap: 1rem; }
  .readyapp__cta { width: 100%; }

  /* QR card centered under the copy at a scannable, non-stretched size.
     Overrides the base justify-self:start so it stops hugging the edge; the
     generous frame padding preserves the QR quiet zone for camera scanning. */
  .qr-card {
    justify-self: center;
    margin-inline: auto;
    width: min(300px, 100%);
    max-width: 300px;
  }
  .qr-card__frame { padding: 14px; margin-inline: auto; }
  .qr-card__img { min-width: 160px; }

  /* Be on the show: portrait over form, both centered in the column. */
  .beonshow__grid { gap: clamp(1.75rem, 6vw, 2.75rem); }
  .host-portrait {
    width: 100%;
    max-width: 420px;
    margin-inline: auto;
    text-align: center;
  }
  .host-portrait__frame { max-width: none; margin-inline: auto; }
  .host-portrait__cap { text-align: left; max-width: 54ch; margin-inline: auto; }
  .guest-form__lead { max-width: none; }

  /* Episodes: pull the grid gap in a touch as the columns narrow. */
  .episode-grid { gap: 1.1rem; }
}

/* ---- 19.3 DRAWER + TOUCH TARGETS + FOCUS + iOS ZOOM FIX (<= 859px) ---------
   Matches the JS matchMedia exactly. Do not change drawer mechanics, only refine
   spacing and hit areas. */
@media (max-width: 859px) {
  /* iOS FOCUS-ZOOM FIX (the single most important touch fix). The base inputs
     are 0.98rem (about 15.7px), under the 16px threshold that makes iOS Safari
     zoom the viewport on focus. 16px is a browser constant, not a color, so this
     keeps the tokens-only rule intact. Lives once, here, at the widest mobile
     scope so every phone and tablet-portrait is covered. */
  .guest-field input,
  .guest-field textarea {
    font-size: 16px;
    line-height: 1.4;
    min-height: 44px;
    padding: 0.85rem 0.95rem;
  }
  .guest-field textarea { min-height: 120px; }

  /* Drawer link rhythm + a guaranteed thumb-friendly tap area. */
  .nav-links { gap: 0.15rem; }
  .nav-links a {
    display: flex;
    align-items: center;
    min-height: 56px;
  }

  /* Logo lockup: the whole chip is the back-to-top target. */
  .nav-logo { min-height: 44px; align-items: center; }

  /* Nav toggle: a real 44px box. */
  .nav-toggle { min-width: 44px; min-height: 44px; }

  /* Episode Listen link: base had only padding-top, so the horizontal hit area
     was just the text. Give it a real box and a 44px floor (padding is never
     clipped by the card's overflow:hidden). */
  .episode-card__link {
    min-height: 44px;
    padding: 0.75rem 0.3rem 0.25rem 0.2rem;
    margin-left: -0.2rem;
  }

  /* Store badges: base padding gives about 41px, lift to a comfortable 48. */
  .store-badge { min-height: 48px; padding: 0.7rem 1.1rem; }

  /* Footer link lists: 0.6rem gap + small text is a cramped tap column. */
  .footer-links a,
  .footer-social a {
    display: inline-flex;
    align-items: center;
    min-height: 44px;
    padding: 0.35rem 0;
    font-size: 0.98rem;
  }
  .footer-links ul,
  .footer-social ul { gap: 0.15rem; }

  /* Guest-form fallback links + the mailto get a real tap box. */
  .guest-form__fallback a {
    display: inline-block;
    min-height: 44px;
    padding: 0.55rem 0;
    line-height: 1.5;
  }

  /* Footer inline Ready App link breathes a little more. */
  .footer-ready a { display: inline-block; padding: 0.15rem 0; }

  /* Focus-visible rings that survive on touch + clipping. The drawer links drop
     their ring for an underline that is disabled in the drawer, and the episode
     link sits inside overflow:hidden. Restore clear amber rings; outline draws
     outside layout so it shifts nothing. */
  .nav-links a:focus-visible {
    outline: 2px solid var(--amber);
    outline-offset: 2px;
    border-radius: var(--r-sm);
  }
  .episode-card__link:focus-visible,
  .platform-btn:focus-visible,
  .store-badge:focus-visible,
  .social-link:focus-visible,
  .episodes-all:focus-visible {
    outline: 2px solid var(--amber);
    outline-offset: 2px;
  }
}

/* ---- 19.4 SMALL TABLET / LARGE PHONE (<= 720px) ---------------------------
   Tighten vertical rhythm (re-declare the token, not padding-block, so the
   boundary pseudo-elements stay in sync) and center the single-column hero. */
@media (max-width: 720px) {
  :root { --section-y: clamp(3.25rem, 9vw, 5rem); }

  .hero-inner {
    gap: clamp(2rem, 7vw, 3rem);
    padding-block: clamp(2.5rem, 8vw, 4rem);
    text-align: center;
    justify-items: center;
  }
  .hero-content { max-width: 40rem; }
  .hero-tagline::after { margin-inline: auto; }
  .hero-hosts { margin-inline: auto; }
  .hero-cta-row { justify-content: center; }
  .hero-visual { align-items: center; }
  .hero-image,
  .soundwave { width: min(320px, 86vw); }

  main > section > .section-inner > h2 { padding-top: 1.9rem; }
  .section-subtitle { margin-bottom: clamp(1.75rem, 5vw, 2.5rem); }

  /* Episodes + guests read a touch denser as the column narrows. */
  .episode-card { padding: 1.35rem 1.3rem 1.3rem; }
  .topic { padding-block: 1.15rem; }
  .guest { padding: 1.3rem 1.35rem; }

  /* Spotify wrapper fills the narrow column edge to edge. */
  .spotify-embed { max-width: none; }
}

/* ---- 19.5 PHONE (<= 640px) ------------------------------------------------
   Clean single-column stacks, the guest form collapses fully (base only does it
   at 560, which left name/company + email/phone side by side in the 561 to 640
   band), and heavy paint is trimmed for perf. */
@media (max-width: 640px) {
  :root { --section-y: clamp(3rem, 10vw, 4.5rem); }

  /* Episodes: re-floor the auto-fill to a smaller min that reads better on
     phones before the hard single column at 560. */
  .episode-grid {
    grid-template-columns: repeat(auto-fill, minmax(min(100%, 260px), 1fr));
    gap: 1rem;
  }

  /* Guest form: one column. Lean on the .guest-field margin for rhythm (do not
     re-add grid gap, the 560 base zeroes the row gap). */
  .guest-form__row { grid-template-columns: 1fr; gap: 0; }
  .guest-form__row .guest-field { margin-bottom: 1rem; }
  .guest-form__actions { flex-direction: column; align-items: stretch; gap: 0.85rem; }
  .guest-form__submit { width: 100%; min-height: 48px; justify-content: center; }
  .guest-form__status { text-align: center; }

  /* Ready App: full-width actions, keep the intro readable. */
  .readyapp__logo { margin-bottom: 1.15rem; }
  .readyapp__actions { width: 100%; align-items: stretch; }
  .readyapp__actions > .readyapp__cta { width: 100%; }
  .store-badges { width: 100%; }

  /* Spotify: full-width in the steel frame, round to match it (the 232px min is
     already on both wrapper and iframe, so no dead band). */
  .spotify-embed,
  .spotify-embed iframe.lazy-embed { border-radius: var(--r); }

  /* Episode + guest cells tighter but comfortable. */
  .episode-card { padding: 1.25rem 1.2rem 1.2rem; }
  .episode-card__link { padding-top: 0.55rem; }
  .guest { padding: 1.2rem 1.25rem; }

  /* Host portrait steps down a touch on true phones. */
  .host-portrait__frame { max-width: 300px; }

  /* PERF: trim heavy paint on small screens. The matte aesthetic (borders,
     tokens, amber edges, the machined inset highlight) all stay. Fallback
     backgrounds reuse rgba values already present in the base, so no new colors. */
  #site-nav {
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
    background: rgba(18, 14, 12, 0.97);
  }
  #site-nav.is-scrolled { background: rgba(18, 14, 12, 0.99); }
  .nav-links {
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
    background: var(--steel-deep);
  }
  .hero-image {
    box-shadow: 0 1px 0 rgba(255, 255, 255, 0.045) inset;
    will-change: auto;
  }
  body::before { display: none; }
  .readyapp::after { display: none; }
  .host-portrait__img { filter: none; }
  .episode-card,
  .guest { will-change: auto; }
}

/* ---- 19.6 LARGE PHONES (430 to 560) ---------------------------------------
   The base stacks the hero + platform CTAs full-width at 560; give the roomy
   phones back the paired row where they comfortably fit. Store badges are NOT
   re-paired here (their two-line label is cramped side by side); they stack
   full-width in the 560 block below. */
@media (min-width: 430px) and (max-width: 560px) {
  .hero-cta-row,
  .platform-btns { flex-direction: row; flex-wrap: wrap; }
  .hero-cta,
  .hero-cta--secondary,
  .platform-btn { width: auto; flex: 1 1 auto; }
}

/* ---- 19.7 SMALL PHONE (<= 560px) ------------------------------------------
   Hard single-column episodes, restored form-field rhythm, stacked actions,
   comfortable fat-finger gaps, primary-action min-heights, and centered blocks. */
@media (max-width: 560px) {
  :root { --section-y: clamp(2.75rem, 11vw, 4rem); }

  /* Episodes: hard single column on true phones. */
  .episode-grid { grid-template-columns: 1fr; }

  /* Guests: a single hairline column reads cleaner than a cramped 2-up. */
  .guest-list { grid-template-columns: 1fr; }

  /* Form breathing room + centered lead. */
  .guest-field { margin-bottom: 0.9rem; }
  .guest-form__lead { margin-bottom: 1.25rem; }

  /* Fat-finger gaps on the stacked button rows. */
  .platform-btns { gap: 0.85rem; }
  .hero-cta-row  { gap: 0.85rem; }
  .social-links  { gap: 0.85rem; }

  /* Primary actions clear 52px for glove-friendly reach. */
  .hero-cta,
  .hero-cta--secondary,
  .platform-btn,
  .episodes-all,
  .readyapp__cta,
  .guest-form__submit { min-height: 52px; }

  /* Ready App actions stack: CTA over badges, both full width. */
  .readyapp__actions { flex-direction: column; align-items: stretch; gap: 0.9rem; }

  /* Store badges: stack full width, each a fat >=52px tap row. Override the base
     flex:1 1 auto (which keeps them side by side and can fall under 44px tall). */
  .store-badges {
    width: 100%;
    flex-direction: column;
    flex-wrap: nowrap;
    gap: 0.7rem;
  }
  .store-badge {
    flex: 0 0 auto;
    width: 100%;
    min-height: 52px;
    justify-content: flex-start;
    padding: 0.7rem 1.1rem;
  }
  .store-badge__text { font-size: 1.02rem; }
  .store-badge__text small { font-size: 0.58rem; }

  /* QR + logo settle one notch smaller. */
  .qr-card { width: min(280px, 100%); padding: 1.2rem 1.2rem 1.35rem; }
  .qr-card__frame { padding: 12px; }
  .qr-card__sub { font-size: 0.83rem; }
  .readyapp__logo { height: clamp(32px, 9vw, 42px); max-width: 220px; }

  /* Host portrait a touch smaller so the caption is not pushed far down. */
  .host-portrait { max-width: 340px; }
  .host-portrait__cap { text-align: center; }

  /* Keep long copy comfortable; wrap subtitles cleanly. */
  .hero-hosts,
  .readyapp__intro,
  .guest-form__lead,
  .host-portrait__cap { max-width: 40ch; }
  .section-subtitle { text-wrap: pretty; }

  /* Footer: keep the copyright close under the line, release the 34ch clamp so
     the blurb does not read mean in a narrow column. */
  .footer-bottom { padding-top: 1.5rem; gap: 0.6rem; }
  .footer-content { gap: 2rem; padding-bottom: 2rem; }
  .footer-branding p { max-width: none; }
}

/* ---- 19.8 TINY PHONE (<= 360px) -------------------------------------------
   Last-mile tightening so nothing overflows the narrowest common viewport
   (320 and 360 wide). Never shrink caption text below the base sizes. */
@media (max-width: 360px) {
  :root {
    --gutter: 1rem;
    --section-y: clamp(2.5rem, 11vw, 3.5rem);
  }

  /* Cap the fluid wordmark so its widest word cannot approach the edge. */
  .hero-wordmark {
    font-size: clamp(2.5rem, 11vw, 3rem);
    line-height: 0.92;
    overflow-wrap: break-word;
    word-break: break-word;
    hyphens: none;
  }
  .hero-image,
  .soundwave { width: min(260px, 88vw); }

  /* Section H2 clamp floor can crowd 360; ease it and let it wrap. */
  main > section > .section-inner > h2 {
    font-size: clamp(1.8rem, 8.5vw, 2.1rem);
    padding-top: 1.6rem;
    overflow-wrap: break-word;
  }
  .episode-card__title,
  .guest-name { overflow-wrap: break-word; }

  /* Tagline stays on the rails on the narrowest screens. */
  .hero-tagline { font-size: clamp(1rem, 4.6vw, 1.05rem); }
  .hero-tagline::after { width: min(64px, 40%); }

  /* Long mailto in the fallback line must never force horizontal scroll. */
  .guest-form__fallback a { word-break: break-word; }

  /* Cards + roster + badges get a touch less inner padding to preserve width. */
  .episode-card { padding: 1.15rem 1.1rem; }
  .guest { padding: 1.1rem 1.15rem; }
  .topic { gap: 0.85rem; }
  .store-badge { padding: 0.7rem 0.9rem; }
  .store-badge__text { font-size: 0.96rem; }

  /* QR + logo + CTA last-mile. */
  .qr-card { width: 100%; }
  .qr-card__frame { padding: 10px; }
  .readyapp__logo { height: 30px; max-width: 200px; }
  .readyapp__cta { padding: 0.95rem 1.25rem; }
}

/* ---- 19.9 TOUCH AFFORDANCES (no hover on this device) ---------------------
   The episode-card amber rail, the topic amber edge, and the platform/store
   lifts are hover-gated and invisible to touch users. On coarse pointers surface
   a quiet resting tell and a :active press so touch users get the site's core
   machined-edge motif and real feedback. Scoped to (hover:none) and
   (pointer:coarse) so desktop hover behavior is completely untouched. */
@media (hover: none) and (pointer: coarse) {
  /* Episode cards: reveal the amber machined rail at rest (quiet, not full). */
  html.js .episode-card::before,
  .episode-card::before {
    transform: scaleY(1);
    opacity: 0.45;
  }
  .episode-card:active {
    border-color: var(--amber);
    background: var(--steel-hi);
  }
  .episode-card:active::before { opacity: 1; }
  .episode-card__link:active { color: var(--amber-hi); }
  .episode-card__link:active::after { transform: translateX(4px); }

  /* Topic rows: give the hover-only amber edge + color shift a press tell. */
  .topic:active {
    color: #fff;
    padding-left: 0.85rem;
  }
  .topic:active::after { opacity: 1; }

  /* Platform + CTA + badge press states (hover lifts do nothing on touch). */
  .platform-btn:active,
  .hero-cta:active,
  .hero-cta--secondary:active,
  .readyapp__cta:active,
  .episodes-all:active,
  .store-badge:active,
  .guest-form__submit:active,
  .social-link:active {
    border-color: var(--amber);
  }

  /* Guest roster cells: reveal the amber edge on press for parity with cards. */
  .guest:active { background: var(--steel-hi); }
  .guest:active::before { transform: scaleY(1); }

  /* Inline body links get their underline cue without needing hover. */
  .hero-hosts a,
  .readyapp__intro a { border-bottom-color: var(--amber-dim); }
}

/* ---- 19.10 LANDSCAPE PHONES (short viewport) ------------------------------
   Triple-gated (max-width AND orientation AND max-height) so tablets and
   desktops in landscape, which are tall enough, keep the full editorial hero.
   Trim vertical padding, cap the cover, hide the crowded scroll cue, and make
   the fixed drawer scroll. The hero is deliberately NOT re-split to two columns:
   that reintroduces the desktop split at phone widths and desyncs the centered
   cyan ON AIR pill math (the right-edge re-anchor only fires at min-width:900). */
@media (max-width: 900px) and (orientation: landscape) and (max-height: 560px) {
  :root { --section-y: clamp(2.25rem, 7vh, 3.25rem); }

  .hero-inner { padding-block: clamp(1.75rem, 6vh, 2.75rem); }
  .hero-wordmark { font-size: clamp(2rem, 1.2rem + 5vw, 3.5rem); margin-bottom: 0.6rem; }
  .hero-tagline { margin-bottom: 0.5rem; }
  .hero-tagline::after { margin-top: 0.5rem; width: 48px; }
  .hero-hosts { font-size: 0.88rem; margin-bottom: 1.25rem; }
  /* Cap the cover so a short landscape viewport is not dominated by it. */
  .hero-image,
  .soundwave { width: min(220px, 55vh); }
  .hero-scroll-cue { display: none; }

  /* Trim section rhythm in the short viewport. */
  main > section { padding-block: clamp(2rem, 6vh, 4rem); }
  main > section > .section-inner > h2 { padding-top: 1.5rem; }

  /* Keep the new components from eating the whole short view. */
  .host-portrait__frame { max-width: 280px; }
  .spotify-embed iframe.lazy-embed { height: 232px; }

  /* The mobile drawer must scroll when the viewport is short, with big taps. */
  #site-nav.nav-open .nav-links {
    padding-block: 1.25rem 2rem;
    overflow-y: auto;
    -webkit-overflow-scrolling: touch;
  }
  .nav-links a { font-size: 1.2rem; min-height: 48px; }

  /* Respect the notch on the drawer sides + bottom in landscape. */
}
@supports (padding: max(0px)) {
  @media (max-width: 900px) and (orientation: landscape) and (max-height: 560px) {
    #site-nav.nav-open .nav-links {
      padding-left: max(var(--gutter), env(safe-area-inset-left));
      padding-right: max(var(--gutter), env(safe-area-inset-right));
      padding-bottom: max(2rem, env(safe-area-inset-bottom));
    }
  }
}

/* ---- 19.11 REDUCED MOTION GAP-CLOSURE -------------------------------------
   The base has a wildcard block zeroing all animation/transition durations plus
   a targeted block, so most motion is already covered. Close the genuine gaps:
   the nav-cta shine sweep (a pseudo-element that should not exist at all under
   reduced motion), a couple of hover transforms not expressed as transitions,
   the new touch resting/press transitions, and a landscape transform safety. */
@media (prefers-reduced-motion: reduce) {
  .nav-cta::after { content: none !important; }
  .hero-cta:hover,
  .hero-cta--secondary:hover,
  .readyapp__cta:hover,
  .episodes-all:hover,
  .social-link:hover,
  .nav-cta:hover { transform: none !important; }

  .store-badge,
  .qr-card,
  .host-portrait__frame,
  .episode-card,
  .guest,
  .guest-form__submit { transition: none !important; }

  @media (hover: none) and (pointer: coarse) {
    .episode-card::before,
    .guest::before,
    .topic::after,
    .episode-card__link::after,
    .episode-card:active,
    .topic:active { transition: none !important; }
  }

  @media (orientation: landscape) and (max-height: 560px) {
    .hero-image { transform: none !important; }
  }
}


/* ---- 20. FAQ (native details/summary accordion, SEO FAQ rich-result content) ---- */
.faq .section-inner { max-width: 840px; }
.faq-list { border-top: 1px solid var(--line); }
.faq-item { border-bottom: 1px solid var(--line); }
.faq-q {
  list-style: none;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding: 1.25rem 0;
  font-family: var(--font-heavy);
  font-weight: 600;
  font-size: clamp(1.02rem, 0.96rem + 0.5vw, 1.28rem);
  color: var(--cream);
  transition: color var(--dur-fast, 0.18s) var(--ease);
}
.faq-q::-webkit-details-marker { display: none; }
.faq-q:hover { color: var(--amber-hi); }
.faq-q::after {
  content: "";
  flex: 0 0 auto;
  width: 12px;
  height: 12px;
  border-right: 2px solid var(--amber);
  border-bottom: 2px solid var(--amber);
  transform: rotate(45deg);
  transition: transform 0.25s var(--ease);
}
.faq-item[open] .faq-q::after { transform: rotate(225deg); }
.faq-a { padding: 0 0 1.35rem; color: var(--muted); line-height: 1.65; }
.faq-a p { max-width: 68ch; }
.faq-a a { color: var(--amber); border-bottom: 1px solid var(--line); transition: color var(--dur-fast,0.18s) var(--ease), border-color var(--dur-fast,0.18s) var(--ease); }
.faq-a a:hover { color: var(--amber-hi); border-bottom-color: var(--amber-hi); }
@media (prefers-reduced-motion: reduce) {
  .faq-q::after { transition: none !important; }
}

/* =============================================================================
   21. BOTTOM TICKER (live-TV style scrolling marquee, fixed across the bottom)
   ============================================================================= */
:root { --ticker-h: 44px; }

/* Reserve space so the footer + content never hide behind the fixed ticker. */
body { padding-bottom: var(--ticker-h); }

.ticker {
  position: fixed;
  left: 0; right: 0; bottom: 0;
  z-index: 95;                         /* under the mobile drawer, over content */
  height: var(--ticker-h);
  display: flex;
  align-items: stretch;
  background: var(--steel-deep);
  border-top: 1px solid var(--line);
  box-shadow: 0 -6px 24px rgba(0,0,0,0.35);
  font-family: var(--font-heavy);
  overflow: hidden;
}

/* Left brand block, like a news channel bug. */
.ticker__brand {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  padding: 0 1rem 0 max(1rem, env(safe-area-inset-left));
  background: var(--amber);
  color: var(--amber-ink);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.14em;
  font-size: 0.72rem;
  white-space: nowrap;
  position: relative;
  z-index: 2;
}
.ticker__brand:hover { background: var(--amber-hi); color: var(--amber-ink); }
.ticker__brand::after {           /* angled trailing edge into the track */
  content: "";
  position: absolute;
  right: -10px; top: 0; bottom: 0;
  width: 10px;
  background: var(--amber);
  clip-path: polygon(0 0, 100% 50%, 0 100%);
}
.ticker__brand:hover::after { background: var(--amber-hi); }
.ticker__live {
  width: 9px; height: 9px;
  border-radius: 50%;
  background: var(--amber-ink);
  box-shadow: 0 0 0 0 rgba(20,15,11,0.55);
  animation: ticker-pulse 1.8s var(--ease) infinite;
}
@keyframes ticker-pulse {
  0%   { box-shadow: 0 0 0 0 rgba(20,15,11,0.55); }
  70%  { box-shadow: 0 0 0 7px rgba(20,15,11,0); }
  100% { box-shadow: 0 0 0 0 rgba(20,15,11,0); }
}

/* Scrolling viewport + track. */
.ticker__viewport {
  position: relative;
  flex: 1 1 auto;
  overflow: hidden;
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 3%, #000 97%, transparent);
          mask-image: linear-gradient(90deg, transparent, #000 3%, #000 97%, transparent);
}
.ticker__track {
  display: inline-flex;
  align-items: center;
  height: 100%;
  white-space: nowrap;
  will-change: transform;
  animation: ticker-scroll var(--ticker-dur, 60s) linear infinite;
}
.ticker:hover .ticker__track,
.ticker__track:focus-within { animation-play-state: paused; }

@keyframes ticker-scroll {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }   /* JS duplicates the set, so -50% loops seamlessly */
}

.ticker__item {
  display: inline-flex;
  align-items: center;
  color: var(--cream);
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  font-size: 0.72rem;
  padding: 0 1.15rem;
}
.ticker__item--tag { color: var(--amber); }
/* Amber diamond separator between items. */
.ticker__item::before {
  content: "";
  width: 6px; height: 6px;
  margin-right: 1.15rem;
  background: var(--amber);
  transform: rotate(45deg);
  flex: 0 0 auto;
  opacity: 0.85;
}
.ticker__item a { color: inherit; }
.ticker__item a:hover { color: var(--amber-hi); }

/* Keep the hero scroll cue clear of the ticker. */
.hero-scroll-cue { bottom: calc(clamp(1rem, 3vh, 2.25rem) + var(--ticker-h)); }

@media (max-width: 560px) {
  :root { --ticker-h: 40px; }
  .ticker__brand { letter-spacing: 0.1em; font-size: 0.66rem; padding-inline: 0.7rem; }
  .ticker__item { font-size: 0.66rem; padding: 0 0.85rem; }
  .ticker__item::before { margin-right: 0.85rem; }
}

/* Motion safety: no auto-scroll, let users swipe the ticker instead. */
@media (prefers-reduced-motion: reduce) {
  .ticker__viewport { overflow-x: auto; }
  .ticker__track { animation: none !important; }
  .ticker__live { animation: none !important; }
}
