/* Hallmark · pre-emit critique: P5 H5 E4 S5 R4 V5 · contrast: pass (40–41) · slop: pass (42–45) · honest: pass (46) · chrome: pass (47) · tokens: pass (48) · responsive: pass (49) · icons: pass (30) · mobile: pass (34, 50–57)
 * Hallmark · macrostructure: Horizon "La Mesa Larga" (index) · Split Studio (comunidad) · Letter (donaciones)
 *   — three distinct page shapes; no two pages share a fingerprint.
 * Horizon: the page IS a table. Verse leads in both languages at equal weight; a
 *   solid card carries the name + single CTA and straddles the leading edge of a
 *   full-bleed band. Type never touches the artwork — contrast comes from spatial
 *   separation, not overlay.
 *   Derived from the church's own emblem: their logo is a long banquet table seen in
 *   one-point perspective. They drew themselves as a table, then sat down at one.
 *   Macrostructure selected from 6 concepts x 3 adversarial judges (avg 4.7, floor 4).
 * Hero artwork: "La Mesa Larga" — an ORIGINAL inline-SVG panorama, not a photograph.
 *   One 1200-unit tile drawn twice, drifting exactly one tile width, so the loop
 *   point is pixel-identical and the table has no end. ~13KB, zero image requests.
 *   Every motif is traceable to something the congregation owns: the banquet table
 *   of their seal, the flame and dove of their logo, and the communion still-life
 *   (bread, grapes, wheat, clay vessel) from their own anniversary photograph.
 *   Explicitly refused: sombreros, papel picado, calaveras, serape stripes, cactus —
 *   Mexican folk motifs, wrong sea entirely for a Caribbean congregation.
 * Motion mechanics ported from three.js (mrdoob/three.js) WITHOUT bundling it:
 *   - depth planes at 1/z speeds (PerspectiveCamera relationship) => real parallax
 *   - MathUtils.smootherstep sampled into a native CSS linear() easing
 *   - MathUtils.damp(x,y,lambda,dt) for frame-rate-independent pointer parallax
 *   A WebGL runtime would cost ~600KB and hand the hero to a canvas no screen
 *   reader can see; the maths was the part worth having.
 * Hallmark · tone: warm/celebratory (playful-Hum, brand-tuned) · anchor hue: flame orange (~45)
 * H6 hero knobs: area=80dvh, caption=lower-left, text=band-below · nav: N1b (links=3, dropdowns=none, scroll=frost, CTA=fill+toggle)
 * footer: Ft8 (speed=48s, glyph=middot) · verse: T3 (width=60ch, attribution=separate-band, face=roman serif)
 * enrichment: real photography (client assets) · i18n: es default / en toggle · pages: index · comunidad · donaciones */

@import url("tokens.css");

/* ===================== Reset & base ===================== */
*, *::before, *::after { box-sizing: border-box; }
html { overflow-x: clip; scroll-behavior: smooth; }
body {
  overflow-x: clip;
  margin: 0;
  background: var(--color-paper);
  color: var(--color-ink);
  font-family: var(--font-body);
  font-size: var(--text-base);
  line-height: 1.65;
  -webkit-font-smoothing: antialiased;
}
/* height:auto is REQUIRED alongside max-width — without it the width shrinks to fit
   but the HTML height attribute holds, stretching the image vertically. */
img { max-width: 100%; height: auto; display: block; }
h1, h2, h3, h4 {
  font-family: var(--font-display);
  font-weight: 700;
  font-style: normal;            /* typography purity — never italic headers */
  line-height: 1.12;
  letter-spacing: -0.02em;
  margin: 0;
  overflow-wrap: anywhere;
  min-width: 0;
}
p { margin: 0; }
a { color: var(--color-accent-deep); text-underline-offset: 3px; }
a:hover { color: var(--color-accent); }
:focus { outline: none; }
:focus-visible {
  outline: 2px solid var(--color-focus);
  outline-offset: 2px;
  border-radius: inherit;
}
.visually-hidden {
  position: absolute; width: 1px; height: 1px;
  clip-path: inset(50%); overflow: hidden; white-space: nowrap;
}
.skip-link {
  position: absolute; inset-block-start: var(--space-xs); inset-inline-start: var(--space-xs);
  background: var(--color-ink); color: var(--color-paper);
  padding: var(--space-xs) var(--space-md); border-radius: var(--radius-input);
  transform: translateY(-300%); z-index: var(--z-toast); text-decoration: none;
  transition: transform var(--dur-short) var(--ease-out);
}
.skip-link:focus-visible { transform: none; }

/* ===================== Layout shells ===================== */
.wrap { max-width: var(--page-max); margin-inline: auto; padding-inline: var(--page-gutter); }
.band { padding-block: var(--space-3xl); }
.band--tight { padding-block: var(--space-2xl); }
.band--tint { background: var(--color-paper-2); }
.band--ink { background: var(--color-ink); color: var(--color-paper); }

.section-head { max-width: 38ch; margin-block-end: var(--space-xl); }
.section-head h2 { font-size: var(--text-2xl); }
.section-head p { margin-block-start: var(--space-sm); color: var(--color-muted); }
.band--ink .section-head p { color: var(--color-on-ink); }

/* ===================== Nav — N1b ===================== */
.nav {
  position: fixed; inset: 0 0 auto; z-index: var(--z-sticky);
  background: transparent; border-block-end: 1px solid transparent;
  transition: background 240ms var(--ease-out), border-color 240ms var(--ease-out), box-shadow 240ms var(--ease-out);
}
.nav.is-scrolled {
  background: color-mix(in oklch, var(--color-paper) 88%, transparent);
  backdrop-filter: blur(18px) saturate(160%);
  -webkit-backdrop-filter: blur(18px) saturate(160%);
  border-block-end-color: var(--color-rule);
  box-shadow: var(--shadow-whisper);
}
.nav__inner {
  max-width: var(--page-max); margin-inline: auto; padding-inline: var(--page-gutter);
  height: 72px; display: grid; grid-template-columns: 1fr auto 1fr; align-items: center; gap: var(--space-md);
}
.nav__brand {
  justify-self: start; display: flex; align-items: center; gap: var(--space-sm);
  text-decoration: none; color: var(--color-ink); min-width: 0;
}
.nav__brand img { width: 44px; height: 44px; border-radius: 50%; flex: none; box-shadow: var(--shadow-whisper); }
.nav__brand-text { display: grid; line-height: 1.15; min-width: 0; }
.nav__brand-name {
  font-family: var(--font-display); font-weight: 800; font-size: 0.98rem; letter-spacing: -0.01em;
  white-space: nowrap;
}
.nav__brand-sub { font-size: var(--text-xs); color: var(--color-muted); white-space: nowrap; }
.nav__center { justify-self: center; display: flex; gap: var(--space-2xs); }
.nav__link {
  font-family: var(--font-display); font-weight: 600; font-size: 0.95rem;
  color: var(--color-ink); text-decoration: none; white-space: nowrap;
  padding: var(--space-xs) var(--space-md); border-radius: var(--radius-pill);
  transition: background var(--dur-short) var(--ease-out), color var(--dur-short) var(--ease-out);
  min-height: 44px; display: inline-flex; align-items: center;
}
.nav__link[aria-current="page"] { color: var(--color-accent-deep); }
@media (hover: hover) {
  .nav__link:hover { background: var(--color-paper-3); }
}
.nav__right { justify-self: end; display: flex; align-items: center; gap: var(--space-sm); }
.lang-toggle {
  display: flex; border: 1px solid var(--color-rule-2); border-radius: var(--radius-pill);
  overflow: hidden; background: var(--color-paper);
}
.lang-toggle button {
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  padding: var(--space-xs) var(--space-sm); border: 0; background: transparent; color: var(--color-muted);
  cursor: pointer; min-height: 40px; min-width: 44px;
  transition: background var(--dur-micro) var(--ease-out), color var(--dur-micro) var(--ease-out);
}
.lang-toggle button[aria-pressed="true"] { background: var(--color-ink); color: var(--color-paper); }
.nav__menu-btn { display: none; }

