/*
 * Axiom — axiom.css
 * =================================================================
 * The identity layer. Loaded last, scoped to `body.luxe`, so all
 * eight pages move together without rewriting eight files.
 *
 * WHAT CHANGED AND WHY
 *   The previous register was obsidian-and-champagne with a serif
 *   display: a luxury-goods vocabulary borrowed for a developer
 *   operating system. It read as a watch advert, and the gold fought
 *   the sapphire it was paired with. This replaces it with the
 *   register the product occupies — instrument, not jewellery.
 *
 * THE FUTURE LAYER, ACTUALLY SHIPPED
 *   "Modern" on a 2026 site is not a darker grey. It is the platform
 *   features that did not exist when the current design vocabulary
 *   was set, each used where it genuinely beats the old way:
 *
 *   · OKLCH + Display-P3   — perceptually-even neon ramps, and glow
 *                            that goes brighter than sRGB can encode
 *                            on capable screens. sRGB hex first,
 *                            wide-gamut upgraded behind @supports.
 *   · @property            — typed custom properties, so gradient
 *                            angles and glow stops ANIMATE instead of
 *                            snapping. This is what makes the card
 *                            edges sweep.
 *   · scroll-driven anim   — animation-timeline: view()/scroll() puts
 *                            parallax, progress and reveals on the
 *                            compositor with zero JS per frame.
 *   · View Transitions     — cross-document morphs between the eight
 *                            pages; kills the white flash natively.
 *   · Container queries    — cards respond to THEIR box, not the
 *                            viewport, so the same card is correct in
 *                            a 4-up grid and in a sidebar.
 *   · :has()               — stateful styling with no JS classes.
 *   · Variable-font axes   — weight animates on scroll (kinetic type)
 *                            at the payload of one font file.
 *
 *   Every one of them is progressive: @supports-gated, with the JS
 *   path or the static value underneath. Nothing here is required for
 *   the page to read.
 *
 * DEPTH IS LIGHT, NOT LINES
 *   Surfaces separate by luminance and a top highlight, the way real
 *   material does. Borders are a last resort; where one is needed it
 *   is a hairline that catches the accent at the top edge only.
 *
 * CSP
 *   `style-src 'self'` — no inline style attributes, no external
 *   fonts. Geist and Geist Mono are self-hosted by studio.css.
 */

/* ===================================================================
 * Typed properties — the reason the light can move
 * =================================================================== */

@property --edge-angle {
  syntax: '<angle>';
  inherits: false;
  initial-value: 0deg;
}

@property --glow {
  syntax: '<number>';
  inherits: false;
  initial-value: 0;
}

@property --sweep {
  syntax: '<percentage>';
  inherits: false;
  initial-value: -30%;
}

/* ===================================================================
 * Tokens
 * =================================================================== */

body.luxe {
  --void: #04060B;
  --ground: #070A12;
  --raised: #0B0F1A;
  --ink: #EEF3F9;
  --ink-dim: #A3AFC0;
  --ink-mute: #77839A;

  --ice: #6FD8FF;
  --indigo: #5C6BFF;
  --violet: #A46BFF;

  --hair: rgba(198, 220, 255, 0.10);
  --hair-2: rgba(198, 220, 255, 0.18);

  --accent-grad: linear-gradient(100deg, var(--ice), var(--indigo));
  --ease: cubic-bezier(0.16, 1, 0.3, 1);

  /* The old luxury tokens are aliased rather than left dangling, so any
     rule in luxe.css/studio.css still referencing them lands on the new
     palette instead of on stale gold. */
  --champagne: var(--ice);
  --champagne-soft: #BFE9FF;
  --platinum: var(--ink);
  --silver: var(--ink-dim);
  --pewter: var(--ink-mute);
  --obsidian: var(--ground);

  --font-display: 'Geist', var(--font-sans);

  background: var(--void);
  color: var(--ink);
  background-image: none;
  -webkit-font-smoothing: antialiased;
}

/* Wide gamut. On a P3 display the accent leaves the sRGB triangle and
   the glow reads as emitted light rather than as a bright blue. On an
   sRGB display this block simply never applies. */
@supports (color: oklch(70% 0.2 240)) {
  body.luxe {
    --ice: oklch(84% 0.132 219);
    --indigo: oklch(62% 0.221 275);
    --violet: oklch(66% 0.212 305);
    --ink: oklch(96.5% 0.008 250);
    --ink-dim: oklch(76% 0.021 255);
    --ink-mute: oklch(61% 0.030 257);
    --void: oklch(12.5% 0.014 260);
    --ground: oklch(15.5% 0.017 262);
    --raised: oklch(18.5% 0.020 264);
  }
}

