/* ════════════════════════════════════════════════════════════════
   RIFF LANDING  —  scoped under .riff-landing
   Identity (from the app): monochrome black + white, coral accent only.
   Type: Clash Display (headings) + Inter (body). No gradients, no cursive.
   Sub-pages (pricing/privacy/terms/refund) are unaffected.
   ════════════════════════════════════════════════════════════════ */

:root {
  /* Neutrals */
  --off:      #FAFAFA;
  --ink:      #0A0A0A;
  --ink-mid:  #6B6B6B;
  --ink-ter:  #B0B0B0;
  --rule:     #EBEBEB;
  /* Fonts */
  --display:  'Clash Display', 'Clash Display Variable', system-ui, sans-serif;
}

/* ── Base ─────────────────────────────────────────────── */
body.riff-landing {
  background: var(--white);
  color: var(--ink);
}
.riff-landing h1, .riff-landing h2, .riff-landing h3 {
  font-family: var(--display);
  font-weight: 600;
}
.riff-landing .accent-text { color: var(--coral); }
.riff-landing a:focus-visible,
.riff-landing button:focus-visible,
.riff-landing input:focus-visible {
  outline: 2px solid var(--coral);
  outline-offset: 3px;
  border-radius: 6px;
}

/* ── Buttons ──────────────────────────────────────────── */
/* Primary = black pill with a thin coral ring + soft coral glow (app CTA). */
.riff-landing .btn {
  text-transform: uppercase;
  letter-spacing: 0.08em;
  font-weight: 600;
  font-family: var(--display);
}
.riff-landing .btn-primary,
.riff-landing .btn-dark {
  background: var(--ink);
  color: var(--white);
  border: 1.5px solid var(--coral);
  box-shadow:
    0 10px 24px -8px rgba(10,10,10,0.45),   /* dark drop shadow */
    0 6px 18px -8px rgba(242,73,104,0.55);  /* coral glow */
}
.riff-landing .btn-primary:hover,
.riff-landing .btn-dark:hover {
  opacity: 1;
  background: #1a1a1a;
  transform: translateY(-2px);
  box-shadow:
    0 18px 34px -10px rgba(10,10,10,0.55),
    0 10px 24px -8px rgba(242,73,104,0.65);
}
.riff-landing .btn-ghost {
  background: transparent;
  color: var(--ink);
  border: 1.5px solid var(--rule);
}
.riff-landing .btn-ghost:hover { border-color: var(--ink); background: var(--off); }

/* ── Header (black bar) ───────────────────────────────── */
.riff-landing .site-header {
  background: var(--ink);
  border-bottom: 1px solid rgba(255,255,255,0.10);
}
/* Ghost CTA sits on black now — white text + light border. */
.riff-landing .site-header .btn-ghost {
  color: var(--white);
  border-color: rgba(255,255,255,0.30);
}
.riff-landing .site-header .btn-ghost:hover {
  border-color: var(--white);
  background: rgba(255,255,255,0.08);
}
.riff-landing .logo { color: var(--coral); }   /* the lockup inherits this */
.riff-landing .logo-lockup {
  display: block;
  height: clamp(38px, 4.4vw, 46px);
  width: auto;                       /* 482:369 lockup — mic sits over the R */
}
.riff-landing .logo-wordmark {
  font-family: var(--display);
  font-weight: 700;
  letter-spacing: 0.04em;
}

/* ── Hero ─────────────────────────────────────────────── */
.riff-landing .hero { background: var(--white); }
.riff-landing .hero-h1 {
  color: var(--ink);
  font-weight: 600;
  letter-spacing: -0.035em;
  line-height: 0.98;
}
.riff-landing .hero-sub { color: var(--ink-mid); }
.riff-landing .strapline { color: var(--ink-ter); }
.riff-landing .hero-line { display: block; }

/* Voice waveform above the hero heading (centre aligned, coral) */
.riff-landing .voice-wave {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 4px;
  height: 44px;
  margin: 0 auto clamp(24px, 3vw, 36px);
}
.riff-landing .voice-wave span {
  width: 4px;
  height: 100%;
  border-radius: 2px;
  background: var(--coral);
  transform-origin: center;
  transform: scaleY(var(--p, 0.55));   /* static fallback height */
  animation: voiceBar 1.1s ease-in-out infinite;
  animation-delay: calc(var(--i, 0) * -0.09s);  /* offset phases → travelling wave */
}
@keyframes voiceBar {
  0%, 100% { transform: scaleY(0.22); }
  50%      { transform: scaleY(var(--p, 1)); }
}

