/* ============================================================================
   encore-app.com

   Same tokens as the app (Design/EncoreTheme.swift → app/src/styles/tokens.css).
   The site and the product are one system; a visitor who signs up should not
   feel handed to a different company.

   Daylight. The site now opens on the same surface the product does, so the
   step from marketing into the app is a navigation rather than a change of
   company.

   Values below are copied from `app/src/styles/tokens.css`, not approximated.
   If a colour changes there it changes here, and nowhere else.
   ============================================================================ */

:root {
  --signal: #ff7a2e;

  /* The deck's Daylight is #F2F1ED. The page drops a step below it so white
     panels read as objects rather than faint rectangles. */
  --bg: #edebe6;
  --panel: #ffffff;
  --panel-raised: #e4e2dc;
  --accent-wash: rgb(255 122 46 / 0.14);

  --text-primary: #141414;
  --text-secondary: rgb(20 20 20 / 0.6);
  --text-tertiary: rgb(20 20 20 / 0.6);

  --hairline: rgb(20 20 20 / 0.16);
  --accent: var(--signal);
  /* Signal on Daylight is 2.60:1 on white — nowhere near readable at body
     size. Accent TEXT darkens while fills, dots and rules stay true orange.
     #B84406 clears both surfaces: 4.56:1 on the page, 5.43:1 on a panel. */
  --accent-text: #b84406;
  --on-accent: #ffffff;

  /* Depth was carried by lighter panels on black. On a light page it has to
     come from shadow, or every card reads as a flat outline. */
  --shadow-card: 0 1px 2px rgb(20 20 20 / 0.06);
  --shadow-pop: 0 12px 32px rgb(20 20 20 / 0.14);

  --font-display: 'Archivo Black', system-ui, sans-serif;
  --font-ui: 'Space Grotesk', system-ui, -apple-system, sans-serif;
  --font-spec: 'IBM Plex Mono', ui-monospace, SFMono-Regular, monospace;

  --radius: 14px;
  --gutter: 28px;
  --maxw: 1180px;
}

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  scroll-behavior: smooth;
  -webkit-text-size-adjust: 100%;
}

body {
  margin: 0;
  background: var(--bg);
  color: var(--text-primary);
  font-family: var(--font-ui);
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

img,
svg {
  display: block;
  max-width: 100%;
}
a {
  color: inherit;
  text-decoration: none;
}
h1,
h2,
h3,
h4,
p,
figure {
  margin: 0;
}
ul {
  margin: 0;
  padding: 0;
  list-style: none;
}

:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 3px;
}

/* Keyboard users shouldn't tab the whole nav to reach the page. Hidden until
   focused, then it's the first thing in the tab order. */
.skip {
  position: absolute;
  left: 12px;
  top: -60px;
  z-index: 100;
  padding: 10px 16px;
  border-radius: 8px;
  background: var(--accent);
  color: var(--on-accent);
  font-weight: 600;
  transition: top 0.15s ease;
}
.skip:focus {
  top: 12px;
}

::selection {
  background: var(--accent-wash);
}

.wrap {
  width: 100%;
  max-width: var(--maxw);
  margin: 0 auto;
  padding: 0 var(--gutter);
}

/* ---------------------------------------------------------------- type ---- */

.display {
  font-family: var(--font-display);
  font-weight: 400;
  text-transform: uppercase;
  letter-spacing: -0.02em;
  line-height: 1.02;
}

/*
   Above 1180px the wrap stops growing, so the longest line has a fixed 1124px
   to live in. "IN ONE CLEAN SYSTEM." runs about 12.9x the font size, which
   caps the type at ~87px however wide the window gets. 6rem overflowed it and
   pushed the hero to three lines on any large display.
*/
.d-hero {
  font-size: clamp(2.3rem, 7.1vw, 5.3rem);
}
.d-section {
  font-size: clamp(1.9rem, 3.6vw, 3rem);
}
.d-card {
  font-size: clamp(1.3rem, 2vw, 1.7rem);
}

/* The orange full stop. One per statement — it is the whole punctuation joke
   in the brand, and two of them stops being one. */
.stop {
  color: var(--accent-text);
}

/* The hero's full stop is true Signal rather than the darkened accent ink.
   It carries no information — at 6rem it's a mark, not a word — so the
   readability rule that forces --accent-text on body copy doesn't apply. */
.stop-signal {
  color: var(--signal);
}

.spec {
  font-family: var(--font-spec);
  font-variant-numeric: tabular-nums;
}

.eyebrow {
  font-family: var(--font-spec);
  font-size: 0.68rem;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  color: var(--text-tertiary);
}

.lede {
  font-size: clamp(1rem, 1.5vw, 1.16rem);
  color: var(--text-secondary);
  max-width: 54ch;
}

.dim {
  color: var(--text-secondary);
}
.faint {
  color: var(--text-tertiary);
}

/* ------------------------------------------------------------ structure ---- */

section {
  padding: clamp(64px, 9vw, 120px) 0;
  border-top: 1px solid var(--hairline);
}

/* Numbered section head — the deck's own device: a small orange ordinal, then
   the heading in heavy uppercase. */
.sec-head {
  display: flex;
  align-items: baseline;
  gap: 18px;
  margin-bottom: 14px;
}

.sec-num {
  font-family: var(--font-spec);
  font-size: 0.8rem;
  font-weight: 600;
  color: var(--accent-text);
  flex: none;
}

.sec-intro {
  margin-bottom: clamp(32px, 5vw, 56px);
}

/* -------------------------------------------------------------- header ---- */

header.site {
  position: sticky;
  top: 0;
  z-index: 20;
  /* Was Stage Black at 82%. On Daylight it has to be the page colour, or the
     header reads as a black bar bolted across a light site. */
  background: rgb(237 235 230 / 0.82);
  backdrop-filter: blur(12px);
  border-bottom: 1px solid var(--hairline);
}

.nav {
  display: flex;
  align-items: center;
  gap: 28px;
  height: 66px;
}

.logo {
  display: flex;
  align-items: center;
  gap: 8px;
}
.logo img {
  height: 19px;
  width: auto;
}
/* The wordmark on a phone leaves the button nowhere to go, so the mark takes
   over below the nav's breakpoint. */
.logo-mark {
  display: none;
  /* The wordmark SVG carries no fill, so it renders black — which is exactly
     right on Daylight. The inversion that made it legible on Stage Black is
     gone; leaving it in would have painted white-on-white. */
}
.logo .dot {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--accent);
}

.nav-links {
  display: flex;
  gap: 26px;
  margin-left: auto;
}
.nav-links a {
  font-family: var(--font-spec);
  font-size: 0.74rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--text-secondary);
  transition: color 0.15s ease;
}
.nav-links a:hover {
  color: var(--text-primary);
}
.nav-links a[aria-current='page'] {
  color: var(--accent-text);
  font-weight: 600;
}

/* -------------------------------------------------------------- buttons ---- */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  padding: 12px 22px;
  border-radius: 10px;
  font-size: 0.9rem;
  font-weight: 600;
  white-space: nowrap;
  transition:
    background-color 0.15s ease,
    border-color 0.15s ease;
}