/* ===================== Buttons ===================== */
.btn {
  font-family: var(--font-display); font-weight: 700; font-size: 0.95rem;
  display: inline-flex; align-items: center; justify-content: center; gap: var(--space-xs);
  padding: var(--space-sm) var(--space-lg); min-height: 44px;
  border-radius: var(--radius-pill); border: 1px solid transparent;
  text-decoration: none; cursor: pointer; white-space: nowrap;
  transition: background-color var(--dur-short) var(--ease-out),
              transform var(--dur-micro) var(--ease-out),
              border-color var(--dur-short) var(--ease-out),
              box-shadow var(--dur-short) var(--ease-out);
}
.btn--accent { background: var(--color-accent); color: var(--color-accent-ink); }
@media (hover: hover) {
  .btn--accent:hover { background: var(--color-accent-deep); transform: translateY(-1.5px); box-shadow: var(--shadow-lift); }
}
.btn--accent:active { transform: translateY(0); transition-duration: 60ms; }
.btn--outline { background: transparent; color: var(--color-ink); border-color: var(--color-rule-2); }
@media (hover: hover) {
  .btn--outline:hover { background: var(--color-paper-3); transform: translateY(-1.5px); }
}
.btn--outline:active { transform: translateY(0); transition-duration: 60ms; }
.btn[disabled], .btn[aria-disabled="true"] { opacity: 0.5; cursor: not-allowed; transform: none; box-shadow: none; }
.btn .spinner {
  width: 1em; height: 1em; border-radius: 50%;
  border: 2px solid currentColor; border-block-start-color: transparent;
  animation: spin 0.9s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }

/* C3 typographic link */
.tlink {
  font-family: var(--font-display); font-weight: 700; font-size: 1rem;
  color: var(--color-accent-deep); text-decoration: none;
  border-block-end: 1px solid var(--color-accent);
  padding-block-end: 2px; white-space: nowrap;
  transition: border-color var(--dur-short) var(--ease-out), color var(--dur-short) var(--ease-out);
}
.tlink:hover { border-block-end-width: 2px; color: var(--color-accent); }

/* ===================== HORIZON — "La Mesa Larga" (index hero) =====================
   The page is a table; things rest on it. Type NEVER touches imagery — every text
   surface is a flat token fill, so contrast comes from spatial separation rather
   than a scrim. That is what lets the pink satin and the food keep their own
   tonality instead of being dimmed under an overlay.
   Measured: ink/paper 14.88:1 · muted/paper 7.87:1 · accent-deep/paper 7.04:1 */
.mesa-larga {
  background: var(--color-paper);
  overflow-x: clip;
  padding-block-start: calc(72px + var(--space-xl));
  /* height is content-driven — never 100dvh; a long table should run out of view */
}

/* Row 1 — the room. Left-ragged; the right ~45% stays deliberately empty cream.
   The measure is constrained on the CHILDREN, not on .ml__room itself — .wrap
   carries margin-inline:auto, so shrinking the wrap would centre the whole block. */
.ml__room > .ml__kicker,
.ml__room > .ml__verse { max-inline-size: 46ch; }
.ml__kicker {
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-muted);
}
.ml__kicker .ml__sep { color: var(--color-accent-deep); }
.ml__verse { margin: var(--space-lg) 0 0; }
.ml__verse p {
  font-family: var(--font-verse); font-weight: 500; font-style: normal;
  font-size: clamp(1.25rem, 1rem + 1.1vw, 1.75rem);
  line-height: 1.35; color: var(--color-ink); text-wrap: balance;
}
/* Both languages carry identical size, weight and colour — neither is a gloss. */
.ml__verse p + p { margin-block-start: var(--space-sm); }
.ml__tie {
  margin-block-start: var(--space-lg);
  font-size: var(--text-sm); color: var(--color-muted); max-inline-size: 42ch;
}

/* Row 2 — the card straddles the photograph's leading edge. */
.ml__cardwrap { position: relative; z-index: 2; margin-block-start: var(--space-xl); }
.ml__card {
  inline-size: min(100%, 30rem);
  background: var(--color-paper);          /* solid fill — never a scrim */
  border: 1px solid var(--color-rule);
  border-radius: var(--radius-card);
  box-shadow: var(--shadow-card);
  padding: var(--space-xl);
}
.ml__card h1 {
  /* NOT --text-display (max 84px): inside a 30rem card that wrapped to three lines
     and pushed the CTA below the fold at 1366x768. This scale breaks it to two
     ("En La Mesa" / "Con Jesús") and lifts the button back into view. */
  font-size: clamp(2.25rem, 1.5rem + 2.8vw, 4rem); font-weight: 800;
  line-height: 1.04; letter-spacing: -0.02em;
  color: var(--color-ink); max-inline-size: 11ch;
}
.ml__flame { color: var(--color-accent); }   /* their own single-word emphasis device */
.ml__cta { margin-block-start: var(--space-lg); }
.ml__where {
  margin-block-start: var(--space-md);
  font-size: var(--text-xs); color: var(--color-muted); line-height: 1.6;
}
.ml__where .ml__dir { display: inline-block; margin-block-start: var(--space-2xs); }

/* The table itself. No scrim, no gradient, no filter, no radius, no rotation. */
.ml__photo {
  /* Capped at 3rem, NOT the 5rem the spec called for. Measured: an 80px overlap
     reaches source-y 100 of the 800px crop, and the seated woman on the left has
     her hairline at ~y60 — the card was clipping the top of her head. The overlap
     must never rise above the faces. Everything it covers now is tablecloth. */
  --ml-overlap: clamp(1rem, 3vw, 3rem);
  inline-size: 100%;                        /* never 100vw — that reintroduces scroll */
  position: relative; z-index: 1;
  margin-block-start: calc(-1 * var(--ml-overlap));
}
.ml__photo img { inline-size: 100%; block-size: auto; }

/* ---- The endless table: an illustrated, seamlessly looping panorama ----
   Two copies of one 1200-unit tile drift exactly one tile width, so the loop
   point is pixel-identical. Every sub-animation is independently infinite and
   returns to its own start, so nothing can drift out of sync over time. */
.ml__scene {
  --ml-overlap: clamp(1rem, 3vw, 3rem);
  inline-size: 100%;
  position: relative; z-index: 1;
  margin-block-start: calc(-1 * var(--ml-overlap));
  overflow: clip;                       /* the drift must never widen the page */
  background: var(--scene-sky-bottom);  /* paint-in colour before the SVG lays out */
}
/* Every animation in the scene obeys one switch, set by the IntersectionObserver
   "frustum cull" in main.js. Defaults to running so the scene is never frozen if
   JS fails to load. */