body.luxe.luxe-interior {
  background-image:
    radial-gradient(80% 46% at 50% -6%, color-mix(in oklab, var(--indigo) 16%, transparent), transparent 64%),
    radial-gradient(46% 32% at 88% 4%, color-mix(in oklab, var(--ice) 10%, transparent), transparent 62%);
  background-attachment: fixed;
}

/* The repeating-conic film grain in luxe.css costs a full-screen
   composite for something almost invisible, and the renderer does its
   own grain in-shader. Off. */
body.luxe::after { display: none; }
body.luxe::before { opacity: 0.22; }

/* ===================================================================
 * View Transitions — cross-document, native
 * =================================================================== */

@view-transition { navigation: auto; }

::view-transition-old(root) { animation: axiom-vt-out 260ms var(--ease) both; }
::view-transition-new(root) { animation: axiom-vt-in 380ms var(--ease) both; }

@keyframes axiom-vt-out { to { opacity: 0; transform: scale(0.994); filter: blur(3px); } }
@keyframes axiom-vt-in  { from { opacity: 0; transform: scale(1.006); filter: blur(4px); } }

/* The chrome persists across the navigation instead of being redrawn. */
body.luxe .site-header { view-transition-name: axiom-header; }
body.luxe .site-footer { view-transition-name: axiom-footer; }

@media (prefers-reduced-motion: reduce) {
  ::view-transition-old(root),
  ::view-transition-new(root) { animation: none; }
}

/* ===================================================================
 * The stage — WebGL behind everything
 * =================================================================== */

.axiom-stage {
  position: fixed;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  opacity: var(--stage-fade, 1);
  /* CSS stand-in when WebGL is absent, reduced-motion is set, or the
     shader fails. It is never removed — the canvas paints over it. */
  background:
    radial-gradient(52% 44% at 68% 42%, color-mix(in oklab, var(--indigo) 32%, transparent), transparent 68%),
    radial-gradient(38% 34% at 74% 34%, color-mix(in oklab, var(--ice) 22%, transparent), transparent 66%),
    radial-gradient(90% 60% at 50% 100%, color-mix(in oklab, var(--violet) 12%, transparent), transparent 70%),
    var(--void);
  transition: opacity 220ms linear;
}

.axiom-stage .axiom-canvas {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  display: block;
}

.axiom-field {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  overflow: hidden;
}
.axiom-field .axiom-canvas { position: absolute; inset: 0; width: 100%; height: 100%; }

/* Interior pages get the same room the crystal stands in, without the
   crystal: a fixed light-field behind the content, held well back so it
   never competes with body copy. */
.axiom-field-fixed {
  position: fixed;
  inset: 0;
  z-index: 0;
  opacity: 0.5;
}

body.luxe main,
body.luxe .site-header,
body.luxe .site-footer { position: relative; z-index: 1; }

/* ===================================================================
 * HUD chrome — the spatial language
 * =================================================================== */

/* A thin progress rail across the top, driven by the document's own
   scroll timeline. No scroll listener, no rAF, no JS at all. */
body.luxe .axiom-rail {
  position: fixed;
  top: 0; left: 0; right: 0;
  height: 2px;
  z-index: 60;
  transform-origin: 0 50%;
  transform: scaleX(0);
  background: linear-gradient(90deg, var(--ice), var(--indigo) 55%, var(--violet));
  box-shadow: 0 0 18px -2px color-mix(in oklab, var(--ice) 70%, transparent);
  pointer-events: none;
}

@supports (animation-timeline: scroll()) {
  body.luxe .axiom-rail {
    animation: axiom-rail-grow linear;
    animation-timeline: scroll(root block);
  }
}
@keyframes axiom-rail-grow { from { transform: scaleX(0); } to { transform: scaleX(1); } }

/* Corner brackets. The cheapest way to say "instrument" — four
   hairlines that only touch the corners, so the panel reads as
   registered in space rather than as a rounded rectangle. */
.axiom-hud {
  position: relative;
}
.axiom-hud::before,
.axiom-hud::after {
  content: '';
  position: absolute;
  width: 14px;
  height: 14px;
  border: 1px solid color-mix(in oklab, var(--ice) 45%, transparent);
  pointer-events: none;
}
.axiom-hud::before { top: -1px; left: -1px; border-right: 0; border-bottom: 0; }
.axiom-hud::after { bottom: -1px; right: -1px; border-left: 0; border-top: 0; }