.btn-primary {
  background: var(--accent);
  color: var(--on-accent);
}
.btn-primary:hover {
  background: #ff8f4f;
}

.btn-ghost {
  border: 1px solid var(--hairline);
  color: var(--text-primary);
}
.btn-ghost:hover {
  border-color: rgb(20 20 20 / 0.34);
}

/* ----------------------------------------------------------------- hero ---- */

.hero {
  padding: clamp(56px, 8vw, 104px) 0 clamp(56px, 8vw, 100px);
  position: relative;
  overflow: hidden;
}

/* One slow wash off the top corner. The orange budget for the whole page is
   about 5%, and this spends a fraction of it. */
.hero::before {
  content: '';
  position: absolute;
  inset: -20% 40% 40% -20%;
  background: radial-gradient(closest-side, rgb(255 122 46 / 0.16), transparent);
  pointer-events: none;
}

.hero .wrap {
  position: relative;
}

/* The headline runs the full measure, then the supporting copy and the day
   sheet share a row underneath. The day sheet is deliberately the narrower
   column — it illustrates the claim, it doesn't compete with it. */
.hero-body {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 0.82fr);
  gap: clamp(36px, 6vw, 88px);
  align-items: start;
  margin-top: clamp(32px, 4vw, 52px);
}

.hero-copy {
  max-width: 44ch;
}

.badge {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 5px 12px;
  border: 1px solid var(--hairline);
  border-radius: 999px;
  font-family: var(--font-spec);
  font-size: 0.66rem;
  text-transform: uppercase;
  letter-spacing: 0.14em;
  color: var(--text-secondary);
  margin-bottom: 26px;
}
.badge i {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--accent);
}

.hero h1 {
  margin-bottom: 0;
}

.hero-actions {
  display: flex;
  gap: 12px;
  flex-wrap: wrap;
  margin-top: 32px;
}

.hero-note {
  margin-top: 18px;
  font-family: var(--font-spec);
  font-size: 0.7rem;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  color: var(--text-tertiary);
}

/* ------------------------------------------------------------ day sheet ---- */

/* The product, shown rather than described: a real day sheet in the app's own
   mono rows. Sells the thing better than a screenshot of a screenshot. */
.daysheet {
  background: var(--panel);
  border: 1px solid var(--hairline);
  border-radius: var(--radius);
  overflow: hidden;
}

.daysheet-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 16px 18px;
  border-bottom: 1px solid var(--hairline);
}

.daysheet-head .city {
  font-family: var(--font-display);
  text-transform: uppercase;
  font-size: 1.7rem;
  letter-spacing: -0.02em;
  line-height: 1;
}

.daysheet-rows {
  display: flex;
  flex-direction: column;
}

.daysheet-rows .row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 16px;
  padding: 13px 18px;
  font-size: 0.92rem;
}
.daysheet-rows .row + .row {
  border-top: 1px solid var(--hairline);
}
.daysheet-rows .row time {
  font-family: var(--font-spec);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
}

/* Exactly one row is live. If two are, one of them is wrong. */
.daysheet-rows .row.live,
.daysheet-rows .row.live time {
  color: var(--accent-text);
  font-weight: 600;
}

/* ---------------------------------------------------------------- cards ---- */

.grid {
  display: grid;
  gap: 16px;
}
.grid-3 {
  grid-template-columns: repeat(3, minmax(0, 1fr));
}
.grid-2 {
  grid-template-columns: repeat(2, minmax(0, 1fr));
}

.card {
  background: var(--panel);
  border: 1px solid var(--hairline);
  border-radius: var(--radius);
  padding: 22px;
}

.card h3 {
  margin: 10px 0 8px;
}

.card p {
  color: var(--text-secondary);
  font-size: 0.94rem;
}

/* ---------------------------------------------------------------- steps ---- */

/* -------------------------------------------------------------- roadmap ---- */

.status {
  border: 1px solid var(--hairline);
  border-radius: var(--radius);
  overflow: hidden;
}

.status .row {
  display: flex;
  align-items: center;
  gap: 16px;
  padding: 15px 20px;
  background: var(--panel);
  font-size: 0.95rem;
}
.status .row + .row {
  border-top: 1px solid var(--hairline);
}
.status .row .grow {
  flex: 1;
  min-width: 0;
}

.tag {
  font-family: var(--font-spec);
  font-size: 0.62rem;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  padding: 4px 9px;
  border-radius: 999px;
  background: rgb(20 20 20 / 0.07);
  color: rgb(20 20 20 / 0.62);
  flex: none;
}
.tag.shipped {
  background: var(--accent-wash);
  color: var(--accent-text);
}

/* ----------------------------------------------------------------- quote ---- */

/* ------------------------------------------------------------------- cta ---- */

.cta {
  background: var(--panel);
  border: 1px solid var(--hairline);
  border-radius: var(--radius);
  padding: clamp(30px, 5vw, 54px);
  text-align: center;
}
.cta .lede {
  margin: 14px auto 26px;
}

/* ---------------------------------------------------------------- footer ---- */

footer.site {
  border-top: 1px solid var(--hairline);
  padding: 44px 0;
}

.foot {
  display: flex;
  align-items: center;
  gap: 22px;
  flex-wrap: wrap;
}

.foot .links {
  display: flex;
  gap: 20px;
  margin-left: auto;
  flex-wrap: wrap;
}

.foot a,
.foot span {
  font-family: var(--font-spec);
  font-size: 0.7rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--text-tertiary);
}
.foot a:hover {
  color: var(--text-primary);
}

/* ----------------------------------------------------------- responsive ---- */

@media (max-width: 900px) {
  .logo-word {
    display: none;
  }
  .logo-mark {
    display: block;
    height: 22px;
  }
  /* `.nav-links` carried the auto margin that pushed the button right. Hidden,
     it pushed nothing, and the button sat against the logo. */
  .nav .btn-primary {
    margin-left: auto;
  }
  .hero-body {
    grid-template-columns: minmax(0, 1fr);
    gap: 32px;
  }
  .hero-copy {
    max-width: 54ch;
  }
  .grid-3 {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
  .nav-links {
    display: none;
  }
}

@media (max-width: 620px) {
  :root {
    --gutter: 20px;
  }
  .grid-3,
  .grid-2 {
    grid-template-columns: minmax(0, 1fr);
  }
  .demo-step {
    grid-template-columns: minmax(0, 1fr);
    gap: 8px;
  }
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }
  * {
    transition-duration: 0.01ms !important;
  }
}

/* -------------------------------------------------------------- legal ---- */

/* The privacy and terms pages share this stylesheet and are pure prose.
   They keep their own markup — the copy is legal text and shouldn't be
   restructured to suit a layout — so the classes they already use are styled
   here rather than the pages being rewritten around new ones. */
.legal {
  padding: clamp(48px, 7vw, 84px) 0 100px;
}
.legal .wrap,
.legal .doc {
  max-width: 780px;
}

.legal h1 {
  font-family: var(--font-display);
  text-transform: uppercase;
  letter-spacing: -0.02em;
  line-height: 1.04;
  font-size: clamp(1.9rem, 4vw, 2.8rem);
  margin-bottom: 10px;
}