.ml__scene :is(.ml-loop, .ml-bulb, .ml-flame, .ml-glow, .ml-dove, .ml-person, .ml-steam path) {
  animation-play-state: var(--ml-play, running);
}
.ml__scene svg {
  display: block;
  inline-size: 100%;
  /* xMidYMax slice anchors the crop to the BOTTOM, so the table and everything set
     on it is never cut — narrow screens simply see fewer people, larger. */
  block-size: clamp(18rem, 34vw, 30rem);
}
.ml-sky  { fill: url(#ml-sky); }
.ml-warm { fill: url(#ml-warm); }

/* three.js smootherstep — x³(x(6x−15)+10), Perlin's quintic — sampled into a native
   CSS easing. Zero acceleration at BOTH endpoints, which cubic-bezier ease-in-out
   cannot give you; motion that reverses (sway, bob, twinkle) stops being able to
   betray its turning points. */
.mesa-larga {
  --ease-smoother: linear(0, 0.0016, 0.0115, 0.0355, 0.0764, 0.135, 0.2099, 0.2984,
                          0.3967, 0.5, 0.6033, 0.7016, 0.7901, 0.865, 0.9236, 0.9645,
                          0.9885, 0.9984, 1);
}

/* the drift — each plane travels exactly one tile width, so each loops seamlessly
   on its own. Periods differ per depth, so the composite never visibly repeats. */
.ml-loop { animation: ml-drift var(--dur, 150s) linear infinite; }
@keyframes ml-drift {
  from { transform: translateX(0); }
  to   { transform: translateX(-1200px); }
}
/* .ml-plane is written only by JS (damped pointer offset). Keeping it on a separate
   element from .ml-loop means the parallax can never disturb the loop. */
.ml-plane { will-change: transform; }

/* string lights */
.ml-wire { fill: none; stroke: var(--scene-wire); stroke-width: 2; }
.ml-bulb {
  fill: var(--scene-bulb);
  animation: ml-twinkle 3.4s var(--ease-smoother) infinite;
  animation-delay: var(--d, 0s);
}
@keyframes ml-twinkle {
  0%, 100% { opacity: 0.55; }
  50%      { opacity: 1; }
}

/* dove */
.ml-dove-b, .ml-dove-w, .ml-dove-t { fill: var(--scene-dove); }
.ml-dove-w { opacity: 0.82; }
.ml-dove { animation: ml-dove-bob 7s var(--ease-smoother) infinite; }
@keyframes ml-dove-bob {
  0%, 100% { transform: translate(600px, 150px); }
  50%      { transform: translate(600px, 136px); }
}

/* people — tonal variation so neighbours never read as the same stamp */
.ml-body { fill: var(--scene-figure); }
.ml-body--a { fill: var(--scene-figure); }
.ml-body--b { fill: var(--scene-figure-b); }
.ml-body--c { fill: var(--scene-figure-c); }
/* a hair taller than wide — perfect circles read as icons, not heads */
.ml-head {
  fill: var(--scene-figure-hi);
  transform-box: fill-box; transform-origin: 50% 60%;
  transform: scaleY(1.13);
}
.ml-arm {
  fill: none; stroke: var(--scene-figure-b); stroke-width: 15;
  stroke-linecap: round;
}
/* the back row sits away from the light: smaller, paler, hazier */
.ml-back { opacity: 0.42; }
.ml-back .ml-body, .ml-back .ml-head { fill: var(--scene-figure-back); }
.ml-person {
  transform-box: fill-box; transform-origin: 50% 100%;
  animation: ml-sway 6.5s var(--ease-smoother) infinite;
  animation-delay: var(--s, 0s);
}
@keyframes ml-sway {
  0%, 100% { transform: rotate(-0.5deg); }
  50%      { transform: rotate(0.5deg); }
}

/* the table */
.ml-top    { fill: var(--scene-cloth-hi); }
.ml-runner { fill: var(--scene-runner); }
.ml-cloth  { fill: url(#ml-cloth); }
.ml-floor  { fill: var(--scene-floor); }

/* what is set on it */
.ml-plate  { fill: var(--scene-plate); }
.ml-bread  { fill: var(--scene-bread); }
.ml-dish   { fill: var(--scene-dish); }
.ml-grapes circle { fill: var(--scene-grape); }
.ml-wheat path {
  fill: var(--scene-wheat); stroke: var(--scene-wheat);
  stroke-width: 2.5; stroke-linecap: round;
}
.ml-jar, .ml-jar-neck { fill: var(--scene-jar); }
.ml-wax    { fill: var(--scene-wax); }
/* scaled back from the drawn size — at full size a votive stood taller than a
   person's head. Origin at the base keeps it seated on the table. */
.ml-candle {
  transform-box: fill-box; transform-origin: 50% 100%;
  transform: scale(0.78);
}
/* warm bloom around each flame — carries the candlelight into the air */
.ml-glow {
  fill: var(--color-accent);
  opacity: 0.13;
  filter: blur(14px);
}
/* A candle does not breathe in and out on a metronome. This is a full cycle with
   irregular stops (0% and 100% identical, so it still closes perfectly) instead of
   a two-keyframe `alternate` ping-pong — the giveaway of a CSS flame. */
.ml-flame {
  fill: var(--color-accent);
  transform-box: fill-box; transform-origin: 50% 100%;
  animation: ml-flicker var(--f, 1.7s) var(--ease-smoother) infinite;
}
@keyframes ml-flicker {
  0%   { transform: scale(1,    1)    translateY(0);    opacity: 0.90; }
  9%   { transform: scale(1.06, 1.11) translateY(-1px); opacity: 0.97; }
  17%  { transform: scale(0.97, 1.04) translateY(0);    opacity: 0.93; }
  28%  { transform: scale(1.11, 1.19) translateY(-2px); opacity: 1.00; }
  36%  { transform: scale(1.02, 1.07) translateY(-1px); opacity: 0.95; }
  47%  { transform: scale(0.95, 1.02) translateY(0);    opacity: 0.90; }
  58%  { transform: scale(1.09, 1.16) translateY(-2px); opacity: 0.99; }
  66%  { transform: scale(1.01, 1.05) translateY(-1px); opacity: 0.94; }
  79%  { transform: scale(1.13, 1.21) translateY(-2px); opacity: 1.00; }
  88%  { transform: scale(0.99, 1.03) translateY(0);    opacity: 0.92; }
  100% { transform: scale(1,    1)    translateY(0);    opacity: 0.90; }
}
/* the bloom breathes with its flame, a half-beat behind */
.ml-glow {
  animation: ml-bloom calc(var(--f, 1.7s) * 2) var(--ease-smoother) infinite;
}
@keyframes ml-bloom {
  0%, 100% { opacity: 0.11; }
  43%      { opacity: 0.17; }
}

/* steam off the shared dish */
.ml-steam path {
  fill: none; stroke: var(--scene-cloth-hi); stroke-width: 2.5;
  stroke-linecap: round; opacity: 0;
  animation: ml-steam 5s ease-out infinite;
  animation-delay: var(--w, 0s);
}
@keyframes ml-steam {
  0%   { opacity: 0;    transform: translateY(4px); }
  30%  { opacity: 0.55; }
  100% { opacity: 0;    transform: translateY(-22px); }
}

.ml__caption {
  margin-block-start: var(--space-md);
  display: flex; gap: var(--space-md); justify-content: space-between;
  align-items: baseline; flex-wrap: wrap;
}
.ml__cap-what { font-size: var(--text-xs); color: var(--color-muted); max-inline-size: 58ch; }
.ml__cap-who  { font-size: var(--text-xs); color: var(--color-muted); }

/* Exactly one animation, on the card only. Both keyframes written explicitly so no
   fill-mode can strand it. The photograph is never animated — it stays the LCP
   candidate and paints immediately. */
@media (prefers-reduced-motion: no-preference) {
  .ml__card { animation: ml-rise var(--dur-long) var(--ease-out); }
  @keyframes ml-rise {
    from { opacity: 0; translate: 0 10px; }
    to   { opacity: 1; translate: 0 0; }
  }
}

@media (max-width: 64rem) {
  .mesa-larga { padding-block-start: calc(72px + var(--space-xl)); }
  .ml__card { inline-size: min(100%, 34rem); }
  .ml__photo { --ml-overlap: clamp(1rem, 3vw, 2rem); }
}
@media (max-height: 800px) and (min-width: 64rem) {
  .mesa-larga { padding-block-start: calc(72px + var(--space-xl)); }
}
@media (max-width: 48rem) {
  .ml__card { inline-size: 100%; padding: var(--space-lg); }
  .ml__photo { --ml-overlap: 1.5rem; }
  .ml__caption { flex-direction: column; gap: var(--space-xs); }
}
@media (max-width: 30rem) {
  .ml__kicker { letter-spacing: 0.1em; }   /* holds one line at 320px */
}

/* ===================== H6 — Photographic fold ===================== */
.photo-fold { position: relative; }
/* <picture> must not introduce a layout box — the img is sized to the fold */
.photo-fold picture, .gallery picture, .pastor-grid picture { display: contents; }
.photo-fold--hero { height: 82dvh; min-height: 30rem; }
.photo-fold--mid { height: 64dvh; min-height: 24rem; }
.photo-fold .bleed { width: 100%; height: 100%; object-fit: cover; }
.photo-fold .scrim {
  position: absolute; inset: 0;
  background: var(--overlay-scrim);
}
.photo-fold .caption {
  position: absolute; inset-block-end: var(--space-lg); inset-inline-start: var(--page-gutter);
  color: var(--color-paper); max-width: 46ch;
}
.photo-fold .caption .cap-line {
  font-family: var(--font-display); font-weight: 800;
  font-size: clamp(1.6rem, 1.1rem + 2.4vw, 3rem);
  line-height: 1.08; letter-spacing: -0.02em;
  text-shadow: var(--shadow-photo);
}
.photo-fold .caption .cap-sub {
  margin-block-start: var(--space-sm); font-size: var(--text-sm);
  color: var(--color-paper-hi); text-shadow: var(--shadow-photo-soft);
}
.photo-fold .caption .cap-actions { margin-block-start: var(--space-md); display: flex; gap: var(--space-sm); flex-wrap: wrap; }

/* Hero-specific: brand block above caption */
.hero-brand {
  position: absolute; inset-block-start: calc(72px + var(--space-lg)); inset-inline-start: var(--page-gutter);
  display: flex; align-items: center; gap: var(--space-md); color: var(--color-paper);
}
.hero-brand img {
  width: clamp(72px, 10vw, 120px); height: auto; border-radius: 50%;
  box-shadow: var(--shadow-logo);
}
.hero-brand .hb-name {
  font-family: var(--font-display); font-weight: 800;
  font-size: clamp(1.05rem, 0.9rem + 1vw, 1.5rem); line-height: 1.15;
  text-shadow: var(--shadow-photo-soft); max-width: 22ch;
}
.hero-brand .hb-sub { font-size: var(--text-sm); color: var(--color-paper-hi); text-shadow: var(--shadow-photo-soft); }

/* ===================== Text fold — welcome + times ===================== */
/* 1.15/0.85 rather than 1.25/0.75: at the old ratio the schedule column was
   320px, and "Domingo — Culto de adoración" plus a bold "11:00 AM" needs ~341.
   Sunday wrapped onto two lines. Widening the card also makes it shorter, which
   shrinks the void beside it — the same change fixes both symptoms. */
.welcome-grid {
  display: grid; grid-template-columns: 1.15fr 0.85fr; gap: var(--space-2xl); align-items: start;
}
/* This section is intrinsically lopsided — a short welcome beside a tall
   schedule — so the standard 96px band padding compounds the void instead of
   giving it air. Pull the two edges in, and let the next section start sooner.
   NOTE: .welcome-grid IS the .wrap element (class="wrap welcome-grid"), so the
   child combinator is `> .welcome-grid`, not `> .wrap > .welcome-grid`.
   :has() is progressive: browsers without it just keep the old rhythm. */
.band:has(> .welcome-grid) { padding-block-end: var(--space-xl); }
.band:has(> .welcome-grid) + .band { padding-block-start: var(--space-2xl); }
/* Between the stack breakpoint and ~1200px the two columns exist but the card
   column is back under ~340px, so Sunday's bold time wraps again. Give the card
   a larger share through that band rather than letting it squeeze. */
@media (min-width: 60rem) and (max-width: 75rem) {
  .welcome-grid { grid-template-columns: 1fr 0.95fr; gap: var(--space-xl); }
}
.welcome-copy h2 { font-size: var(--text-3xl); max-width: 18ch; }
.welcome-copy .lede { margin-block-start: var(--space-lg); font-size: var(--text-lg); color: var(--color-ink-2); max-width: 52ch; }
.welcome-copy .lede + .lede { margin-block-start: var(--space-md); }
/* The schedule grew from 2 rows to 5 plus address, phone and directions, which
   made this card 673px tall against 296px of copy beside it — an L-shaped void
   down the left column. Tightened the internal rhythm rather than dropping
   information: the rows are a list to scan, not paragraphs to read. */
.times-card {
  background: var(--color-paper-2); border: 1px solid var(--color-rule);
  border-radius: var(--radius-card); padding: var(--space-lg); box-shadow: var(--shadow-whisper);
}
.times-card h3 { font-size: var(--text-lg); display: flex; align-items: center; gap: var(--space-sm); }
.times-card h3 .sq {
  width: 10px; height: 10px; background: var(--color-accent); border-radius: 2px; flex: none;
}
.times-card dl { margin: var(--space-md) 0 0; display: grid; gap: var(--space-sm); }
/* Day and time on ONE line. Stacking them doubled the height of every row for
   no reading benefit — a schedule is scanned in pairs, and the eye wants the
   time on the same baseline as the day. Falls back to stacked when the column
   is too narrow to hold both. */
.times-card .row {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: var(--space-sm) var(--space-md); flex-wrap: wrap;
  padding-block-end: var(--space-sm);
  border-block-end: 1px solid var(--color-rule);
}
.times-card dt { flex: 1 1 auto; min-inline-size: 0; }
.times-card dd { flex: 0 0 auto; white-space: nowrap; }
.times-card .row:last-child { border-block-end: 0; padding-block-end: 0; }
.times-card dt { font-family: var(--font-display); font-weight: 700; font-size: 0.95rem; }
.times-card dd { margin: 0; color: var(--color-muted); font-size: var(--text-sm); font-variant-numeric: tabular-nums; }
.times-card .pending { color: var(--color-accent-deep); font-size: var(--text-xs); font-weight: 700; }
/* Sunday is the service a visitor is most likely to attend first, so it carries
   weight — but on the TIME, not the label. Enlarging the label pushed it to the
   full column width and wrapped the time onto its own line, costing 42px and
   breaking the day/time pairing that makes the list scannable. */
.times-card .time-strong {
  color: var(--color-ink); font-weight: 700; font-size: var(--text-base);
}
.times-card address { font-style: normal; margin-block-start: var(--space-lg); color: var(--color-muted); font-size: var(--text-sm); line-height: 1.5; }
.times-card .dir-link { margin-block-start: var(--space-sm); display: inline-block; }
/* Honeypot. Deliberately NOT display:none or hidden — bots increasingly skip
   those. Pushed off-canvas instead, and taken out of the a11y tree + tab order
   so no real person (sighted, screen-reader, or keyboard) can ever reach it. */
.hp {
  position: absolute !important;
  left: -9999px !important;
  inline-size: 1px; block-size: 1px;
  overflow: hidden;
  pointer-events: none;
}

.times-card .times-phone {
  margin-block-start: var(--space-sm); font-size: var(--text-sm); color: var(--color-muted);
}
.foot-phone { margin-block-start: var(--space-2xs); }
.foot-phone a, .times-phone a { font-variant-numeric: tabular-nums; }

/* ===================== T3 — Verse room ===================== */
.verse-room { text-align: center; padding-block: var(--space-4xl); }
.verse-room blockquote {
  margin: 0 auto; max-width: 26ch;
  font-family: var(--font-verse); font-weight: 500; font-style: normal;
  font-size: var(--text-verse); line-height: 1.3; letter-spacing: -0.01em;
  color: var(--color-ink);
}
.verse-room .attribution {
  margin-block-start: var(--space-xl);
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-accent-deep);
}
.verse-room .verse-kicker {
  margin-block-end: var(--space-xl);
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-muted);
}
.verse-room .verse-tie {
  margin-block-start: var(--space-lg); margin-inline: auto; max-width: 46ch;
  font-size: var(--text-sm); color: var(--color-muted);
}
.verse-room .pending-note {
  margin-block-start: var(--space-md); font-size: var(--text-xs); color: var(--color-muted);
}

/* ===================== Bento — eventos preview ===================== */
.bento { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); grid-auto-rows: 11rem; gap: var(--space-md); }
.bento .cell {
  background: var(--color-paper-2); border: 1px solid var(--color-rule); border-radius: var(--radius-card);
  padding: var(--space-lg); display: flex; flex-direction: column; justify-content: flex-end; gap: var(--space-2xs);
  box-shadow: var(--shadow-whisper); min-width: 0; overflow: hidden;
}
.bento .cell--accent { background: var(--color-ink); color: var(--color-paper); border-color: var(--color-ink); }
.bento .cell--accent .cell-kicker { color: var(--color-gold); }
.bento .cell--accent .cell-meta { color: var(--color-on-ink-mid); }
.bento .cell--photo { padding: var(--space-sm); background: var(--color-paper-3); display: grid; place-items: center; }
.bento .cell--photo img { max-width: 100%; max-height: 100%; width: auto; height: auto; border-radius: calc(var(--radius-card) - var(--space-sm)); }
.bento .cell--empty { background: transparent; border-style: dashed; justify-content: center; align-items: flex-start; }
.bento .span-2x2 { grid-column: span 2; grid-row: span 2; }
.bento .span-2x1 { grid-column: span 2; }
.bento .span-1x2 { grid-row: span 2; }
.bento .cell-kicker {
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.10em; text-transform: uppercase; color: var(--color-accent-deep);
}
.bento .cell-title { font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg); line-height: 1.2; }
.bento .cell-meta { font-size: var(--text-sm); color: var(--color-muted); font-variant-numeric: tabular-nums; }
.bento .cell-more { margin-block-start: var(--space-xs); }
.bento-more { margin-block-start: var(--space-lg); }

/* ===================== Forms — visit + prayer ===================== */
.forms-grid { display: grid; grid-template-columns: 1.15fr 0.85fr; gap: var(--space-3xl); align-items: start; }
.form-card {
  background: var(--color-paper); border: 1px solid var(--color-rule);
  border-radius: var(--radius-card); padding: var(--space-xl); box-shadow: var(--shadow-whisper);
}
.band--ink .form-card { background: var(--color-ink-card); border-color: var(--color-ink-card-rule); color: var(--color-paper); }
.form-card h3 { font-size: var(--text-xl); }
.form-card .form-intro { margin-block-start: var(--space-xs); color: var(--color-muted); font-size: var(--text-sm); max-width: 46ch; }
.band--ink .form-intro { color: var(--color-on-ink-mid); }
.form-card form { margin-block-start: var(--space-lg); display: grid; gap: var(--space-lg); }
.field { display: grid; gap: var(--space-2xs); min-width: 0; }
.field label { font-family: var(--font-display); font-weight: 700; font-size: var(--text-sm); }
.field .req { color: var(--color-accent-deep); font-weight: 700; }
.field input, .field select, .field textarea {
  font: inherit; color: var(--color-ink);
  background: var(--color-paper);
  border: 1px solid var(--color-rule-2);     /* constant 1px — no layout shift */
  outline: 2px solid transparent; outline-offset: 1px;  /* reserved focus slot */
  border-radius: var(--radius-input);
  min-height: 44px; padding: var(--space-sm) var(--space-md);
  width: 100%; min-width: 0;
  transition: background-color var(--dur-short) var(--ease-out), border-color var(--dur-short) var(--ease-out);
}
.field textarea { min-height: 7rem; resize: vertical; line-height: 1.55; }
.field input::placeholder, .field textarea::placeholder { color: var(--color-muted); opacity: 0.75; }
@media (hover: hover) {
  .field input:hover, .field select:hover, .field textarea:hover { background: var(--color-paper-2); }
}
.field input:focus-visible, .field select:focus-visible, .field textarea:focus-visible {
  outline-color: var(--color-focus); border-color: var(--color-ink-2);
}
.field .helper { font-size: var(--text-xs); color: var(--color-muted); min-height: 1lh; }
.field .helper--error { color: var(--color-error); font-weight: 700; }
.field [aria-invalid="true"] { border-color: var(--color-error); }
.field-row { display: grid; grid-template-columns: 1fr 1fr; gap: var(--space-md); }
fieldset.checks { border: 0; padding: 0; margin: 0; display: grid; gap: var(--space-xs); }
fieldset.checks legend { font-family: var(--font-display); font-weight: 700; font-size: var(--text-sm); padding: 0; margin-block-end: var(--space-2xs); }
.check { display: flex; align-items: center; gap: var(--space-sm); font-size: var(--text-sm); min-height: 44px; }
.check input { width: 1.15rem; height: 1.15rem; accent-color: var(--color-accent); flex: none; }
.form-foot { display: flex; align-items: center; gap: var(--space-md); flex-wrap: wrap; }
.form-note { font-size: var(--text-xs); color: var(--color-muted); max-width: 38ch; }
.band--ink .form-note { color: var(--color-on-ink-soft); }

/* Failure panel (persists in-form; never auto-dismisses) */
.form-failure {
  border: 1px solid var(--color-error);
  border-inline-start-width: 3px;
  border-radius: var(--radius-input);
  padding: var(--space-md) var(--space-lg);
  background: color-mix(in oklch, var(--color-error) 8%, var(--color-paper));
  display: grid;
  gap: var(--space-2xs);
}
.band--ink .form-failure { background: color-mix(in oklch, var(--color-error) 22%, var(--color-ink-card)); }
.form-failure .ff-head { font-family: var(--font-display); font-weight: 800; font-size: var(--text-sm); color: var(--color-error); }
.band--ink .form-failure .ff-head { color: var(--color-paper); }
.form-failure .ff-body { font-size: var(--text-sm); color: var(--color-ink-2); max-width: 52ch; }
.band--ink .form-failure .ff-body { color: var(--color-on-ink); }
.form-failure .tlink { justify-self: start; margin-block-start: var(--space-2xs); }
.band--ink .form-failure .tlink { color: var(--color-paper); border-color: var(--color-paper); }

/* Success panel (replaces form after submit) */
.form-success { display: none; text-align: start; padding-block: var(--space-lg); }
.form-success.is-visible { display: block; }
.form-success .check-ring {
  width: 56px; height: 56px; border-radius: 50%;
  background: var(--color-pear); color: oklch(30% 0.09 130);
  display: grid; place-items: center; margin-block-end: var(--space-md);
}
.form-success h4 { font-size: var(--text-lg); }
.form-success p { margin-block-start: var(--space-xs); color: var(--color-muted); font-size: var(--text-sm); max-width: 46ch; }
.band--ink .form-success p { color: var(--color-on-ink-mid); }
form.is-sent { display: none; }

/* ===================== Footer — Ft8 marquee + meta ===================== */
.foot-marquee { overflow: clip; border-block-start: 2px solid var(--color-ink); background: var(--color-paper); }
.foot-marquee__track {
  display: flex; gap: var(--space-2xl); white-space: nowrap;
  padding-block: var(--space-md); width: max-content;
  animation: foot-marquee 48s linear infinite;
}
.foot-marquee__track span {
  font-family: var(--font-display); font-weight: 800; letter-spacing: 0.06em;
  font-size: clamp(1rem, 2.5vw, 1.5rem); color: var(--color-ink);
}
.foot-marquee__track .dot { color: var(--color-accent); }
@keyframes foot-marquee { from { transform: translateX(0); } to { transform: translateX(-50%); } }
@media (hover: hover) { .foot-marquee:hover .foot-marquee__track { animation-play-state: paused; } }

.foot-meta { background: var(--color-ink); color: var(--color-paper); padding-block: var(--space-2xl); }
.foot-meta .grid { display: grid; grid-template-columns: 1.2fr 1fr 1fr; gap: var(--space-xl); align-items: start; }
.foot-meta .f-brand { display: flex; gap: var(--space-md); align-items: center; }
.foot-meta .f-brand img { width: 56px; height: 56px; border-radius: 50%; }
.foot-meta .f-brand .n { font-family: var(--font-display); font-weight: 800; line-height: 1.2; }
.foot-meta .f-brand .s { font-size: var(--text-xs); color: var(--color-on-ink-soft); }
.foot-meta h4 { font-size: var(--text-sm); letter-spacing: 0.08em; text-transform: uppercase; color: var(--color-gold); margin-block-end: var(--space-sm); }
.foot-meta ul { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-xs); }
.foot-meta a { color: var(--color-paper); text-decoration: none; font-size: var(--text-sm); white-space: nowrap; }
.foot-meta a:hover { color: var(--color-accent); }
.foot-meta address { font-style: normal; font-size: var(--text-sm); color: var(--color-on-ink); line-height: 1.6; }
.foot-meta .legal { margin-block-start: var(--space-xl); padding-block-start: var(--space-md); border-block-start: 1px solid var(--color-ink-card-rule); font-size: var(--text-xs); color: var(--color-on-ink-faint); display: flex; justify-content: space-between; gap: var(--space-md); flex-wrap: wrap; }

/* ===================== Page hero (interior pages) ===================== */
.page-hero { padding-block-start: calc(72px + var(--space-3xl)); padding-block-end: var(--space-2xl); }
.page-hero h1 { font-size: var(--text-display); max-width: 16ch; }
.page-hero .lede { margin-block-start: var(--space-lg); font-size: var(--text-lg); color: var(--color-muted); max-width: 52ch; }

/* ===================== Split Studio — diptych (comunidad) =====================
   Every block halves the screen; direction alternates down the page. */
.split {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  align-items: center;
  gap: clamp(var(--space-xl), 5vw, var(--space-3xl));
  padding-inline: var(--page-gutter);
  padding-block: var(--space-3xl);
  max-width: 84rem;
  margin-inline: auto;
}
.split--hero { padding-block-start: calc(72px + var(--space-2xl)); }
/* .split--flip puts media first in source order; on mobile the text leads */
.split__text { min-width: 0; display: grid; gap: var(--space-md); }
.split__text h1 { font-size: var(--text-display); max-width: 14ch; }
.split__text h2 { font-size: var(--text-3xl); max-width: 16ch; }
.split__text p { color: var(--color-ink-2); max-width: 54ch; }
.split__text .lede { font-size: var(--text-lg); color: var(--color-muted); }
.split__kicker {
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-accent-deep);
}
.split__meta { font-size: var(--text-sm); color: var(--color-muted); }
.split__meta.pending { color: var(--color-accent-deep); font-weight: 700; font-size: var(--text-xs); }
.split__date {
  font-family: var(--font-display); font-weight: 800;
  font-size: clamp(2.5rem, 1.8rem + 3vw, 4.5rem); line-height: 1;
  letter-spacing: -0.04em; color: var(--color-accent);
  font-variant-numeric: tabular-nums;
}
.split__date span { color: var(--color-rule-2); margin-inline: 0.1em; }
.split__media { margin: 0; min-width: 0; }
.split__media img {
  width: 100%; height: auto; border-radius: var(--radius-card);
  box-shadow: var(--shadow-lift);
}
.split__media figcaption {
  font-size: var(--text-xs); color: var(--color-muted);
  padding-block-start: var(--space-sm);
}