/* Hero reveal: each element rises from below + fades in, staggered.
   Hidden only when JS is active (.js); revealed when .hero-in is set
   as the intro curtain lifts. */
.riff-landing.js .hero-line,
.riff-landing.js .hero-sub,
.riff-landing.js .hero-inner .btn,
.riff-landing.js .strapline {
  opacity: 0;
  transform: translateY(30px);
  will-change: opacity, transform;
}
@keyframes heroRise {
  to { opacity: 1; transform: translateY(0); }
}
.riff-landing.hero-in .hero-line,
.riff-landing.hero-in .hero-sub,
.riff-landing.hero-in .hero-inner .btn,
.riff-landing.hero-in .strapline {
  animation: heroRise 0.75s cubic-bezier(0.16, 1, 0.3, 1) forwards;
}
.riff-landing.hero-in .hero-line:nth-child(1) { animation-delay: 0s; }
.riff-landing.hero-in .hero-line:nth-child(2) { animation-delay: 0.12s; }
.riff-landing.hero-in .hero-sub               { animation-delay: 0.30s; }
.riff-landing.hero-in .hero-inner .btn        { animation-delay: 0.44s; }
.riff-landing.hero-in .strapline              { animation-delay: 0.56s; }

/* ── Full-viewport sections: each section fills the screen so one section
   is visible at a time, regardless of display size (laptop or iMac). ── */
.riff-landing .hero,
.riff-landing .section {
  min-height: 100vh;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  justify-content: center;
}

/* ── Section rhythm: white default, two black beats (problem + kicker) ── */
.riff-landing .section--dark { background: var(--white); color: var(--ink); }
.riff-landing .section--pink { background: var(--off); color: var(--ink); }
.riff-landing .section--dark h2,
.riff-landing .section--pink h2 { color: var(--ink); }

/* Problem = black beat */
.riff-landing #problem { background: var(--ink); color: rgba(255,255,255,0.72); }
.riff-landing #problem h2 { color: var(--white); }
.riff-landing #problem p { color: rgba(255,255,255,0.72); }
.riff-landing #problem .prose-section p:first-of-type { color: rgba(255,255,255,0.92); }
.riff-landing #problem .problem-list li { color: rgba(255,255,255,0.72); }
.riff-landing #problem .problem-list li::before { background: var(--coral); }
.riff-landing .prose-section h2 { font-family: var(--display); font-weight: 600; }

/* Pivot statement: standalone section, each word fades up in sequence
   when it scrolls into view. */
.riff-landing .section--statement {
  background: var(--white);
  text-align: center;
  padding-block: clamp(120px, 18vw, 220px);
}
.riff-landing .statement-line {
  margin: 0 auto;
  max-width: 16ch;
  font-family: var(--display);
  font-weight: 600;
  color: var(--coral);
  font-size: clamp(34px, 6vw, 80px);
  line-height: 1.1;
  letter-spacing: -0.02em;
}
/* Word-by-word reveal: any element with .word fades up in sequence once its
   ancestor section (.words-reveal) gets .is-visible on scroll. */
.riff-landing .word { display: inline-block; }
.riff-landing.js .word {
  opacity: 0;
  transform: translateY(0.6em);
  will-change: opacity, transform;
}
@keyframes wordIn {
  to { opacity: 1; transform: translateY(0); }
}
.riff-landing .is-visible .word {
  animation: wordIn 0.6s cubic-bezier(0.16, 1, 0.3, 1) forwards;
  animation-delay: calc(var(--i, 0) * 0.09s);
}

/* Solution */
.riff-landing .section-lead { color: var(--ink-mid); }
.riff-landing .how-title { color: var(--ink); font-family: var(--display); }
.riff-landing .step-num { background: var(--ink); color: var(--white); font-family: var(--display); }
.riff-landing .step-text { color: var(--ink-mid); }
.riff-landing .section-closing { color: var(--ink); }

/* Benefits — filled black panel with white text */
.riff-landing #benefits { background: var(--ink); }
.riff-landing #benefits h2 { color: var(--white); }
.riff-landing .benefit-card {
  position: relative;
  overflow: hidden;
  background: rgba(255,255,255,0.04);
  border: 1px solid rgba(255,255,255,0.10);
}
.riff-landing .benefit-card::before {
  content: '';
  position: absolute;
  inset: 0 0 auto 0;
  height: 3px;
  background: var(--coral);
  opacity: 0;
  transition: opacity 0.2s ease-out;
}
.riff-landing .benefit-card:hover {
  background: rgba(255,255,255,0.07);
  border-color: rgba(255,255,255,0.20);
  transform: translateY(-3px);
  box-shadow: 0 18px 40px -18px rgba(0,0,0,0.55);
}
.riff-landing .benefit-card:hover::before { opacity: 1; }
.riff-landing .benefit-card h3 { color: var(--white); font-family: var(--display); }
.riff-landing .benefit-card p { color: rgba(255,255,255,0.72); }