/* A vertical data rail down the left edge of the hero. */
.axiom-readout {
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.62rem;
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--ink-mute);
}
.axiom-readout b { color: var(--ice); font-weight: 500; }

/* ===================================================================
 * Typography
 * =================================================================== */

body.luxe h1,
body.luxe h2,
body.luxe h3,
body.luxe h4 {
  font-family: var(--font-display);
  font-weight: 620;
  letter-spacing: -0.032em;
  color: var(--ink);
  text-wrap: balance;
}

body.luxe .luxe-display,
body.luxe .axiom-display {
  font-size: clamp(3rem, 8.4vw, 8rem);
  line-height: 0.92;
  font-weight: 680;
  letter-spacing: -0.046em;
  margin: 0.16em 0 0;
}

/* Kinetic type: the display's weight and optical width breathe as the
   hero scrolls past. One variable font, no extra bytes, and it puts
   the motion on an axis the typeface was designed for rather than on
   a transform. */
@supports (animation-timeline: view()) and (font-variation-settings: 'wght' 700) {
  body.luxe .axiom-display {
    animation: axiom-weight linear both;
    animation-timeline: view(block);
    animation-range: entry 0% cover 60%;
  }
  @keyframes axiom-weight {
    from { font-variation-settings: 'wght' 760; letter-spacing: -0.052em; }
    to   { font-variation-settings: 'wght' 580; letter-spacing: -0.036em; }
  }
}

/* The accented clause. A gradient on text is a cliché when it runs the
   whole headline; on one clause, against 60 characters of plain white,
   it is punctuation. The angle is a typed property, so it drifts. */
body.luxe .luxe-display em,
body.luxe .axiom-display em {
  font-style: normal;
  background: linear-gradient(var(--edge-angle, 96deg),
              color-mix(in oklab, var(--ice) 70%, white) 0%,
              var(--ice) 34%,
              var(--indigo) 74%,
              var(--violet) 100%);
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
  animation: axiom-hue 14s var(--ease) infinite alternate;
}
@keyframes axiom-hue {
  from { --edge-angle: 84deg; }
  to   { --edge-angle: 116deg; }
}

body.luxe .luxe-title {
  font-size: clamp(1.85rem, 3.6vw, 3.25rem);
  line-height: 1.03;
  letter-spacing: -0.036em;
  margin: 0;
}

body.luxe h3 { font-size: clamp(1.12rem, 1.5vw, 1.32rem); letter-spacing: -0.022em; }

body.luxe .luxe-lead,
body.luxe .lead {
  font-family: var(--font-sans);
  font-size: clamp(1.02rem, 1.35vw, 1.2rem);
  line-height: 1.66;
  color: var(--ink-dim);
  max-width: 62ch;
  text-wrap: pretty;
}

body.luxe .luxe-eyebrow,
body.luxe .eyebrow,
body.luxe .luxe-kicker {
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.68rem;
  font-weight: 500;
  letter-spacing: 0.26em;
  text-transform: uppercase;
  color: var(--ice);
}

body.luxe .luxe-eyebrow::before {
  width: 1.7rem;
  background: linear-gradient(90deg, transparent, var(--ice));
}

body.luxe .axiom-pulse { display: inline-flex; align-items: center; gap: 0.55em; }
body.luxe .axiom-pulse::before {
  content: '';
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: var(--ice);
  animation: axiom-ping 2.4s var(--ease) infinite;
}
@keyframes axiom-ping {
  0%   { box-shadow: 0 0 0 0 color-mix(in oklab, var(--ice) 55%, transparent); }
  70%  { box-shadow: 0 0 0 9px transparent; }
  100% { box-shadow: 0 0 0 0 transparent; }
}

body.luxe strong { color: var(--ink); font-weight: 620; }

/* ===================================================================
 * Header
 * =================================================================== */

body.luxe .site-header {
  background: transparent;
  border-bottom: 1px solid transparent;
  transition: background 320ms var(--ease), border-color 320ms var(--ease);
}

body.luxe .site-header[data-scrolled] {
  background: color-mix(in oklab, var(--void) 78%, transparent);
  backdrop-filter: blur(18px) saturate(1.35);
  -webkit-backdrop-filter: blur(18px) saturate(1.35);
  border-bottom-color: var(--hair);
}

body.luxe .brand-word {
  font-family: var(--font-display);
  font-weight: 640;
  letter-spacing: -0.02em;
  font-size: 1.06rem;
}

body.luxe .nav a {
  font-size: 0.895rem;
  color: var(--ink-dim);
  transition: color 180ms var(--ease);
}
body.luxe .nav a:hover { color: var(--ink); }