/* ===================== Pillars — the three pastoral pillars ===================== */
.pillars { list-style: none; margin: 0; padding: 0; display: grid; gap: 0; border-block-start: 1px solid var(--color-rule); }
.pillar {
  display: grid; grid-template-columns: auto minmax(0, 1fr);
  gap: var(--space-lg); align-items: start;
  padding-block: var(--space-xl); border-block-end: 1px solid var(--color-rule);
}
.pillar__num {
  font-family: var(--font-display); font-weight: 800; font-size: var(--text-xl);
  line-height: 1.1; color: var(--color-accent); font-variant-numeric: tabular-nums;
}
.pillar h3 { font-size: var(--text-xl); }
.pillar p { margin-block-start: var(--space-xs); color: var(--color-muted); max-width: 60ch; }

/* ===================== Pastores ===================== */
.pastor-grid { display: grid; grid-template-columns: 0.9fr 1.1fr; gap: var(--space-3xl); align-items: center; }
.pastor-grid figure { margin: 0; border-radius: var(--radius-card); overflow: hidden; box-shadow: var(--shadow-lift); }
.pastor-grid figcaption { font-size: var(--text-xs); color: var(--color-muted); padding-block-start: var(--space-sm); }
.pastor-copy h2 { font-size: var(--text-2xl); }
.pastor-copy .who { margin-block-start: var(--space-xs); color: var(--color-accent-deep); font-family: var(--font-display); font-weight: 700; }
.pastor-copy p { margin-block-start: var(--space-md); color: var(--color-ink-2); max-width: 52ch; }

