/* ===========================================
   Exhale Waitlist - Premium Design System
   Retains original hero animation with WaitlistTwo styling
   =========================================== */

:root {
    /* Primary Colors - Cyan Palette */
    --cyan-deep: #0D7377;
    --cyan-medium: #14919B;
    --cyan-light: #32E0C4;
    --cyan-pale: #E8F8F5;
    --cyan-glow: #ADFBF6;

    /* Gold Accents */
    --gold-rich: #D4A857;
    --gold-light: #E8C87D;
    --gold-pale: #F5E6C8;
    --gold-glow: rgba(212, 168, 87, 0.3);

    /* Neutrals */
    --white: #FFFFFF;
    --gray-50: #FAFAFA;
    --gray-100: #F5F5F5;
    --gray-200: #E5E5E5;
    --gray-300: #D4D4D4;
    --gray-400: #A3A3A3;
    --gray-500: #737373;
    --gray-600: #525252;
    --gray-700: #404040;
    --gray-800: #262626;
    --gray-900: #171717;
    --black: #0A0A0A;

    /* Semantic */
    --bg-primary: var(--black);
    --bg-secondary: #0a0a0f;
    --text-primary: #f5f5f5;
    --text-secondary: #a0a0a0;
    --text-muted: #606060;
    --accent: var(--cyan-glow);
    --accent-deep: var(--cyan-deep);

    /* Glass Effect */
    --glass-bg: rgba(255, 255, 255, 0.06);
    --glass-border: rgba(255, 255, 255, 0.1);

    /* Shadows */
    --shadow-sm: 0 1px 2px rgba(0, 0, 0, 0.2);
    --shadow-md: 0 4px 12px rgba(0, 0, 0, 0.3);
    --shadow-lg: 0 12px 40px rgba(0, 0, 0, 0.4);
    --shadow-xl: 0 24px 64px rgba(0, 0, 0, 0.5);
    --shadow-cyan: 0 8px 32px rgba(173, 251, 246, 0.2);
    --shadow-gold: 0 8px 32px rgba(212, 168, 87, 0.25);

    /* Typography */
    --font-serif: 'Cormorant Garamond', Georgia, serif;
    --font-sans: 'Inter', -apple-system, BlinkMacSystemFont, sans-serif;

    /* Spacing */
    --section-padding: 120px;
    --container-max: 1200px;
}

/* Motion curves. Built-in easings are too weak for deliberate animation. */
:root {
    --ease-out: cubic-bezier(0.23, 1, 0.32, 1);
    --ease-in-out: cubic-bezier(0.77, 0, 0.175, 1);
    --ease-drawer: cubic-bezier(0.32, 0.72, 0, 1);
}

/* ===========================================
   Light Mode
   =========================================== */
body.light-mode {
    --bg-primary: var(--gray-50);
    --bg-secondary: var(--white);
    --text-primary: var(--gray-900);
    --text-secondary: var(--gray-600);
    --text-muted: var(--gray-400);
    --accent: var(--cyan-deep);

    --glass-bg: rgba(255, 255, 255, 0.6);
    --glass-border: rgba(255, 255, 255, 0.8);

    --shadow-sm: 0 1px 2px rgba(0, 0, 0, 0.05);
    --shadow-md: 0 4px 12px rgba(0, 0, 0, 0.08);
    --shadow-lg: 0 12px 40px rgba(0, 0, 0, 0.12);
    --shadow-xl: 0 24px 64px rgba(0, 0, 0, 0.16);
}

/* ===========================================
   Reset & Base
   =========================================== */
*, *::before, *::after {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}

html {
    font-size: 16px;
    scroll-behavior: smooth;
}

body {
    font-family: var(--font-sans);
    background: var(--bg-primary);
    color: var(--text-primary);
    line-height: 1.6;
    overflow-x: hidden;
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
}

/* ===========================================
   Blur Overlay (Page Load Effect)
   =========================================== *

/* ===========================================
   Ambient Background Orbs
   =========================================== */
.ambient-orb {
    position: fixed;
    border-radius: 50%;
    filter: blur(80px);
    pointer-events: none;
    z-index: 0;
    opacity: 0.4;
}

.ambient-orb-1 {
    width: 600px;
    height: 600px;
    background: radial-gradient(circle, var(--cyan-glow) 0%, transparent 70%);
    top: -200px;
    right: -100px;
    animation: float1 20s ease-in-out infinite;
}

.ambient-orb-2 {
    display: none;
}

.ambient-orb-3 {
    width: 400px;
    height: 400px;
    background: radial-gradient(circle, var(--cyan-medium) 0%, transparent 70%);
    top: 50%;
    right: 10%;
    animation: float3 18s ease-in-out infinite;
    opacity: 0.2;
}

body.light-mode .ambient-orb {
    opacity: 0.5;
}

@keyframes float1 {
    0%, 100% { transform: translate(0, 0) scale(1); }
    33% { transform: translate(-30px, 50px) scale(1.05); }
    66% { transform: translate(20px, -30px) scale(0.95); }
}

@keyframes float2 {
    0%, 100% { transform: translate(0, 0) scale(1); }
    50% { transform: translate(40px, -40px) scale(1.1); }
}

@keyframes float3 {
    0%, 100% { transform: translate(0, 0) scale(1); }
    25% { transform: translate(-20px, 30px) scale(1.05); }
    75% { transform: translate(30px, -20px) scale(0.95); }
}

/* ===========================================
   Section glow

   The same cyan light as the orbs above, for sections further down the page.
   Not the orbs themselves: those are `position: fixed`, so letting them show
   through a section would pin the glow to the same screen coordinates for the
   whole scroll — light that sits on the display rather than in the page — and
   would put their 20s float on screen continuously instead of for one
   viewport. These are anchored to their section and completely static; they
   travel with the content and hold still while you read.

   Each section places its own with the three variables. Deliberately not
   applied to every section: see the notes at each one for why it is or isn't
   there. --glow-color is an unwrapped triplet so the alpha stays adjustable.
   =========================================== */
.features,
.faq {
    --glow-color: 173, 251, 246;
    --glow-size: 58rem;
    --glow-strength: 0.13;
}

/* On a near-white ground the pale cyan reads as nothing at all, so light mode
   swaps in the deep cyan at a lower alpha — a tint of the same hue rather than
   a highlight, which is what "glow" means on a light background. */
body.light-mode .features,
body.light-mode .faq {
    --glow-color: 13, 115, 119;
    --glow-strength: 0.05;
}

/* z-index: -1 rather than 0. Inside the section's own stacking context that
   paints above its background and below the content; at 0 it would paint above
   the ordinary, non-positioned content instead, and wash over the type. */
.features::before,
.faq::before {
    content: '';
    position: absolute;
    inset: 0;
    z-index: -1;
    pointer-events: none;
    background: radial-gradient(var(--glow-size) var(--glow-size)
        at var(--glow-x) var(--glow-y),
        rgba(var(--glow-color), var(--glow-strength)) 0%,
        transparent 68%);
}

/* Placed off the deck's top corner, the same quarter the hero's light comes
   from — the section where the product finally answers gets the brand's own
   colour behind it, and the phone's glow already lives on the other side. */
.features { --glow-x: 74%; --glow-y: 18%; }

/* Low and to the left, deliberately not where the last one was: two washes in
   the same corner read as one repeated stamp rather than as a page with light
   in it. It also lifts the flattest panel on the site off the footer. */
.faq {
    --glow-x: 24%;
    --glow-y: 82%;
    --glow-size: 44rem;
    --glow-strength: 0.12;
}

/* ===========================================
   Dark Mode Toggle
   =========================================== */
.theme-toggle {
    position: fixed;
    top: 2rem;
    right: 2rem;
    z-index: 1001;
    display: flex;
    align-items: center;
    gap: 0.75rem;
    padding: 0.6rem 1.25rem;
    background: var(--glass-bg);
    backdrop-filter: blur(20px) saturate(180%);
    -webkit-backdrop-filter: blur(20px) saturate(180%);
    border: 1px solid var(--glass-border);
    border-radius: 100px;
    cursor: pointer;
    transition: transform 300ms var(--ease-out), box-shadow 300ms var(--ease-out);
    box-shadow: var(--shadow-md);
}

/* Gated: on touch, a tap fires :hover and would leave the control raised. */
@media (hover: hover) and (pointer: fine) {
    .theme-toggle:hover {
        transform: translateY(-2px);
        box-shadow: var(--shadow-lg);
    }
}

.theme-toggle-track {
    width: 48px;
    height: 26px;
    background: linear-gradient(135deg, var(--cyan-glow) 0%, var(--cyan-medium) 100%);
    border-radius: 13px;
    position: relative;
    transition: background 300ms var(--ease-out), box-shadow 300ms var(--ease-out);
    box-shadow: 0 0 16px rgba(173, 251, 246, 0.4);
}

body.light-mode .theme-toggle-track {
    background: linear-gradient(135deg, rgba(0, 0, 0, 0.1) 0%, rgba(0, 0, 0, 0.15) 100%);
    box-shadow: inset 0 2px 4px rgba(0, 0, 0, 0.1);
}

