/*
 * Forever Charlotte — public landing page.
 *
 * A quiet single hero held in the same dusk as the memorial (DESIGN.md): a drenched OKLCH night,
 * warm off-white ink, Spectral serif. One portrait of Charlotte glowing in the dark like the
 * offerings in her garden, her name and years, a line of remembrance, and one way through to the
 * obituary. Restraint with intent: every neutral is tinted warm, nothing is pure black or white,
 * and all motion is gated behind prefers-reduced-motion so the no-JS / reduced-motion state is
 * fully visible.
 */

@font-face {
  font-family: "Spectral";
  font-style: normal;
  font-weight: 300;
  font-display: swap;
  src: url("/fonts/spectral-300.woff2") format("woff2");
}
@font-face {
  font-family: "Spectral";
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url("/fonts/spectral-400.woff2") format("woff2");
}
@font-face {
  font-family: "Spectral";
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url("/fonts/spectral-500.woff2") format("woff2");
}
@font-face {
  font-family: "Spectral";
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url("/fonts/spectral-400-italic.woff2") format("woff2");
}

:root {
  /* Night sky and ground — the drenched surface (matches the memorial scene). */
  --sky-top: oklch(0.21 0.05 277);
  --sky-mid: oklch(0.26 0.045 268);
  --sky-horizon: oklch(0.34 0.045 250);

  /* Warm light: the candlelight Charlotte's portrait gives off in the dark. */
  --glow-warm: oklch(0.86 0.13 78);
  --glow-amber: oklch(0.82 0.12 70);

  /* Warm off-white ink, tinted toward candlelight — never pure white. */
  --ink: oklch(0.95 0.016 85);
  --ink-soft: oklch(0.88 0.02 84);
  --ink-mute: oklch(0.76 0.025 80);
  --edge: oklch(0.42 0.03 80 / 0.3);

  --display: "Spectral", "Iowan Old Style", "Palatino Linotype", Palatino, Georgia, serif;
  --ease: cubic-bezier(0.16, 1, 0.3, 1);
}

* {
  box-sizing: border-box;
}

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