/* ===================== Ministerios list ===================== */
.min-list { display: grid; gap: 0; border-block-start: 1px solid var(--color-rule); }
.min-row {
  display: grid; grid-template-columns: 1fr auto; gap: var(--space-md); align-items: baseline;
  padding-block: var(--space-lg); border-block-end: 1px solid var(--color-rule);
}
.min-row .min-name { font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg); }
.min-row .min-desc { color: var(--color-muted); font-size: var(--text-sm); margin-block-start: var(--space-2xs); max-width: 56ch; }
.min-row .min-tag { font-size: var(--text-xs); color: var(--color-accent-deep); font-weight: 700; white-space: nowrap; }

/* ===================== Events calendar ===================== */
.ev-list { display: grid; gap: var(--space-md); }
.ev-card {
  display: grid; grid-template-columns: 5.5rem 1fr auto; gap: var(--space-lg); align-items: center;
  background: var(--color-paper); border: 1px solid var(--color-rule); border-radius: var(--radius-card);
  padding: var(--space-lg); box-shadow: var(--shadow-whisper);
}
.ev-date {
  display: grid; place-items: center; text-align: center; background: var(--color-paper-3);
  border-radius: var(--radius-input); padding-block: var(--space-sm);
}
.ev-date .d { font-family: var(--font-display); font-weight: 800; font-size: var(--text-xl); line-height: 1; font-variant-numeric: tabular-nums; }
/* the ":30" rides small so the hour stays the thing you read */
.ev-date .d small { font-size: 0.58em; font-weight: 700; }
.ev-date .m { font-size: var(--text-xs); font-weight: 700; letter-spacing: 0.08em; text-transform: uppercase; color: var(--color-accent-deep); }
.ev-body .ev-name { font-family: var(--font-display); font-weight: 800; font-size: 1.05rem; }
.ev-body .ev-meta { color: var(--color-muted); font-size: var(--text-sm); margin-block-start: var(--space-3xs); font-variant-numeric: tabular-nums; }
.ev-tag { font-size: var(--text-xs); font-weight: 700; color: var(--color-accent-deep); border: 1px solid var(--color-rule-2); padding: var(--space-2xs) var(--space-sm); border-radius: var(--radius-pill); white-space: nowrap; }
.ev-empty {
  border: 1px dashed var(--color-rule-2); border-radius: var(--radius-card);
  padding: var(--space-2xl); text-align: start; background: var(--color-paper-2);
}
.ev-empty .t { font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg); }
.ev-empty p { color: var(--color-muted); font-size: var(--text-sm); margin-block-start: var(--space-xs); max-width: 52ch; }