.theme-toggle-thumb {
    position: absolute;
    top: 3px;
    left: 25px;
    width: 20px;
    height: 20px;
    background: linear-gradient(135deg, #1a1a1f 0%, #0a0a0f 100%);
    border-radius: 50%;
    transition: left 300ms var(--ease-out), background 300ms var(--ease-out);
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
}

body.light-mode .theme-toggle-thumb {
    left: 3px;
    background: linear-gradient(135deg, #ffffff 0%, #f0f0f0 100%);
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);
}

.theme-toggle-icon {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 20px;
    height: 20px;
}

.theme-toggle-icon svg {
    width: 18px;
    height: 18px;
}

.theme-toggle-icon.moon {
    color: var(--cyan-glow);
    filter: drop-shadow(0 0 4px rgba(173, 251, 246, 0.4));
}

.theme-toggle-icon.sun {
    display: none;
    color: var(--gold-rich);
    filter: drop-shadow(0 0 4px rgba(212, 168, 87, 0.4));
}

body.light-mode .theme-toggle-icon.moon {
    display: none;
}

body.light-mode .theme-toggle-icon.sun {
    display: flex;
}

/* ===========================================
   Hero Section - Original Design
   =========================================== */
.hero {
    min-height: 100vh;
    display: flex;
    align-items: center;
    justify-content: center;
    position: relative;
    z-index: 1;
}

.hero-content {
    text-align: center;
    padding: 40px 20px;
    animation: focusIn 2s ease-out forwards;
}

/* Original Focus-In Animation */
@keyframes focusIn {
    0% {
        filter: blur(25px);
        opacity: 0.2;
        transform: scale(1.03);
    }
    20% {
        filter: blur(18px);
        opacity: 0.4;
    }
    40% {
        filter: blur(12px);
        opacity: 0.6;
    }
    60% {
        filter: blur(6px);
        opacity: 0.8;
    }
    80% {
        filter: blur(2px);
        opacity: 0.95;
    }
    100% {
        filter: blur(0);
        opacity: 1;
        transform: scale(1);
    }
}

h1 {
    font-family: var(--font-serif);
    font-weight: 300;
    font-size: clamp(4rem, 10vw, 7rem);
    letter-spacing: 0.35em;
    color: var(--cyan-glow);
    text-transform: uppercase;
    margin-bottom: 20px;
}

/* The clamp floor above is 4rem, which with 0.35em of tracking holds the
   wordmark at a fixed 372px however narrow the screen gets — on a 320px phone
   that cut both E's off, and dragged the whole hero block out with it. Below
   the width where 4rem still fits, size it from the viewport instead. */
@media (max-width: 440px) {
    .hero-content h1 {
        font-size: clamp(2.5rem, 13.5vw, 4rem);
        letter-spacing: 0.3em;
    }
}

.logo-e {
    position: relative;
    text-shadow:
        0 0 10px rgba(173, 251, 246, 1),
        0 0 20px rgba(173, 251, 246, 0.9),
        0 0 40px rgba(173, 251, 246, 0.7),
        0 0 60px rgba(173, 251, 246, 0.5),
        0 0 80px rgba(173, 251, 246, 0.3);
}

.logo-e::after {
    content: '';
    position: absolute;
    left: 0;
    bottom: 0.05em;
    width: 100%;
    height: 2px;
    background: linear-gradient(90deg, #ADFBF6, #5CECD3);
    border-radius: 1px;
    box-shadow: 0 0 10px rgba(173, 251, 246, 0.8);
}

body.light-mode .logo-e {
    text-shadow:
        0 0 10px rgba(13, 115, 119, 0.8),
        0 0 20px rgba(13, 115, 119, 0.6),
        0 0 40px rgba(13, 115, 119, 0.4),
        0 0 60px rgba(13, 115, 119, 0.2);
}

body.light-mode .logo-e::after {
    background: linear-gradient(90deg, #0D7377, #14919B);
    box-shadow: 0 0 10px rgba(13, 115, 119, 0.5);
}

h1.logo-text {
    display: inline-flex;
    align-items: flex-end;
    justify-content: center;
    gap: 0;
    position: relative;
}

h1.logo-text-extended {
    position: relative;
    display: inline-block;
}

.logo-e-extended {
    display: block;
    height: 1em;
    width: auto;
    filter: drop-shadow(0 0 10px rgba(173, 251, 246, 0.6));
}

.logo-text-overlay {
    position: absolute;
    left: 0.62em;
    top: 0;
    line-height: 1;
}

.logo-monogram {
    height: 1em;
    width: auto;
    margin-right: 0.05em;
    filter: drop-shadow(0 0 10px rgba(173, 251, 246, 0.6));
    flex-shrink: 0;
}

.logo-monogram-footer {
    height: 1em;
    width: auto;
    margin-right: 0.05em;
    filter: drop-shadow(0 0 6px rgba(173, 251, 246, 0.4));
    flex-shrink: 0;
}

body.light-mode h1 {
    color: var(--cyan-deep);
}

body.light-mode .logo-monogram rect,
body.light-mode .logo-monogram-footer rect,
body.light-mode .logo-e-extended rect {
    fill: var(--cyan-deep);
}

.tagline {
    font-size: 1.2rem;
    color: var(--text-secondary);
    letter-spacing: 0.1em;
    margin-bottom: 50px;
}

.by-grey-ai {
    display: inline-block;
    font-size: 0.75rem;
    letter-spacing: 0.3em;
    text-transform: uppercase;
    color: var(--text-secondary);
    text-decoration: none;
    margin-bottom: 18px;
    opacity: 0.7;
    transition: opacity 0.3s ease, color 0.3s ease;
}

.by-grey-ai:hover {
    opacity: 1;
    color: var(--text-primary);
}

/* ===========================================
   Form Styles - Original Glassmorphism
   =========================================== */
form {
    max-width: 520px;
    margin: 0 auto;
}

.input-group {
    display: flex;
    background: linear-gradient(135deg, rgba(255, 255, 255, 0.1), rgba(255, 255, 255, 0.05));
    backdrop-filter: blur(24px) saturate(180%);
    -webkit-backdrop-filter: blur(24px) saturate(180%);
    border-radius: 16px;
    padding: 6px;
    border: 1px solid rgba(255, 255, 255, 0.18);
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.4), inset 0 1px 0 rgba(255, 255, 255, 0.2);
    transition: border-color 300ms var(--ease-out), box-shadow 300ms var(--ease-out);
}

body.light-mode .input-group {
    background: linear-gradient(135deg, rgba(255, 255, 255, 0.8), rgba(255, 255, 255, 0.6));
    border: 1px solid rgba(0, 0, 0, 0.08);
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.1);
}

.input-group:hover {
    border-color: rgba(173, 251, 246, 0.3);
}

body.light-mode .input-group:hover {
    border-color: rgba(13, 115, 119, 0.3);
}

.input-group:focus-within {
    border-color: rgba(173, 251, 246, 0.4);
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.45), 0 0 60px rgba(173, 251, 246, 0.12);
}

body.light-mode .input-group:focus-within {
    border-color: var(--cyan-deep);
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.15), 0 0 30px rgba(13, 115, 119, 0.1);
}

.input-wrapper {
    flex: 1;
}

input {
    width: 100%;
    padding: 18px 24px;
    font-size: 1rem;
    font-family: var(--font-sans);
    background: transparent;
    border: none;
    color: var(--text-primary);
    outline: none;
}

input::placeholder {
    color: var(--text-muted);
}

button[type="submit"] {
    padding: 18px 36px;
    font-size: 0.95rem;
    font-family: var(--font-sans);
    font-weight: 500;
    letter-spacing: 0.05em;
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.2), rgba(173, 251, 246, 0.1));
    backdrop-filter: blur(10px);
    color: var(--cyan-glow);
    border: 1px solid rgba(173, 251, 246, 0.35);
    border-radius: 12px;
    cursor: pointer;
    transition: transform 160ms var(--ease-out), background 250ms var(--ease-out), border-color 250ms var(--ease-out), color 250ms var(--ease-out);
    white-space: nowrap;
}

body.light-mode button[type="submit"] {
    background: linear-gradient(135deg, var(--cyan-deep) 0%, var(--cyan-medium) 100%);
    color: var(--white);
    border: none;
    box-shadow: var(--shadow-cyan);
}

button[type="submit"]:hover {
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.3), rgba(173, 251, 246, 0.15));
    border-color: rgba(173, 251, 246, 0.5);
    color: #fff;
    transform: translateY(-1px);
    box-shadow: 0 8px 30px rgba(173, 251, 246, 0.2);
}

body.light-mode button[type="submit"]:hover {
    transform: translateY(-3px);
    box-shadow: 0 16px 48px rgba(13, 115, 119, 0.35);
}

button[type="submit"]:disabled {
    cursor: not-allowed;
    opacity: 0.7;
    transform: none;
}

.success {
    display: none;
    margin-top: 24px;
    padding: 20px 28px;
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.12), rgba(173, 251, 246, 0.06));
    backdrop-filter: blur(24px);
    border: 1px solid rgba(173, 251, 246, 0.25);
    border-radius: 12px;
    color: var(--cyan-glow);
}

body.light-mode .success {
    background: linear-gradient(135deg, rgba(13, 115, 119, 0.08) 0%, rgba(50, 224, 196, 0.08) 100%);
    border: 1px solid rgba(13, 115, 119, 0.2);
    color: var(--cyan-deep);
}

.success.show {
    display: block;
    animation: fadeUp 0.6s;
}

@keyframes fadeUp {
    from {
        opacity: 0;
        transform: translateY(15px);
    }
    to {
        opacity: 1;
        transform: translateY(0);
    }
}

/* ===========================================
   Join Waitlist Button (Hero)
   =========================================== */
.join-waitlist-btn {
    padding: 20px 48px;
    font-size: 1rem;
    font-family: var(--font-sans);
    font-weight: 500;
    letter-spacing: 0.05em;
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.2), rgba(173, 251, 246, 0.1));
    backdrop-filter: blur(10px);
    color: var(--cyan-glow);
    border: 1px solid rgba(173, 251, 246, 0.35);
    border-radius: 16px;
    cursor: pointer;
    transition: transform 160ms var(--ease-out), background 250ms var(--ease-out), border-color 250ms var(--ease-out), color 250ms var(--ease-out), box-shadow 250ms var(--ease-out);
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.4);
}

body.light-mode .join-waitlist-btn {
    background: linear-gradient(135deg, var(--cyan-deep) 0%, var(--cyan-medium) 100%);
    color: var(--white);
    border: none;
    box-shadow: var(--shadow-cyan);
}

.join-waitlist-btn:hover {
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.3), rgba(173, 251, 246, 0.15));
    border-color: rgba(173, 251, 246, 0.5);
    color: #fff;
    transform: translateY(-3px);
    box-shadow: 0 12px 40px rgba(173, 251, 246, 0.25);
}