body.luxe .btn-nav {
  border: 1px solid var(--hair-2);
  border-radius: 999px;
  padding: 0.52rem 1.05rem;
  color: var(--ink);
  font-size: 0.82rem;
  text-transform: none;
  background: color-mix(in oklab, var(--indigo) 8%, transparent);
  transition: border-color 200ms var(--ease), background 200ms var(--ease);
}
body.luxe .btn-nav:hover {
  border-color: color-mix(in oklab, var(--ice) 50%, transparent);
  background: color-mix(in oklab, var(--ice) 12%, transparent);
}

/* ===================================================================
 * Buttons
 * =================================================================== */

body.luxe .btn {
  font-family: var(--font-sans);
  font-weight: 560;
  border-radius: 999px;
  padding: 0.86rem 1.55rem;
  text-transform: none;
  position: relative;
  overflow: hidden;
  transform: translate(var(--mx, 0px), var(--my, 0px));
  transition: transform 260ms var(--ease), box-shadow 260ms var(--ease),
              background 200ms var(--ease), border-color 200ms var(--ease);
}

/* A specular sweep crossing the face on hover — the typed --sweep
   property is what lets it animate at all. */
body.luxe .btn::after {
  content: '';
  position: absolute;
  inset: 0;
  background: linear-gradient(100deg, transparent 0%,
              rgba(255, 255, 255, 0.30) var(--sweep), transparent calc(var(--sweep) + 22%));
  pointer-events: none;
  opacity: 0;
}
body.luxe .btn:hover::after {
  opacity: 1;
  animation: axiom-sweep 720ms var(--ease) 1;
}
@keyframes axiom-sweep {
  from { --sweep: -30%; }
  to   { --sweep: 130%; }
}

body.luxe .btn-primary {
  background: var(--accent-grad);
  color: #04070E;
  border: none;
  box-shadow:
    0 1px 0 rgba(255, 255, 255, 0.34) inset,
    0 14px 40px -14px color-mix(in oklab, var(--indigo) 85%, transparent);
}
body.luxe .btn-primary:hover {
  filter: none;
  box-shadow:
    0 1px 0 rgba(255, 255, 255, 0.42) inset,
    0 22px 56px -14px color-mix(in oklab, var(--ice) 75%, transparent);
}

body.luxe .btn-ghost {
  background: color-mix(in oklab, var(--indigo) 6%, transparent);
  border: 1px solid var(--hair-2);
  color: var(--ink);
}
body.luxe .btn-ghost:hover {
  background: color-mix(in oklab, var(--ice) 10%, transparent);
  border-color: color-mix(in oklab, var(--ice) 45%, transparent);
}

body.luxe .btn-lg { padding: 1rem 1.9rem; font-size: 1.01rem; }

/* ===================================================================
 * Sections and rhythm
 * =================================================================== */

body.luxe .luxe-section { padding: clamp(5rem, 11vh, 9rem) 0; position: relative; }
body.luxe .luxe-section.is-raised {
  background: linear-gradient(180deg, transparent, var(--raised) 12%, var(--raised) 88%, transparent);
}
body.luxe .luxe-section.is-raised::before,
body.luxe .luxe-section.is-raised::after {
  content: '';
  position: absolute;
  left: 0; right: 0;
  height: 1px;
  background: linear-gradient(90deg, transparent, var(--hair), transparent);
}
body.luxe .luxe-section.is-raised::before { top: 0; }
body.luxe .luxe-section.is-raised::after { bottom: 0; }

body.luxe .luxe-head { margin-bottom: clamp(2.4rem, 5vh, 3.6rem); }
body.luxe .luxe-head.head-split {
  display: grid;
  grid-template-columns: minmax(0, 1.05fr) minmax(0, 1fr);
  gap: clamp(1.5rem, 4vw, 4rem);
  align-items: end;
}
@media (max-width: 860px) {
  body.luxe .luxe-head.head-split { grid-template-columns: minmax(0, 1fr); gap: 1.1rem; }
}

/* ===================================================================
 * Cards
 * =================================================================== */

/* One card treatment shared by every card-ish component on the site,
   so the pages stop looking like three different products. */
body.luxe .luxe-cell,
body.luxe .luxe-product,
body.luxe .card,
body.luxe .price-card,
body.luxe .value-card,
body.luxe .custom-pillar,
body.luxe .download-card {
  position: relative;
  container-type: inline-size;
  border-radius: 18px;
  border: 1px solid var(--hair);
  background:
    linear-gradient(180deg, color-mix(in oklab, var(--indigo) 7%, transparent),
                            color-mix(in oklab, var(--indigo) 1.5%, transparent) 42%),
    var(--ground);
  box-shadow:
    0 1px 0 rgba(190, 220, 255, 0.09) inset,
    0 28px 60px -40px rgba(0, 0, 0, 0.9);
  overflow: hidden;
  transition: border-color 320ms var(--ease), transform 420ms var(--ease),
              box-shadow 420ms var(--ease);
}