/* ===================== Gallery — masonry, natural aspect ===================== */
.gallery { columns: 3; column-gap: var(--space-md); }
.gallery button.g-item {
  display: block; width: 100%; margin: 0 0 var(--space-md); break-inside: avoid;
  padding: 0; border: 0; border-radius: var(--radius-card); overflow: hidden; cursor: pointer;
  background: var(--color-paper-3); position: relative;
  transition: transform var(--dur-short) var(--ease-out), box-shadow var(--dur-short) var(--ease-out);
}
@media (hover: hover) {
  .gallery button.g-item:hover { transform: translateY(-2px); box-shadow: var(--shadow-lift); }
}
.gallery button.g-item img { width: 100%; height: auto; }
.gallery .g-empty {
  border: 1px dashed var(--color-rule-2); border-radius: var(--radius-card);
  padding: var(--space-2xl); background: var(--color-paper-2);
}
dialog.lightbox {
  border: 0; padding: 0; background: transparent; max-width: min(92vw, 64rem);
  position: fixed; inset: 0; margin: auto; height: fit-content; max-height: min(86vh, 48rem);
}
dialog.lightbox::backdrop { background: var(--backdrop-modal); }
dialog.lightbox img { width: 100%; height: auto; max-height: 78vh; object-fit: contain; border-radius: var(--radius-card); }
dialog.lightbox .lb-cap { color: var(--color-paper); font-size: var(--text-sm); margin-block-start: var(--space-sm); text-align: center; }
dialog.lightbox .lb-close {
  position: absolute; inset-block-start: calc(-1 * var(--space-xl)); inset-inline-end: 0;
  background: var(--color-paper); color: var(--color-ink); border: 0; border-radius: var(--radius-pill);
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-sm);
  min-height: 44px; min-width: 44px; padding-inline: var(--space-md); cursor: pointer;
}

