/* ============================================================================
   Dakshin Vrindavan Trust — site-wide stylesheet
   Mobile-first. Breakpoints: 480, 640, 768, 1024, 1280.
   No build step. No JS required for layout.
   ========================================================================= */
@import url("./tokens.css");

/* ── Reset + base ───────────────────────────────────────────────────────── */
*, *::before, *::after { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; overflow-x: clip; }
/* Honour the hidden attribute even when later rules set display: */
[hidden] { display: none !important; }
body {
  margin: 0;
  font-family: var(--font-body);
  font-size: var(--fs-base);
  line-height: 1.6;
  color: var(--c-text);
  background: var(--c-cream);
  text-rendering: optimizeLegibility;
  -webkit-font-smoothing: antialiased;
  /* Safety net: any stray child wider than the viewport (third-party embed,
     a forgotten inline width, a long unbroken URL in a paragraph) must NOT
     produce a horizontal scrollbar on a donation page. We use `clip` rather
     than `hidden` so position:sticky and focus rings still work correctly.
     Root causes are still fixed at the source — this just keeps a future
     mistake from breaking the donor flow. */
  overflow-x: clip;
}
img, svg, video { display: block; max-width: 100%; height: auto; }
button { font: inherit; cursor: pointer; border: 0; background: none; color: inherit; }
input, select, textarea { font: inherit; }
a { color: var(--c-danger); text-decoration: none; }
a:hover, a:focus-visible { text-decoration: underline; }
h1, h2, h3, h4 { font-family: var(--font-display); font-weight: 600; letter-spacing: -.005em; line-height: 1.15; margin: 0 0 .4em; color: var(--c-ink); }
h1 { font-size: var(--fs-h1); font-weight: 700; }
h2 { font-size: var(--fs-h2); font-weight: 600; }
h3 { font-size: var(--fs-h3); font-weight: 600; }
p { margin: 0 0 1em; }

/* ── Accessibility helpers ──────────────────────────────────────────────── */
:focus-visible { outline: 3px solid var(--c-saffron); outline-offset: 3px; border-radius: 4px; }
.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; }
.skip-link { position: absolute; left: -9999px; }
.skip-link:focus { left: 16px; top: 16px; padding: 12px 18px; background: var(--c-white); color: var(--c-danger); border: 2px solid var(--c-saffron); border-radius: 8px; z-index: 9999; font-weight: 600; }

/* ── Layout primitives ──────────────────────────────────────────────────── */
.container { width: 100%; max-width: var(--container); margin: 0 auto; padding: 0 var(--s-4); }
@media (min-width: 768px) { .container { padding: 0 var(--s-5); } }
.narrow { max-width: var(--container-narrow); margin: 0 auto; }
section { padding: var(--s-7) 0; }
@media (min-width: 768px) { section { padding: var(--s-9) 0; } }
.section-eyebrow { display: inline-block; font-family: var(--font-body); font-size: var(--fs-sm); font-weight: 600; letter-spacing: .12em; text-transform: uppercase; color: var(--c-saffron-text); margin-bottom: var(--s-3); }
.section-lede { font-size: var(--fs-md); color: var(--c-ink-soft); max-width: 64ch; margin: 0 0 var(--s-6); }
.bg-cream { background: var(--c-cream); }
.bg-white { background: var(--c-white); }
.bg-saffron-soft { background: var(--c-saffron-soft); }
.bg-gold-soft { background: var(--c-gold-soft); }
.bg-success-soft { background: var(--c-success-soft); }
.bg-ink { background: var(--c-ink); color: var(--c-white); }
.bg-ink h1, .bg-ink h2, .bg-ink h3 { color: var(--c-white); }