/* The top edge catches the accent, the way a bevel catches a light. */
body.luxe .luxe-cell::before,
body.luxe .luxe-product::before,
body.luxe .price-card::before,
body.luxe .value-card::before,
body.luxe .custom-pillar::before {
  content: '';
  position: absolute;
  top: 0; left: 12%; right: 12%;
  height: 1px;
  background: linear-gradient(90deg, transparent,
              color-mix(in oklab, var(--ice) 60%, transparent), transparent);
  opacity: 0.5;
  transition: opacity 380ms var(--ease), left 480ms var(--ease), right 480ms var(--ease);
}

body.luxe .luxe-cell:hover,
body.luxe .luxe-product:hover,
body.luxe .price-card:hover,
body.luxe .value-card:hover,
body.luxe .custom-pillar:hover {
  border-color: var(--hair-2);
  box-shadow:
    0 1px 0 rgba(190, 220, 255, 0.14) inset,
    0 40px 80px -46px rgba(0, 0, 0, 0.95),
    0 0 60px -28px color-mix(in oklab, var(--indigo) 55%, transparent);
}
body.luxe .luxe-cell:hover::before,
body.luxe .luxe-product:hover::before,
body.luxe .price-card:hover::before,
body.luxe .value-card:hover::before,
body.luxe .custom-pillar:hover::before { opacity: 1; left: 2%; right: 2%; }

/* Container queries: the card answers to ITS box, so the same markup is
   right in a 4-up grid, in a 2-up, and in a sidebar — which viewport
   breakpoints could never get right at the same time. */
@container (min-width: 380px) {
  body.luxe .luxe-product .luxe-price { display: flex; align-items: baseline; gap: 0.7rem; flex-wrap: wrap; }
}
@container (max-width: 300px) {
  body.luxe .luxe-cell h3 { font-size: 1.02rem; }
  body.luxe .luxe-feats li { padding-left: 1.35rem; }
}

/* :has() — a card that contains a primary action earns a stronger
   resting state. No JS, no extra class, no chance of drift. */
body.luxe .luxe-cell:has(.btn-primary),
body.luxe .luxe-product:has(.btn-primary) {
  border-color: color-mix(in oklab, var(--ice) 22%, var(--hair));
}

/* An open FAQ row tints its whole group, so the page shows you where
   you are without a scripted "active" class. */
body.luxe .faq:has(details[open]) { --hair: rgba(198, 220, 255, 0.14); }

/* Pointer tilt. Transform only — no layout, so it stays on the
   compositor and cannot reflow the grid it sits in. */
body.luxe [data-tilt] { transform-style: preserve-3d; will-change: transform; }
body.luxe [data-tilt="on"] {
  transform: perspective(1100px) rotateX(var(--rx, 0deg)) rotateY(var(--ry, 0deg)) translateZ(6px);
}

/* The cursor drags a soft light across the card face. */
body.luxe [data-tilt]::after {
  content: '';
  position: absolute;
  inset: 0;
  pointer-events: none;
  background: radial-gradient(28% 42% at var(--gx, 50%) var(--gy, 0%),
              color-mix(in oklab, var(--ice) 16%, transparent), transparent 72%);
  opacity: 0;
  transition: opacity 340ms var(--ease);
}
body.luxe [data-tilt="on"]::after { opacity: 1; }

body.luxe .luxe-product.is-flagship {
  border-color: color-mix(in oklab, var(--ice) 30%, transparent);
  background:
    linear-gradient(180deg, color-mix(in oklab, var(--ice) 10%, transparent),
                            color-mix(in oklab, var(--indigo) 3%, transparent) 46%),
    var(--ground);
}

body.luxe .luxe-idx {
  font-family: 'Geist Mono', var(--font-mono);
  color: var(--ice);
  opacity: 0.65;
  letter-spacing: 0.1em;
}

/* Ticks: absolutely positioned, NEVER a grid column. These <li> hold a
   variable number of children — a tick, text, a <strong>, a hydrated
   [data-money] span — and as a grid track every child past the second
   lands in the icon column, breaking the sentence to one word a line. */