/* ===================== Letter (donaciones) =====================
   Intimate, written, single measure. No buttons in the fold. */
.letter {
  padding-block: calc(72px + var(--space-3xl)) var(--space-3xl);
  padding-inline: var(--page-gutter);
}
.letter__sheet { max-width: 60ch; margin-inline: auto; }
.letter__salutation {
  font-family: var(--font-verse); font-style: normal; font-size: var(--text-xl);
  color: var(--color-muted); margin-block-end: var(--space-xl);
}
.letter__lead {
  font-family: var(--font-verse); font-weight: 500; font-style: normal;
  font-size: clamp(1.5rem, 1.1rem + 1.8vw, 2.4rem); line-height: 1.25;
  letter-spacing: -0.015em; color: var(--color-ink);
  overflow-wrap: anywhere;
}
.letter__sheet p + p { margin-block-start: var(--space-lg); }
.letter__sheet > p:not(.letter__lead):not(.letter__salutation):not(.letter__signature):not(.letter__draft) {
  font-size: var(--text-lg); line-height: 1.7; color: var(--color-ink-2);
}
.letter__verse {
  margin: var(--space-2xl) 0; padding-inline-start: var(--space-lg);
  border-inline-start: 3px solid var(--color-accent);
  font-family: var(--font-verse); font-style: normal;
  font-size: var(--text-xl); line-height: 1.45; color: var(--color-ink);
}
.letter__verse cite {
  display: block; margin-block-start: var(--space-md);
  font-family: var(--font-display); font-style: normal; font-weight: 700;
  font-size: var(--text-xs); letter-spacing: 0.12em; text-transform: uppercase;
  color: var(--color-accent-deep);
}
.letter__signoff { margin-block-start: var(--space-2xl); color: var(--color-muted); }
.letter__signature {
  margin-block-start: var(--space-sm);
  font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg);
  line-height: 1.35; color: var(--color-ink);
}
.letter__signature-sub {
  font-family: var(--font-body); font-weight: 400; font-size: var(--text-sm);
  color: var(--color-muted);
}
.letter__draft {
  margin-block-start: var(--space-2xl); padding: var(--space-md) var(--space-lg);
  border: 1px dashed var(--color-rule-2); border-radius: var(--radius-input);
  background: var(--color-paper-2);
  font-size: var(--text-xs); color: var(--color-muted);
}

/* ===================== Donaciones ===================== */
.give-grid { display: grid; grid-template-columns: 1.1fr 0.9fr; gap: var(--space-3xl); align-items: start; }
.give-methods { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--space-md); align-items: start; }
.give-card {
  border: 1px solid var(--color-rule); border-radius: var(--radius-card); padding: var(--space-xl);
  background: var(--color-paper); box-shadow: var(--shadow-whisper); display: grid; gap: var(--space-sm);
}
.give-card .g-name { font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg); display: flex; align-items: center; gap: var(--space-sm); }
.give-card .g-name .sq { width: 10px; height: 10px; background: var(--color-accent); border-radius: 2px; flex: none; }
.give-card p { color: var(--color-muted); font-size: var(--text-sm); }
.give-card--pending { border-style: dashed; background: var(--color-paper-2); }
.give-card .pending-pill {
  display: inline-block; font-size: var(--text-xs); font-weight: 700; color: var(--color-accent-deep);
  border: 1px solid var(--color-accent); border-radius: var(--radius-pill); padding: var(--space-3xs) var(--space-sm);
  width: fit-content;
}
.give-verse { border-inline-start: 3px solid var(--color-accent); padding-inline-start: var(--space-lg); }
.give-verse blockquote { margin: 0; font-family: var(--font-verse); font-size: var(--text-xl); line-height: 1.4; }
.give-verse .attribution { margin-block-start: var(--space-sm); font-size: var(--text-xs); font-weight: 700; letter-spacing: 0.1em; text-transform: uppercase; color: var(--color-accent-deep); }