/* Social proof */
.riff-landing .quote-card {
  position: relative;
  overflow: hidden;
  background: var(--white);
  border: 1px solid var(--rule);
  border-radius: var(--radius-md);
  padding-left: 36px;
}
.riff-landing .quote-card::before {
  content: '';
  position: absolute;
  left: 0; top: 0; bottom: 0;
  width: 4px;
  background: var(--coral);
}
.riff-landing .quote-card p { color: var(--ink); }

/* Kicker = full-height black statement section */
.riff-landing .section--kicker {
  position: relative;
  overflow: hidden;
  background: var(--ink);
  min-height: 90vh;
  display: grid;
  place-items: center;
  padding-block: clamp(120px, 20vw, 240px);
}
.riff-landing .section--kicker .container { position: relative; z-index: 1; }
.riff-landing .kicker-h2 { color: var(--white); font-family: var(--display); font-weight: 600; }

/* Alpha-channel animation sitting under the headline — decorative, so it
   stays hidden until script.js confirms the browser can play VP9 webm and
   motion is welcome. The headline and CTA never depend on it. */
.riff-landing .kicker-video { display: none; }
.riff-landing .kicker-has-video .kicker-video {
  display: block;
  width: min(100%, 430px);
  height: auto;
  margin: 0 auto;             /* the h2's 40px bottom margin does the spacing */
}

/* Subtle pulsing ring outlines drifting behind the statement. */
.riff-landing .kicker-rings {
  position: absolute;
  inset: 0;
  pointer-events: none;
  z-index: 0;
}
.riff-landing .kicker-rings span {
  position: absolute;
  top: 50%;
  left: 50%;
  width: clamp(220px, 34vw, 360px);
  aspect-ratio: 1;
  border-radius: 50%;
  border: 1.5px solid rgba(255,255,255,0.16);
  opacity: 0;
  transform: translate(-50%, -50%) scale(0.9);
  animation: kickerPulse 7s ease-in-out infinite;
}
.riff-landing .kicker-rings span:nth-child(2) { width: clamp(340px, 50vw, 540px); animation-delay: -1.75s; border-color: rgba(242,73,104,0.24); }
.riff-landing .kicker-rings span:nth-child(3) { width: clamp(460px, 66vw, 720px); animation-delay: -3.5s; }
.riff-landing .kicker-rings span:nth-child(4) { width: clamp(600px, 84vw, 920px); animation-delay: -5.25s; border-color: rgba(242,73,104,0.18); }
@keyframes kickerPulse {
  0%, 100% { transform: translate(-50%, -50%) scale(0.9);  opacity: 0; }
  50%      { transform: translate(-50%, -50%) scale(1.06); opacity: 0.85; }
}

