/* =====================================================================
   ZV CONSULTING — base.css
   Design tokens · reset · typography · buttons · shared utilities
   ===================================================================== */

:root {
  /* ---- Warm dark luxury palette ---- */
  --noir:        #0A0806;   /* warm near-black base            */
  --noir-2:      #0E0B08;   /* slightly raised background      */
  --espresso:    #17110B;   /* elevated surfaces / panels      */
  --espresso-2:  #211812;   /* card surface                    */
  --line:        rgba(233, 205, 155, 0.12);  /* hairline gold  */
  --line-strong: rgba(233, 205, 155, 0.22);

  --gold:        #D9A94E;   /* antique gold — primary accent   */
  --gold-deep:   #B8863B;   /* deep gold                       */
  --gold-lit:    #F5D486;   /* champagne highlight / lit metal */
  --amber:       #C67A2E;   /* warm ambient orb light          */
  --ember:       #8A4B1E;   /* darkest ambient                 */

  --cream:       #F4ECDC;   /* warm off-white text             */
  --cream-soft:  rgba(244, 236, 220, 0.72);
  --cream-mute:  rgba(244, 236, 220, 0.50);
  --cream-faint: rgba(244, 236, 220, 0.32);

  /* ---- Type ---- */
  --font-display: "Fraunces", "Times New Roman", serif;
  --font-body:    "Hanken Grotesk", system-ui, -apple-system, "Segoe UI", sans-serif;

  /* ---- Fluid scale (clamp: min / vw / max) ---- */
  --step--1: clamp(0.80rem, 0.76rem + 0.20vw, 0.92rem);
  --step-0:  clamp(1.00rem, 0.94rem + 0.28vw, 1.18rem);
  --step-1:  clamp(1.25rem, 1.14rem + 0.55vw, 1.60rem);
  --step-2:  clamp(1.60rem, 1.35rem + 1.20vw, 2.40rem);
  --step-3:  clamp(2.10rem, 1.60rem + 2.40vw, 3.60rem);
  --step-4:  clamp(2.80rem, 1.90rem + 4.40vw, 5.60rem);
  --step-5:  clamp(3.40rem, 2.00rem + 7.00vw, 8.00rem);

  /* ---- Rhythm ---- */
  --pad-x: clamp(1.25rem, 5vw, 6rem);
  --maxw:  1240px;
  --radius: 22px;
  --radius-lg: 30px;

  /* ---- Motion ---- */
  --ease-out: cubic-bezier(0.16, 1, 0.3, 1);
  --ease-io:  cubic-bezier(0.65, 0, 0.35, 1);

  /* Live scroll-progress vars, written by JS (0 → 1) */
  --ignite: 0;       /* monogram ignition amount */
  --nav-solid: 0;
  color-scheme: dark;
}

/* ---------------------------------------------------------------- reset */
*, *::before, *::after { box-sizing: border-box; }
* { margin: 0; }

html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) { html { scroll-behavior: auto; } }

body {
  background: var(--noir);
  color: var(--cream);
  font-family: var(--font-body);
  font-size: var(--step-0);
  font-weight: 400;
  line-height: 1.6;
  letter-spacing: 0.005em;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  overflow-x: hidden;
}

/* Lock scroll when mobile menu is open */
body.is-locked { overflow: hidden; }

img, svg, video { display: block; max-width: 100%; }
a { color: inherit; text-decoration: none; }
button { font: inherit; color: inherit; background: none; border: none; cursor: pointer; }
input, textarea { font: inherit; color: inherit; }
ul, ol { list-style: none; padding: 0; }

::selection { background: var(--gold); color: var(--noir); }

:focus-visible {
  outline: 2px solid var(--gold-lit);
  outline-offset: 3px;
  border-radius: 4px;
}

/* --------------------------------------------------------- typography */
h1, h2, h3 {
  font-family: var(--font-display);
  font-weight: 400;
  line-height: 1.02;
  letter-spacing: -0.02em;
  font-optical-sizing: auto;
}

.text-gold { color: var(--gold); }

.section-eyebrow {
  font-family: var(--font-body);
  font-size: var(--step--1);
  font-weight: 600;
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--cream-mute);
  display: inline-flex;
  align-items: center;
  gap: 0.7em;
}
.section-eyebrow::before {
  content: "";
  width: 26px;
  height: 1px;
  background: linear-gradient(90deg, var(--gold), transparent);
}
.section-eyebrow--gold { color: var(--gold); }
.section-eyebrow--gold::before { background: linear-gradient(90deg, var(--gold-lit), transparent); }

/* ------------------------------------------------------------ buttons */
.btn {
  --btn-py: 0.85em;
  display: inline-flex;
  align-items: center;
  gap: 0.6em;
  padding: var(--btn-py) 1.7em;
  border-radius: 100px;
  font-family: var(--font-body);
  font-size: var(--step-0);
  font-weight: 600;
  letter-spacing: 0.01em;
  line-height: 1;
  transition: transform 0.5s var(--ease-out), box-shadow 0.5s var(--ease-out),
              background 0.4s var(--ease-out), color 0.4s var(--ease-out);
  will-change: transform;
}
.btn__arrow { transition: transform 0.5s var(--ease-out); }
.btn:hover .btn__arrow { transform: translateX(4px); }