body.luxe .luxe-feats li,
body.luxe .feature-list li,
body.luxe .spec-list li {
  position: relative;
  display: block;
  padding-left: 1.6rem;
  line-height: 1.6;
}
body.luxe .luxe-feats li .tick,
body.luxe .feature-list li .tick,
body.luxe .spec-list li .tick {
  position: absolute;
  left: 0;
  top: 0.5em;
  line-height: 1;
  font-size: 0.62em;
  color: var(--ice);
}

/* ===================================================================
 * Price display
 * =================================================================== */

body.luxe .luxe-price .amount,
body.luxe .founding-price .now,
body.luxe .luxe-founding-price .now {
  font-family: var(--font-display);
  font-weight: 660;
  letter-spacing: -0.04em;
  background: linear-gradient(100deg,
              color-mix(in oklab, var(--ice) 55%, white), var(--ice) 55%, var(--indigo));
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
body.luxe .luxe-founding-price .now { font-size: clamp(2.6rem, 6vw, 4.6rem); }
body.luxe .luxe-price .strike,
body.luxe .luxe-founding-price .was { color: var(--ink-mute); }
body.luxe .luxe-founding-price .save,
body.luxe .save {
  color: var(--ice);
  border: 1px solid color-mix(in oklab, var(--ice) 34%, transparent);
  background: color-mix(in oklab, var(--ice) 8%, transparent);
  border-radius: 999px;
}

/* ===================================================================
 * Slot tracker
 * =================================================================== */

body.luxe .slot-pips span,
body.luxe .slot-pips i { background: rgba(198, 220, 255, 0.16); box-shadow: none; }
body.luxe .slot-pips .is-open,
body.luxe .slot-pips [data-open] {
  background: var(--accent-grad);
  box-shadow: 0 0 14px -2px color-mix(in oklab, var(--ice) 70%, transparent);
}
body.luxe .slot-caption {
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.7rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--ink-mute);
}
body.luxe .slot-caption strong { color: var(--ice); }

/* ===================================================================
 * FAQ
 * =================================================================== */

body.luxe .faq details {
  border: 1px solid var(--hair);
  border-radius: 14px;
  background: linear-gradient(180deg, color-mix(in oklab, var(--indigo) 5%, transparent), transparent 60%),
              var(--ground);
  transition: border-color 260ms var(--ease);
}
body.luxe .faq details[open] { border-color: color-mix(in oklab, var(--ice) 32%, transparent); }
body.luxe .faq summary {
  font-family: var(--font-display);
  font-weight: 580;
  letter-spacing: -0.018em;
  color: var(--ink);
}
body.luxe .faq summary::marker { color: var(--ice); }

/* ===================================================================
 * Footer
 * =================================================================== */

body.luxe .site-footer {
  border-top: 1px solid var(--hair);
  background: linear-gradient(180deg, transparent, color-mix(in oklab, var(--void) 92%, transparent));
  color: var(--ink-mute);
  font-size: 0.86rem;
}
body.luxe .site-footer a { color: var(--ink-mute); }
body.luxe .site-footer a:hover { color: var(--ice); }

/* ===================================================================
 * Hero
 * =================================================================== */

.axiom-hero {
  position: relative;
  min-height: min(100svh, 1000px);
  display: flex;
  align-items: center;
  padding: clamp(7rem, 16vh, 11rem) 0 clamp(3rem, 8vh, 6rem);
}

/* A scrim under the copy column. The crystal drifts with the pointer and
   the scroll, so legibility cannot depend on it staying out of the way:
   this guarantees the text always has ground beneath it, and falls off
   to nothing before it reaches the object. */
.axiom-hero::before {
  content: '';
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  background: linear-gradient(90deg,
    color-mix(in oklab, var(--void) 88%, transparent) 0%,
    color-mix(in oklab, var(--void) 74%, transparent) 32%,
    transparent 62%);
}
.axiom-hero > .container { position: relative; z-index: 1; }

.axiom-hero-inner { max-width: 46rem; }
.axiom-hero .luxe-lead { max-width: 44ch; margin-top: 1.6rem; }

.axiom-actions { display: flex; flex-wrap: wrap; gap: 0.85rem; margin-top: 2.3rem; }

/* The credential strip: mono, spaced, quiet. Facts, not badges. */
.axiom-strip {
  display: flex;
  flex-wrap: wrap;
  gap: 0.6rem 2rem;
  margin-top: 3.2rem;
  padding-top: 1.4rem;
  border-top: 1px solid var(--hair);
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.68rem;
  letter-spacing: 0.17em;
  text-transform: uppercase;
  color: var(--ink-mute);
}
.axiom-strip span { display: inline-flex; align-items: center; gap: 0.55em; }
.axiom-strip span::before {
  content: '';
  width: 4px; height: 4px;
  border-radius: 50%;
  background: var(--ice);
  opacity: 0.8;
}