/* ===================== Toast ===================== */
.toast-stack { position: fixed; inset-block-end: var(--space-lg); inset-inline-end: var(--space-lg); z-index: var(--z-toast); display: grid; gap: var(--space-sm); }
.toast {
  background: var(--color-ink); color: var(--color-paper); border-radius: var(--radius-input);
  padding: var(--space-sm) var(--space-lg); font-size: var(--text-sm); box-shadow: var(--shadow-lift);
  transform: translateY(8px); opacity: 0;
  transition: transform var(--dur-long) var(--ease-out), opacity var(--dur-long) var(--ease-out);
}
.toast.is-in { transform: none; opacity: 1; }
.toast--error { background: var(--color-error); }

/* ===================== Reveal (one-shot) ===================== */
.reveal { opacity: 0; transform: translateY(8px); }
.reveal.is-in {
  animation: reveal var(--dur-long) var(--ease-out) forwards;
  animation-delay: calc(var(--i, 0) * 90ms);
}
@keyframes reveal { to { opacity: 1; transform: none; } }

/* ===================== i18n visibility ===================== */
[data-lang] { display: none; }
html[lang="es"] [data-lang="es"] { display: revert; }
html[lang="en"] [data-lang="en"] { display: revert; }
/* inline variants stay inline */
html[lang="es"] span[data-lang="es"], html[lang="en"] span[data-lang="en"] { display: inline; }

/* ===================== Responsive ===================== */
@media (max-width: 60rem) {
  .nav__center { display: none; }
  .nav__inner { grid-template-columns: auto 1fr auto; }
  .nav__menu-btn {
    display: inline-flex; justify-self: end; align-items: center; gap: var(--space-2xs);
    font-family: var(--font-display); font-weight: 700; font-size: var(--text-sm);
    background: transparent; border: 1px solid var(--color-rule-2); border-radius: var(--radius-pill);
    min-height: 44px; padding-inline: var(--space-md); cursor: pointer; color: var(--color-ink);
  }
  .nav__cta-desktop { display: none; }
  .nav-sheet {
    position: fixed; inset: 0; z-index: var(--z-modal); background: var(--color-paper);
    padding: var(--space-xl) var(--page-gutter); display: grid; gap: var(--space-xs);
    align-content: start; transform: translateY(-100%);
    transition: transform var(--dur-long) var(--ease-out);
  }
  .nav-sheet.is-open { transform: none; }
  .nav-sheet .nav-sheet__close { justify-self: end; }
  .nav-sheet a {
    font-family: var(--font-display); font-weight: 800; font-size: var(--text-2xl);
    color: var(--color-ink); text-decoration: none; padding-block: var(--space-md);
    border-block-end: 1px solid var(--color-rule); min-height: 44px; display: flex; align-items: center;
  }
  .nav-sheet .sheet-cta { margin-block-start: var(--space-lg); }
  .welcome-grid, .forms-grid, .pastor-grid, .give-grid { grid-template-columns: 1fr; gap: var(--space-2xl); }
  .split { grid-template-columns: minmax(0, 1fr); gap: var(--space-xl); padding-block: var(--space-2xl); }
  .give-methods { grid-template-columns: minmax(0, 1fr); }
  .letter { padding-block-start: calc(72px + var(--space-2xl)); }
  .split--hero { padding-block-start: calc(72px + var(--space-xl)); }
  /* text always leads on mobile, whichever way the diptych faces on desktop */
  .split__text { order: -1; }
  .svc-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .bento { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .gallery { columns: 2; }
  .foot-meta .grid { grid-template-columns: 1fr 1fr; }
  .hero-brand { inset-block-start: calc(72px + var(--space-md)); }
  .photo-fold .caption .cap-actions .btn { min-height: 48px; }
}
@media (min-width: 60.01rem) {
  .nav-sheet { display: none; }
}
@media (max-width: 40rem) {
  .nav__inner { gap: var(--space-xs); }
  .nav__brand-sub { display: none; }
  .nav__brand-name { display: none; }  /* logo carries the brand on phones; full name lives in the hero + footer */
  .nav__brand img { width: 40px; height: 40px; }
  .bento { grid-template-columns: 1fr; grid-auto-rows: minmax(9rem, auto); }
  .bento .span-2x2, .bento .span-2x1 { grid-column: span 1; }
  .field-row { grid-template-columns: 1fr; }
  .svc-grid { grid-template-columns: 1fr; }
  .gallery { columns: 1; }
  .ev-card { grid-template-columns: 4.5rem 1fr; }
  .ev-tag { grid-column: 2; justify-self: start; }
  .foot-meta .grid { grid-template-columns: 1fr; }
  .band { padding-block: var(--space-2xl); }
  .photo-fold--hero { min-height: 26rem; }
  .hero-brand .hb-name { max-width: 16ch; }
  .toast-stack { inset-inline: var(--space-md); inset-block-end: var(--space-md); }
}

/* ===================== Services — ministry services grid ===================== */
.svc-grid { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--space-md); }
.svc-card {
  background: var(--color-paper); border: 1px solid var(--color-rule); border-radius: var(--radius-card);
  padding: var(--space-lg); display: flex; flex-direction: column; gap: var(--space-2xs);
  box-shadow: var(--shadow-whisper); min-width: 0;
  transition: transform var(--dur-short) var(--ease-out), box-shadow var(--dur-short) var(--ease-out);
}
@media (hover: hover) {
  .svc-card:hover { transform: translateY(-2px); box-shadow: var(--shadow-lift); }
}
.svc-card .cell-kicker {
  font-family: var(--font-display); font-weight: 700; font-size: var(--text-xs);
  letter-spacing: 0.10em; text-transform: uppercase; color: var(--color-accent-deep);
}
.svc-card .cell-title { font-family: var(--font-display); font-weight: 800; font-size: var(--text-lg); line-height: 1.2; }
.svc-card .cell-meta { font-size: var(--text-sm); color: var(--color-muted); }
.svc-note { margin-block-start: var(--space-lg); }

/* ===================== Reduced motion ===================== */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 150ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 150ms !important;
  }
  html { scroll-behavior: auto; }
  .foot-marquee__track { animation: none; }
  /* the hero scene holds completely still — but stays fully composed. Steam is
     keyframed from opacity 0, so it needs an explicit resting value or it vanishes. */
  .ml-loop, .ml-bulb, .ml-flame, .ml-glow, .ml-dove, .ml-person, .ml-steam path {
    animation: none !important;
  }
  .ml-steam path { opacity: 0.3; }
  .ml-glow { opacity: 0.13; }
  /* JS also checks this and never starts the pointer-parallax loop at all */
  .reveal { opacity: 1; transform: none; }
  .nav-sheet { transition: opacity 150ms linear; transform: none; }
  .nav-sheet:not(.is-open) { opacity: 0; visibility: hidden; }
}