body.light-mode .join-waitlist-btn:hover {
    transform: translateY(-3px);
    box-shadow: 0 16px 48px rgba(13, 115, 119, 0.35);
}

/* Both selectors, after both hover rules: the light-mode hover is 0,3,0 and
   would otherwise outrank a bare .join-waitlist-btn:active. */
.join-waitlist-btn:active,
body.light-mode .join-waitlist-btn:active {
    transform: scale(0.97);
}

.beta-free-note {
    margin-top: 16px;
    font-size: 0.85rem;
    letter-spacing: 0.1em;
    color: var(--text-muted);
}

/* ===========================================
   Typeform Container
   =========================================== */
/* The min-height only reserves the form's space so the page doesn't jump while
   the embed boots — so it has to be no taller than what the embed actually
   renders, or the surplus becomes a strip of empty glass under the button. It
   was 550 against an embed that lays itself out at 500, which was invisible
   while this was a centred box on its own and obvious the moment it stood
   beside a column with a clean bottom edge. Matching it is the whole fix: the
   embed writes its height inline, so nothing short of !important would move it
   and there is no reason to fight a script that is sizing itself correctly. */
.typeform-container {
    position: relative;
    z-index: 1;
    min-height: 500px;
    width: 100%;
}

/* ===========================================
   Scroll Indicator
   =========================================== */
.scroll-indicator {
    position: absolute;
    bottom: 40px;
    left: 50%;
    transform: translateX(-50%);
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 8px;
    color: var(--text-muted);
    font-size: 0.85rem;
    letter-spacing: 0.1em;
    cursor: pointer;
    transition: color 0.3s;
    text-decoration: none;
}

/* The hint only runs while the hero is on screen. A view() timeline is the
   wrong tool here: it would map the bounce iterations to scroll position, so
   the arrow would bounce as you scroll instead of on its own. A class does it. */
.scroll-indicator.is-hinting {
    animation: bounce 2s infinite;
}

.scroll-indicator:hover {
    color: var(--cyan-glow);
}

body.light-mode .scroll-indicator:hover {
    color: var(--cyan-deep);
}

.scroll-indicator svg {
    width: 24px;
    height: 24px;
}

@keyframes bounce {
    0%, 20%, 50%, 80%, 100% {
        transform: translateX(-50%) translateY(0);
    }
    40% {
        transform: translateX(-50%) translateY(-10px);
    }
    60% {
        transform: translateX(-50%) translateY(-5px);
    }
}

@keyframes shake {
    0%, 100% { transform: translateX(0); }
    10%, 30%, 50%, 70%, 90% { transform: translateX(-6px); }
    20%, 40%, 60%, 80% { transform: translateX(6px); }
}

/* ===========================================
   Sections Base
   =========================================== */
.section-container {
    max-width: var(--container-max);
    margin: 0 auto;
    padding: 0 2rem;
    overflow: visible;
}

.section-header {
    text-align: center;
    margin-bottom: 4rem;
}

.section-title {
    font-family: var(--font-serif);
    font-size: clamp(2rem, 5vw, 3.5rem);
    font-weight: 500;
    line-height: 1.2;
    color: var(--text-primary);
    letter-spacing: -0.02em;
}

/* Decorative flourish below section titles */
.section-title::after {
    content: '';
    display: block;
    width: 60px;
    height: 2px;
    margin: 1.25rem auto 0;
    background: linear-gradient(90deg, transparent, var(--cyan-glow), transparent);
    border-radius: 2px;
}

body.light-mode .section-title::after {
    background: linear-gradient(90deg, transparent, var(--cyan-deep), transparent);
}

/* The accent word. .cta-form-title is a stepped-down heading rather than a
   section title, but it is the same sentence pattern — one word carrying the
   colour — and it would be the only title on the page that doesn't. */
.section-title span,
.cta-form-title span {
    font-style: italic;
    color: var(--cyan-glow);
}

.section-title span.no-italic,
.cta-form-title span.no-italic {
    font-style: normal;
}

body.light-mode .section-title span,
body.light-mode .cta-form-title span {
    color: var(--cyan-deep);
}

/* ===========================================
   Video Showcase
   =========================================== */
.video-showcase {
    padding: var(--section-padding) 0;
    background: var(--bg-secondary);
    position: relative;
    z-index: 1;
}

body.light-mode .video-showcase {
    background: var(--white);
}

.video-container {
    position: relative;
    border-radius: 24px;
    overflow: hidden;
    border: 1px solid var(--glass-border);
    background: var(--glass-bg);
    backdrop-filter: blur(24px) saturate(180%);
    -webkit-backdrop-filter: blur(24px) saturate(180%);
    cursor: pointer;
    transition: transform 0.5s cubic-bezier(0.25, 0.46, 0.45, 0.94),
                box-shadow 0.5s cubic-bezier(0.25, 0.46, 0.45, 0.94);
}

@keyframes videoGlow {
    0%, 100% {
        box-shadow:
            var(--shadow-lg),
            0 0 40px rgba(173, 251, 246, 0.08),
            0 0 80px rgba(173, 251, 246, 0.04);
    }
    50% {
        box-shadow:
            var(--shadow-lg),
            0 0 60px rgba(173, 251, 246, 0.15),
            0 0 120px rgba(173, 251, 246, 0.06);
    }
}

body.light-mode .video-container {
}

@keyframes videoGlowLight {
    0%, 100% {
        box-shadow:
            var(--shadow-lg),
            0 0 40px rgba(13, 115, 119, 0.06),
            0 0 80px rgba(13, 115, 119, 0.03);
    }
    50% {
        box-shadow:
            var(--shadow-lg),
            0 0 60px rgba(13, 115, 119, 0.12),
            0 0 120px rgba(13, 115, 119, 0.05);
    }
}

@media (hover: hover) and (pointer: fine) {
    .video-container:hover {
        transform: translateY(-4px);
    }
}

/* Cinematic vignette overlay */
.video-container::after {
    content: '';
    position: absolute;
    inset: 0;
    background: radial-gradient(ellipse at center, transparent 40%, rgba(0, 0, 0, 0.5) 100%);
    z-index: 1;
    pointer-events: none;
    transition: opacity 0.6s ease;
}

body.light-mode .video-container::after {
    background: radial-gradient(ellipse at center, transparent 40%, rgba(0, 0, 0, 0.25) 100%);
}

.video-container.playing::after {
    opacity: 0;
}

.video-container video {
    width: 100%;
    display: block;
}

/* Play button */
.video-play-btn {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    width: 90px;
    height: 90px;
    border-radius: 50%;
    border: 2px solid rgba(255, 255, 255, 0.25);
    background: rgba(0, 0, 0, 0.35);
    backdrop-filter: blur(16px);
    -webkit-backdrop-filter: blur(16px);
    color: var(--white);
    cursor: pointer;
    display: flex;
    align-items: center;
    justify-content: center;
    transition: transform 160ms var(--ease-out), background 250ms var(--ease-out), border-color 250ms var(--ease-out), box-shadow 250ms var(--ease-out), opacity 250ms var(--ease-out);
    z-index: 3;
    box-shadow:
        0 0 0 6px rgba(173, 251, 246, 0.08),
        0 0 30px rgba(173, 251, 246, 0.1);
}

.video-play-btn svg {
    width: 30px;
    height: 30px;
    margin-left: 3px;
}

.video-play-btn:hover {
    background: rgba(173, 251, 246, 0.15);
    border-color: var(--cyan-glow);
    transform: translate(-50%, -50%) scale(1.12);
    box-shadow:
        0 0 0 8px rgba(173, 251, 246, 0.15),
        0 0 40px rgba(173, 251, 246, 0.25);
    animation: none;
}

body.light-mode .video-play-btn {
    background: rgba(255, 255, 255, 0.45);
    border-color: rgba(13, 115, 119, 0.25);
    color: var(--gray-900);
    box-shadow:
        0 0 0 6px rgba(13, 115, 119, 0.06),
        0 0 30px rgba(13, 115, 119, 0.08);
}

body.light-mode .video-play-btn:hover {
    background: rgba(13, 115, 119, 0.12);
    border-color: var(--cyan-deep);
    box-shadow:
        0 0 0 8px rgba(13, 115, 119, 0.12),
        0 0 40px rgba(13, 115, 119, 0.2);
    animation: none;
}

/* After :hover, which also sets transform — otherwise pressing while hovering
   would keep the hover scale and the press would never show. Composed with the
   centring translate, or the button jumps to the corner. */
.video-play-btn:active,
body.light-mode .video-play-btn:active {
    transform: translate(-50%, -50%) scale(0.97);
}

.video-container.playing .video-play-btn {
    opacity: 0;
    pointer-events: none;
}

.video-container:hover .video-play-btn {
    opacity: 1;
}

.video-container.playing:hover .video-play-btn {
    opacity: 0.9;
    pointer-events: auto;
}

/* Caption */
.video-caption {
    text-align: center;
    margin-top: 1.25rem;
    font-size: 0.85rem;
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: var(--text-muted);
}

/* ===========================================
   Pain Points Section
   =========================================== */
/* Same ground as the hero, continuous with it.

   Three things used to set this section apart and none of them earned it: a
   background one notch off the hero's (--bg-secondary, #0a0a0f against
   #0A0A0A — invisible in the dark, but white against off-white in light mode),
   a 32px dot grid, and a hairline across the top. Together they made the page's
   second beat read as a panel laid over the page rather than as the page
   continuing.

   The colour is the hero's now. The section is still opaque further down — it
   has to be, or the fixed orbs would sit at the same screen coordinates the
   whole way through it — but it starts transparent and fades in over the first
   stretch, so the hero's light carries across the join and dies away naturally
   instead of being sliced off at a hard horizontal edge. */