/* Scroll hint, tied to the real scroll position: it disappears the
   moment the page moves. A cue that outlives its usefulness becomes
   furniture. */
.axiom-scroll-hint {
  position: absolute;
  left: 20px;
  bottom: clamp(1.2rem, 4vh, 2.4rem);
  display: flex;
  align-items: center;
  gap: 0.7rem;
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.62rem;
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--ink-mute);
  opacity: calc(1 - var(--act, 0) * 6);
  transition: opacity 200ms linear;
  pointer-events: none;
}
.axiom-scroll-hint i {
  display: block;
  width: 1px;
  height: 30px;
  background: linear-gradient(180deg, var(--ice), transparent);
  animation: axiom-drop 2.2s var(--ease) infinite;
}
@keyframes axiom-drop {
  0%   { transform: scaleY(0); transform-origin: top; opacity: 0; }
  40%  { transform: scaleY(1); transform-origin: top; opacity: 1; }
  60%  { transform: scaleY(1); transform-origin: bottom; opacity: 1; }
  100% { transform: scaleY(0); transform-origin: bottom; opacity: 0; }
}

/* ===================================================================
 * Marquee
 * =================================================================== */

.axiom-marquee {
  position: relative;
  overflow: hidden;
  border-top: 1px solid var(--hair);
  border-bottom: 1px solid var(--hair);
  padding: 1.05rem 0;
  background: color-mix(in oklab, var(--void) 60%, transparent);
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 9%, #000 91%, transparent);
  mask-image: linear-gradient(90deg, transparent, #000 9%, #000 91%, transparent);
}
.axiom-marquee-track {
  display: flex;
  width: max-content;
  gap: 3.2rem;
  animation: axiom-slide 42s linear infinite;
}
.axiom-marquee:hover .axiom-marquee-track { animation-play-state: paused; }
.axiom-marquee span {
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.72rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
  white-space: nowrap;
  display: inline-flex;
  align-items: center;
  gap: 0.9rem;
}
.axiom-marquee span::after {
  content: '';
  width: 4px; height: 4px;
  border-radius: 50%;
  background: var(--indigo);
}
@keyframes axiom-slide {
  from { transform: translate3d(0, 0, 0); }
  to   { transform: translate3d(-50%, 0, 0); }
}

/* ===================================================================
 * Metric row
 * =================================================================== */

.axiom-metrics {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: clamp(1rem, 2.4vw, 2rem);
}
@media (max-width: 900px) { .axiom-metrics { grid-template-columns: repeat(2, minmax(0, 1fr)); } }

.axiom-metric { padding: 1.4rem 0 0; border-top: 1px solid var(--hair); }
.axiom-metric b {
  display: block;
  font-family: var(--font-display);
  font-weight: 660;
  font-size: clamp(2.1rem, 4.2vw, 3.1rem);
  letter-spacing: -0.045em;
  line-height: 1;
  background: linear-gradient(100deg,
              color-mix(in oklab, var(--ice) 45%, white), var(--ice) 60%, var(--indigo));
  -webkit-background-clip: text;
  background-clip: text;
  color: transparent;
}
.axiom-metric small {
  display: block;
  margin-top: 0.6rem;
  font-family: 'Geist Mono', var(--font-mono);
  font-size: 0.66rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-mute);
  line-height: 1.5;
}

/* ===================================================================
 * Field band
 * =================================================================== */

.axiom-band {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  padding: clamp(6rem, 14vh, 10rem) 0;
  background: var(--void);
}
.axiom-band > .container { position: relative; z-index: 1; }
.axiom-band::after {
  content: '';
  position: absolute;
  inset: 0;
  z-index: 0;
  background: linear-gradient(180deg, var(--void), transparent 22%, transparent 78%, var(--void));
  pointer-events: none;
}

/* ===================================================================
 * Motion
 * =================================================================== */

/* Nothing is hidden until JS is running: the class is added by
   axiom.js, never present in the HTML, so a no-JS visitor sees the
   whole page. */
.axiom-reveal-ready [data-reveal] {
  opacity: 0;
  transform: translate3d(0, 22px, 0);
  filter: blur(6px);
  transition:
    opacity 900ms var(--ease),
    transform 900ms var(--ease),
    filter 900ms var(--ease);
  will-change: opacity, transform;
}
.axiom-reveal-ready [data-reveal="in"] { opacity: 1; transform: none; filter: none; }