.legal h2 {
  font-family: var(--font-display);
  text-transform: uppercase;
  letter-spacing: -0.01em;
  font-size: 1.1rem;
  margin: 40px 0 12px;
}

.legal h3 {
  font-size: 1rem;
  font-weight: 600;
  margin: 24px 0 8px;
}

.legal p,
.legal li {
  color: var(--text-secondary);
  margin-bottom: 12px;
}

.legal ul {
  list-style: disc;
  padding-left: 20px;
  margin-bottom: 16px;
}

.legal a {
  color: var(--accent-text);
}

.legal .updated {
  font-family: var(--font-spec);
  font-size: 0.7rem;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  color: var(--text-tertiary);
  margin-bottom: 28px;
}

/* The plain-English summary at the top of each document. */
.legal .callout {
  background: var(--panel);
  border: 1px solid var(--hairline);
  border-left: 2px solid var(--accent);
  border-radius: var(--radius);
  padding: 18px 20px;
  margin: 24px 0 32px;
}
.legal .callout p:last-child {
  margin-bottom: 0;
}

/* Footer variants used by the legal pages. */
.foot-links {
  display: flex;
  gap: 20px;
  margin-left: auto;
  flex-wrap: wrap;
}
.foot-links a,
.foot-legal {
  font-family: var(--font-spec);
  font-size: 0.7rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--text-tertiary);
}
.foot-links a:hover {
  color: var(--text-primary);
}
.foot .logo img {
  height: 16px;
}

/* The caption exists for screen readers; the artwork carries it visually. */
.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  padding: 0;
  margin: -1px;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}

/* ------------------------------------------------------------- bento ---- */

/*
   The feature mosaic.

   Real interface rather than screenshots, so the cards are live DOM and the
   grid is explicit: named areas on a 12-column track, mixed spans, one dark
   cell the eye lands on first. Every area below is a rectangle — if you
   rearrange them, keep them rectangular or the whole template is discarded.
*/
.bento {
  display: grid;
  grid-template-columns: repeat(12, minmax(0, 1fr));
  grid-auto-rows: minmax(94px, auto);
  gap: clamp(10px, 1vw, 14px);
  grid-template-areas:
    "sched   sched   sched   sched   crew    crew    crew    hero    hero    hero    plat  plat"
    "roster  roster  roster  roster  roster  travel  travel  hero    hero    hero    plat  plat"
    "roster  roster  roster  roster  roster  travel  travel  hero    hero    hero    exp   exp"
    "offline offline offline db      db      db      db      push    push    push    exp   exp";
}

.b-sched   { grid-area: sched; }
.b-crew    { grid-area: crew; }
.b-hero    { grid-area: hero; }
.b-plat    { grid-area: plat; }
.b-roster  { grid-area: roster; }
.b-travel  { grid-area: travel; }
.b-exp     { grid-area: exp; }
.b-offline { grid-area: offline; }
.b-db      { grid-area: db; }
.b-push    { grid-area: push; }

/* Graphic at the top, label at the bottom — the arrangement the reference
   uses, and the reason `.bcard-ui` takes the auto margin. */
.bcard {
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  gap: 8px;
  min-width: 0;
  padding: clamp(15px, 1.5vw, 22px);
  position: relative;
  background: none;
}

/*
   The visible surface. Sizing stays with the card — which keeps the grid rows
   honest — while this layer is free to grow past its own edges on hover
   without moving a single word of the content in front of it.
*/
.bcard-bg {
  position: absolute;
  inset: 0;
  z-index: 0;
  border-radius: clamp(16px, 1.7vw, 24px);
  background: var(--panel-raised);
}

.bcard > *:not(.bcard-bg) {
  position: relative;
  z-index: 1;
}

.js-on .bcard-bg {
  transition: inset 0.34s cubic-bezier(0.22, 0.61, 0.36, 1);
}

@media (prefers-reduced-motion: reduce) {
  .js-on .bcard-bg {
    transition: none;
  }
}

.bcard-ui {
  margin-bottom: auto;
}

.bcard-title {
  font-family: var(--font-ui);
  font-weight: 600;
  font-size: clamp(1rem, 1.35vw, 1.28rem);
  line-height: 1.18;
  letter-spacing: -0.01em;
  text-wrap: balance;
  color: var(--text-primary);
}

/* The page's --text-secondary was set against the page, not against a card.
   On --panel-raised it lands at 4.3:1, just under AA — so small type inside a
   card gets its own darker ink. */
.bcard-sub {
  font-size: 0.83rem;
  line-height: 1.45;
  color: rgb(20 20 20 / 0.7);
  max-width: 40ch;
}

.bcard-eyebrow {
  font-family: var(--font-spec);
  font-size: 0.62rem;
  text-transform: uppercase;
  letter-spacing: 0.16em;
  color: rgb(20 20 20 / 0.72);
}

/* The one big numeral, per the reference's "64GB" beat. */
.bcard-stat {
  font-family: var(--font-display);
  font-size: clamp(3.2rem, 5.5vw, 5rem);
  line-height: 0.86;
  color: var(--accent-text);
  margin-bottom: auto;
}

/* ---- the dark cell ---- */

.b-hero {
  gap: 14px;
}
.b-hero .bcard-bg {
  background: #141414;
}
.b-hero .bcard-title { color: #fff; }
.b-hero .bcard-eyebrow {
  color: rgb(255 255 255 / 0.5);
  margin-bottom: 2px;
}

/* ---- mini day sheet ---- */

.daysheet-mini {
  border-radius: 10px;
  background: var(--panel);
  overflow: hidden;
}
.dm-row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 12px;
  padding: 7px 11px;
  font-size: 0.78rem;
  color: var(--text-secondary);
}
.dm-row + .dm-row { border-top: 1px solid var(--hairline); }
.dm-row time {
  font-family: var(--font-spec);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  color: var(--text-primary);
}
.dm-row.live span,
.dm-row.live time { color: var(--accent-text); }

/* ---- crew chips ---- */

.crew-mini {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
}
.chip {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 38px;
  height: 30px;
  padding: 0 9px;
  border-radius: 999px;
  background: var(--panel);
  font-family: var(--font-spec);
  font-size: 0.66rem;
  font-weight: 600;
  letter-spacing: 0.06em;
  color: var(--text-primary);
}
.chip-more {
  background: var(--accent-wash);
  color: var(--accent-text);
}

/* ---- the tour run, inside the dark cell ---- */

.run-mini {
  display: flex;
  flex-direction: column;
}
.rm-row {
  display: flex;
  align-items: baseline;
  gap: 12px;
  padding: 7px 0;
  font-size: 0.84rem;
  color: rgb(255 255 255 / 0.82);
}
.rm-row + .rm-row { border-top: 1px solid rgb(255 255 255 / 0.1); }
.rm-d {
  font-family: var(--font-spec);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  color: rgb(255 255 255 / 0.45);
}
.rm-c { flex: 1; min-width: 0; }
.rm-row.off .rm-c { color: rgb(255 255 255 / 0.4); font-style: italic; }
.rm-row.live .rm-c,
.rm-row.live .rm-d { color: var(--accent); }
.rm-tag {
  font-family: var(--font-spec);
  font-size: 0.58rem;
  text-transform: uppercase;
  letter-spacing: 0.14em;
  padding: 2px 7px;
  border-radius: 999px;
  background: var(--accent);
  color: var(--on-accent);
}