.pain-points {
    padding: var(--section-padding) 0;
    background: linear-gradient(180deg, transparent 0, var(--bg-primary) 30rem);
    position: relative;
    z-index: 1;
}
/* No light-mode override: --bg-primary already re-resolves, and what shows
   through the transparent end is the body, which is that same colour. */

/* ===========================================
   Features Section
   =========================================== */
.features {
    padding: var(--section-padding) 0;
    background: var(--bg-primary);
    position: relative;
    z-index: 1;
    overflow: visible;
}

body.light-mode .features {
    background: var(--gray-50);
}

.feature-card {
    padding: 2.5rem;
    background: var(--glass-bg);
    backdrop-filter: blur(20px) saturate(180%);
    -webkit-backdrop-filter: blur(20px) saturate(180%);
    border-radius: 24px;
    border: 1px solid var(--glass-border);
    transition: transform 0.3s ease, border-color 0.3s ease, box-shadow 0.3s ease;
    position: relative;
    overflow: hidden;
    will-change: transform;
    backface-visibility: hidden;
}

body.light-mode .feature-card {
    background: rgba(255, 255, 255, 0.6);
    border: 1px solid rgba(255, 255, 255, 0.8);
    box-shadow: var(--shadow-md);
}

.feature-card::before {
    content: '';
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    height: 3px;
    background: white;
    transform: scaleX(0);
    transform-origin: left;
    transition: transform 0.4s ease;
}

body.light-mode .feature-card::before {
    background: #999;
}

.feature-card:hover {
    transform: translateY(-8px);
    border-color: rgba(255, 255, 255, 0.4);
    box-shadow: 0 30px 60px rgba(255, 255, 255, 0.1);
}

body.light-mode .feature-card:hover {
    box-shadow: var(--shadow-lg);
}

.feature-card:hover::before {
    transform: scaleX(1);
}

.feature-icon {
    width: 56px;
    height: 56px;
    display: flex;
    align-items: center;
    justify-content: center;
    background: linear-gradient(135deg, rgba(173, 251, 246, 0.2) 0%, rgba(50, 224, 196, 0.1) 100%);
    border-radius: 16px;
    margin-bottom: 1.5rem;
    color: var(--cyan-glow);
}

body.light-mode .feature-icon {
    background: linear-gradient(135deg, var(--cyan-pale) 0%, rgba(50, 224, 196, 0.2) 100%);
    color: var(--cyan-deep);
}

.feature-icon svg {
    width: 32px;
    height: 32px;
}

.feature-card h3 {
    font-family: var(--font-serif);
    font-size: 1.35rem;
    font-weight: 600;
    color: var(--text-primary);
    margin-bottom: 0.75rem;
    padding-bottom: 0.75rem;
    border-bottom: 1px solid rgba(173, 251, 246, 0.1);
}

body.light-mode .feature-card h3 {
    border-bottom-color: rgba(13, 115, 119, 0.12);
}

.feature-card > p {
    font-size: 0.9375rem;
    line-height: 1.7;
    color: var(--text-secondary);
}

.feature-list {
    margin-top: 1.25rem;
    list-style: none;
}

.feature-list li {
    color: var(--text-muted);
    font-size: 0.85rem;
    padding: 6px 0;
    padding-left: 20px;
    position: relative;
    font-style: italic;
}

.feature-list li::before {
    content: '';
    position: absolute;
    left: 0;
    top: 10px;
    width: 8px;
    height: 8px;
    border-right: 2px solid var(--cyan-glow);
    border-top: 2px solid var(--cyan-glow);
    transform: rotate(45deg);
}

body.light-mode .feature-list li::before {
    border-color: var(--cyan-deep);
}

/* ===========================================
   How It Works Section
   =========================================== */
.how-it-works {
    padding: var(--section-padding) 0;
    background: var(--bg-secondary);
    position: relative;
    z-index: 1;
}

body.light-mode .how-it-works {
    background: var(--white);
}

.steps {
    display: flex;
    flex-direction: column;
    gap: 3rem;
    max-width: 800px;
    margin: 0 auto;
}

.step {
    display: flex;
    align-items: flex-start;
    gap: 2rem;
    padding: 2rem;
    background: var(--glass-bg);
    border-radius: 20px;
    border: 1px solid var(--glass-border);
    transition: transform 0.3s ease, border-color 0.3s ease;
    backface-visibility: hidden;
}

body.light-mode .step {
    background: rgba(255, 255, 255, 0.6);
    border: 1px solid rgba(255, 255, 255, 0.8);
    box-shadow: var(--shadow-md);
}

.step:hover {
    transform: translateX(8px);
    border-color: rgba(173, 251, 246, 0.3);
}

/* A quiet marker, not a badge: the number counts the steps, it doesn't
   compete with the heading beside it. */
.step-number {
    position: relative;
    width: 2.75rem;
    height: 2.75rem;
    min-width: 2.75rem;
    background: var(--glass-bg);
    border: 1px solid var(--glass-border);
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    font-family: var(--font-sans);
    font-size: 0.9375rem;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    color: var(--accent);
}

body.light-mode .step-number {
    background: rgba(255, 255, 255, 0.7);
    border-color: rgba(13, 115, 119, 0.18);
    color: var(--cyan-deep);
}

.step-content h3 {
    font-family: var(--font-sans);
    font-size: 1.25rem;
    font-weight: 600;
    line-height: 1.28;
    letter-spacing: -0.014em;
    color: var(--text-primary);
    margin-bottom: 0.5rem;
}

.step-content p {
    color: var(--text-secondary);
    line-height: 1.7;
}

/* ===========================================
   The bespoke claim

   Was a centred paragraph inside a pane of glass, floating over concentric
   rings: 848px of section carrying 54 words, where every element on screen
   except the words was decoration. The rings and the panel went, and what was
   left was the argument, set as a statement — left ranged, one measure wide.

   It is no longer a section of its own. As a standalone beat it was prose
   between two visual sections with nothing happening in it, which is why it
   spent a while hidden. It now leads the application (see .cta-split), where
   it is the answer to the question the form raises: why this is something you
   apply for rather than something you download.

   The closing line is not a pill. It was the only real sentence here and it
   was being worn as a badge; it is the thing the column builds to.
   =========================================== */

/* Left ranged, one measure wide. Centred prose across 720px reads as a
   template hero and is measurably harder to scan than a fixed left edge. */
.cta-claim .section-title {
    margin-bottom: 2rem;
}

/* The shared flourish under section titles is centred, which left a short
   cyan rule floating in the middle of a block ranged hard left. It also
   competed with the accent rule above the closing line — two accent marks in
   a column this short is noise, and the one that matters is the second. */
.cta-claim .section-title::after { display: none; }

.bespoke-body p {
    /* A measure, not a column width: ~70 characters is where a line stops
       needing the eye to hunt for the next one. */
    max-width: 38rem;
    font-size: 1.0625rem;
    line-height: 1.75;
    color: var(--text-secondary);
}

.bespoke-body p + p { margin-top: 1.1rem; }

/* The point. A hairline in the accent, then the sentence the whole section
   exists to deliver — same serif as the headings, so it reads as a statement
   rather than as a caption. */
.bespoke-note {
    display: block;
    max-width: 38rem;
    margin: 2.5rem 0 0;
    padding-top: 1.75rem;
    border-top: 1px solid var(--glass-border);
    font-family: var(--font-serif);
    font-style: italic;
    font-size: clamp(1.35rem, 3vw, 1.75rem) !important;
    line-height: 1.35;
    letter-spacing: 0;
    color: var(--text-primary);
}

.bespoke-note::before {
    content: '';
    display: block;
    width: 2.5rem;
    height: 2px;
    margin-bottom: 1.35rem;
    background: var(--cyan-light);
    box-shadow: 0 0 10px rgba(173, 251, 246, 0.55);
}

body.light-mode .bespoke-note::before {
    background: var(--cyan-deep);
    box-shadow: none;
}

@media (max-width: 640px) {
    .cta-claim .section-title { margin-bottom: 1.5rem; }
    .bespoke-body p { font-size: 0.9375rem; line-height: 1.7; }
    .bespoke-note { margin-top: 2rem; padding-top: 1.4rem; }
}

/* No bespoke-specific reveal any more. The blur-and-scale materialise was
   there because the panel was glass and had to read as arriving; text ranged
   on the page just rises with everything else. */

/* ===========================================
   CTA Section
   =========================================== */

/* The sign-up line was a glass pill, centred under a centred headline. It
   can't stay one: it now sits an inch above the glass form wrapper, and a
   translucent badge on top of a translucent panel is the one stack that
   reliably turns to mud. Plain line, same italic voice, doing the same job —
   saying what the form is before you look at it. */
.cta-note {
    margin-top: 0.5rem;
    font-size: 0.9rem;
    line-height: 1.5;
    font-style: italic;
    letter-spacing: 0.04em;
    color: var(--text-secondary);
}

/* A hidden section must not hold its padding open. */
[hidden] { display: none !important; }

.cta-section {
    padding: var(--section-padding) 0;
    background: var(--bg-primary);
    position: relative;
    z-index: 1;
    /* The photograph layer below is scaled up past the section's edges to hide
       the blur's soft fringe; without this it reaches past the right edge of
       the page and puts a horizontal scrollbar on the whole document. Nothing
       in this section overflows on purpose. */
    overflow: hidden;
}

body.light-mode .cta-section {
    background: var(--gray-50);
}

/* --- the photograph under the application ---------------------------------
   The one image of actual people on a page that is otherwise devices and
   type, and it sits under the only place we ask for something. Softened to
   about a depth-of-field rather than hidden: the room reads, the faces read,
   and the scrim below carries the job of keeping the words legible instead of
   the blur doing it by erasing the picture.

   Its own layer rather than a background on the section, because `filter`
   would otherwise blur the claim and the form along with it.

   Served from Cloudinary through the same f_auto,q_auto transform as the
   lockscreen and the benefits rack — w_1800 covers the widest viewport this
   is drawn across, at roughly a fifteenth of the original's weight. */