/* The shipped feature photograph was lit warm champagne for the old
   gold register and now fights the palette head-on. Rather than ship a
   clashing asset or fake a new one, it is treated editorially: stripped
   to luminance, then re-tinted through the accent in `color` blend, so
   it keeps its real light and shadow but belongs to this page. */
body.luxe .feature-visual {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  border-radius: 16px;
}
body.luxe .feature-visual img {
  filter: grayscale(1) brightness(0.92) contrast(1.14);
  display: block;
  width: 100%;
  height: auto;
}
body.luxe .feature-visual::after {
  content: '';
  position: absolute;
  inset: 0;
  pointer-events: none;
  mix-blend-mode: color;
  opacity: 0.72;
  background: linear-gradient(150deg, var(--ice), var(--indigo) 62%, var(--violet));
}

/* Parallax on the section visuals, native and compositor-driven. */
@supports (animation-timeline: view()) {
  body.luxe .feature-visual img {
    animation: axiom-parallax linear both;
    animation-timeline: view(block);
    animation-range: entry 0% exit 100%;
  }
  @keyframes axiom-parallax {
    from { transform: translate3d(0, 5%, 0) scale(1.06); }
    to   { transform: translate3d(0, -5%, 0) scale(1.06); }
  }
}

/* Line-split headline. Each word rides in its own mask; the delay is
   set per rendered LINE by axiom.js after measuring, so the stagger
   survives any reflow. */
[data-split] .sp-w {
  display: inline-block;
  overflow: hidden;
  vertical-align: top;
  /* Descenders would be clipped by an exact-height mask. */
  padding-bottom: 0.12em;
  margin-bottom: -0.12em;
}
[data-split] .sp-i {
  display: inline-block;
  transform: translate3d(0, 105%, 0);
  transition: transform 1000ms var(--ease);
  transition-delay: var(--d, 0ms);
}
[data-split="in"] .sp-i { transform: translate3d(0, 0, 0); }

@media (prefers-reduced-motion: reduce) {
  .axiom-reveal-ready [data-reveal] { opacity: 1; transform: none; filter: none; transition: none; }
  [data-split] .sp-i { transform: none; transition: none; }
  .axiom-marquee-track,
  .axiom-scroll-hint i,
  body.luxe .axiom-pulse::before,
  body.luxe .luxe-display em,
  body.luxe .axiom-display em { animation: none; }
  body.luxe [data-tilt="on"] { transform: none; }
  body.luxe .axiom-rail { animation: none; }
  body.luxe .feature-visual img { animation: none; }
}

/* ===================================================================
 * Responsive
 * =================================================================== */

@media (max-width: 640px) {
  /* app.css deliberately lets the nav WRAP at this width ("no
     hamburger"). With six links plus a pill CTA that builds a 330px-tall
     header on a 390px phone — over a third of the first screen spent on
     chrome before a single word of copy, and it pushed the hero's own
     top padding down into a dead gap beneath it.

     One nowrap row that scrolls instead: every link stays reachable, no
     JS menu to build or get wrong, and the header comes back to ~100px.
     The right-edge mask is the affordance that says it scrolls. */
  body.luxe .site-header .container {
    gap: 4px 12px;
    padding-top: 8px;
    padding-bottom: 8px;
  }
  body.luxe .nav {
    flex-wrap: nowrap;
    width: 100%;
    overflow-x: auto;
    overscroll-behavior-x: contain;
    scrollbar-width: none;
    gap: 2px;
    -webkit-mask-image: linear-gradient(90deg, #000 88%, transparent);
    mask-image: linear-gradient(90deg, #000 88%, transparent);
  }
  body.luxe .nav::-webkit-scrollbar { display: none; }
  body.luxe .nav a { white-space: nowrap; font-size: 0.86rem; padding: 8px 10px; }
  body.luxe .btn-nav { flex: 0 0 auto; padding: 0.45rem 0.9rem; font-size: 0.78rem; }
}

@media (max-width: 720px) {
  /* The crystal is lifted above the copy by the shader on portrait; this
     holds it back as well, so the headline keeps its contrast. */
  .axiom-stage { opacity: calc(var(--stage-fade, 1) * 0.78); }
  .axiom-hero { min-height: auto; padding-top: clamp(6rem, 18vh, 8rem); }
  .axiom-scroll-hint { display: none; }
  body.luxe .btn { width: 100%; justify-content: center; }
  body.luxe .axiom-actions { gap: 0.7rem; }
  .axiom-hud::before, .axiom-hud::after { display: none; }
}