/* ---- platforms ---- */

.plat-mini {
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.plat-mini span {
  padding: 7px 11px;
  border-radius: 9px;
  background: var(--panel);
  font-family: var(--font-spec);
  font-size: 0.68rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: var(--text-primary);
}

/* ---- roster timeline ---- */

.roster-mini {
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.rs-row {
  display: grid;
  grid-template-columns: 62px repeat(10, minmax(0, 1fr));
  align-items: center;
  gap: 3px;
}
.rs-name {
  font-family: var(--font-spec);
  font-size: 0.6rem;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: rgb(20 20 20 / 0.72);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
/* The bar sits on the day track it actually covers. */
.rs-row i {
  grid-row: 1;
  grid-column: calc(var(--s) + 1) / calc(var(--e) + 2);
  height: 13px;
  border-radius: 4px;
  background: var(--panel);
}
.rs-row i.clash {
  background: var(--accent);
}

/* ---- flight ---- */

.flight-mini {
  padding: 11px 13px;
  border-radius: 10px;
  background: var(--panel);
}
.fm-leg {
  display: flex;
  align-items: center;
  gap: 9px;
  font-family: var(--font-spec);
  font-weight: 600;
  font-size: 0.95rem;
  color: var(--text-primary);
}
.fm-leg i {
  flex: 1;
  height: 1px;
  background: var(--hairline);
  position: relative;
}
.fm-leg i::after {
  content: '';
  position: absolute;
  right: -1px;
  top: -2px;
  border-left: 5px solid var(--accent);
  border-top: 2.5px solid transparent;
  border-bottom: 2.5px solid transparent;
}
.fm-meta {
  margin-top: 5px;
  font-family: var(--font-spec);
  font-size: 0.64rem;
  letter-spacing: 0.06em;
  color: rgb(20 20 20 / 0.72);
}

/* ---- signal bars ---- */

.sig-mini {
  display: flex;
  align-items: flex-end;
  gap: 4px;
  height: 30px;
}
.sig-mini i {
  width: 8px;
  border-radius: 2px;
  background: var(--accent);
}
.sig-mini i:nth-child(1) { height: 30%; }
.sig-mini i:nth-child(2) { height: 55%; }
.sig-mini i:nth-child(3) { height: 78%; }
.sig-mini i:nth-child(4) { height: 100%; }
.sig-mini i.dim { background: var(--hairline); }

/*
   Tablet: six columns. The mosaic keeps its mixed spans but the tall right-hand
   stack folds into the flow, since at this width a 2/12 column is a sliver.
*/
@media (max-width: 1000px) {
  .bento {
    grid-template-columns: repeat(6, minmax(0, 1fr));
    grid-template-areas:
      "hero    hero    hero    sched   sched   sched"
      "hero    hero    hero    crew    crew    crew"
      "roster  roster  roster  roster  travel  travel"
      "exp     exp     plat    plat    offline offline"
      "db      db      db      push    push    push";
  }
}

/*
   Phone: still a mosaic, just a two-column one.

   Stacking all ten cards full-width made the section about 2,000px of scroll.
   Only the two cards that genuinely need the measure — the tour run and the
   roster timeline — stay full width; the rest pair up. Grid rows stretch, so
   each pair matches height without any minimum being set.

   The mini interfaces shrink with it: the run list drops its tail, the platform
   list turns into a row rather than a stack, and the type steps down a notch.
*/
@media (max-width: 700px) {
  .bento {
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 8px;
    grid-template-areas:
      "hero    hero"
      "sched   sched"
      "crew    travel"
      "roster  roster"
      "exp     offline"
      "plat    push"
      "db      db";
  }

  .bcard {
    padding: 13px;
    border-radius: 15px;
    gap: 6px;
  }

  .bcard-title {
    font-size: 0.94rem;
    line-height: 1.22;
  }
  .bcard-sub {
    font-size: 0.75rem;
    line-height: 1.4;
  }
  .bcard-stat {
    font-size: 2.9rem;
  }

  /* Nine dates is a scroll of its own on a phone. Five makes the point. */
  .rm-row:nth-child(n + 6) {
    display: none;
  }
  .rm-row {
    padding: 5px 0;
    font-size: 0.8rem;
  }
  .b-hero {
    gap: 10px;
  }

  .dm-row {
    padding: 6px 10px;
  }

  .plat-mini {
    flex-direction: row;
    flex-wrap: wrap;
  }
  .plat-mini span {
    padding: 5px 9px;
    font-size: 0.62rem;
  }

  .chip {
    min-width: 0;
    height: 25px;
    padding: 0 7px;
    font-size: 0.58rem;
  }
  .crew-mini {
    flex-wrap: nowrap;
  }

  /* 52px clipped "ARTIST A" to an ellipsis. Smaller label, wider column. */
  .rs-name {
    font-size: 0.53rem;
    letter-spacing: 0.04em;
  }
  .rs-row {
    grid-template-columns: 58px repeat(10, minmax(0, 1fr));
  }
  .rs-row i {
    height: 11px;
  }

  .sig-mini {
    height: 22px;
  }
  .sig-mini i {
    width: 6px;
  }
}

/* ------------------------------------------------------------- motion ---- */

/*
   Entrances. Gated on `js-on` so that if the script never runs, nothing is
   ever left hidden — the page degrades to no animation rather than no content.
*/
.js-on .reveal {
  opacity: 0;
  transform: translateY(18px);
  transition:
    opacity 0.6s cubic-bezier(0.22, 0.61, 0.36, 1),
    transform 0.6s cubic-bezier(0.22, 0.61, 0.36, 1);
}
.js-on .reveal.is-in {
  opacity: 1;
  transform: none;
}

/*
   The lifted card rises very slightly out of the page while it grows, and the
   contents come with it: the panel expanding on its own reads as a background
   change, whereas the type and the mini interfaces easing up a step sells the
   card as one object being picked up.

   Everything here is transform and opacity, so the inner motion costs nothing
   on top of the inset transition already running on the panel.
*/
.js-on .bcard.is-lift .bcard-bg {
  box-shadow: 0 10px 26px rgb(20 20 20 / 0.1);
}

.js-on .bcard > *:not(.bcard-bg) {
  transition: transform 0.34s cubic-bezier(0.22, 0.61, 0.36, 1);
}
.js-on .bcard.is-lift > *:not(.bcard-bg) {
  transform: translateY(-3px);
}

/* The graphic leads, the words follow. A hair more travel and a hair more
   scale on the interface pieces than on the type reading under them. */
.js-on .bcard.is-lift .bcard-ui,
.js-on .bcard.is-lift .bcard-stat {
  transform: translateY(-5px) scale(1.03);
}
.js-on .bcard .bcard-ui,
.js-on .bcard .bcard-stat {
  transform-origin: left center;
}

/* The one row of live colour in the collage brightens as the card comes up. */
.js-on .bcard .rs-row i.clash,
.js-on .bcard .sig-mini i {
  transition:
    transform 0.34s cubic-bezier(0.22, 0.61, 0.36, 1),
    filter 0.34s ease;
}
.js-on .bcard.is-lift .rs-row i.clash {
  transform: scaleX(1.04);
}
.js-on .bcard.is-lift .sig-mini i:not(.dim) {
  filter: saturate(1.15);
}

/* Cards the hover pushed against ease back a touch, so the squeeze reads on
   both sides of every shared edge. */
.js-on .bcard:not(.is-lift) > *:not(.bcard-bg) {
  transform: translateY(0);
}

@media (prefers-reduced-motion: reduce) {
  .js-on .bcard > *:not(.bcard-bg),
  .js-on .bcard.is-lift > *:not(.bcard-bg),
  .js-on .bcard.is-lift .bcard-ui,
  .js-on .bcard.is-lift .bcard-stat {
    transform: none;
    transition: none;
  }
}

.btn,
.nav-links a,
.tier,
.demo-arrow,
.demo-dots button {
  transition:
    background-color 0.2s ease,
    border-color 0.2s ease,
    color 0.2s ease,
    transform 0.2s cubic-bezier(0.22, 0.61, 0.36, 1),
    box-shadow 0.2s ease;
}
.btn:hover {
  transform: translateY(-1px);
}
.btn:active {
  transform: translateY(0);
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }
  .js-on .reveal {
    opacity: 1;
    transform: none;
    transition: none;
  }
  .btn:hover {
    transform: none;
  }
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
  }
}

/* --------------------------------------------------------------- demo ---- */

.demo {
  display: flex;
  flex-direction: column;
  gap: clamp(18px, 2.4vw, 30px);
}

/* The window. Desktop only — below that it reads as a postage stamp, and the
   four cards carry the explanation on their own. */
.demo-app {
  display: none;
  border-radius: 16px;
  overflow: hidden;
  background: var(--panel);
  border: 1px solid var(--hairline);
  box-shadow: var(--shadow-pop);
}

@media (min-width: 1001px) {
  .demo-app {
    display: block;
  }
}

.app-bar {
  display: flex;
  align-items: center;
  gap: 7px;
  padding: 10px 14px;
  border-bottom: 1px solid var(--hairline);
  background: var(--panel-raised);
}
.app-bar .tl {
  width: 10px;
  height: 10px;
  border-radius: 50%;
  background: rgb(20 20 20 / 0.16);
}
.app-url {
  margin-left: 14px;
  padding: 3px 12px;
  border-radius: 999px;
  background: var(--panel);
  font-family: var(--font-spec);
  font-size: 0.62rem;
  color: rgb(20 20 20 / 0.55);
}

.app-body {
  display: grid;
  grid-template-columns: 156px minmax(0, 1fr);
  min-height: 436px;
}

.app-side {
  display: flex;
  flex-direction: column;
  gap: 3px;
  padding: 16px 12px;
  border-right: 1px solid var(--hairline);
  background: var(--bg);
}
.app-brand {
  display: flex;
  align-items: center;
  gap: 5px;
  margin-bottom: 14px;
  padding-left: 8px;
  font-family: var(--font-display);
  font-size: 0.86rem;
  text-transform: lowercase;
  letter-spacing: -0.02em;
}
.app-brand i {
  width: 4px;
  height: 4px;
  border-radius: 50%;
  background: var(--accent);
}
.app-nav {
  padding: 7px 10px;
  border-radius: 8px;
  font-size: 0.78rem;
  color: rgb(20 20 20 / 0.62);
  transition:
    background-color 0.3s ease,
    color 0.3s ease;
}
.app-nav.quiet {
  color: rgb(20 20 20 / 0.34);
}
.app-nav.is-on {
  background: var(--accent-wash);
  color: var(--accent-text);
  font-weight: 600;
}

.app-main {
  position: relative;
  padding: 20px 22px;
}

/* One stage visible at a time; the others are laid out on top of each other so
   the window keeps a single height as the story moves. */
.stage {
  position: absolute;
  inset: 20px 22px auto 22px;
  opacity: 0;
  transform: translateY(10px);
  pointer-events: none;
  transition:
    opacity 0.4s ease,
    transform 0.4s cubic-bezier(0.22, 0.61, 0.36, 1);
}
.stage.is-on {
  opacity: 1;
  transform: none;
  pointer-events: auto;
}

.app-head {
  display: flex;
  align-items: center;
  gap: 10px;
  margin-bottom: 14px;
}
.app-title {
  font-family: var(--font-display);
  font-size: 1.15rem;
  text-transform: uppercase;
  letter-spacing: -0.02em;
}
.app-pill {
  padding: 2px 9px;
  border-radius: 999px;
  background: var(--panel-raised);
  font-family: var(--font-spec);
  font-size: 0.58rem;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  color: rgb(20 20 20 / 0.62);
}
.app-pill.live {
  background: var(--accent);
  color: var(--on-accent);
}
.app-eyebrow {
  display: block;
  font-family: var(--font-spec);
  font-size: 0.56rem;
  text-transform: uppercase;
  letter-spacing: 0.14em;
  color: rgb(20 20 20 / 0.55);
}

/* ---- forms that fill themselves in ---- */

.app-form {
  display: flex;
  flex-direction: column;
  gap: 8px;
  margin-bottom: 14px;
}
.fld-row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 8px;
}
.fld {
  display: flex;
  align-items: center;
  gap: 10px;
  min-height: 34px;
  padding: 6px 11px;
  border: 1px solid var(--hairline);
  border-radius: 9px;
  background: var(--panel);
}
.fld > span {
  flex: none;
  width: 52px;
  font-family: var(--font-spec);
  font-size: 0.58rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: rgb(20 20 20 / 0.5);
}
.fld > b {
  font-size: 0.84rem;
  font-weight: 500;
}
/* The caret only exists while something is being typed. */
.fld > b.is-typing::after {
  content: '';
  display: inline-block;
  width: 1.5px;
  height: 0.95em;
  margin-left: 1px;
  background: var(--accent);
  vertical-align: -0.12em;
  animation: caret 0.9s steps(1) infinite;
}
@keyframes caret {
  50% {
    opacity: 0;
  }
}