.cta-section::before {
    content: '';
    position: absolute;
    inset: 0;
    z-index: 0;
    background-image: url('https://res.cloudinary.com/dayr3egl3/image/upload/f_auto,q_auto,w_1800/v1787865693/exhale-background_eszswr.jpg');
    background-size: cover;
    background-position: center;
    /* Enough softness to read as depth of field rather than as a sharp photo
       competing with the type, and no more. The heavy blur that was here did
       the hiding on its own, which meant hiding the picture to protect the
       words; the scrim below now does that job, so the room can be a room. */
    filter: blur(4px) saturate(0.95) brightness(0.62);
    /* A blur samples from beyond the element and leaves a soft transparent
       fringe at each edge. Scaling up pushes that fringe outside the section. */
    transform: scale(1.06);
    opacity: 0.62;
    /* Faded out top and bottom so it reads as light in the room rather than as
       a panel banding against the FAQ above and the footer below. */
    -webkit-mask-image: linear-gradient(180deg, transparent 0, #000 18%, #000 82%, transparent 100%);
    mask-image: linear-gradient(180deg, transparent 0, #000 18%, #000 82%, transparent 100%);
    pointer-events: none;
}

/* --- the scrim that keeps the words readable ------------------------------
   A photograph this legible has bright patches and hard edges in it, and the
   claim is light text ranged across the left half. So the darkening is no
   longer spread evenly over the picture — it is weighted to where the words
   are and lifts off toward the form, which is how the room stays visible
   without the copy having to survive whatever happens to be behind it.

   Written per theme rather than through the token, because these need alpha
   and --bg-primary is a flat colour: #0A0A0A dark, --gray-50 light. */
.cta-section::after {
    content: '';
    position: absolute;
    inset: 0;
    z-index: 0;
    pointer-events: none;
    background: linear-gradient(96deg,
        rgba(10, 10, 10, 0.93) 0%,
        rgba(10, 10, 10, 0.82) 26%,
        rgba(10, 10, 10, 0.58) 50%,
        rgba(10, 10, 10, 0.42) 72%,
        rgba(10, 10, 10, 0.34) 100%);
}

body.light-mode .cta-section::after {
    background: linear-gradient(96deg,
        rgba(250, 250, 250, 0.94) 0%,
        rgba(250, 250, 250, 0.86) 26%,
        rgba(250, 250, 250, 0.62) 50%,
        rgba(250, 250, 250, 0.4) 72%,
        rgba(250, 250, 250, 0.28) 100%);
}

/* Stacked, the copy runs the full width of the screen, so there is no clear
   side for the scrim to lift toward — a horizontal gradient would leave the
   right-hand end of every line unprotected. One even veil instead. */
@media (max-width: 900px) {
    .cta-section::after { background: rgba(10, 10, 10, 0.72); }
    body.light-mode .cta-section::after { background: rgba(250, 250, 250, 0.8); }
}

/* Light mode has nowhere near as much room to hide a photograph. A dark scrim
   is not available to it, and the desaturated middle setting that works on
   black turns to grey mud on a pale ground — a smudge rather than a room. So
   it goes the other way: much fainter, and warmer rather than greyer, so what
   survives is the colour of the light in the photograph and nothing else. */
body.light-mode .cta-section::before {
    filter: blur(4px) saturate(0.95) brightness(1.06);
    opacity: 0.5;
}

/* The image is decoration; text contrast is not negotiable. */
@media (prefers-contrast: more) {
    .cta-section::before { display: none; }
}

/* Above the photograph. Without this the claim and the form share the
   pseudo-element's plane and the paint order is left to source order. */
.cta-section > .section-container {
    position: relative;
    z-index: 1;
}

/* The claim and the form, one row. Proportioned so the form gets the larger
   share: the prose has a measure it must not exceed anyway, and the Typeform
   embed is the thing being asked for. `start`, not `stretch` — the claim is a
   statement that ends where it ends, not a panel to be squared off against a
   form twice its height. */
.cta-split {
    display: grid;
    grid-template-columns: minmax(0, 0.85fr) minmax(0, 1fr);
    gap: clamp(2.5rem, 5vw, 4.5rem);
    align-items: start;
}

/* Ranged left against the form, and held to a measure — ~70 characters is
   where a line stops needing the eye to hunt for the next one. */
.cta-claim {
    max-width: 38rem;
    /* The claim is the argument; the form beside it is taller. Nudged down so
       the two read as a pair rather than as a heading with a box after it. */
    padding-top: clamp(0rem, 2vw, 1.5rem);
}

/* The action, stepped down. It was the section title when the form stood
   alone; beside a claim that is now the headline, a second h2 would be two
   headlines shouting over each other. Same serif, smaller voice, and it sits
   directly above the thing it names. */
.cta-form-header {
    margin-bottom: 1.25rem;
}

.cta-form-title {
    font-family: var(--font-serif);
    font-size: clamp(1.5rem, 2.6vw, 2rem);
    font-weight: 500;
    line-height: 1.2;
    letter-spacing: -0.015em;
    color: var(--text-primary);
}

/* One column below the same line the capabilities deck stands down at. The
   embed is the constraint: split any narrower and the form is answering
   questions in a 400px gutter. Stacked, the claim still comes first — you
   read why before you are asked to. */
@media (max-width: 900px) {
    .cta-split {
        grid-template-columns: minmax(0, 1fr);
        gap: 2.5rem;
    }

    .cta-claim { padding-top: 0; }
}

.typeform-wrapper {
    background: var(--glass-bg);
    backdrop-filter: blur(24px) saturate(180%);
    -webkit-backdrop-filter: blur(24px) saturate(180%);
    border-radius: 24px;
    padding: 2rem;
    border: 1px solid var(--glass-border);
    position: relative;
    overflow: hidden;
}

body.light-mode .typeform-wrapper {
    background: rgba(255, 255, 255, 0.6);
    border: 1px solid rgba(255, 255, 255, 0.8);
    box-shadow: var(--shadow-lg);
}

.typeform-wrapper::before {
    content: '';
    position: absolute;
    top: -50%;
    right: -20%;
    width: 500px;
    height: 500px;
    background: radial-gradient(circle, rgba(173, 251, 246, 0.12) 0%, transparent 70%);
    pointer-events: none;
}

body.light-mode .typeform-wrapper::before {
    background: radial-gradient(circle, var(--cyan-pale) 0%, transparent 70%);
    opacity: 0.5;
}

.cta-form-container {
    position: relative;
    z-index: 1;
}

.form-note {
    margin-top: 1rem;
    font-size: 0.8125rem;
    color: var(--text-muted);
    text-align: center;
}

/* ===========================================
   Footer
   =========================================== */
.footer {
    padding: 1.5rem 2rem;
    background: #1a1a1f;
    position: relative;
    z-index: 1;
}

.footer::before {
    content: '';
    position: absolute;
    top: 0;
    left: 50%;
    transform: translateX(-50%);
    width: 120px;
    height: 1px;
    background: linear-gradient(90deg, transparent, rgba(173, 251, 246, 0.3), transparent);
}

body.light-mode .footer {
    background: var(--gray-900);
}

.footer-container {
    max-width: var(--container-max);
    margin: 0 auto;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 2rem;
    text-align: center;
}

.footer-brand {
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: center;
    gap: 1rem;
}

/* Same fixed-tracking problem as the hero: the row is an intrinsic 411px and
   never wraps, so on any phone narrower than that the E and the AI were cut
   off at the edges. */
@media (max-width: 460px) {
    .footer-brand { flex-wrap: wrap; gap: 0.625rem; }
    .footer-logo { font-size: 1.5rem; letter-spacing: 0.26em; }
    .footer-by { font-size: 0.875rem; }
    .footer-grey-logo { height: 2rem; }
}

.footer-logo {
    font-family: var(--font-serif);
    font-size: 2rem;
    font-weight: 300;
    letter-spacing: 0.35em;
    text-transform: uppercase;
    color: var(--cyan-glow);
    line-height: 1;
}


.footer-tagline {
    font-size: 0.875rem;
    color: var(--gray-400);
}

.footer-links {
    display: flex;
    gap: 2rem;
}

.footer-links a {
    font-size: 0.875rem;
    color: var(--gray-400);
    text-decoration: none;
    transition: color 0.3s ease;
}

.footer-links a:hover {
    color: var(--white);
}

.footer-by {
    font-family: var(--font-serif);
    font-size: 1rem;
    font-weight: 300;
    font-style: italic;
    color: var(--gray-400);
    letter-spacing: 0.1em;
}

.footer-brand a {
    display: flex;
    align-items: center;
}

.footer-grey-logo {
    height: 2.5rem;
    width: auto;
    padding: 0.3rem 0.3rem;
    border-radius: 6px;
}

/* ===========================================
   Utility Classes
   =========================================== */
.hidden {
    display: none !important;
}

/* ===========================================
   Reveal Animations - GPU Accelerated
   =========================================== */
.reveal {
    opacity: 0;
    transform: translate3d(0, 40px, 0);
    transition: opacity 0.6s var(--ease-out),
                transform 0.6s var(--ease-out);
    backface-visibility: hidden;
    -webkit-backface-visibility: hidden;
}

.reveal.revealed {
    opacity: 1;
    transform: translate3d(0, 0, 0);
}

.feature-card.reveal {
    transform: translate3d(0, 30px, 0);
}

.feature-card.revealed {
    transform: translate3d(0, 0, 0);
}

.step.reveal {
    transform: translate3d(-20px, 0, 0);
}

.step.revealed {
    transform: translate3d(0, 0, 0);
}

/* ===========================================
   Cursor Glow
   =========================================== */
/* It follows the pointer across the whole page, not just the hero.

   It used to sit at z-index 0, behind every section — and every section from
   The Reality down paints an opaque background, so the light only ever showed
   in the hero, which is the one section with no background of its own. Raising
   it above them is the only way it reaches the rest of the page.

   Which means it is now in front of the content rather than behind it, so it
   has to add light rather than paint over it: `screen` on a dark ground, where
   the transparent falloff is the blend's own no-op, and `multiply` in light
   mode, where a pale cyan screened onto near-white would be nothing at all.
   Under 1000 so it stays beneath the nav pill and the theme toggle. */
.cursor-glow {
    position: fixed;
    top: 0;
    left: 0;
    width: 400px;
    height: 400px;
    border-radius: 50%;
    background: radial-gradient(circle, rgba(173, 251, 246, 0.12) 0%, transparent 70%);
    pointer-events: none;
    z-index: 4;
    mix-blend-mode: screen;
    /* main.js writes the translate3d; the -50% centres it on the pointer.
       Positioned by transform rather than by left/top so following the mouse
       costs a composite instead of a layout on every frame. */
    transform: translate3d(-50%, -50%, 0);
    will-change: transform;
    /* Dark until the pointer has actually been somewhere, and dark again when
       it leaves the window — otherwise the light sits in the corner of a page
       nobody is touching. */
    opacity: 0;
    transition: opacity 0.3s ease;
}

.cursor-glow.is-lit { opacity: 1; }

body.light-mode .cursor-glow {
    background: radial-gradient(circle, rgba(13, 115, 119, 0.12) 0%, transparent 70%);
    mix-blend-mode: multiply;
}

/* ===========================================
   Responsive Design
   =========================================== */
@media (max-width: 1024px) {
    :root {
        --section-padding: 80px;
    }

    .typeform-wrapper {
        padding: 1.5rem;
    }
}

@media (max-width: 768px) {
    .theme-toggle {
        top: 1rem;
        right: 1rem;
        padding: 0.5rem 1rem;
        gap: 0.5rem;
    }

    .theme-toggle-track {
        width: 40px;
        height: 22px;
    }

    .theme-toggle-thumb {
        width: 16px;
        height: 16px;
    }

    body:not(.light-mode) .theme-toggle-thumb {
        left: 21px;
    }

    .input-group {
        flex-direction: column;
        padding: 8px;
    }

    input {
        text-align: center;
    }

    button[type="submit"] {
        width: 100%;
        margin-top: 8px;
    }

    .typeform-wrapper {
        border-radius: 16px;
        padding: 1rem;
    }

    .typeform-container {
        min-height: 450px;
    }

    .ambient-orb-2,
    .ambient-orb-3 {
        display: none;
    }

    .video-container {
        border-radius: 16px;
    }

    .video-play-btn {
        width: 70px;
        height: 70px;
    }

    .video-play-btn svg {
        width: 24px;
        height: 24px;
    }
}

@media (max-width: 480px) {
    .theme-toggle {
        top: 0.75rem;
        right: 0.75rem;
        padding: 0.3rem 0.6rem;
        gap: 0.35rem;
    }

    .theme-toggle-track { width: 32px; height: 18px; }
    .theme-toggle-thumb { width: 13px; height: 13px; }
    body:not(.light-mode) .theme-toggle-thumb { left: 16px; }
    .theme-toggle-icon svg { width: 14px; height: 14px; }

    .section-container {
        padding: 0 1.5rem;
    }

    .feature-card {
        padding: 2rem;
    }
}

/* ===========================================
   Accessibility & Reduced Motion
   =========================================== */
@media (prefers-reduced-motion: reduce) {
    *, *::before, *::after {
        animation-duration: 0.01ms !important;
        animation-iteration-count: 1 !important;
        /* Gentler, not zero: positional transitions never run, but the ones
           that aid comprehension — opacity, colour — still do. */
        transition-property: opacity, color, background-color, border-color, box-shadow !important;
        transition-duration: 200ms !important;
    }

    .ambient-orb,
    .cursor-glow {
        display: none;
    }

    .reveal {
        opacity: 1;
        transform: none;
    }

}

a:focus-visible,
button:focus-visible,
input:focus-visible {
    outline: 2px solid var(--cyan-glow);
    outline-offset: 2px;
}

body.light-mode a:focus-visible,
body.light-mode button:focus-visible,
body.light-mode input:focus-visible {
    outline-color: var(--cyan-deep);
}

/* Top-left legal nav — second visible touchpoint for privacy/terms,
   required for Google OAuth verification. Mirrors the glass-pill aesthetic
   of the theme-toggle (top-right) so the two corners balance. */
.top-nav {
  position: fixed;
  top: 2rem;
  left: 2rem;
  z-index: 1001;
  display: flex;
  align-items: center;
  gap: 0.75rem;
  padding: 0.55rem 1.1rem;
  background: var(--glass-bg, rgba(255,255,255,0.04));
  backdrop-filter: blur(20px) saturate(180%);
  -webkit-backdrop-filter: blur(20px) saturate(180%);
  border: 1px solid var(--glass-border, rgba(255,255,255,0.1));
  border-radius: 100px;
  font-family: 'Inter', system-ui, sans-serif;
  font-size: 0.82rem;
  letter-spacing: 0.06em;
  box-shadow: var(--shadow-md, 0 8px 24px rgba(0,0,0,0.25));
  transition: border-color 250ms var(--ease-out);
}
.top-nav:hover {
  border-color: rgba(173, 251, 246, 0.3);
}
.top-nav a {
  color: var(--gray-300, #c8c8c8);
  text-decoration: none;
  transition: color 0.2s ease;
}
.top-nav a:hover {
  color: var(--cyan-glow, #ADFBF6);
}
.top-nav-sep {
  color: var(--gray-600, #666);
  user-select: none;
}
.top-nav .top-nav-beta {
  color: var(--cyan-glow, #ADFBF6);
  font-weight: 500;
  letter-spacing: 0.05em;
}
.top-nav .top-nav-beta:hover {
  color: var(--white, #fff);
}
@media (max-width: 640px) {
  /* Both fixed corners shrink on a phone: they float over everything that
     scrolls past, and at desktop size they were landing on top of the phone
     mockups in The Reality and the capabilities deck. */
  .top-nav {
    top: 0.75rem;
    left: 0.75rem;
    padding: 0.35rem 0.7rem;
    font-size: 0.6875rem;
    letter-spacing: 0.04em;
    gap: 0.4rem;
  }
}

/* Footer legal links — added for the integrated Vercel project.
   Visible privacy/terms references are required for Google OAuth verification. */
.footer-links {
  margin-top: 4px;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 14px;
  font-family: 'Inter', sans-serif;
  font-size: 0.95rem;
  letter-spacing: 0.04em;
  flex-wrap: wrap;
}
.footer-links a {
  color: var(--gray-300, #c8c8c8);
  text-decoration: none;
  border-bottom: 1px solid rgba(173, 251, 246, 0.18);
  padding-bottom: 1px;
  transition: color 0.2s ease, border-color 0.2s ease;
}
.footer-links a:hover {
  color: var(--cyan-glow, #ADFBF6);
  border-bottom-color: var(--cyan-glow, #ADFBF6);
}
.footer-sep {
  color: var(--gray-600, #666);
  user-select: none;
}

/* Social icon links (Instagram, Facebook) — no text underline, inherits the
   themed link color. The 14px flex gap keeps the pair reading as a group, so
   they deliberately have no "·" separator between them. */
.footer-links a.footer-social {
  display: inline-flex;
  align-items: center;
  border-bottom: none;
  padding-bottom: 0;
}
.footer-social svg {
  width: 20px;
  height: 20px;
  display: block;
}

/* "By applying you agree..." line just under the Typeform.
   Second touchpoint for privacy/terms — required by Google OAuth verification
   reviewers. */
.cta-legal-note {
  margin-top: 24px;
  font-family: 'Inter', sans-serif;
  font-size: 0.875rem;
  color: var(--gray-400, #a8a8a8);
  text-align: center;
  line-height: 1.6;
}
.cta-legal-note a {
  color: var(--cyan-glow, #ADFBF6);
  text-decoration: none;
  border-bottom: 1px solid rgba(173, 251, 246, 0.3);
  transition: border-color 0.2s ease;
}
.cta-legal-note a:hover {
  border-bottom-color: var(--cyan-glow, #ADFBF6);
}

/* ============================================================
   Legal pages (privacy, terms) — long-form prose
   ============================================================ */
.legal-page {
  max-width: 820px;
  margin: 0 auto;
  padding: 80px 24px 120px;
  font-family: 'Inter', system-ui, sans-serif;
  color: var(--gray-200, #e0e0e0);
  line-height: 1.7;
}
.legal-page header.legal-header {
  margin-bottom: 56px;
  text-align: center;
  padding-bottom: 28px;
  border-bottom: 1px solid rgba(255,255,255,0.08);
}
.legal-page header.legal-header .legal-eyebrow {
  display: inline-block;
  font-family: 'Inter', sans-serif;
  font-size: 12px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--cyan-glow, #ADFBF6);
  margin-bottom: 18px;
}
.legal-page header.legal-header .legal-eyebrow .lower {
  text-transform: lowercase;
}
.legal-page header.legal-header h1 {
  font-family: 'Cormorant Garamond', serif;
  font-weight: 400;
  font-size: clamp(2.2rem, 5vw, 3.4rem);
  letter-spacing: 0.01em;
  margin: 0 0 12px;
  color: var(--white, #fff);
}
.legal-page header.legal-header p.legal-meta {
  font-size: 13px;
  color: var(--gray-500, #888);
  letter-spacing: 0.02em;
}
.legal-page h2 {
  font-family: 'Cormorant Garamond', serif;
  font-weight: 500;
  font-size: clamp(1.5rem, 3vw, 1.9rem);
  letter-spacing: 0.01em;
  margin: 56px 0 16px;
  color: var(--white, #fff);
}
.legal-page h3 {
  font-family: 'Cormorant Garamond', serif;
  font-weight: 500;
  font-size: 1.2rem;
  letter-spacing: 0.01em;
  margin: 28px 0 10px;
  color: var(--cyan-pale, #E8F8F5);
}
.legal-page p, .legal-page li {
  font-size: 15px;
  margin-bottom: 14px;
  color: var(--gray-200, #d8d8d8);
}
.legal-page ul, .legal-page ol {
  margin: 0 0 18px 22px;
}
.legal-page a {
  color: var(--cyan-glow, #ADFBF6);
  text-decoration: none;
  border-bottom: 1px solid rgba(173, 251, 246, 0.3);
  transition: border-color 0.2s ease;
}
.legal-page a:hover {
  border-bottom-color: var(--cyan-glow, #ADFBF6);
}
.legal-page .legal-callout {
  margin: 28px 0;
  padding: 18px 22px;
  background: rgba(173, 251, 246, 0.06);
  border-left: 3px solid var(--cyan-glow, #ADFBF6);
  border-radius: 4px;
  font-size: 14.5px;
  line-height: 1.65;
}
.legal-page .legal-back {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin-top: 80px;
  padding-top: 32px;
  border-top: 1px solid rgba(255,255,255,0.08);
  font-size: 13px;
  letter-spacing: 0.04em;
  color: var(--gray-400, #a8a8a8);
  text-decoration: none;
  border-bottom: none;
}
.legal-page .legal-back:hover {
  color: var(--cyan-glow, #ADFBF6);
}

/* ===========================================
   Scroll-Driven Motion
   Replaces the one-shot IntersectionObserver reveals with motion bound to
   scroll position, so the page keeps responding instead of spending its
   animation once and freezing.

   Gated twice: the browser must support view timelines, and the visitor
   must not have asked for reduced motion. If either fails, main.js runs
   the original observer path and nothing below applies.
   =========================================== */
@supports (animation-timeline: view()) {
@media (prefers-reduced-motion: no-preference) {

    /* --- Reveals ------------------------------------------------------ */
    /* One keyframe set covers every direction: the implicit 0% frame is
       whatever transform the element already carries, so .step keeps
       coming from the left and the cards keep rising. */
    .reveal {
        transition: none;
        animation: sd-rise linear both;
        animation-timeline: view();
        animation-range: entry 15% cover 40%;
    }

    @keyframes sd-rise {
        to { opacity: 1; transform: translate3d(0, 0, 0); }
    }

    /* --- Hero recedes rather than dimming ----------------------------- */
    .hero-content {
        animation: sd-hero-exit linear both;
        animation-timeline: view();
        animation-range: exit 0% exit 70%;
    }

    @keyframes sd-hero-exit {
        to { opacity: 0; transform: translate3d(0, -48px, 0) scale(0.96); }
    }

    /* --- The film settles into place ---------------------------------- */
    .video-container.reveal {
        opacity: 0;
        transform: scale(0.94);
        animation-name: sd-video-settle;
        animation-range: entry 0% cover 45%;
    }

    @keyframes sd-video-settle {
        to { opacity: 1; transform: scale(1); }
    }

    /* Each number lights as you reach it, and stays lit — completed steps
       shouldn't dim again on the way past. */
    .step-number {
        animation: sd-ignite linear both;
        animation-timeline: view();
        animation-range: entry 20% cover 40%;
    }

    @keyframes sd-ignite {
        0%        { opacity: 0.3; }
        45%, 100% { opacity: 1; }
    }

    /* Three items meant to be read as a set: finish revealing while the step
       is still entering, so the last one is never left faded on screen. */
    .how-it-works .reveal { animation-range: entry 25% cover 30%; }

    /* The claim used to reveal in three pieces low in a short section of its
       own, which needed a later range or it finished before the eye arrived.
       It is one block at the top of a tall section now — the default entry
       range is where it belongs, and its three parts rise together. */


    /* --- Section title flourish draws --------------------------------- */
    .section-title::after {
        transform: scaleX(0);
        transform-origin: center;
        animation: sd-flourish linear both;
        animation-timeline: view();
        animation-range: entry 30% cover 55%;
    }

    @keyframes sd-flourish {
        to { transform: scaleX(1); }
    }
}
}

/* ===========================================
   Capabilities Gallery
   The three cards become a horizontal gallery instead of a static grid.
   Same glass, same serif headings, same cyan — only the composition and
   the interaction change.
   =========================================== */
.gallery { position: relative; }

/* A deck rather than a rail: the cards sit on top of each other and you send
   the front one away. Depth is carried by the two behind it, so the stack
   reads as a finite pile you're working through.

   Everything here is scoped to `.is-deck`, which gallery.js adds only when
   there is a deck to run — wide enough for the pile, and JS alive to deal it.
   Without that class the cards stay in flow as an ordinary column, which is
   what a browser with no JS should get instead of three cards on one pixel. */
/* No deck: a plain column, which is also the no-JS fallback. */
.gallery-stack {
    display: flex;
    flex-direction: column;
    gap: 1.25rem;
}

.gallery.is-deck .gallery-stack {
    display: block;
    position: relative;
    /* The stack is one fixed height and every card fills it, so the deck
       doesn't resize under your hand as it cycles. The value is the tallest
       card's content at this width. */
    height: 34rem;
    /* Room for the depth offsets and the shadows beneath. */
    padding-bottom: 2rem;
}

.gallery-stack:focus { outline: none; }

.gallery.is-deck .feature-card {
    position: absolute;
    /* The right edge is held back by the width of the fan, so the two cards
       behind can peek out there without the deck growing or overflowing its
       column. Without that peek the pile is invisible and nothing says there
       is anything to swipe. */
    inset: 0 2.25rem 0 0;
    display: flex;
    flex-direction: column;
    /* Opaque, deliberately. The glass tint is fine on a rail where cards sit
       side by side; in a pile you read straight through the front card to the
       two behind it and every line of text doubles. The section colour under
       the same tint keeps the look without the transparency. */
    background-color: var(--bg-primary);
    background-image: linear-gradient(var(--glass-bg), var(--glass-bg));
    backdrop-filter: none;
    -webkit-backdrop-filter: none;
    will-change: transform;
    touch-action: pan-y;   /* horizontal belongs to the deck, vertical to the page */
}

/* Depth. Each step back is smaller, dimmer and slightly out of focus — the
   same recipe the scrollytelling scenes use for the cards you've passed. */
.gallery.is-deck .feature-card[data-depth="0"] {
    transform: translate3d(0, 0, 0) scale(1);
    opacity: 1;
    z-index: 3;
    cursor: grab;
}

/* Fanned to the right and tilted a degree or two, the way a dealt hand sits.
   Depth alone (straight down) hides them exactly behind the front card. */
.gallery.is-deck .feature-card[data-depth="1"] {
    transform: translate3d(1.15rem, 0.6rem, 0) scale(0.975) rotate(1.1deg);
    opacity: 0.75;
    filter: blur(0.3px);
    z-index: 2;
    pointer-events: none;
}

.gallery.is-deck .feature-card[data-depth="2"] {
    transform: translate3d(2.25rem, 1.2rem, 0) scale(0.95) rotate(2.2deg);
    opacity: 0.45;
    filter: blur(0.8px);
    z-index: 1;
    pointer-events: none;
}

/* The one-time nudge that shows the top card is loose, and the card on its way
   out, are both written frame by frame — a transition would fight them. */
.gallery .feature-card.is-nudging,
.gallery .feature-card.is-gone { transition: none; }

/* --- the controls ---------------------------------------------------------
   A flick is the quick way through the deck and an invisible one: nothing on
   a fanned pile says it can be thrown, and a mouse never tries. So the two
   moves the gesture makes are also two buttons, with the dots carrying the
   one thing the fan can't say — which card of how many you are on. */
.deck-nav {
    display: none;
    align-items: center;
    justify-content: center;
    gap: 0.75rem;
    margin-top: 1.5rem;
}

.gallery.is-deck .deck-nav { display: flex; }

.deck-arrow {
    display: grid;
    place-items: center;
    width: 36px;
    height: 36px;
    border-radius: 50%;
    border: 1px solid var(--glass-border);
    background: var(--glass-bg);
    color: var(--text-secondary);
    cursor: pointer;
    transition: transform 160ms var(--ease-out),
                background-color 220ms var(--ease-out),
                border-color 220ms var(--ease-out),
                color 220ms var(--ease-out);
}

.deck-arrow svg { width: 17px; height: 17px; }

.deck-arrow:hover {
    color: var(--cyan-glow);
    border-color: rgba(173, 251, 246, 0.35);
    background: rgba(173, 251, 246, 0.08);
}

/* Feedback on the press, not on the release. */
.deck-arrow:active { transform: scale(0.92); }

.deck-arrow:focus-visible {
    outline: 2px solid var(--cyan-glow);
    outline-offset: 3px;
}

.deck-dots {
    display: flex;
    align-items: center;
    gap: 0.5rem;
}

.deck-dot {
    width: 7px;
    height: 7px;
    padding: 0;
    border: none;
    border-radius: 50%;
    background: var(--glass-border);
    cursor: pointer;
    transition: transform 260ms var(--ease-out), background-color 260ms var(--ease-out);
}

/* The current card's dot is the only one that carries the accent, and it grows
   rather than just brightening — a 7px dot has no room to change value alone. */
.deck-dot.is-on {
    background: var(--cyan-glow);
    transform: scale(1.4);
}

.deck-dot:focus-visible {
    outline: 2px solid var(--cyan-glow);
    outline-offset: 4px;
}

body.light-mode .deck-dot { background: rgba(13, 115, 119, 0.2); }
body.light-mode .deck-dot.is-on { background: var(--cyan-deep); }
body.light-mode .deck-arrow:hover {
    color: var(--cyan-deep);
    border-color: rgba(13, 115, 119, 0.25);
    background: rgba(13, 115, 119, 0.07);
}

/* --- the gesture affordance ------------------------------------------------ */
.deck-hint {
    display: none;
    align-items: center;
    justify-content: center;
    gap: 0.45rem;
    margin-top: 0.75rem;
    font-size: 0.75rem;
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: var(--text-muted);
    transition: opacity 500ms var(--ease-out);
}

.gallery.is-deck .deck-hint { display: flex; }

.deck-hint svg {
    width: 15px;
    height: 15px;
    animation: deck-hint-nudge 2.4s var(--ease-in-out) infinite;
}

/* Once you've flicked one, or pressed an arrow, you know. */
.deck-hint.is-used { opacity: 0; pointer-events: none; }

@keyframes deck-hint-nudge {
    0%, 62%, 100% { transform: translateX(0); opacity: 0.75; }
    76%           { transform: translateX(-4px); opacity: 1; }
}

@media (prefers-reduced-motion: reduce) {
    .deck-hint svg { animation: none; }
}

/* Mid-gesture the card must not fight the pointer with a transition. */
.gallery .feature-card.is-grabbing {
    transition: none;
    cursor: grabbing;
    user-select: none;
    z-index: 4;
}

/* A card you can grab shouldn't also lift away from the pointer. Only the
   front card can be hovered — the ones behind it are pointer-events: none —
   so this is the resting transform of depth 0, not `none`. */
.gallery.is-deck .feature-card:hover { transform: translate3d(0, 0, 0) scale(1); }

/* Example prompts are things you'd send an assistant — so they look like it. */
.gallery .feature-list {
    margin-top: auto;
    padding-top: 1.5rem;
    display: flex;
    flex-direction: column;
    align-items: flex-end;
    gap: 0.5rem;
}

.gallery .feature-list li {
    max-width: 92%;
    padding: 0.625rem 0.9375rem;
    border-radius: 18px 18px 5px 18px;
    background: rgba(173, 251, 246, 0.1);
    border: 1px solid var(--glass-border);
    color: var(--text-secondary);
    text-align: left;
    position: static;
}

.gallery .feature-list li::before { display: none; }

body.light-mode .gallery .feature-list li {
    background: rgba(13, 115, 119, 0.07);
    border-color: rgba(13, 115, 119, 0.14);
}

/* ===========================================
   How It Works — a left-aligned list, not a centred statement

   The one section on the page that reads as instructions rather than as a
   claim, so it sets flush left as a numbered list you scan, with the numbers
   doing the sequencing that the old horizontal stagger used to. The title
   stays in the page serif — the layout is the exception here, the type is not.
   =========================================== */
.how-it-works .section-header {
    text-align: left;
    margin-bottom: clamp(2.5rem, 5vw, 4rem);
}

.how-it-works .section-eyebrow { margin-bottom: 0.875rem; }

.how-it-works .section-title {
    font-size: clamp(2.25rem, 5.2vw, 3.5rem);
    line-height: 1.1;
    text-wrap: balance;
}

/* The flourish centres itself under a centred title; there is nothing for it
   to sit under here, and the eyebrow already marks the section. */
.how-it-works .section-title::after { display: none; }

.steps { gap: 0; }

.step {
    position: relative;
    display: grid;
    grid-template-columns: 2.75rem 1fr;
    gap: clamp(1.25rem, 3vw, 2rem);
    padding: 0 0 clamp(2.25rem, 4vw, 3.25rem);
    background: none;
    border: 0;
    border-radius: 0;
    box-shadow: none;
}

body.light-mode .step {
    background: none;
    border: 0;
    box-shadow: none;
}

.step:last-child { padding-bottom: 0; }
.step:hover { transform: none; border-color: transparent; }

/* Optically align the heading with the centre of the number. */
.step-content h3 { padding-top: 0.4375rem; }

/* Flush left under the title rather than centred in the container — the list
   and the heading share one edge. */
.steps { max-width: 46rem; margin: 0; }

@media (max-width: 768px) {
    /* The marker is small enough to keep its column on a phone. */
    .step { gap: 1rem; }
}

/* ===========================================
   FAQ — three questions, then the full page
   A disclosure list rather than a card grid: an answer should open where
   the question sits, not somewhere else on the page.
   =========================================== */
/* The hero's ground, like everything else. This was the last section on
   --bg-secondary: invisible against --bg-primary in the dark (#0a0a0f against
   #0A0A0A), but pure white against off-white in light mode, which made the
   final panel of the page a visibly different sheet of paper. */
.faq {
    padding: var(--section-padding) 0;
    background: var(--bg-primary);
    position: relative;
    z-index: 1;
}

.section-eyebrow {
    font-size: 0.75rem;
    font-weight: 500;
    letter-spacing: 0.18em;
    text-transform: uppercase;
    color: var(--text-muted);
    margin-bottom: 1rem;
}

.faq-list {
    max-width: 44rem;
    margin: 0 auto;
    border-top: 1px solid var(--glass-border);
}

.faq-item { border-bottom: 1px solid var(--glass-border); }

body.light-mode .faq-list,
body.light-mode .faq-item { border-color: rgba(13, 115, 119, 0.14); }

.faq-heading { margin: 0; font-weight: inherit; }

.faq-trigger {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 1.5rem;
    width: 100%;
    padding: 1.5rem 0;
    background: none;
    border: 0;
    cursor: pointer;
    text-align: left;
    font-family: var(--font-sans);
    font-size: 1.0625rem;
    font-weight: 400;
    line-height: 1.45;
    color: var(--text-primary);
    transition: color 240ms var(--ease-out);
}

.faq-item.is-open .faq-trigger { color: var(--accent); }

@media (hover: hover) and (pointer: fine) {
    .faq-trigger:hover { color: var(--accent); }
}

/* The plus is drawn, not typed, so one stroke can rotate away into a minus. */
.faq-icon {
    position: relative;
    flex: 0 0 auto;
    width: 16px;
    height: 16px;
    color: var(--text-muted);
}

.faq-icon::before,
.faq-icon::after {
    content: '';
    position: absolute;
    top: 50%;
    left: 50%;
    width: 16px;
    height: 1.5px;
    border-radius: 2px;
    background: currentColor;
    transform: translate(-50%, -50%);
    transition: transform 420ms var(--ease-drawer), opacity 260ms var(--ease-out);
}

.faq-icon::after { transform: translate(-50%, -50%) rotate(90deg); }

.faq-item.is-open .faq-icon { color: var(--accent); }
/* The vertical stroke turns into the horizontal one rather than vanishing. */
.faq-item.is-open .faq-icon::after { transform: translate(-50%, -50%) rotate(0deg); }

/* 0fr -> 1fr animates to the content's own height without measuring it in JS,
   and stays interruptible: click again mid-open and it reverses from where
   it is instead of snapping. */
.faq-panel {
    display: grid;
    grid-template-rows: 0fr;
    transition: grid-template-rows 460ms var(--ease-drawer);
}

.faq-item.is-open .faq-panel { grid-template-rows: 1fr; }

.faq-panel-inner {
    overflow: hidden;
    opacity: 0;
    transition: opacity 260ms var(--ease-out);
}

.faq-item.is-open .faq-panel-inner {
    opacity: 1;
    /* Text arrives after the room has been made for it. */
    transition-delay: 120ms;
}

.faq-panel-inner p {
    padding: 0 3rem 1.75rem 0;
    color: var(--text-secondary);
    font-size: 1rem;
    line-height: 1.7;
}

.faq-more {
    max-width: 44rem;
    margin: 2.5rem auto 0;
    text-align: center;
}

.faq-more-link {
    display: inline-flex;
    align-items: center;
    gap: 0.5rem;
    padding: 0.75rem 1.5rem;
    border-radius: 999px;
    border: 1px solid var(--glass-border);
    background: var(--glass-bg);
    backdrop-filter: blur(20px) saturate(180%);
    -webkit-backdrop-filter: blur(20px) saturate(180%);
    color: var(--text-primary);
    font-size: 0.9375rem;
    text-decoration: none;
    transition: transform 200ms var(--ease-out), color 200ms ease,
                border-color 200ms ease, background-color 200ms ease;
}

.faq-more-link svg {
    width: 16px;
    height: 16px;
    transition: transform 320ms var(--ease-out);
}

.faq-more-link:active { transform: scale(0.97); }

body.light-mode .faq-more-link {
    background: rgba(255, 255, 255, 0.6);
    border-color: rgba(13, 115, 119, 0.18);
    box-shadow: var(--shadow-sm);
}

@media (hover: hover) and (pointer: fine) {
    .faq-more-link:hover {
        color: var(--accent);
        border-color: rgba(173, 251, 246, 0.35);
    }
    /* The arrow leads by a few pixels — the link already points somewhere. */
    .faq-more-link:hover svg { transform: translateX(3px); }
}

@media (max-width: 768px) {
    .faq-trigger { font-size: 1rem; gap: 1rem; }
    .faq-panel-inner p { padding-right: 1.5rem; }
}

body.light-mode .gallery .feature-card {
    background-color: var(--gray-50);
    background-image: linear-gradient(rgba(255, 255, 255, 0.7), rgba(255, 255, 255, 0.7));
    border-color: rgba(0, 0, 0, 0.07);
}

/* ===========================================
   Fixed corners that get out of the way

   The nav pill and the theme toggle float above everything, which means they
   cross whatever is scrolling underneath — the phone mockups worst of all.
   Scrolling down tucks them away; scrolling up brings them straight back, so
   they cost nothing while reading and are never more than a flick away.
   Placed last so the tucked transform wins over the toggle's hover lift.
   =========================================== */
.top-nav,
.theme-toggle {
    transition: transform 320ms var(--ease-out),
                opacity 220ms var(--ease-out),
                border-color 250ms var(--ease-out),
                box-shadow 300ms var(--ease-out);
    will-change: transform;
}

.top-nav.is-tucked,
.theme-toggle.is-tucked {
    /* Past its own height plus the gap above it, so nothing peeks. */
    transform: translateY(calc(-100% - 1.5rem));
    opacity: 0;
    /* Invisible chrome must not be clickable. */
    pointer-events: none;
}

@media (prefers-reduced-motion: reduce) {
    /* The global rule already drops the transform transition; without a slide
       a fade is the whole gesture, so give it a beat to read as one. */
    .top-nav,
    .theme-toggle { transition-duration: 200ms; }
}