/* ── Buttons ────────────────────────────────────────────────────────────── */
.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: var(--s-2);
  padding: 14px 28px; border-radius: var(--r-pill);
  font-weight: 600; font-size: var(--fs-base); line-height: 1;
  transition: transform var(--d-base) var(--ease), box-shadow var(--d-base) var(--ease), background var(--d-base) var(--ease), color var(--d-base) var(--ease);
  border: 2px solid transparent;
  white-space: nowrap;
  min-height: 44px; /* WCAG 2.5.5 target size */
}
.btn:hover, .btn:focus-visible { text-decoration: none; transform: translateY(-1px); }
.btn-primary { background: var(--c-saffron); color: var(--c-ink); box-shadow: 0 4px 14px rgba(234,175,0,.32); }
.btn-primary:hover, .btn-primary:focus-visible { background: var(--c-saffron-deep); color: var(--c-white); }
.btn-ghost { background: transparent; color: var(--c-saffron-deep); border-color: var(--c-saffron); }
.btn-ghost:hover, .btn-ghost:focus-visible { background: var(--c-saffron-soft); }
.btn-dark { background: var(--c-ink); color: var(--c-white); }
.btn-dark:hover, .btn-dark:focus-visible { background: #000; }
.btn-block { width: 100%; }
.btn-sm { padding: 10px 18px; font-size: var(--fs-sm); min-height: 36px; }
.btn-lg { padding: 18px 36px; font-size: var(--fs-md); }

/* ── Header ─────────────────────────────────────────────────────────────── */
.site-header {
  position: sticky; top: 0; z-index: 50;
  background: rgba(253,251,246,.96);
  backdrop-filter: saturate(160%) blur(8px);
  -webkit-backdrop-filter: saturate(160%) blur(8px);
  border-bottom: 1px solid var(--c-rule);
}
.site-header .container { display: flex; align-items: center; justify-content: space-between; min-height: var(--header-h); padding-top: var(--s-3); padding-bottom: var(--s-3); gap: var(--s-2); }
/* The logo PNG already carries the "Dakshin Vrindavan · Care for cows" name, so the
   accompanying .brand-text element is hidden on mobile (would overlap visually) and
   only revealed on wide screens where there's space for the "Gaushala · Palakkad" subtitle. */
.brand { display: flex; align-items: center; gap: var(--s-3); color: var(--c-ink); min-width: 0; flex: 0 1 auto; overflow: hidden; }
.brand img { height: 38px; width: auto; flex-shrink: 0; }
.brand-text { display: none; font-family: var(--font-display); font-weight: 600; font-size: 16px; line-height: 1.1; min-width: 0; }
.brand-text small { display: block; font-family: var(--font-body); font-weight: 400; font-size: 11px; color: var(--c-ink-soft); letter-spacing: .04em; text-transform: uppercase; }
@media (min-width: 480px) { .brand img { height: 42px; } }
@media (min-width: 1024px) {
  .brand img { height: 48px; }
  .brand-text { display: block; }
  .site-header .container { gap: var(--s-3); }
}

.nav { display: none; gap: var(--s-5); }
.nav a { color: var(--c-ink); font-weight: 500; font-size: var(--fs-sm); padding: 6px 4px; }
/* P3 contrast: saffron-text (#8A6800) is the AA-safe accent for 14px text on
   the saffron-soft pill — saffron-deep (#B68900) measured 2.91:1 there. */
.nav a:hover, .nav a.is-active { color: var(--c-saffron-text); text-decoration: none; }
@media (min-width: 1024px) { .nav { display: flex; } }

.header-cta { display: flex; align-items: center; gap: var(--s-2); flex-shrink: 0; }
.header-cta .btn { padding: 8px 14px; font-size: var(--fs-sm); min-height: 40px; }
@media (min-width: 480px) { .header-cta .btn { padding: 10px 18px; } }
/* Hide the saffron Donate pill on the smallest screens — the dv-mobar covers it */
@media (max-width: 379px) { .header-cta .btn-primary { display: none; } }

/* Mobile nav toggle */
.nav-toggle { display: inline-flex; align-items: center; justify-content: center; width: 44px; height: 44px; border-radius: 10px; background: transparent; }
.nav-toggle:hover { background: var(--c-saffron-soft); }
@media (min-width: 1024px) { .nav-toggle { display: none; } }

/* Mobile drawer.
   `top` uses --header-bottom which site.js sets to the actual rendered
   bottom of the topbar+header (so it sits flush below them at every
   viewport — including narrow folds where the topbar wraps to 2 lines).
   --header-h is the SSR fallback if JS hasn't run yet. */
.mobile-nav {
  position: fixed;
  top: var(--header-bottom, var(--header-h));
  inset-inline: 0;
  bottom: 0;
  z-index: 49;
  background: var(--c-white);
  display: none; flex-direction: column; padding: var(--s-5);
  overflow-y: auto;
}
.mobile-nav.is-open { display: flex; }
/* Plain nav links — separated by a thin rule. The :not(.btn) excludes the
   donate-now button below so it keeps its own padding, border-radius and
   centred text alignment. */
.mobile-nav a:not(.btn) { display: block; padding: var(--s-4) 0; border-bottom: 1px solid var(--c-rule); color: var(--c-ink); font-weight: 500; font-size: var(--fs-md); }
.mobile-nav .btn {
  margin-top: var(--s-5);
  padding: 14px 22px;
  text-align: center;
  border-radius: var(--r-pill);
  font-size: var(--fs-md);
  font-weight: 700;
  width: 100%;
  box-sizing: border-box;
  border-bottom: 0;          /* override any inherited link rule */
}
@media (min-width: 1024px) { .mobile-nav { display: none !important; } }

/* ── Topbar (above header) ──────────────────────────────────────────────── */
.topbar { background: var(--c-saffron-soft); color: var(--c-saffron-deep); font-size: var(--fs-xs); padding: 6px 0; text-align: center; }
.topbar strong { font-weight: 600; }
/* On very narrow phones (Galaxy Z Fold 5 folded ≤ 380px) the trust strip
   would otherwise wrap to 2 lines — pushing the header down and clipping
   the first item of the mobile drawer. Force single-line + horizontal
   scroll so the strip stays exactly one row tall regardless of width. */
@media (max-width: 380px) {
  .topbar {
    font-size: 10.5px;
    padding: 5px 12px;
    white-space: nowrap;
    overflow-x: auto;
    -webkit-overflow-scrolling: touch;
    scrollbar-width: none;
  }
  .topbar::-webkit-scrollbar { display: none; }
  .topbar strong { letter-spacing: -0.01em; }
}

/* ── Hero block ─────────────────────────────────────────────────────────── */
/* Two-mode hero:
     • Phone + tablet  (<1024px): full-bleed image with dark gradient + text
       overlay anchored to bottom (cinematic, donor-friendly).
     • Desktop (≥1024px): editorial side-by-side — text left, image right.
   Mobile rules live further down under the @media (max-width: 1023px) block. */
.hero { position: relative; padding: 0 0 var(--s-7); overflow: hidden; background: var(--c-cream); }
@media (min-width: 1024px) { .hero { padding: var(--s-9) 0; } }
.hero-grid { display: grid; gap: var(--s-4); align-items: center; }
@media (min-width: 1024px) { .hero-grid { grid-template-columns: 1fr 1.1fr; gap: var(--s-7); } }
.hero h1 { font-size: var(--fs-hero); margin-bottom: var(--s-4); line-height: 1.05; letter-spacing: -.02em; }
.hero-sub { font-size: var(--fs-md); color: var(--c-ink-soft); max-width: 56ch; margin-bottom: var(--s-5); line-height: 1.55; }
.hero-cta { display: flex; flex-wrap: wrap; gap: var(--s-3); }
.hero-img { position: relative; border-radius: var(--r-lg); overflow: hidden; box-shadow: var(--shadow-md); aspect-ratio: 5/4; background: var(--c-saffron-soft); }
.hero-img img { width: 100%; height: 100%; object-fit: cover; }
/* Desktop hero — give the headline more comfortable breathing room. */
@media (min-width: 1024px) {
  .hero h1 { font-size: clamp(40px, 4vw, 60px); max-width: 14ch; }
  .hero-sub { font-size: clamp(15px, 1.05vw, 18px); }
}

/* ── .hero-extras: trust pills + ticker, always below the image ─────────── */
.hero-extras { margin-top: var(--s-5); display: flex; flex-direction: column; gap: var(--s-4); padding: 0 var(--s-4); }
@media (min-width: 1024px) {
  .hero-extras { margin-top: var(--s-6); padding: 0; }
}

/* ── Mobile + tablet (<1024px): OVERLAY the .hero-content on top of the
        .hero-img.

        Layout strategy:
          • The .hero-grid becomes a positioning context with a responsive
            height. .hero-img fills it (absolute, inset:0). .hero-content
            is absolute-positioned at the BOTTOM so the photo stays the
            visual anchor regardless of headline length.
          • A dark vignette gradient on the image gives the white text
            contrast without darkening the focal subject.
          • Typography tightens at narrow widths via clamp().
          • At ≥640px (large phones / portrait tablets) the height grows
            and the content padding loosens so it doesn't feel cramped.
        ─────────────────────────────────────────────────────────────────── */
@media (max-width: 1023px) {
  /* FULL-BLEED hero on mobile — escape the container's left/right padding
     so the image touches both viewport edges (matches the live site). */
  .hero > .container {
    padding-left: 0;
    padding-right: 0;
    max-width: none;
  }
  .hero-extras {
    padding-left: var(--s-4);
    padding-right: var(--s-4);
  }
  .hero-grid {
    position: relative;
    display: block;
    width: 100%;
    /* Height scales with viewport: dramatic on tablets, contained on phones.
       Avoid combining aspect-ratio with min-height — the browser computes
       width back from height and creates horizontal overflow on narrow
       viewports. Use a clamp()'d explicit height instead. */
    height: clamp(480px, 78vh, 760px);
    border-radius: 0;            /* edge-to-edge on mobile + tablet */
    overflow: hidden;
    box-shadow: none;
    background: #1a1815;
  }
  /* Larger phones / portrait tablets get more breathing room. */
  @media (min-width: 640px) {
    .hero-grid { height: clamp(520px, 70vh, 760px); }
  }
  @media (min-width: 768px) {
    .hero-grid { height: clamp(560px, 68vh, 800px); }
  }
  .hero-grid > .hero-img {
    position: absolute;
    inset: 0;
    aspect-ratio: auto;
    border-radius: 0;
    box-shadow: none;
    margin: 0;
    z-index: 1;
  }
  .hero-grid > .hero-img img {
    width: 100%;
    height: 100%;
    object-fit: cover;
    /* Default focal point — works for the homepage cow portrait where
       the face is in the right ~25% of the landscape frame. Each other
       page sets its own object-position via inline style on the <img>
       since each hero photo has a different subject placement. */
    object-position: 88% 55%;
  }

  /* Cinematic vignette: bottom-heavy, plus a subtle left-side darkening
     so the headline (which sits left-aligned on the lower-left) reads
     cleanly without darkening the cow's face on the right. */
  .hero-grid > .hero-img::after {
    content: "";
    position: absolute;
    inset: 0;
    background:
      /* Bottom-up dark fade for text legibility */
      linear-gradient(180deg,
        rgba(20, 18, 15, 0)   0%,
        rgba(20, 18, 15, 0)   35%,
        rgba(20, 18, 15, .55) 65%,
        rgba(20, 18, 15, .92) 100%),
      /* Subtle left-side darkening so left-aligned text reads cleanly
         even before the bottom gradient kicks in */
      linear-gradient(90deg,
        rgba(20, 18, 15, .35) 0%,
        rgba(20, 18, 15, .15) 35%,
        rgba(20, 18, 15, 0)   65%);
    pointer-events: none;
    z-index: 2;
  }
  .hero-grid > .hero-content {
    position: absolute;
    left: 0;
    right: 0;
    bottom: 0;
    z-index: 3;
    padding: var(--s-6) var(--s-5);
    color: #fff;
    max-width: 560px;
  }
  /* Tablet sizing: more padding + a bit wider text column. */
  @media (min-width: 640px) {
    .hero-grid > .hero-content {
      padding: var(--s-7) var(--s-6);
      max-width: 620px;
    }
  }
  @media (min-width: 768px) {
    .hero-grid > .hero-content {
      padding: var(--s-8) var(--s-7);
      max-width: 720px;
    }
  }
  .hero-grid > .hero-content .section-eyebrow {
    color: var(--c-saffron);
    text-shadow: 0 1px 4px rgba(0, 0, 0, .65);
    font-size: clamp(11px, 1.4vw, 13px);
    font-weight: 700;
    letter-spacing: .12em;
    margin-bottom: 10px;
    display: block;
  }
  /* Cinematic h1 — confident but doesn't fight the photo for attention. */
  .hero-grid > .hero-content h1 {
    color: #fff;
    text-shadow: 0 2px 12px rgba(0, 0, 0, .55);
    margin-bottom: var(--s-3);
    font-size: clamp(26px, 5.5vw, 48px);
    line-height: 1.1;
    letter-spacing: -.015em;
    font-weight: 600;
  }
  .hero-grid > .hero-content .hero-sub {
    color: rgba(255, 255, 255, .94);
    text-shadow: 0 1px 6px rgba(0, 0, 0, .55);
    font-size: clamp(14px, 1.8vw, 17px);
    line-height: 1.5;
    margin-bottom: var(--s-5);
    max-width: none;
  }
  .hero-grid > .hero-content .hero-cta {
    margin-top: 0;
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
  }
  .hero-grid > .hero-content .hero-cta .btn {
    flex: 0 1 auto;
    text-align: center;
    padding: 13px 22px;
    font-size: clamp(14px, 1.7vw, 16px);
    font-weight: 700;
    min-width: 140px;
  }
  /* On very narrow phones, let the buttons stretch full-row. */
  @media (max-width: 419px) {
    .hero-grid > .hero-content .hero-cta .btn { flex: 1 1 130px; }
  }
  /* On Galaxy Z Fold 5 folded (344px) and similar tiny screens, two
     buttons side-by-side leaves ~135px each — too cramped for a label
     like "See Donation Options". Stack vertically and let each button
     span the full content width for comfortable tap targets. */
  @media (max-width: 380px) {
    .hero-grid > .hero-content .hero-cta {
      flex-direction: column;
      align-items: stretch;
      gap: 8px;
    }
    .hero-grid > .hero-content .hero-cta .btn {
      flex: 1 1 100%;
      width: 100%;
      min-width: 0;
    }
  }
  /* Ghost button on dark background: solid white border + translucent fill
     so it visibly stands apart from the gradient at the bottom of the
     image. Without this, the button blends into the dark vignette. */
  .hero-grid > .hero-content .btn-ghost {
    color: #fff;
    border: 2px solid #fff;
    background: rgba(255, 255, 255, .12);
    backdrop-filter: blur(4px);
    -webkit-backdrop-filter: blur(4px);
  }
  .hero-grid > .hero-content .btn-ghost:hover {
    background: rgba(255, 255, 255, .22);
    border-color: #fff;
  }
}

/* ── Trust pills ────────────────────────────────────────────────────────── */
.trust-row { list-style: none; padding: 0; margin: var(--s-5) 0 0; display: flex; flex-wrap: wrap; gap: var(--s-3) var(--s-5); }
.trust-pill { display: inline-flex; align-items: center; gap: 6px; font-size: var(--fs-sm); font-weight: 500; color: var(--c-ink-soft); }
.trust-pill svg { width: 18px; height: 18px; color: var(--c-success); flex-shrink: 0; }

/* ── Stats band (counters) ──────────────────────────────────────────────── */
.stats { background: var(--c-success-soft); border-top: 1px solid var(--c-rule); border-bottom: 1px solid var(--c-rule); padding: var(--s-7) 0; }
.stats-grid { display: grid; grid-template-columns: 1fr; gap: var(--s-6); text-align: center; }
@media (min-width: 640px) { .stats-grid { grid-template-columns: repeat(3, 1fr); } }
.stat-num { font-family: var(--font-display); font-size: clamp(40px, 4vw + 1rem, 72px); font-weight: 700; color: var(--c-saffron-deep); line-height: 1; font-variant-numeric: tabular-nums; }
.stat-cap { font-size: var(--fs-sm); color: var(--c-ink-soft); margin-top: 6px; letter-spacing: .04em; text-transform: uppercase; font-weight: 500; }

/* ── Cards (generic) ────────────────────────────────────────────────────── */
.card-grid { display: grid; gap: var(--s-5); grid-template-columns: 1fr; }
@media (min-width: 640px) { .card-grid { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .card-grid { grid-template-columns: repeat(3, 1fr); } }
.card-grid-4 { display: grid; gap: var(--s-5); grid-template-columns: 1fr; }
@media (min-width: 640px) { .card-grid-4 { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .card-grid-4 { grid-template-columns: repeat(4, 1fr); } }
.card { background: var(--c-white); border-radius: var(--r-lg); overflow: hidden; box-shadow: var(--shadow-sm); display: flex; flex-direction: column; transition: transform var(--d-base) var(--ease), box-shadow var(--d-base) var(--ease); }
.card:hover { transform: translateY(-4px); box-shadow: var(--shadow-md); }
.card-img { aspect-ratio: 5/3; overflow: hidden; background: var(--c-saffron-soft); }
.card-img img { width: 100%; height: 100%; object-fit: cover; transition: transform var(--d-slow) var(--ease); }
.card:hover .card-img img { transform: scale(1.04); }
.card-body { padding: var(--s-5); display: flex; flex-direction: column; gap: var(--s-2); flex: 1; }
.card-title { font-family: var(--font-display); font-size: var(--fs-lg); font-weight: 600; color: var(--c-ink); margin: 0; }
.card-desc { font-size: var(--fs-sm); color: var(--c-ink-soft); flex: 1; margin: 0; }
.card .btn { margin-top: var(--s-3); }
.card-amount { font-family: var(--font-display); font-size: var(--fs-xl); font-weight: 700; color: var(--c-saffron-deep); }
.card-badge { position: absolute; top: var(--s-3); left: var(--s-3); background: var(--c-gold); color: var(--c-ink); padding: 4px 12px; border-radius: var(--r-pill); font-size: 11px; font-weight: 600; letter-spacing: .05em; text-transform: uppercase; }

/* ── Trust bar (compact 4-icon row) ─────────────────────────────────────── */
.trust-bar { display: grid; gap: var(--s-4); grid-template-columns: 1fr; padding: var(--s-6) 0; }
@media (min-width: 640px) { .trust-bar { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .trust-bar { grid-template-columns: repeat(4, 1fr); } }
.trust-block { display: flex; gap: var(--s-3); align-items: flex-start; }
.trust-block svg { width: 36px; height: 36px; color: var(--c-saffron); flex-shrink: 0; }
.trust-block h3 { font-size: var(--fs-md); margin: 0 0 4px; }
.trust-block p { font-size: var(--fs-sm); color: var(--c-ink-soft); margin: 0; }

/* ── Forms (contact) ────────────────────────────────────────────────────── */
.form { display: grid; gap: var(--s-4); }
.form label { font-size: var(--fs-sm); font-weight: 600; color: var(--c-ink); display: block; margin-bottom: 6px; }
.form .field { display: block; }
.form input[type=text], .form input[type=email], .form input[type=tel], .form input[type=number], .form select, .form textarea {
  width: 100%; padding: 12px 14px; border-radius: var(--r-md);
  border: 2px solid var(--c-rule); background: var(--c-white);
  font-size: var(--fs-base); color: var(--c-ink);
  min-height: 44px;
  transition: border-color var(--d-fast);
}
.form input:focus, .form select:focus, .form textarea:focus { outline: none; border-color: var(--c-saffron); }
.form textarea { resize: vertical; min-height: 120px; }

/* (P4-18) The legacy bottom-bar mobile CTA is retired; redesign.css §8
   (.dv-fab + .dv-mobar) is the single implementation and owns the <1024px
   body padding-bottom reservation. */

/* ── .p-card (mirrors portal.css for use on public pages) ───────────────────
   .p-card is the standard portal card primitive. Public pages (donate,
   contact, about) sometimes use it too — e.g. donate.html's "USA cheques
   by post" block — but those pages do NOT load portal.css, so without this
   rule the inner content sits flush against the card border (no padding).
   This duplicates just the visual padding/radius/shadow so the class works
   identically on every page. Keep in sync with portal.css line 100. */
.p-card { background: var(--c-white); border-radius: var(--r-lg); padding: var(--s-5); box-shadow: var(--shadow-sm); border: 1px solid var(--c-rule); }
.p-card-pad-sm { padding: var(--s-4); }

/* ── Footer ─────────────────────────────────────────────────────────────── */
.site-footer { background: var(--c-ink); color: var(--c-white); padding: var(--s-8) 0 var(--s-5); font-size: var(--fs-sm); }
.footer-grid { display: grid; gap: var(--s-6); grid-template-columns: 1fr; margin-bottom: var(--s-6); }
@media (min-width: 640px) { .footer-grid { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .footer-grid { grid-template-columns: 1.4fr repeat(3, 1fr); } }
.footer-grid h4 { color: var(--c-white); font-family: var(--font-display); font-size: var(--fs-md); margin-bottom: var(--s-3); font-weight: 600; }
.footer-grid a { display: block; color: rgba(255,255,255,.7); padding: 4px 0; }
.footer-grid a:hover { color: var(--c-saffron); text-decoration: none; }
.footer-grid p { color: rgba(255,255,255,.7); line-height: 1.6; }
.social-row { display: flex; gap: var(--s-3); margin-top: var(--s-3); }
.social-row a { display: inline-flex; width: 38px; height: 38px; align-items: center; justify-content: center; border-radius: 50%; background: rgba(255,255,255,.06); padding: 0; }
.social-row a:hover { background: var(--c-saffron); color: var(--c-ink); }
.social-row svg { width: 18px; height: 18px; }
.footer-bottom { border-top: 1px solid rgba(255,255,255,.1); padding-top: var(--s-4); display: flex; flex-wrap: wrap; gap: var(--s-3) var(--s-5); justify-content: space-between; font-size: var(--fs-xs); color: rgba(255,255,255,.5); }
.footer-bottom a { color: rgba(255,255,255,.5); }

/* ── Bank / payment block ───────────────────────────────────────────────── */
.bank-grid { display: grid; gap: var(--s-5); grid-template-columns: 1fr; }
@media (min-width: 768px) { .bank-grid { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .bank-grid { grid-template-columns: repeat(3, 1fr); } }
.bank-card { background: var(--c-white); border-radius: var(--r-lg); padding: var(--s-5); box-shadow: var(--shadow-sm); }
.bank-card h3 { font-family: var(--font-display); font-size: var(--fs-md); margin-bottom: var(--s-4); display: flex; align-items: center; gap: 8px; }
.bank-row { display: flex; justify-content: space-between; align-items: center; padding: 10px 0; border-bottom: 1px solid var(--c-rule); font-size: var(--fs-sm); gap: var(--s-3); }
.bank-row:last-child { border-bottom: 0; }
.bank-row .key { color: var(--c-ink-soft); flex-shrink: 0; }
.bank-row .val { font-family: var(--font-mono); color: var(--c-ink); font-weight: 600; word-break: break-all; text-align: right; }
.copy-btn { padding: 10px 16px; font-size: 12px; border-radius: var(--r-pill); background: var(--c-saffron-soft); color: var(--c-saffron-deep); font-weight: 600; flex-shrink: 0; min-height: 44px; min-width: 44px; cursor: pointer; border: 1px solid var(--c-saffron); }
.copy-btn:hover { background: var(--c-saffron); color: var(--c-ink); }
.copy-btn:disabled { opacity: .7; cursor: default; }

/* ── Tier card (donate page) ────────────────────────────────────────────── */
.tier-grid { display: grid; gap: var(--s-5); grid-template-columns: 1fr; }
@media (min-width: 640px) { .tier-grid { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 1024px) { .tier-grid { grid-template-columns: repeat(3, 1fr); } }
.tier-card { background: var(--c-white); border-radius: var(--r-lg); padding: var(--s-5); box-shadow: var(--shadow-sm); display: flex; flex-direction: column; gap: var(--s-3); position: relative; transition: transform var(--d-base) var(--ease), box-shadow var(--d-base) var(--ease); }
.tier-card:hover { transform: translateY(-4px); box-shadow: var(--shadow-md); }
.tier-card.is-featured { border: 2px solid var(--c-gold); }
.tier-card .tag { position: absolute; top: -10px; right: var(--s-4); background: var(--c-gold); color: var(--c-ink); padding: 4px 12px; border-radius: var(--r-pill); font-size: 11px; font-weight: 700; letter-spacing: .05em; text-transform: uppercase; }
.tier-amount { font-family: var(--font-display); font-size: var(--fs-h3); color: var(--c-saffron-deep); font-weight: 700; }
.tier-frequency { font-size: var(--fs-xs); color: var(--c-muted); text-transform: uppercase; letter-spacing: .08em; font-weight: 600; }
.tier-card h3 { font-family: var(--font-display); font-size: var(--fs-md); margin: 0; }
.tier-card p { font-size: var(--fs-sm); color: var(--c-ink-soft); flex: 1; margin: 0; }

/* ── Cow card (adoption) ────────────────────────────────────────────────── */
.cow-grid { display: grid; gap: var(--s-4); grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); }
.cow-card { background: var(--c-white); border-radius: var(--r-md); overflow: hidden; box-shadow: var(--shadow-sm); transition: transform var(--d-base) var(--ease); display: flex; flex-direction: column; }
.cow-card:hover { transform: translateY(-3px); box-shadow: var(--shadow-md); }
.cow-card .img { aspect-ratio: 4/3; overflow: hidden; background: var(--c-saffron-soft); }
.cow-card .img img { width: 100%; height: 100%; object-fit: cover; transition: transform .4s var(--ease); }
.cow-card:hover .img img { transform: scale(1.05); }
.cow-card .body { padding: var(--s-3); display: flex; flex-direction: column; gap: 6px; flex: 1; }
.cow-card .id { font-family: var(--font-display); font-size: var(--fs-md); font-weight: 600; color: var(--c-ink); }
.cow-card .price { font-size: var(--fs-sm); color: var(--c-saffron-deep); font-weight: 600; }
.cow-card .btn { font-size: 12px; padding: 8px 14px; min-height: 32px; margin-top: 4px; }

/* ── Patron / tier (membership) ─────────────────────────────────────────── */
.member-tier { background: var(--c-white); border-radius: var(--r-lg); padding: var(--s-6); box-shadow: var(--shadow-sm); display: flex; flex-direction: column; gap: var(--s-3); position: relative; border-top: 4px solid var(--c-rule); }
.member-tier.silver  { border-top-color: #B0B0B0; }
.member-tier.gold    { border-top-color: var(--c-gold); }
.member-tier.premium { border-top-color: var(--c-saffron); }
.member-tier h3 { font-family: var(--font-display); font-size: var(--fs-h3); margin: 0; }
.member-tier .sanskrit { font-family: var(--font-accent); color: var(--c-ink-soft); font-style: italic; font-size: var(--fs-sm); }
.member-tier .price-row { display: flex; align-items: baseline; gap: var(--s-3); margin: var(--s-3) 0; }
.member-tier .price-row .inr { font-family: var(--font-display); font-size: var(--fs-h2); font-weight: 700; color: var(--c-saffron-deep); }
.member-tier .price-row .usd { font-size: var(--fs-sm); color: var(--c-ink-soft); }
.member-tier ul { list-style: none; padding: 0; margin: var(--s-3) 0; display: flex; flex-direction: column; gap: 8px; }
.member-tier li { display: flex; gap: 8px; font-size: var(--fs-sm); color: var(--c-ink-soft); }

.patron-grid { display: grid; gap: var(--s-4); grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); align-items: center; }
.patron-grid img { width: 100%; height: 80px; object-fit: contain; filter: grayscale(.2); transition: filter var(--d-base); background: var(--c-white); border-radius: var(--r-md); padding: var(--s-3); border: 1px solid var(--c-rule); }
.patron-grid img:hover { filter: none; }

/* ── Tiered patrons (Premium / Gold / Silver) ─────────────────────────── */
.patron-tier-block { background: var(--c-white); border: 1px solid var(--c-rule); border-radius: var(--r-lg); padding: var(--s-5) var(--s-4); }
@media (min-width: 768px) { .patron-tier-block { padding: var(--s-6); } }
.patron-tier-block[data-patron-tier="premium"] { border-top: 4px solid var(--c-gold); }
.patron-tier-block[data-patron-tier="gold"]    { border-top: 4px solid var(--c-saffron); }
.patron-tier-block[data-patron-tier="silver"]  { border-top: 4px solid #B0B6BD; }
.patron-tier-head { text-align: center; margin-bottom: var(--s-5); }
.patron-tier-eyebrow {
  display: inline-block;
  font-family: var(--font-display);
  font-size: 11px;
  font-weight: 700;
  letter-spacing: .15em;
  text-transform: uppercase;
  color: var(--c-saffron-deep);
  margin-bottom: 6px;
}
.patron-tier-title {
  font-family: var(--font-accent);
  font-size: clamp(22px, 3vw, 32px);
  font-weight: 500;
  font-style: italic;
  color: var(--c-ink);
  margin: 0;
  letter-spacing: .005em;
}
.patron-card-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  gap: var(--s-4) var(--s-3);
  align-items: start;
}
@media (min-width: 480px) { .patron-card-grid { grid-template-columns: repeat(3, 1fr); } }
@media (min-width: 768px) { .patron-card-grid { grid-template-columns: repeat(4, 1fr); gap: var(--s-5) var(--s-4); } }
.patron-card { text-align: center; display: flex; flex-direction: column; align-items: center; }
.patron-photo {
  width: clamp(80px, 22vw, 120px);
  height: clamp(80px, 22vw, 120px);
  border-radius: 50%;
  overflow: hidden;
  background: var(--c-saffron-soft);
  margin-bottom: var(--s-3);
  border: 2px solid var(--c-rule);
}
.patron-photo img { width: 100%; height: 100%; object-fit: cover; }
.patron-name {
  font-family: var(--font-display);
  font-size: var(--fs-sm);
  font-weight: 600;
  color: var(--c-saffron-deep);
  letter-spacing: .04em;
  line-height: 1.25;
  margin-bottom: 2px;
}
.patron-place { font-size: 12px; color: var(--c-ink-soft); line-height: 1.35; }
.patron-note  { font-size: 11px; color: var(--c-ink-soft); margin-top: 4px; line-height: 1.4; }
.patron-name-list {
  list-style: none;
  padding: 0;
  margin: 0;
  display: grid;
  grid-template-columns: 1fr;
  gap: var(--s-2);
  max-width: 720px;
  margin-inline: auto;
  font-size: var(--fs-sm);
}
@media (min-width: 640px) { .patron-name-list { grid-template-columns: 1fr 1fr; } }
.patron-name-list li {
  background: var(--c-cream);
  padding: 10px 14px;
  border-radius: var(--r-sm);
  text-align: center;
  color: var(--c-ink);
}

/* ── Testimonial card ───────────────────────────────────────────────────── */
.testi { background: var(--c-white); border-radius: var(--r-lg); padding: var(--s-5); box-shadow: var(--shadow-sm); display: flex; flex-direction: column; gap: var(--s-3); }
.testi blockquote { font-family: var(--font-accent); font-size: var(--fs-md); line-height: 1.55; margin: 0; color: var(--c-ink); font-style: italic; padding-left: var(--s-3); border-left: 3px solid var(--c-gold); }
.testi-author { display: flex; align-items: center; gap: var(--s-3); margin-top: var(--s-2); }
.testi-author img { width: 44px; height: 44px; border-radius: 50%; object-fit: cover; flex-shrink: 0; }
.testi-author .who { font-weight: 600; font-size: var(--fs-sm); color: var(--c-ink); }
.testi-author .who small { display: block; color: var(--c-ink-soft); font-weight: 400; font-size: 12px; }
/* Handle odd-count testimonials gracefully so we don't leave empty cells in
   the grid. With 7 testimonials in a 3-col layout we get one orphan in the
   final row → center it. In a 2-col tablet layout we also center the orphan
   instead of leaving an empty slot beside it. */
@media (min-width: 1024px) {
  .card-grid > .testi:last-child:nth-child(3n+1) { grid-column: 2 / 3; }
}
@media (min-width: 640px) and (max-width: 1023px) {
  .card-grid > .testi:last-child:nth-child(odd) {
    grid-column: 1 / -1;
    justify-self: center;
    max-width: calc((100% - var(--s-5)) / 2);
  }
}

/* ── Final CTA ──────────────────────────────────────────────────────────── */
.final-cta { background: linear-gradient(135deg, var(--c-saffron-deep) 0%, var(--c-saffron) 100%); color: var(--c-ink); text-align: center; padding: var(--s-8) 0; }
.final-cta h2 { color: var(--c-ink); max-width: 760px; margin: 0 auto var(--s-4); }
.final-cta .btn { background: var(--c-white); color: var(--c-ink); border-color: var(--c-white); }
.final-cta .btn:hover { background: var(--c-ink); color: var(--c-white); }
.final-cta-note { margin-top: var(--s-4); font-size: var(--fs-sm); opacity: .85; }

/* ── Breadcrumb ─────────────────────────────────────────────────────────── */
.breadcrumb { font-size: var(--fs-sm); color: var(--c-ink-soft); padding: var(--s-3) 0; }
.breadcrumb a { color: var(--c-ink-soft); }
.breadcrumb a:hover { color: var(--c-saffron-deep); }
.breadcrumb [aria-current=page] { color: var(--c-ink); font-weight: 600; }
.breadcrumb span { margin: 0 8px; }

/* ── Print ──────────────────────────────────────────────────────────────── */
@media print {
  .site-header, .dv-mobar, .dv-fab, .final-cta, .nav-toggle { display: none !important; }
  body { background: white; color: black; padding: 0; }
  a::after { content: " (" attr(href) ")"; font-size: 11px; color: #555; }
  .card, .tier-card, .bank-card { box-shadow: none; border: 1px solid #ccc; }
}

/* ── Forced colours (Windows high-contrast) ─────────────────────────────── */
@media (forced-colors: active) {
  .btn-primary, .btn-ghost { border: 1px solid CanvasText; }
  .card, .tier-card, .bank-card { border: 1px solid CanvasText; }
}

/* ============================================================================
   ── Error pages (404 / 500 / offline) ──────────────────────────────────────
   Shared layout for `/404.html`, `/500.html`, `/offline.html`. Centred hero,
   illustrated mark, headline, sub, recovery actions, helpful links grid.
   ========================================================================= */
.err-wrap {
  flex: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--s-7) var(--s-4);
  background: linear-gradient(180deg, var(--c-cream) 0%, var(--c-saffron-soft) 100%);
}
.err-card {
  width: 100%;
  max-width: 720px;
  text-align: center;
}
.err-mark {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: clamp(180px, 38vw, 260px);
  aspect-ratio: 1 / 1;
  margin: 0 auto var(--s-5);
}
.err-mark svg {
  width: 100%;
  height: auto;
  filter: drop-shadow(0 16px 28px rgba(35,34,32,.10));
}
.err-mark .err-code {
  position: absolute;
  inset: auto 0 -10px 0;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(72px, 12vw, 128px);
  line-height: 1;
  color: var(--c-saffron-deep);
  letter-spacing: -.02em;
  text-shadow: 0 6px 0 rgba(255,255,255,.65);
  pointer-events: none;
}
.err-eyebrow {
  display: inline-block;
  font-family: var(--font-body);
  font-size: var(--fs-sm);
  font-weight: 600;
  letter-spacing: .14em;
  text-transform: uppercase;
  color: var(--c-saffron-deep);
  margin: 0 0 var(--s-3);
  padding: 6px 14px;
  border-radius: var(--r-pill);
  background: rgba(234,175,0,.14);
}
.err-card h1 {
  font-family: var(--font-display);
  font-size: clamp(28px, 4vw, 44px);
  margin: 0 0 var(--s-3);
}
.err-lede {
  font-size: var(--fs-md);
  color: var(--c-ink-soft);
  max-width: 52ch;
  margin: 0 auto var(--s-6);
}
.err-actions {
  display: flex;
  gap: var(--s-3);
  justify-content: center;
  flex-wrap: wrap;
  margin-bottom: var(--s-7);
}
.err-helpful {
  text-align: left;
  background: var(--c-white);
  border: 1px solid var(--c-rule);
  border-radius: var(--r-lg);
  padding: var(--s-5);
  box-shadow: var(--shadow-sm);
}
.err-helpful h2 {
  font-size: var(--fs-md);
  margin: 0 0 var(--s-3);
  color: var(--c-ink);
  text-align: center;
}
.err-helpful ul {
  list-style: none;
  padding: 0;
  margin: 0;
  display: grid;
  gap: var(--s-2);
  grid-template-columns: 1fr;
}
@media (min-width: 560px) {
  .err-helpful ul { grid-template-columns: 1fr 1fr; }
}
.err-helpful li a {
  display: flex;
  align-items: center;
  gap: var(--s-2);
  padding: 10px 12px;
  border-radius: var(--r-md);
  color: var(--c-ink);
  font-weight: 500;
  font-size: var(--fs-sm);
  background: var(--c-cream);
  border: 1px solid transparent;
  transition: background var(--d-fast), border-color var(--d-fast), transform var(--d-fast);
}
.err-helpful li a:hover,
.err-helpful li a:focus-visible {
  background: var(--c-saffron-soft);
  border-color: var(--c-saffron);
  text-decoration: none;
  transform: translateY(-1px);
}
.err-helpful li a::before {
  content: "→";
  font-weight: 700;
  color: var(--c-saffron-deep);
}
.err-meta {
  margin-top: var(--s-5);
  font-size: var(--fs-xs);
  color: var(--c-ink-soft);
}
.err-meta code {
  background: var(--c-white);
  padding: 2px 8px;
  border-radius: 4px;
  border: 1px solid var(--c-rule);
  font-family: var(--font-mono);
  font-size: 12px;
  color: var(--c-ink);
}
/* Subtle bobbing motion on the mark — disabled under prefers-reduced-motion */
@keyframes errFloat {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-6px); }
}
.err-mark svg { animation: errFloat 4.5s ease-in-out infinite; }
@media (prefers-reduced-motion: reduce) {
  .err-mark svg { animation: none; }
}

/* WebP <picture> wrappers must not affect layout */
picture{display:contents}

/* ============================================================================
   ── REFINEMENTS · 2026-06 ──────────────────────────────────────────────────
   Additive polish layer, loaded site-wide (site.css is on every page). Changes
   NO markup and NO existing rule. Every rule is either progressive-enhancement
   (silently ignored where unsupported) or a coarse-pointer / focus refinement,
   so nothing here can regress an existing layout.
   OODO Dev Team | Dakshin Vrindavan Trust
   ========================================================================= */

/* In-page anchor jumps (#bank, #adopt, #main, TOC links…) land clear of the
   sticky header instead of tucking the target heading beneath it. Legal pages
   set their own larger value on the TOC, which still wins by specificity. */
:target { scroll-margin-top: calc(var(--header-h) + 1rem); }

/* Balanced, orphan-free typography. `text-wrap` is ignored by browsers that
   don't support it, so this is purely additive: headings balance across lines
   and body copy avoids a single stranded last word. */
h1, h2, h3 { text-wrap: balance; }
p, li, .section-lede, .hero-sub, blockquote { text-wrap: pretty; }

/* Brand-tinted text selection on pages outside the .dv-redesign scope (donor
   portal, legal, error). redesign.css keeps its own selection tint where set,
   and wins by specificity. */
::selection { background: rgba(234, 175, 0, .26); color: var(--c-ink); }

/* Comfortable touch targets on the handful of compact controls — applied on
   touch devices only, so pointer/desktop density is untouched
   (WCAG 2.5.8 Target Size). Covers public .btn-sm + cow cards AND the donor
   portal's .btn-sm, since site.css loads there too.
   P3-04 extends the SAME block (never a second one) to the redesigned
   surfaces that still sat at ~32 px on touch: portal filter tabs, table
   action buttons, table-toolbar controls, and any adopt CTA rendered
   inside the redesigned cow grid. */
@media (pointer: coarse) {
  .btn-sm,
  .cow-card .btn,
  .dv-cow-grid article .btn,
  .dv-cow-grid article a,
  .tabs button,
  .p-table .actions .btn,
  .table-wrap .toolbar .btn,
  .table-wrap .toolbar button { min-height: 44px; }
  /* Icon-only controls need width too, not just height. */
  .p-table .actions .btn { min-width: 44px; }
}

/* ── P3-05 · Hindi display typography ─────────────────────────────────────
   Cormorant Garamond / Marcellus / Lora carry no Devanagari glyphs, so in
   Hindi the display layer silently fell back to inconsistent system serifs.
   When the runtime language is Hindi (portal-i18n.js sets <html lang="hi">
   and injects the Tiro Devanagari Hindi stylesheet — the font downloads
   ONLY then), these rules put the dedicated face at the FRONT of every
   display stack. English pages never match the selector, so English
   rendering and English users' font payload are untouched.
   The [style*=…] !important overrides are required because the redesign
   carries its serif stacks as inline styles — !important is the only
   cascade layer that outranks a style attribute. */
html[lang="hi"] {
  --font-display: "Tiro Devanagari Hindi", "Oswald", "Trebuchet MS", "Arial Narrow", sans-serif;
  --font-accent:  "Tiro Devanagari Hindi", "Lora", "Georgia", serif;
  --dv-serif-display: "Tiro Devanagari Hindi", "Cormorant Garamond", Georgia, serif;
  --dv-serif-title:   "Tiro Devanagari Hindi", "Marcellus", serif;
  --dv-serif-quote:   "Tiro Devanagari Hindi", "Lora", Georgia, serif;
}
html[lang="hi"] [style*="Cormorant Garamond"],
html[lang="hi"] [style*="Marcellus"],
html[lang="hi"] [style*="'Lora'"] {
  font-family: "Tiro Devanagari Hindi", Georgia, serif !important;
}
/* M1 (final audit): portal PAGE-SCOPED <style> blocks set literal
   'Marcellus'/'Cormorant Garamond' stacks in stylesheet rules, which neither
   the variable overrides above nor the [style*=…] attribute selectors reach.
   Element-level !important closes that last gap — heading levels and the
   known display-value classes. Gated on lang="hi", so English rendering is
   untouched; Latin inside Hindi headings uses Tiro's own Latin, consistent
   with the rest of the Hindi experience. */
html[lang="hi"] h1,
html[lang="hi"] h2,
html[lang="hi"] h3,
html[lang="hi"] h4,
html[lang="hi"] .stat-tile .value,
html[lang="hi"] .dash-hero__title,
html[lang="hi"] .dash-hero__ask-headline {
  font-family: "Tiro Devanagari Hindi", "Marcellus", "Cormorant Garamond", Georgia, serif !important;
}