.app-split {
  display: grid;
  grid-template-columns: 128px minmax(0, 1fr);
  gap: 14px;
}
.stage[data-stage='3'] .app-split {
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
}

.app-rows {
  display: flex;
  flex-direction: column;
  gap: 7px;
}

/* Everything with data-pop starts folded away and is dealt in by the script. */
[data-pop] {
  opacity: 0;
  transform: translateY(9px) scale(0.985);
  transition:
    opacity 0.36s ease,
    transform 0.36s cubic-bezier(0.22, 0.61, 0.36, 1);
}
[data-pop].is-on {
  opacity: 1;
  transform: none;
}

.poster {
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.poster i {
  display: block;
  aspect-ratio: 2 / 3;
  border-radius: 8px;
  background:
    linear-gradient(140deg, rgb(255 122 46 / 0.9), rgb(255 122 46 / 0.35)),
    var(--panel-raised);
}
.poster figcaption {
  font-family: var(--font-spec);
  font-size: 0.55rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: rgb(20 20 20 / 0.5);
}

.arow {
  display: flex;
  align-items: baseline;
  gap: 10px;
  padding: 8px 11px;
  border-radius: 9px;
  background: var(--panel-raised);
  font-size: 0.8rem;
}
.arow b {
  font-family: var(--font-spec);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  flex: none;
}
.arow span {
  font-weight: 500;
}
.arow i {
  margin-left: auto;
  font-style: normal;
  font-size: 0.72rem;
  color: rgb(20 20 20 / 0.55);
}
.arow.live {
  background: var(--accent-wash);
}
.arow.live b,
.arow.live span {
  color: var(--accent-text);
}

.fcard {
  display: flex;
  align-items: center;
  gap: 11px;
  padding: 9px 12px;
  border: 1px solid var(--hairline);
  border-radius: 10px;
  background: var(--panel);
}
.fcard img {
  flex: none;
  border-radius: 5px;
}
.fc-leg {
  display: flex;
  align-items: center;
  gap: 8px;
  font-family: var(--font-spec);
  font-weight: 600;
  font-size: 0.86rem;
}
.fc-leg i {
  width: 34px;
  height: 1px;
  background: var(--hairline);
  position: relative;
}
.fc-leg i::after {
  content: '';
  position: absolute;
  right: -1px;
  top: -2px;
  border-left: 5px solid var(--accent);
  border-top: 2.5px solid transparent;
  border-bottom: 2.5px solid transparent;
}
.fc-meta {
  display: flex;
  gap: 12px;
  margin-left: auto;
  font-family: var(--font-spec);
  font-size: 0.62rem;
  color: rgb(20 20 20 / 0.55);
}

.hcard {
  display: flex;
  align-items: baseline;
  gap: 10px;
  padding: 9px 12px;
  border-radius: 10px;
  background: var(--panel-raised);
  font-size: 0.8rem;
}
.hcard span {
  margin-left: auto;
  font-family: var(--font-spec);
  font-size: 0.62rem;
  color: rgb(20 20 20 / 0.55);
}

.app-send {
  margin-bottom: 10px;
}
.fakebtn {
  display: inline-block;
  padding: 8px 16px;
  border-radius: 9px;
  background: var(--accent);
  color: var(--on-accent);
  font-size: 0.8rem;
  font-weight: 600;
  transition: transform 0.16s ease;
}
.fakebtn.is-press {
  transform: scale(0.94);
}

.app-toast {
  display: flex;
  align-items: center;
  gap: 9px;
  margin-bottom: 10px;
  padding: 9px 12px;
  border-radius: 9px;
  background: rgb(46 140 74 / 0.12);
  font-size: 0.78rem;
  color: #1f6b39;
}
.app-toast i {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  background: #2e8c4a;
}

.crow {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 11px;
  border-radius: 9px;
  background: var(--panel-raised);
  font-size: 0.8rem;
}
.crow .av {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 32px;
  height: 24px;
  border-radius: 999px;
  background: var(--panel);
  font-family: var(--font-spec);
  font-size: 0.58rem;
  font-weight: 600;
}
.crow i {
  font-style: normal;
  font-size: 0.72rem;
  color: rgb(20 20 20 / 0.55);
}
.crow em {
  margin-left: auto;
  font-style: normal;
  font-family: var(--font-spec);
  font-size: 0.58rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: rgb(20 20 20 / 0.55);
}

.nextup {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 16px;
  margin-bottom: 12px;
  padding: 13px 15px;
  border-radius: 11px;
  background: var(--panel-raised);
  border-left: 3px solid var(--accent);
}
.nextup b {
  display: block;
  font-size: 0.98rem;
  margin-top: 3px;
}
.nextup i {
  font-style: normal;
  font-size: 0.76rem;
  color: rgb(20 20 20 / 0.6);
}
.nu-time {
  text-align: right;
  flex: none;
}
.nu-time b {
  font-family: var(--font-spec);
  font-size: 1.2rem;
  color: var(--accent-text);
}
.nu-time span {
  font-family: var(--font-spec);
  font-size: 0.6rem;
  color: rgb(20 20 20 / 0.55);
}

/* ---- the step heading above the window ---- */

/*
   No card. The step's own heading is the label, sitting between the section
   title and the window, with the only control on the far right.
*/
.demo-deck {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: start;
  gap: 20px;
}

.demo-steps {
  display: grid;
}

.demo-step p {
  margin-top: 8px;
  max-width: 62ch;
  font-size: 0.95rem;
  color: rgb(20 20 20 / 0.68);
}

.demo-arrow {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 48px;
  height: 48px;
  padding: 0;
  border: 1px solid var(--hairline);
  border-radius: 50%;
  background: var(--panel);
  color: var(--text-primary);
  cursor: pointer;
}
.demo-arrow:hover {
  border-color: var(--accent);
  color: var(--accent-text);
  transform: scale(1.06);
}

/* One step at a time, stacked in the same grid cell so the block keeps a
   single height as the copy changes length. */
@media (min-width: 1001px) {
  .demo-step {
    grid-area: 1 / 1;
    opacity: 0;
    transform: translateY(8px);
    pointer-events: none;
    transition:
      opacity 0.34s ease,
      transform 0.34s cubic-bezier(0.22, 0.61, 0.36, 1);
  }
  .demo-step.is-on {
    opacity: 1;
    transform: none;
    pointer-events: auto;
  }
}

.demo-dots {
  display: flex;
  justify-content: center;
  gap: 8px;
}
.demo-dots button {
  width: 8px;
  height: 8px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: rgb(20 20 20 / 0.2);
  cursor: pointer;
}
.demo-dots button.is-on {
  background: var(--accent);
  transform: scale(1.25);
}

/* Below the window's breakpoint there is nothing to step through, so all four
   steps simply stack and the control disappears. */
@media (max-width: 1000px) {
  .demo-dots,
  .demo-arrow {
    display: none;
  }
  .demo-deck {
    display: block;
  }
  .demo-steps {
    gap: 26px;
  }
}

/* ------------------------------------------------------------ pricing ---- */

.tiers {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  grid-template-rows: auto auto auto 1fr auto;
  gap: clamp(10px, 1.1vw, 16px);
  align-items: stretch;
}

@media (max-width: 860px) {
  .tiers {
    grid-template-columns: minmax(0, 1fr);
  }
}

/*
   Subgrid, so name / description / price / features / control each sit on a
   row shared by all three cards. Without it the price floats to wherever the
   description above it happens to end, and the three never line up.
*/
.tier {
  position: relative;
  display: grid;
  grid-row: span 5;
  grid-template-rows: subgrid;
  align-content: start;
  gap: 10px;
  padding: 22px 20px;
  border-radius: 14px;
  background: var(--panel);
  border: 1px solid var(--hairline);
}
.tier:hover {
  box-shadow: var(--shadow-card);
  transform: translateY(-2px);
}

/* One tier is marked, and it is marked with a hairline rather than a fill —
   a solid orange card would spend the whole page's accent budget at once. */
.tier.is-lead {
  border-color: var(--accent);
}
.tier-flag {
  position: absolute;
  top: -9px;
  left: 20px;
  padding: 2px 9px;
  border-radius: 999px;
  background: var(--accent);
  color: var(--on-accent);
  font-family: var(--font-spec);
  font-size: 0.55rem;
  text-transform: uppercase;
  letter-spacing: 0.12em;
}

.tier-name {
  font-family: var(--font-display);
  font-size: 1.25rem;
  text-transform: uppercase;
  letter-spacing: -0.02em;
}
.tier-line {
  font-size: 0.82rem;
  color: rgb(20 20 20 / 0.62);
}
.tier-price {
  padding: 10px 0;
  border-top: 1px solid var(--hairline);
  border-bottom: 1px solid var(--hairline);
}
.tier-price b {
  display: block;
  font-family: var(--font-display);
  font-size: 1.5rem;
  letter-spacing: -0.02em;
  color: var(--accent-text);
}
.tier-price span {
  font-family: var(--font-spec);
  font-size: 0.6rem;
  text-transform: uppercase;
  letter-spacing: 0.12em;
  color: rgb(20 20 20 / 0.55);
}

.tier-list {
  display: flex;
  flex-direction: column;
  gap: 7px;
  font-size: 0.85rem;
  color: rgb(20 20 20 / 0.75);
}
.tier-list li {
  padding-left: 17px;
  position: relative;
}
.tier-list li::before {
  content: '';
  position: absolute;
  left: 0;
  top: 0.55em;
  width: 7px;
  height: 7px;
  border-radius: 2px;
  background: var(--accent);
}
/* A limit, not a feature — so it doesn't get a tick-shaped mark. */
.tier-list li.off::before {
  background: rgb(20 20 20 / 0.22);
}

.tier-btn {
  margin-top: auto;
  align-self: flex-start;
  padding: 9px 16px;
  font-size: 0.82rem;
}

.tier-notes {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
  gap: 18px 28px;
  margin-top: clamp(28px, 3.5vw, 44px);
  padding-top: clamp(24px, 3vw, 34px);
  border-top: 1px solid var(--hairline);
}
.tier-notes p {
  font-size: 0.88rem;
  line-height: 1.55;
  color: rgb(20 20 20 / 0.68);
}
.tier-notes b {
  color: var(--text-primary);
}
.tier-notes a {
  color: var(--accent-text);
  text-decoration: underline;
  text-underline-offset: 2px;
}

/* ------------------------------------------------------------- roadmap ---- */

/* A page hero rather than the home page's: no radial wash competing with a
   dense status list further down. */
.hero-page {
  padding: clamp(48px, 6vw, 84px) 0 clamp(40px, 5vw, 66px);
}
.hero-page::before {
  display: none;
}
.hero-page .d-hero {
  font-size: clamp(2.4rem, 6vw, 4.6rem);
}

.rm-key {
  display: flex;
  flex-direction: column;
  gap: 10px;
  padding: 20px;
  border: 1px solid var(--hairline);
  border-radius: var(--radius);
  background: var(--panel);
}
.rm-key-row {
  display: flex;
  align-items: baseline;
  gap: 12px;
  font-size: 0.83rem;
  color: rgb(20 20 20 / 0.68);
}

.tag.beta {
  background: rgb(255 122 46 / 0.1);
  color: var(--accent-text);
}
.tag.building {
  background: rgb(20 20 20 / 0.86);
  color: #fff;
}

.rm-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
  gap: clamp(10px, 1.1vw, 16px);
}