.btn--gold {
  background: linear-gradient(135deg, var(--gold-lit), var(--gold) 55%, var(--gold-deep));
  color: #241706;
  box-shadow: 0 10px 30px -12px rgba(217, 169, 78, 0.65),
              inset 0 1px 0 rgba(255, 255, 255, 0.4);
}
.btn--gold:hover {
  transform: translateY(-2px);
  box-shadow: 0 18px 44px -14px rgba(217, 169, 78, 0.8),
              inset 0 1px 0 rgba(255, 255, 255, 0.5);
}
.btn--ghost {
  color: var(--cream);
  border: 1px solid var(--line-strong);
  background: rgba(244, 236, 220, 0.02);
  backdrop-filter: blur(4px);
}
.btn--ghost:hover { border-color: var(--gold); color: var(--gold-lit); transform: translateY(-2px); }
.btn--block { width: 100%; justify-content: center; }

/* -------------------------------------------------------- utilities */
.sr-only {
  position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
  overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* Generic scroll-reveal — JS toggles .is-in. --rd staggers siblings. */
[data-reveal] {
  opacity: 0;
  transform: translateY(34px);
  transition: opacity 1s var(--ease-out), transform 1s var(--ease-out);
  transition-delay: var(--rd, 0s);
  will-change: opacity, transform;
}
[data-reveal].is-in { opacity: 1; transform: none; }
@media (prefers-reduced-motion: reduce) {
  [data-reveal] { opacity: 1; transform: none; transition: none; }
}

.section-shell {
  max-width: var(--maxw);
  margin-inline: auto;
  padding-inline: var(--pad-x);
}

/* ----------------------------------------------- preloader + first-paint reveal */
/* Shown from first paint (plain HTML+CSS) so the hero never flashes unstyled or
   mid-load. preloader.js adds .is-done to fade it out + .is-loaded to <html>. */
.preloader {
  position: fixed; inset: 0; z-index: 9999;
  display: grid; place-items: center;
  background: var(--noir);
  transition: opacity 0.8s var(--ease-out), visibility 0.8s var(--ease-out);
  /* failsafe: reveal the page even if JS never runs (broken bundle / no JS) */
  animation: preloader-failsafe 0.7s var(--ease-out) 8s forwards;
}
.preloader.is-done { opacity: 0; visibility: hidden; pointer-events: none; }
.preloader__logo {
  grid-area: 1 / 1; place-self: center;   /* share the centre cell with the ring */
  width: 78px; height: 78px; display: block;
  -webkit-mask: url("../ZV_logo.png") center / contain no-repeat;
          mask: url("../ZV_logo.png") center / contain no-repeat;
  /* gold fill with a bright band that sweeps across = "loading" shine */
  background: linear-gradient(100deg,
    var(--gold-deep) 0%, var(--gold-deep) 34%,
    var(--gold-lit) 50%, var(--gold) 60%, var(--gold-deep) 76%, var(--gold-deep) 100%);
  background-size: 260% 100%;
  animation: preloader-sheen 1.25s ease-in-out infinite;
}
/* spinning ring around the logo = clear "loading" cue */
.preloader::after {
  content: ""; grid-area: 1 / 1; place-self: center;
  width: 128px; height: 128px; border-radius: 50%;
  border: 2px solid rgba(217, 169, 78, 0.15);
  border-top-color: var(--gold);
  animation: preloader-spin 0.85s linear infinite;
}
@keyframes preloader-spin { to { transform: rotate(360deg); } }
@keyframes preloader-sheen { 0% { background-position: 135% 0; } 100% { background-position: -55% 0; } }
@keyframes preloader-failsafe { to { opacity: 0; visibility: hidden; pointer-events: none; } }

/* Hero fades + blurs in when the page is ready. act.js only drives the hero's
   transform, so animating opacity/filter here won't fight it. Base state is
   VISIBLE, so a JS hiccup can never leave the hero blank. */
.act__hero { transition: opacity 1.1s var(--ease-out), filter 1.1s var(--ease-out); }
html:not(.is-loaded) .act__hero {
  opacity: 0; filter: blur(16px);
  animation: hero-reveal-failsafe 1s var(--ease-out) 8s forwards;   /* reveal even if JS dies */
}
@keyframes hero-reveal-failsafe { to { opacity: 1; filter: none; } }

@media (prefers-reduced-motion: reduce) {
  .preloader, .preloader__logo, .preloader::after { animation: none; }
  .act__hero { transition: none; }
  html:not(.is-loaded) .act__hero { opacity: 1; filter: none; animation: none; }
}