body.page {
  margin: 0;
  min-height: 100svh;
  font-family: var(--display);
  font-size: clamp(1.0625rem, 0.95rem + 0.5vw, 1.1875rem);
  line-height: 1.7;
  color: var(--ink-soft);
  background:
    radial-gradient(155% 80% at 50% -10%, oklch(0.255 0.042 270) 0%, transparent 60%),
    linear-gradient(to bottom, var(--sky-top) 0%, var(--sky-mid) 50%, var(--sky-horizon) 100%);
  text-rendering: optimizeLegibility;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

/* Warm horizon glow rising from the foot of the page — the last light of dusk. */
body.page::before {
  content: "";
  position: fixed;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  background: radial-gradient(80% 42% at 50% 116%, oklch(0.7 0.11 72 / 0.22), transparent 70%);
}

/* Film grain + vignette: kill the flat-gradient feel, give the night some air. */
body.page::after {
  content: "";
  position: fixed;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  opacity: 0.06;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
}

.hero {
  position: relative;
  z-index: 1;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: clamp(1rem, 0.7rem + 1.4vw, 1.6rem);
  padding: clamp(2.5rem, 8vh, 5rem) 1.35rem clamp(2rem, 6vh, 4rem);
  text-align: center;
}

.hero__kicker {
  margin: 0;
  text-transform: uppercase;
  letter-spacing: 0.34em;
  font-size: 0.74rem;
  font-weight: 500;
  color: var(--glow-amber);
}

/* The portrait, lit from behind by a warm bloom and melting into the night at its lower edge. */
.hero__portrait {
  position: relative;
  margin: 0.25rem 0 0.5rem;
  width: min(80vw, 332px);
}

.hero__portrait::before {
  content: "";
  position: absolute;
  inset: -26% -22% -14%;
  z-index: -1;
  background: radial-gradient(60% 54% at 50% 41%, oklch(0.82 0.12 72 / 0.5), transparent 74%);
  filter: blur(8px);
}

.hero__img {
  width: 100%;
  height: auto;
  display: block;
  /* Warm, settled grade so the daylight photo belongs to the dusk; a little extra contrast keeps
     her features crisp against the fade. */
  filter: brightness(0.98) contrast(1.06) saturate(0.95) sepia(0.05);
  /*
   * Dissolve into the night as an even soft vignette (sides included, not just top/bottom), so she
   * emerges from the dusk rather than sitting in a framed rectangle. The opaque core holds her face
   * and figure; everything outward, sky, water, deck, and hair, fades to transparent and the warm
   * bloom glows through. No frame, no shadow (a shadow can't follow a mask).
   */
  -webkit-mask-image: radial-gradient(66% 72% at 52% 43%, #000 42%, transparent 100%);
  mask-image: radial-gradient(66% 72% at 52% 43%, #000 42%, transparent 100%);
}

.hero__name {
  margin: 0;
  font-weight: 300;
  font-size: clamp(2.5rem, 1.5rem + 4.4vw, 4.25rem);
  line-height: 1.04;
  letter-spacing: 0.005em;
  color: var(--ink);
  text-wrap: balance;
}

.hero__dates {
  margin: 0;
  font-style: italic;
  font-size: clamp(1.05rem, 0.98rem + 0.4vw, 1.25rem);
  letter-spacing: 0.06em;
  color: var(--glow-amber);
}

.hero__remembrance {
  margin: 0.25rem 0 0;
  max-width: 36ch;
  font-size: clamp(1.0625rem, 0.98rem + 0.5vw, 1.25rem);
  line-height: 1.62;
  color: var(--ink-mute);
  text-wrap: balance;
}

.hero__cta-wrap {
  margin: clamp(0.75rem, 0.4rem + 1vw, 1.5rem) 0 0;
}

.hero__cta {
  display: inline-flex;
  align-items: center;
  gap: 0.55em;
  min-height: 44px;
  padding: 0.78rem 1.6rem;
  font-size: 1.0625rem;
  font-weight: 500;
  letter-spacing: 0.01em;
  color: oklch(0.2 0.03 268);
  background: linear-gradient(to bottom, var(--glow-warm), var(--glow-amber));
  border-radius: 999px;
  text-decoration: none;
  box-shadow:
    0 14px 34px -14px oklch(0.82 0.12 72 / 0.55),
    0 0 0 1px oklch(0.88 0.08 78 / 0.6);
  transition:
    transform 0.5s var(--ease),
    box-shadow 0.5s var(--ease),
    filter 0.5s var(--ease);
}

.hero__cta::after {
  content: "→";
  font-size: 0.95em;
  transition: transform 0.5s var(--ease);
}

.hero__cta:hover {
  filter: brightness(1.04);
  transform: translateY(-2px);
  box-shadow:
    0 20px 44px -16px oklch(0.82 0.12 72 / 0.6),
    0 0 0 1px oklch(0.88 0.08 78 / 0.7);
}

.hero__cta:hover::after {
  transform: translateX(3px);
}

.hero__cta:active {
  transform: translateY(0);
  filter: brightness(0.98);
}

.hero__cta:focus-visible {
  outline: 2px solid var(--ink);
  outline-offset: 4px;
}

/* The memorial: a quieter second way through, beneath the obituary CTA. */
.hero__memorial-wrap {
  margin: clamp(0.5rem, 0.3rem + 0.6vw, 0.9rem) 0 0;
}

.hero__memorial {
  display: inline-flex;
  align-items: center;
  gap: 0.45em;
  min-height: 44px;
  padding: 0.4rem 0.6rem;
  font-style: italic;
  font-size: 1.0625rem;
  color: var(--ink-mute);
  text-decoration: none;
  border-bottom: 1px solid var(--edge);
  transition:
    color 0.5s var(--ease),
    border-color 0.5s var(--ease);
}

.hero__memorial::after {
  content: "→";
  font-style: normal;
  font-size: 0.9em;
  transition: transform 0.5s var(--ease);
}

.hero__memorial:hover {
  color: var(--ink);
  border-color: var(--glow-amber);
}

.hero__memorial:hover::after {
  transform: translateX(3px);
}

.hero__memorial:focus-visible {
  outline: 2px solid var(--ink);
  outline-offset: 4px;
}

/* Entrance: the page kindles gently, one line at a time. CSS-only, fully gated. */
@media (prefers-reduced-motion: no-preference) {
  .hero > * {
    animation: rise 1.1s var(--ease) both;
  }
  .hero__kicker {
    animation-delay: 0.05s;
  }
  .hero__portrait {
    animation-delay: 0.18s;
    animation-duration: 1.4s;
  }
  .hero__name {
    animation-delay: 0.42s;
  }
  .hero__dates {
    animation-delay: 0.56s;
  }
  .hero__remembrance {
    animation-delay: 0.68s;
  }
  .hero__cta-wrap {
    animation-delay: 0.84s;
  }
  .hero__memorial-wrap {
    animation-delay: 0.96s;
  }

  /*
   * Once the page has kindled, the warm bloom behind her portrait breathes — the same idle
   * candlelight that keeps the memorial's offerings alive (DESIGN.md). Near-imperceptible and very
   * slow: it should register as the light being alive, never as an animation. Starts and ends at
   * the resting glow so it eases in from the entrance with no jump. opacity + transform only.
   */
  .hero__portrait::before {
    animation: breath 8s ease-in-out 1.8s infinite;
    /* opacity-only: a blurred layer must never animate transform (re-rasterizes the blur per frame). */
    will-change: opacity;
  }

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

  @keyframes breath {
    0%,
    100% {
      opacity: 1;
    }
    50% {
      opacity: 0.58;
    }
  }
}

/* Reduced motion: no entrance, no breath (gated above), and no CTA transition either. */
@media (prefers-reduced-motion: reduce) {
  .hero__cta {
    transition: none;
  }
}

/*
 * Print: a memorial is something people keep. On paper, drop the dusk and the glow, render her
 * clearly on white, and spell out the obituary link so a printed copy is still useful.
 */
@media print {
  body.page {
    background: #fff;
    color: #1f1b16;
  }
  body.page::before,
  body.page::after {
    display: none;
  }
  .hero {
    min-height: auto;
    padding: 1.5rem;
  }
  .hero__portrait::before {
    display: none;
  }
  .hero__img {
    filter: none;
    -webkit-mask-image: none;
    mask-image: none;
  }
  .hero__kicker,
  .hero__dates {
    color: #7a571a;
  }
  .hero__remembrance {
    color: #3a342c;
  }
  .hero__cta {
    padding: 0;
    color: #1f1b16;
    background: none;
    box-shadow: none;
  }
  .hero__cta::after {
    content: " (" attr(href) ")";
    font-size: 0.85em;
  }
  .hero__memorial {
    color: #1f1b16;
    border: 0;
    padding: 0;
  }
  .hero__memorial::after {
    content: " (" attr(href) ")";
    font-size: 0.85em;
  }
}