.rm-item {
  display: flex;
  flex-direction: column;
  gap: 9px;
  padding: 20px;
  border: 1px solid var(--hairline);
  border-radius: 13px;
  background: var(--panel);
}
.rm-top {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 12px;
}
.rm-item h3 {
  font-family: var(--font-ui);
  font-weight: 600;
  font-size: 1.02rem;
  letter-spacing: -0.01em;
}
.rm-item p {
  font-size: 0.87rem;
  line-height: 1.5;
  color: rgb(20 20 20 / 0.68);
}
/* The platform line is the point of the card — which of the three apps this
   is actually true on. */
.rm-plat {
  margin-top: auto;
  padding-top: 4px;
  font-family: var(--font-spec);
  font-size: 0.6rem;
  text-transform: uppercase;
  letter-spacing: 0.1em;
  color: rgb(20 20 20 / 0.5);
}

@media (max-width: 900px) {
  .rm-key {
    order: -1;
  }
}

/* --------------------------------------------------------- pricing tabs ---- */

.pricing {
  display: flex;
  flex-direction: column;
  gap: clamp(20px, 2.4vw, 32px);
}

.ptabs {
  display: inline-flex;
  align-self: center;
  gap: 4px;
  padding: 4px;
  border-radius: 999px;
  background: var(--panel-raised);
}
.ptabs button {
  padding: 9px 20px;
  border: 0;
  border-radius: 999px;
  background: none;
  font-family: var(--font-ui);
  font-size: 0.84rem;
  font-weight: 600;
  color: rgb(20 20 20 / 0.62);
  cursor: pointer;
  white-space: nowrap;
}
.ptabs button:hover {
  color: var(--text-primary);
}
.ptabs button.is-on {
  background: var(--panel);
  color: var(--text-primary);
  box-shadow: var(--shadow-card);
}