/* Waitlist */
.riff-landing .waitlist-h3 { color: var(--ink); font-family: var(--display); }
.riff-landing .waitlist-copy p { color: var(--ink-mid); }
.riff-landing .what-you-get-label { color: var(--ink) !important; }
.riff-landing .what-you-get li { color: var(--ink-mid); }
.riff-landing .what-you-get li::before { background: var(--coral); }
.riff-landing .form-row input[type="email"] {
  background: var(--white);
  border: 1.5px solid var(--rule);
  color: var(--ink);
}
.riff-landing .form-row input[type="email"]:focus {
  border-color: var(--coral);
  box-shadow: 0 0 0 3px rgba(242,73,104,0.18);
}
.riff-landing .form-row input[type="email"]::placeholder { color: var(--ink-ter); }
.riff-landing .form-disclaimer { color: var(--ink-ter); }
.riff-landing .form-success { background: rgba(52,211,153,0.16); color: #0f7a52; }
.riff-landing .form-error { background: rgba(220,38,38,0.10); color: #b91c1c; }

/* Footer */
.riff-landing .footer { background: var(--off); border-top: 1px solid var(--rule); }
.riff-landing .footer-company { color: var(--ink-mid); }
.riff-landing .footer-links a { color: var(--ink-mid); }
.riff-landing .footer-links a:hover { color: var(--ink); }
.riff-landing .footer-copy { color: var(--ink-ter); }

/* ── Intro curtain (full-screen logo animation on load) ── */
.riff-landing.intro-active { overflow: hidden; }
.intro-curtain {
  position: fixed;
  inset: 0;
  z-index: 1000;
  display: grid;
  place-items: center;
  background: #171717;
  overflow: hidden;
  opacity: 1;
  transition: opacity 0.6s ease;
}
.intro-curtain[hidden] { display: none; }
.intro-curtain.is-done { opacity: 0; pointer-events: none; }
.intro-media {
  width: auto;
  height: auto;
  max-width: 100vw;
  max-height: 100vh;
  object-fit: contain;
  display: block;
  user-select: none;
  pointer-events: none;
}
.intro-skip {
  position: absolute;
  top: clamp(18px, 4vw, 32px);
  right: clamp(18px, 4vw, 32px);
  z-index: 2;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border-radius: var(--radius-pill);
  border: 1.5px solid rgba(255,255,255,0.25);
  background: transparent;
  color: rgba(255,255,255,0.7);
  cursor: pointer;
  transition: color 0.15s, border-color 0.15s, background 0.15s;
}
.intro-skip:hover { color: var(--white); border-color: var(--white); background: rgba(255,255,255,0.08); }
.intro-progress {
  position: absolute;
  left: 0;
  bottom: 0;
  height: 2px;
  width: 0;
  background: var(--coral);
}

/* ════════════════════════════════════════════════════════
   Solution section: gold headings
   ════════════════════════════════════════════════════════ */
.riff-landing { --gold: #f2b441; }
.riff-landing #solution h2,
.riff-landing #solution .how-title { color: var(--gold); }

/* ════════════════════════════════════════════════════════
   Founding-members: emphasised price
   ════════════════════════════════════════════════════════ */
.riff-landing .what-you-get .price-strong {
  font-weight: 700;
  color: var(--ink);            /* darker than the muted line for instant contrast */
}

/* ════════════════════════════════════════════════════════
   Compact, premium email pill (waitlist)
   ════════════════════════════════════════════════════════ */
.riff-landing .waitlist-form .form-row input[type="email"] {
  padding: 12px 24px;           /* tighter vertical, generous horizontal */
  border-radius: 16px;          /* slightly less round than full pill, still premium */
  font-size: 15px;
}
.riff-landing .waitlist-form .form-row input[type="email"]::placeholder {
  font-size: 14px;
}
.riff-landing .waitlist-form .form-row .btn {
  padding-block: 12px;          /* match the field's reduced height */
  border-radius: 16px;
}
/* On mobile the row becomes a column, where the input's `flex-basis: 200px`
   is read as HEIGHT (not width) — making it 200px tall. Reset to content height. */
@media (max-width: 640px) {
  .riff-landing .waitlist-form .form-row input[type="email"] { flex: 0 0 auto; }
}

/* ════════════════════════════════════════════════════════
   Testimonials — a single black card that flips between quotes
   ════════════════════════════════════════════════════════ */
.riff-landing #proof h2 { text-align: center; }
.riff-landing .testimonial-flip {
  margin-top: clamp(28px, 4vw, 48px);
  display: flex;
  justify-content: center;
  perspective: 1200px;          /* gives the flip real depth */
}
.riff-landing .testimonial {
  width: clamp(280px, 42vw, 460px);
  min-height: 150px;
  padding: 34px 38px;
  background: var(--ink);
  border: 1px solid rgba(255,255,255,0.12);
  border-radius: 18px;
  box-shadow: 0 1px 2px rgba(10,10,10,0.10), 0 22px 50px -20px rgba(10,10,10,0.45);
  display: flex;
  flex-direction: column;
  justify-content: center;
  transform-style: preserve-3d;
  will-change: transform;
}
.riff-landing .testimonial-text {
  margin: 0;
  text-align: center;
  font-size: clamp(18px, 2vw, 24px);
  line-height: 1.4;
  font-weight: 500;
  color: var(--white);
}

/* ════════════════════════════════════════════════════════
   Final statement: white line + coral accent line
   ════════════════════════════════════════════════════════ */
.riff-landing .kicker-h2 .word { color: var(--white); }
.riff-landing .kicker-h2 .accent-text { color: var(--coral); }

/* ════════════════════════════════════════════════════════
   Global scroll reveal — subtle fade-up + blur→sharp on scroll.
   Hidden state only applies once JS adds .reveal/.reveal--soft, so
   content is never stuck invisible if JS or IO is unavailable.
   ════════════════════════════════════════════════════════ */
.riff-landing.js .reveal {
  opacity: 0;
  transform: translateY(12px);
  filter: blur(6px);
  will-change: opacity, transform, filter;
}
.riff-landing.js .reveal--soft {
  opacity: 0;
  filter: blur(5px);
  will-change: opacity, filter;
}
.riff-landing .reveal-on .reveal {
  opacity: 1;
  transform: none;
  filter: blur(0);
  transition:
    opacity 0.85s ease-out,
    transform 0.85s cubic-bezier(0.16, 1, 0.3, 1),
    filter 0.85s ease-out;
  transition-delay: calc(var(--reveal-i, 0) * 80ms);
}
.riff-landing .reveal-on .reveal--soft {
  opacity: 1;
  filter: blur(0);
  transition: opacity 0.8s ease-out, filter 0.8s ease-out;
  transition-delay: calc(var(--reveal-i, 0) * 80ms);
}

/* ── Motion preferences ───────────────────────────────── */
@media (prefers-reduced-motion: reduce) {
  .riff-landing *,
  .riff-landing *::before,
  .riff-landing *::after {
    animation: none !important;
    transition: none !important;
  }
  /* Keep the hero + statement visible when their animations are suppressed. */
  .riff-landing.js .hero-line,
  .riff-landing.js .hero-sub,
  .riff-landing.js .hero-inner .btn,
  .riff-landing.js .strapline,
  .riff-landing.js .word,
  .riff-landing.js .reveal,
  .riff-landing.js .reveal--soft {
    opacity: 1 !important;
    transform: none !important;
    filter: none !important;
  }
}

/* ════════════════════════════════════════════════════════
   The brand beat between the question and the answer:
   one sentence with the mark set inside it, on black.

       That's where
         [ RIFF ]
        comes in.

   Broken over three lines because the lockup is a stacked
   mic-over-wordmark — dropped inline it would tower over the
   type. It stays a single <h2> sentence, so it reads as
   "That's where Riff comes in." to a screen reader.

   The reveal is scroll-LINKED, not scroll-triggered. Progress is
   tied to the scrollbar via animation-timeline: view(), so the
   lines rise as you scroll down and sink back out of sight when
   you scroll up — it plays in both directions, at your pace.
   Each part has its own view() range, so the cadence comes from
   where things sit on the page rather than from delays.

   Without scroll-driven animation support (or under
   prefers-reduced-motion) none of the hidden states apply and the
   section is simply there, fully legible and still.
   ════════════════════════════════════════════════════════ */
.riff-landing .section--intro {
  position: relative;
  overflow: hidden;
  background: var(--ink);
  display: grid;
  place-items: center;
  text-align: center;
}

.riff-landing .intro-line {
  margin: 0;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: clamp(18px, 2.8vw, 34px);
  font-family: var(--display);
  font-weight: 500;
  font-size: clamp(26px, 4.4vw, 54px);
  line-height: 1.05;
  letter-spacing: -0.015em;
  color: var(--white);
}
.riff-landing .intro-mark { display: block; }
.riff-landing .intro-logo {
  display: block;
  width: clamp(190px, 27vw, 340px);
  height: auto;
}

@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    /* Each part rises from below as it comes up the screen. `cover`
       (not `entry`) so the range is measured against the viewport, not
       the element's own height — a single line of type would otherwise
       finish its whole travel in its own 40px of scrolling. */
    .riff-landing .intro-said,
    .riff-landing .intro-mark {
      animation: introRise linear both;
      animation-duration: auto;      /* the shorthand would reset this to 0s */
      animation-timeline: view();
      animation-range: cover 8% cover 40%;
    }
    @keyframes introRise {
      from { opacity: 0; translate: 0 48px; }
      to   { opacity: 1; translate: 0 0; }
    }

    /* …and the whole beat dims back out as it leaves the top. Sits on the
       wrapper so it multiplies with each part's own opacity instead of
       fighting it for the same property. */
    .riff-landing .intro-inner {
      animation: introSink linear both;
      animation-duration: auto;
      animation-timeline: view();
      animation-range: cover 74% cover 97%;
    }
    @keyframes introSink {
      from { opacity: 1; }
      to   { opacity: 0; }
    }
  }
}

/* ── Standalone CTA spacing ───────────────────────────── */
/* Layout only: gives the founding + kicker CTAs the same 36px gap the
   solution section already gets from .section-closing. No new tokens,
   no change to how the button itself looks. */
.riff-landing .cta-standalone { margin-top: 36px; }