/* The 5/15 switch inside the Agency card. Same shape as the period tabs, one
   step smaller, so it reads as the same kind of control. */
.seats {
  align-self: end;
  display: flex;
  gap: 3px;
  padding: 3px;
  border-radius: 999px;
  background: var(--panel-raised);
}
.seats button {
  flex: 1;
  padding: 6px 11px;
  border: 0;
  border-radius: 999px;
  background: none;
  font-family: var(--font-spec);
  font-size: 0.62rem;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  color: rgb(20 20 20 / 0.6);
  cursor: pointer;
  white-space: nowrap;
  transition:
    background-color 0.2s ease,
    color 0.2s ease;
}
.seats button[aria-pressed='true'] {
  background: var(--panel);
  color: var(--accent-text);
  box-shadow: var(--shadow-card);
}

.tier-list b {
  color: var(--text-primary);
  font-weight: 600;
}

/* ---- the one-off tab ---- */

/*
   One card on its own would look stranded in a three-column grid, so this tab
   pairs it with the argument for buying it. Copy on the left, card on the
   right, and the card gets a little more room than a normal tier.
*/
.oneoff {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 0.82fr);
  gap: clamp(24px, 4vw, 56px);
  align-items: start;
}

.oneoff-copy {
  display: flex;
  flex-direction: column;
  gap: 16px;
}
.oneoff-copy h3 {
  max-width: 15ch;
}
.oneoff-note {
  font-family: var(--font-spec);
  font-size: 0.7rem;
  text-transform: uppercase;
  letter-spacing: 0.08em;
  line-height: 1.7;
  color: rgb(20 20 20 / 0.5);
}

.tier-solo {
  display: flex;
  flex-direction: column;
  grid-row: auto;
  padding: clamp(24px, 2.6vw, 34px);
  border-color: var(--accent);
  box-shadow: var(--shadow-pop);
}
.tier-solo .tier-name {
  font-size: 1.6rem;
}
.tier-solo .tier-price b {
  font-size: 2.6rem;
}
.tier-solo .tier-list {
  font-size: 0.9rem;
}

/* ---- agency pro ---- */

/* Horizontal, and outside the tab system: it is the same offer whichever
   billing period is showing. */
.strip {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: center;
  align-items: center;
  gap: clamp(20px, 3vw, 44px);
  padding: clamp(20px, 2.4vw, 30px) clamp(20px, 2.6vw, 34px);
  border: 1px solid var(--hairline);
  border-radius: 14px;
  background: var(--panel);
}
.strip-main p {
  margin-top: 6px;
  max-width: 66ch;
  font-size: 0.9rem;
  line-height: 1.55;
  color: rgb(20 20 20 / 0.68);
}
@media (max-width: 860px) {
  .oneoff {
    grid-template-columns: minmax(0, 1fr);
  }
  .strip {
    grid-template-columns: minmax(0, 1fr);
    justify-items: start;
  }
}

@media (max-width: 480px) {
  .ptabs {
    align-self: stretch;
  }
  .ptabs button {
    flex: 1;
    padding: 9px 8px;
    font-size: 0.78rem;
  }
}

/* ------------------------------------------------- pricing, small screens ---- */

.ptabs-bar {
  display: flex;
  justify-content: center;
}

/*
   On a phone the cards are tall enough that the period switch scrolls away
   long before you have finished reading them, so it follows you down. The bar
   bleeds to the page edges and blurs, the way the header does, or content
   would show through beside the pill.
*/
@media (max-width: 860px) {
  .ptabs-bar {
    position: sticky;
    top: 65px;
    z-index: 12;
    margin: 0 calc(var(--gutter) * -1);
    padding: 10px var(--gutter);
    background: rgb(237 235 230 / 0.9);
    backdrop-filter: blur(12px);
  }
  .ptabs {
    width: 100%;
  }

  /* One card in a one-card panel: the emphasis was there to stop it looking
     stranded next to the copy, and stacked there is nothing to stand out
     from. */
  .tier-solo {
    padding: 22px 20px;
    border-color: var(--hairline);
    box-shadow: none;
  }
  .tier-solo .tier-name {
    font-size: 1.25rem;
  }
  .tier-solo .tier-price b {
    font-size: 1.5rem;
  }
  .tier-solo .tier-list {
    font-size: 0.85rem;
  }

  /* Stacked, each card sizes itself; the shared rows only matter side by side. */
  .tiers {
    grid-template-rows: none;
  }
  .tier {
    grid-row: auto;
    grid-template-rows: none;
    display: flex;
    flex-direction: column;
  }
  .seats {
    align-self: stretch;
    margin-top: auto;
  }
}

/* -------------------------------------------------------- hero entrance ---- */

/*
   The hero is above the fold, so it can't wait for a scroll observer: it plays
   once, on load, as a short stagger. Everything is gated on `js-on`, so with
   no script the hero is simply there.

   The headline gets a masked line reveal. Each line is a block with hidden
   overflow and the type inside it starts fully below its own box, which reads
   as the words being dealt out rather than fading up.
*/
.d-hero .ln {
  display: block;
  overflow: hidden;
}
.d-hero .ln i {
  display: block;
  font-style: normal;
}

.js-on .d-hero .ln i {
  transform: translateY(105%);
  animation: heroLine 0.9s cubic-bezier(0.16, 1, 0.3, 1) forwards;
}
.js-on .d-hero .ln:nth-child(1) i {
  animation-delay: 0.12s;
}
.js-on .d-hero .ln:nth-child(2) i {
  animation-delay: 0.22s;
}

@keyframes heroLine {
  to {
    transform: translateY(0);
  }
}

/* Everything either side of the headline rises a little, in reading order.
   `--d` is the beat each element waits for. */
.js-on [data-hero] {
  opacity: 0;
  animation: heroRise 0.7s cubic-bezier(0.22, 0.61, 0.36, 1) forwards;
  animation-delay: calc(var(--d, 0) * 1ms);
}
.js-on [data-hero='1'] { --d: 60; }
.js-on [data-hero='4'] { --d: 460; }
.js-on [data-hero='5'] { --d: 560; }
.js-on [data-hero='6'] { --d: 660; }

@keyframes heroRise {
  from {
    opacity: 0;
    transform: translateY(16px);
  }
  to {
    opacity: 1;
    transform: none;
  }
}

/* The day sheet deals its own rows once the card itself has arrived. */
.js-on .daysheet .daysheet-rows .row {
  opacity: 0;
  animation: heroRise 0.5s cubic-bezier(0.22, 0.61, 0.36, 1) forwards;
}
.js-on .daysheet .row:nth-child(1) { animation-delay: 0.72s; }
.js-on .daysheet .row:nth-child(2) { animation-delay: 0.79s; }
.js-on .daysheet .row:nth-child(3) { animation-delay: 0.86s; }
.js-on .daysheet .row:nth-child(4) { animation-delay: 0.93s; }
.js-on .daysheet .row:nth-child(5) { animation-delay: 1s; }

/* The wash behind the hero comes up last and slowest, so it reads as light
   arriving rather than as another element landing. */
.js-on .hero::before {
  opacity: 0;
  animation: heroWash 1.6s ease forwards 0.3s;
}
@keyframes heroWash {
  to {
    opacity: 1;
  }
}

@media (prefers-reduced-motion: reduce) {
  .js-on .d-hero .ln i,
  .js-on [data-hero],
  .js-on .daysheet .daysheet-rows .row,
  .js-on .hero::before {
    opacity: 1;
    transform: none;
    animation: none;
  }
}

/* ---------------------------------------------------- panel transitions ---- */

/*
   Switching to a tab whose content is different in kind, rather than the same
   cards with new numbers, deserves an entrance. `is-live` is removed and
   re-added by the script so the stagger restarts each time, and `--d` is set
   per element from its index.
*/
.js-on .ppanel [data-in] {
  opacity: 0;
  transform: translateY(16px);
  transition:
    opacity 0.5s ease,
    transform 0.5s cubic-bezier(0.22, 0.61, 0.36, 1);
  transition-delay: calc(var(--d, 0) * 1ms);
}
.js-on .ppanel.is-live [data-in] {
  opacity: 1;
  transform: none;
}

/* The bullets inside the arriving card follow it in. */
.js-on .ppanel [data-in] .tier-list li {
  opacity: 0;
  transform: translateY(8px);
  transition:
    opacity 0.4s ease,
    transform 0.4s cubic-bezier(0.22, 0.61, 0.36, 1);
}
.js-on .ppanel.is-live [data-in] .tier-list li {
  opacity: 1;
  transform: none;
}
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(1) { transition-delay: 0.28s; }
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(2) { transition-delay: 0.34s; }
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(3) { transition-delay: 0.4s; }
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(4) { transition-delay: 0.46s; }
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(5) { transition-delay: 0.52s; }
.js-on .ppanel.is-live [data-in] .tier-list li:nth-child(6) { transition-delay: 0.58s; }

@media (prefers-reduced-motion: reduce) {
  .js-on .ppanel [data-in],
  .js-on .ppanel [data-in] .tier-list li {
    opacity: 1;
    transform: none;
    transition: none;
  }
}
