/*
Theme Name: Northern WV AHEC
Theme URI: https://nwvahec.org
Author: Garland Technology Consulting
Author URI: https://garlandtechconsulting.com
Description: Custom theme for the Northern West Virginia Area Health Education Center. Navy and gold brand identity with accessible, responsive design for healthcare workforce development in 21 WV counties.
Version: 1.1.15
Requires at least: 6.0
Tested up to: 6.7
Requires PHP: 7.4
License: GNU General Public License v2 or later
License URI: https://www.gnu.org/licenses/gpl-2.0.html
Text Domain: nwvahec
Tags: custom-logo, custom-menu, full-width-template, accessibility-ready, education
*/

@import url('https://fonts.googleapis.com/css2?family=Source+Sans+3:wght@200..900&family=Source+Serif+4:wght@200..900&display=swap');

/* ── tokens.css ─────────────────────────────────────── */
/* ═══════════════════════════════════════════════════════════════════════
   NWVAHEC — Design tokens
   Navy and gold are sampled directly from the official West Virginia AHEC
   logo (Logos/AHEC Logo 2 Lines Centered Northern WVAHEC PNG.png), per
   spec WEB-UI-001, not approximated.

     navy  #1B3665   67.7% of the logo's opaque pixels
     gold  #EFB41C   28.7% of the logo's opaque pixels

   CONTRAST RULE — the one thing to preserve when editing:
   Brand gold on a light ground is 1.87:1. It is NEVER text and NEVER a
   focus ring on cream or white. On light grounds gold appears only as a
   rule, a border, or a fill carrying navy text (6.36:1). Where a gold
   *tone* is needed for text on light, use --gold-deep (5.68:1 on cream).
   ═══════════════════════════════════════════════════════════════════════ */
:root {
  /* ── Brand ─────────────────────────────────────────────────────────── */
  --navy:        #1B3665;
  --gold:        #EFB41C;

  /* ── Navy scale ────────────────────────────────────────────────────── */
  --navy-900:    #0D1A30;   /* deepest band, footer                       */
  --navy-800:    #112240;   /* deep band                                  */
  --navy-700:    #162B50;   /* standard navy band                         */
  --navy-600:    #204179;   /* hover state on navy surfaces               */
  --navy-300:    #93A6C7;   /* muted text on ANY navy surface.
                               4.8:1 on --navy, 5.7:1 on --navy-700,
                               7.1:1 on --navy-900. Must clear 4.5 against
                               --navy (the lightest navy it ever sits on). */
  --navy-100:    #E7EDF9;   /* tint band, map "not served" fill           */
  --navy-050:    #F3F6FC;   /* lightest tint band                         */

  /* ── Gold scale ────────────────────────────────────────────────────── */
  --gold-deep:   #7E5D09;   /* the only gold that may carry text on a light
                               surface. Cleared against every light ground the
                               site actually uses: 6.07:1 white, 5.68 cream,
                               5.61 hovered row, 5.31 gold-soft. The earlier
                               #8F6A0A sat at 4.34:1 on gold-soft — under AA. */
  --gold-700:    #B5860D;   /* non-text accents on light (3.29:1)         */
  --gold-300:    #F6D77C;   /* light gold tint, surfaces only              */
  --gold-soft:   #FBEFD0;   /* gold wash surface                          */

  /* ── AHEC region fills ─────────────────────────────────────────────
     Map shapes only, never text and never a border on a control. They
     echo the palette of the statewide AHEC map so the two read as the
     same picture, and every shape carries a dark outline of its own. */
  --map-central:      #F2CB4E;
  --map-eastern:      #E98A72;
  --map-southern:     #8FC6DE;
  --map-southeastern: #E5D8BC;
  --map-none:         #FFFFFF;
  --map-office:       #B5322C;   /* centre-office markers                */

  /* ── Neutrals ──────────────────────────────────────────────────────── */
  --cream:       #FAF7F2;   /* page ground                                */
  --cream-200:   #EFE9DF;   /* decorative hairline on cards (non-essential) */
  --border-strong: #6B7C9C; /* control boundaries — 3.9:1 cream, 4.2:1 white
                               Required by WCAG 1.4.11 for inputs, selects
                               and the map's county outlines. The decorative
                               --cream-200 hairline is NOT sufficient there.  */
  --white:       #FFFFFF;
  --ink:         #16181D;   /* body text — 16.6:1 on cream                */
  --ink-muted:   #4E5563;   /* secondary text — 7.0:1 on cream            */

  /* ── Feedback (no color-only signalling; always paired with text) ──── */
  --error:       #A4262C;
  --error-bg:    #FDF3F3;
  --success:     #1E5B34;
  --success-bg:  #F0F7F2;

  /* ── Radius — restrained. Nothing is a pill. ───────────────────────── */
  --r-sm:  4px;
  --r-md:  8px;    /* buttons, inputs                                     */
  --r-lg:  12px;   /* cards, photo crops                                  */

  /* ── Elevation — warm-tinted, never neutral grey ───────────────────── */
  --shadow-sm: 0 1px 2px rgba(27,54,101,.06), 0 2px 6px rgba(27,54,101,.05);
  --shadow-md: 0 2px 4px rgba(27,54,101,.07), 0 8px 20px rgba(27,54,101,.08);
  --shadow-lg: 0 4px 8px rgba(27,54,101,.08), 0 18px 40px rgba(27,54,101,.12);

  /* ── Spacing ───────────────────────────────────────────────────────── */
  --s-1: .25rem;  --s-2: .5rem;   --s-3: .75rem;  --s-4: 1rem;
  --s-5: 1.5rem;  --s-6: 2rem;    --s-7: 3rem;    --s-8: 4rem;
  --s-9: 6rem;

  /* ── Type ──────────────────────────────────────────────────────────── */
  --font-sans:  'Source Sans 3', ui-sans-serif, system-ui, -apple-system,
                'Segoe UI', Roboto, Helvetica, Arial, sans-serif;
  --font-serif: 'Source Serif 4', ui-serif, Georgia, Cambria,
                'Times New Roman', serif;

  --t--1: clamp(.8125rem, .79rem + .11vw, .875rem);
  --t-0:  clamp(1.0625rem, 1.03rem + .16vw, 1.125rem);
  --t-1:  clamp(1.1875rem, 1.14rem + .24vw, 1.3125rem);
  --t-2:  clamp(1.375rem, 1.29rem + .42vw, 1.625rem);
  --t-3:  clamp(1.625rem, 1.47rem + .77vw, 2.125rem);
  --t-4:  clamp(2rem, 1.72rem + 1.4vw, 2.875rem);
  --t-5:  clamp(2.375rem, 1.9rem + 2.37vw, 3.75rem);

  /* Section headings. One notch above --t-4: with the small uppercase
     eyebrow labels gone, the heading itself has to open the section. */
  --t-section: clamp(2.125rem, 1.79rem + 1.68vw, 3.125rem);

  /* ── Layout ────────────────────────────────────────────────────────── */
  --container: 1200px;
  --measure:   68ch;
  --header-h:  84px;

  /* ── Geometry ──────────────────────────────────────────────────────────
     The logo's two bars are parallelograms. Their leading edges were measured
     off the artwork at 31.9deg and 31.6deg from vertical; every angled element
     on the site is cut to that same slant so the motif reads as the mark's,
     not as decoration. --tab-ratio is tan(32deg), which keeps a corner tab's
     hypotenuse on the same angle at any size.                                */
  --slant:     -32deg;
  --tab-ratio: 0.625;

  /* ── Motion ────────────────────────────────────────────────────────── */
  --ease: cubic-bezier(.2,.6,.3,1);
  --dur:  .18s;
}


/* ── fonts.css ─────────────────────────────────────── */
/* ─────────────────────────────────────────────────────────────
   Self-hosted variable fonts. No third-party requests are made.
   Source Sans 3 & Source Serif 4 — SIL Open Font License 1.1
   Both files carry a wght axis of 200–900, so every weight the
   site uses is served from these four files.
   ───────────────────────────────────────────────────────────── */


/* ── site.css ─────────────────────────────────────── */

/* ═══════════════════════════════════════════════════════════════════════
   1. RESET
   ═══════════════════════════════════════════════════════════════════════ */
*, *::before, *::after { box-sizing: border-box; }
* { margin: 0; }
html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) { html { scroll-behavior: auto; } }

body {
  font-family: var(--font-sans);
  font-size: var(--t-0);
  line-height: 1.65;
  color: var(--ink);
  background: var(--cream);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  overflow-wrap: break-word;
}
img, picture, svg, video { display: block; max-width: 100%; }
/* A <picture> is only a wrapper, and an img inside one sizes itself against
   it. Anything that crops an image gives its <picture> the full box, or the
   img's height:100% resolves against auto and object-fit has nothing to fit
   into. */
.hero__media picture,
.card__media picture,
.slide__media picture,
.split__frame picture,
.staff__photo picture { width: 100%; height: 100%; }
img { height: auto; }
input, button, textarea, select { font: inherit; color: inherit; }
ul, ol { padding: 0; }

/* ═══════════════════════════════════════════════════════════════════════
   2. TYPOGRAPHY
   ═══════════════════════════════════════════════════════════════════════ */
h1, h2, h3, h4 {
  font-family: var(--font-serif);
  font-weight: 600;
  line-height: 1.15;
  letter-spacing: -.012em;
  color: var(--navy);
  text-wrap: balance;
  font-optical-sizing: auto;
}
h1 { font-size: var(--t-5); }
h2 { font-size: var(--t-4); }
h3 { font-size: var(--t-2); }
h4 { font-size: var(--t-1); }
h5 { font-family: var(--font-sans); font-size: var(--t-0); font-weight: 700; color: var(--navy); }

p, li { text-wrap: pretty; }
p { max-width: var(--measure); }

a { color: var(--navy); text-decoration-thickness: 1px; text-underline-offset: .2em; }
a:hover { color: var(--navy-600); text-decoration-thickness: 2px; }

strong { font-weight: 700; }
small  { font-size: var(--t--1); }

.lede { font-size: var(--t-1); line-height: 1.55; color: var(--ink-muted); max-width: 60ch; }
/* Section headings carry their own weight now that the small uppercase
   eyebrow label above them has been removed sitewide. A section is told
   apart from the one before it by three things instead: the band's ground
   colour, the slanted gold marker below, and the size of the heading. */
.band__head > h2:first-child,
.panel > h2:first-child { font-size: var(--t-section); }

/* No marker above the heading: the band's ground colour and the heading's
   own size separate one section from the next. Gold is kept for buttons,
   the KPI flag, and markers that appear on hover. */

/* ═══════════════════════════════════════════════════════════════════════
   3. SKIP LINK  (WEB-A11Y-001)
   ═══════════════════════════════════════════════════════════════════════ */
.skip-link {
  position: absolute; top: 0; left: var(--s-4);
  transform: translateY(-120%);
  z-index: 200;
  background: var(--navy); color: var(--white);
  padding: var(--s-3) var(--s-5);
  border-radius: 0 0 var(--r-md) var(--r-md);
  font-weight: 600; text-decoration: none;
  transition: transform var(--dur) var(--ease);
}
.skip-link:focus-visible { transform: translateY(0); color: var(--white); }

/* ═══════════════════════════════════════════════════════════════════════
   4. FOCUS  —  never removed, always >= 3:1 against its own ground
   ═══════════════════════════════════════════════════════════════════════ */
:focus { outline: none; }
:focus-visible {
  outline: 3px solid var(--navy);
  outline-offset: 2px;
  border-radius: var(--r-sm);
}
.band--navy :focus-visible,
.site-footer :focus-visible,
.btn--primary:focus-visible,
.btn--gold:focus-visible { outline-color: var(--gold); }

/* ═══════════════════════════════════════════════════════════════════════
   5. LAYOUT — container + scroll-band sections
   ═══════════════════════════════════════════════════════════════════════ */
.container { width: min(100% - 2.5rem, var(--container)); margin-inline: auto; }
.container--narrow { width: min(100% - 2.5rem, 820px); margin-inline: auto; }

.band { padding-block: clamp(var(--s-6), 4vw, var(--s-8)); }
.band--cream { background: var(--cream); }
.band--white { background: var(--white); }
.band--tint  { background: var(--navy-050); }
.band--gold  { background: var(--gold-soft); }

.band--navy, .band--navy-deep {
  background: var(--navy-700);
  color: var(--white);
  border-top: 3px solid var(--gold);
  border-bottom: 3px solid var(--gold);
}
.band--navy-deep { background: var(--navy-900); }
.band--navy h1, .band--navy h2, .band--navy h3, .band--navy h4,
.band--navy-deep h1, .band--navy-deep h2, .band--navy-deep h3 { color: var(--gold); }
.band--navy .lede, .band--navy-deep .lede { color: var(--navy-300); }
.band--navy a, .band--navy-deep a { color: var(--white); }
.band--navy a:hover, .band--navy-deep a:hover { color: var(--gold); }

/* consecutive navy bands must not double up their gold rules */
.band--navy + .band--navy, .band--navy + .band--navy-deep,
.band--navy-deep + .band--navy { border-top: 0; }

.band__head { margin-bottom: var(--s-5); max-width: var(--measure); }
.band__head--center { margin-inline: auto; text-align: center; }
.band__head--center > * { margin-inline: auto; }
.band__head > * + * { margin-top: var(--s-3); }

.stack > * + * { margin-top: var(--s-4); }
.stack-lg > * + * { margin-top: var(--s-6); }

/* ═══════════════════════════════════════════════════════════════════════
   6. BUTTONS  —  rectangular, 8px radius. No pills anywhere.
   ═══════════════════════════════════════════════════════════════════════ */
.btn {
  display: inline-flex; align-items: center; gap: var(--s-2);
  min-height: 48px;                        /* WEB-UI-005 touch target */
  padding: var(--s-3) var(--s-5);
  border: 2px solid transparent;
  border-radius: var(--r-md);
  font-weight: 600; font-size: var(--t-0);
  text-decoration: none; cursor: pointer;
  transition: background-color var(--dur) var(--ease),
              border-color var(--dur) var(--ease),
              color var(--dur) var(--ease),
              transform var(--dur) var(--ease);
}
.btn:hover { transform: translateY(-1px); }
.btn:active { transform: translateY(0); }
@media (prefers-reduced-motion: reduce) { .btn, .btn:hover { transform: none; } }

.btn--primary { background: var(--navy); color: var(--white); }
.btn--primary:hover { background: var(--navy-600); color: var(--white); }

.btn--gold { background: var(--gold); color: var(--navy); }
.btn--gold:hover { background: var(--gold-300); color: var(--navy); }

.btn--ghost { background: transparent; color: var(--navy); border-color: var(--border-strong); }
.btn--ghost:hover { background: var(--navy-050); border-color: var(--navy); color: var(--navy); }

/* A gold button keeps navy text wherever it lands — the band's link colour
   must not win here, or the label drops to 1.87:1 on gold. */
.band--navy .btn--gold, .band--navy-deep .btn--gold,
.hero .btn--gold, .page-head .btn--gold { color: var(--navy); }
.band--navy .btn--gold:hover, .band--navy-deep .btn--gold:hover,
.hero .btn--gold:hover, .page-head .btn--gold:hover { color: var(--navy); }
.band--navy .btn--ghost, .band--navy-deep .btn--ghost,
.hero .btn--ghost, .page-head .btn--ghost { color: var(--white); border-color: var(--navy-300); }
.band--navy .btn--ghost:hover, .band--navy-deep .btn--ghost:hover,
.hero .btn--ghost:hover, .page-head .btn--ghost:hover {
  background: var(--navy-600); border-color: var(--gold); color: var(--white);
}

/* Arrow is decorative; the link text always stands alone (WEB-A11Y-008) */
.btn__arrow { transition: transform var(--dur) var(--ease); }
.btn:hover .btn__arrow { transform: translateX(3px); }
@media (prefers-reduced-motion: reduce) { .btn:hover .btn__arrow { transform: none; } }

.btn--sm { min-height: 40px; padding: var(--s-2) var(--s-4); font-size: var(--t--1); }
.btn-row { display: flex; flex-wrap: wrap; gap: var(--s-3); }

/* ═══════════════════════════════════════════════════════════════════════
   7. HEADER  —  logo left, nav optically centred, action right
   ═══════════════════════════════════════════════════════════════════════ */
.site-header {
  position: sticky; top: 0; z-index: 100;
  background: var(--white);
  border-bottom: 2px solid var(--gold);
  box-shadow: var(--shadow-sm);
}
.site-header__inner {
  display: grid;
  grid-template-columns: auto 1fr auto;
  align-items: center;
  gap: var(--s-5);
  min-height: var(--header-h);
  padding-block: var(--s-3);
}
.site-header__logo { display: flex; align-items: center; text-decoration: none; }
.site-header__logo img { width: 190px; height: auto; }
.site-header__logo:focus-visible { outline-offset: 4px; }

.site-header__actions { display: flex; align-items: center; gap: var(--s-3); }

/* ── Primary nav ──────────────────────────────────────────────────────── */
.nav { justify-self: center; }
.nav__list { display: flex; align-items: center; gap: var(--s-1); list-style: none; margin: 0; }
.nav__link, .nav__toggle {
  display: inline-flex; align-items: center; gap: var(--s-2);
  min-height: 44px;
  padding: var(--s-2) var(--s-3);
  border: 0; background: none;
  border-radius: var(--r-md);
  font-size: .975rem; font-weight: 600;
  color: var(--navy);
  text-decoration: none; cursor: pointer;
  white-space: nowrap;
  transition: background-color var(--dur) var(--ease), color var(--dur) var(--ease);
}
.nav__link:hover, .nav__toggle:hover { background: var(--navy-050); color: var(--navy); }

/* Current page is marked by weight + a gold underline, never colour alone */
.nav__link[aria-current="page"] { color: var(--navy); }
.nav__link[aria-current="page"]::after {
  content: ""; position: absolute; left: var(--s-3); right: var(--s-3); bottom: 2px;
  height: 3px; background: var(--gold); border-radius: 2px;
}
.nav__item { position: relative; }
.nav__link { position: relative; }

/* ── The single dropdown (What We Do) — click-operated disclosure.
      Deliberately not hover-opened: a hover-only menu has to satisfy
      WCAG 1.4.13, and a disclosure button is the more predictable
      pattern for keyboard and screen-reader users alike. ──────────────── */
.nav__caret { transition: transform var(--dur) var(--ease); }
.nav__toggle[aria-expanded="true"] .nav__caret { transform: rotate(180deg); }
@media (prefers-reduced-motion: reduce) { .nav__caret { transition: none; } }

.nav__menu {
  position: absolute; top: calc(100% + 10px); left: 50%;
  transform: translateX(-50%);
  min-width: 280px;
  padding: var(--s-2);
  margin: 0; list-style: none;
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-top: 3px solid var(--gold);
  border-radius: var(--r-lg);
  box-shadow: inset 0 2px 0 var(--navy-900), var(--shadow-lg);
}
.nav__menu[hidden] { display: none; }
.nav__menu a {
  display: block;
  padding: var(--s-3);
  border-radius: var(--r-md);
  font-size: .975rem; font-weight: 600;
  color: var(--navy); text-decoration: none;
}
.nav__menu a:hover { background: var(--navy-050); }
.nav__menu a span {
  display: block;
  font-size: var(--t--1); font-weight: 400;
  color: var(--ink-muted); margin-top: 2px;
}

/* ── Mobile ───────────────────────────────────────────────────────────── */
.nav__burger { display: none; }
@media (max-width: 1080px) {
  .site-header__inner { grid-template-columns: auto auto; }
  .site-header__actions { display: none; }
  .nav__burger {
    display: inline-flex; align-items: center; gap: var(--s-2);
    min-height: 48px; padding: var(--s-2) var(--s-4);
    background: none; border: 2px solid var(--border-strong);
    border-radius: var(--r-md);
    font-weight: 600; color: var(--navy); cursor: pointer;
  }
  .nav { justify-self: end; }
  .nav__list {
    display: none;
    position: absolute; left: 0; right: 0; top: 100%;
    flex-direction: column; align-items: stretch; gap: 0;
    padding: var(--s-3);
    background: var(--white);
    border-top: 1px solid var(--cream-200);
    border-bottom: 3px solid var(--gold);
    box-shadow: var(--shadow-lg);
    max-height: calc(100dvh - var(--header-h)); overflow-y: auto;
  }
  .nav__list[data-open="true"] { display: flex; }
  .nav__link, .nav__toggle { min-height: 52px; width: 100%; justify-content: space-between; }
  .nav__link[aria-current="page"]::after { left: var(--s-3); right: auto; width: 22px; bottom: 8px; }
  .nav__menu {
    position: static; transform: none; min-width: 0;
    box-shadow: none; border: 0; border-left: 3px solid var(--gold);
    border-radius: 0; margin-left: var(--s-3); padding-left: var(--s-2);
  }
  .nav__mobile-action { display: block; margin-top: var(--s-3); }
  .nav__mobile-action .btn { width: 100%; justify-content: center; }
}
@media (min-width: 1081px) { .nav__mobile-action { display: none; } }

main:focus { outline: none; }
[id] { scroll-margin-top: calc(var(--header-h) + var(--s-4)); }

/* ═══════════════════════════════════════════════════════════════════════
   8. CARDS
   ═══════════════════════════════════════════════════════════════════════ */
.grid { display: grid; gap: var(--s-5); }
.grid--2 { grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); }
.grid--3 { grid-template-columns: repeat(auto-fit, minmax(280px, 1fr)); }
.grid--4 { grid-template-columns: repeat(auto-fit, minmax(230px, 1fr)); }

/* Five programmes: auto-fit puts four on a wide screen and leaves the fifth
   stranded on its own row. Three and two reads as a decision. */
.grid--programs { grid-template-columns: repeat(3, minmax(0, 1fr)); }
@media (max-width: 980px) { .grid--programs { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (max-width: 640px) { .grid--programs { grid-template-columns: 1fr; } }

/* Exactly three cards: three across, or one column — never the 2+1 layout
   that strands the third card beside an empty track. */
.grid--trio { grid-template-columns: repeat(3, minmax(0, 1fr)); }
@media (max-width: 920px) { .grid--trio { grid-template-columns: 1fr; } }

.card {
  display: flex; flex-direction: column;
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-radius: var(--r-lg);
  box-shadow: var(--shadow-sm);
  overflow: hidden;
  transition: box-shadow var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.card__media { aspect-ratio: 16 / 10; overflow: hidden; background: var(--navy-050); }
.card__media img { width: 100%; height: 100%; object-fit: cover; transition: transform .3s var(--ease); }
.card__body { display: flex; flex-direction: column; gap: var(--s-3); padding: var(--s-5); flex: 1; }
.card__body > p { max-width: none; }
.card__title { font-size: var(--t-2); }
.card__title a { text-decoration: none; color: inherit; }
.card__title a::after { content: ""; position: absolute; inset: 0; }
.card__foot { margin-top: auto; padding-top: var(--s-2); }

/* Whole-card hover, but the accessible name still comes from the heading link */
.card--link { position: relative; }
.card--link:hover { box-shadow: var(--shadow-md); transform: translateY(-3px); }
.card--link:hover .card__media img { transform: scale(1.04); }
.card--link:has(a:focus-visible) { box-shadow: var(--shadow-md); }
.card--link:has(a:focus-visible) .card__title a { outline: 3px solid var(--navy); outline-offset: 3px; border-radius: var(--r-sm); }
@media (prefers-reduced-motion: reduce) {
  .card, .card__media img { transition: none; }
  .card--link:hover { transform: none; }
  .card--link:hover .card__media img { transform: none; }
}

.card--flat { box-shadow: none; background: transparent; border-color: transparent; }
/* .card--accent retired — replaced by .rowlist and .card--tab (section 20). */

.band--navy .card, .band--navy-deep .card {
  background: var(--navy-800); border-color: rgba(255,255,255,.14);
}
.band--navy .card .card__title, .band--navy-deep .card .card__title { color: var(--gold); }
.band--navy .card p, .band--navy-deep .card p { color: var(--navy-300); }

/* ═══════════════════════════════════════════════════════════════════════
   9. STAFF  —  rounded-rect crops, never circular avatars
   ═══════════════════════════════════════════════════════════════════════ */
/* One person per row: the portrait takes a real share of the width instead
   of being a thumbnail beside a column of text. */
.staff-list { display: grid; gap: var(--s-7); }
.staff-list > .staff + .staff { padding-top: var(--s-7); border-top: 1px solid var(--cream-200); }

.staff { display: grid; grid-template-columns: minmax(16rem, 22rem) 1fr; gap: var(--s-5) var(--s-6); align-items: start; }
.staff__photo {
  position: relative;
  border-radius: var(--r-lg);
  overflow: hidden;
  background: var(--navy-050);
  aspect-ratio: 4/5;
  box-shadow: var(--shadow-md);
}
.staff__photo img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 22%; }

.staff__photo--empty { display: grid; place-items: center; padding: var(--s-5); }
.staff__photo--empty p { text-align: center; color: var(--ink-muted); font-size: var(--t--1); max-width: none; }

.staff h3 { font-size: var(--t-3); }
.staff__role { font-weight: 600; color: var(--gold-deep); }
.staff .deflist { margin-top: var(--s-2); }
@media (max-width: 760px) {
  .staff { grid-template-columns: 1fr; }
  .staff__photo { max-width: 22rem; }
}

/* Definition-style contact rows — no icon chips, no coloured dots */
.deflist { display: grid; gap: var(--s-3); }
.deflist__row { display: grid; grid-template-columns: 8.5rem 1fr; gap: var(--s-3); padding-bottom: var(--s-3); border-bottom: 1px solid var(--cream-200); }
.deflist__row:last-child { border-bottom: 0; padding-bottom: 0; }
.deflist dt { font-weight: 700; color: var(--navy); }
.deflist dd { margin: 0; }
@media (max-width: 520px) { .deflist__row { grid-template-columns: 1fr; gap: var(--s-1); } }

/* ═══════════════════════════════════════════════════════════════════════
   10. FORMS  (WEB-FR-031, WEB-A11Y-005)
   ═══════════════════════════════════════════════════════════════════════ */
.form { display: grid; gap: var(--s-5); }
.field { display: grid; gap: var(--s-2); }
.field > label { font-weight: 600; color: var(--navy); }
.field__hint { font-size: var(--t--1); color: var(--ink-muted); }
.req { color: var(--error); font-weight: 700; }

.input, .textarea, .select {
  width: 100%;
  min-height: 48px;
  padding: var(--s-3) var(--s-4);
  background: var(--white);
  border: 2px solid var(--border-strong);
  border-radius: var(--r-md);
  transition: border-color var(--dur) var(--ease), box-shadow var(--dur) var(--ease);
}
.textarea { min-height: 150px; padding-block: var(--s-3); resize: vertical; }
.input:hover, .textarea:hover, .select:hover { border-color: var(--navy); }
.input:focus-visible, .textarea:focus-visible, .select:focus-visible {
  border-color: var(--navy); outline: 3px solid var(--navy); outline-offset: 1px;
}
.input[aria-invalid="true"], .textarea[aria-invalid="true"] { border-color: var(--error); background: var(--error-bg); }

/* Errors always carry text, never colour alone */
.field__error { display: flex; gap: var(--s-2); font-weight: 600; color: var(--error); font-size: var(--t--1); }
.field__error::before { content: "Error:"; }

.form__summary {
  padding: var(--s-4) var(--s-5);
  background: var(--error-bg);
  border: 2px solid var(--error);
  border-radius: var(--r-md);
}
.form__summary h2 { font-size: var(--t-1); color: var(--error); }
.form__summary ul { margin: var(--s-3) 0 0; padding-left: var(--s-5); }
.form__status[data-state="success"] {
  padding: var(--s-4) var(--s-5);
  background: var(--success-bg);
  border: 2px solid var(--success);
  border-left-width: 5px;
  border-radius: var(--r-md);
  color: var(--success); font-weight: 600;
}
.honeypot { position: absolute; left: -9999px; width: 1px; height: 1px; overflow: hidden; }

/* ═══════════════════════════════════════════════════════════════════════
   11. TABLES  (WEB-A11Y-007) — scroll inside their own wrapper
   ═══════════════════════════════════════════════════════════════════════ */
/* Tables keep a light surface even inside a navy band, so they must reset the
   inherited light text colour or they render white-on-white. */
.table-wrap { overflow-x: auto; border: 1px solid var(--cream-200); border-radius: var(--r-lg); background: var(--white); color: var(--ink); }
.band--navy .table-wrap a, .band--navy-deep .table-wrap a { color: var(--navy); }
.band--navy .table-wrap a:hover, .band--navy-deep .table-wrap a:hover { color: var(--navy-600); }
table { width: 100%; border-collapse: collapse; font-size: .975rem; }
caption { padding: var(--s-4) var(--s-5); text-align: left; font-weight: 700; color: var(--navy); border-bottom: 2px solid var(--gold); }
th, td { padding: var(--s-3) var(--s-5); text-align: left; border-bottom: 1px solid var(--cream-200); vertical-align: top; }
thead th { background: var(--navy-050); color: var(--navy); font-weight: 700; white-space: nowrap; }
tbody tr:last-child td, tbody tr:last-child th { border-bottom: 0; }
tbody tr:nth-child(even) { background: #FCFAF7; }

/* ═══════════════════════════════════════════════════════════════════════
   12. SERVICE-AREA MAP  (WEB-FR-041)
   The map is decorative reinforcement. The county table beneath it is the
   authoritative source and is always rendered — never behind a toggle.
   ═══════════════════════════════════════════════════════════════════════ */
.map-figure { display: grid; gap: var(--s-4); margin: 0; justify-items: center; }
.map-figure__canvas { width: 100%; max-width: 660px; }
.wv-map { width: 100%; height: auto; }
.wv-map__other path { fill: var(--navy-100); stroke: var(--border-strong); stroke-width: .8; }
.wv-map__served path { fill: var(--navy); stroke: var(--white); stroke-width: 1.2; }
.band--navy .wv-map__served path { fill: var(--gold); stroke: var(--navy-900); }
.band--navy .wv-map__other path { fill: var(--navy-800); stroke: var(--navy-600); }
.map-figure figcaption { font-size: var(--t--1); color: var(--ink-muted); }

.county-panel { margin-top: var(--s-5); padding: var(--s-5) var(--s-6);
  background: var(--white); border: 1px solid var(--cream-200);
  border-top: 3px solid var(--gold); border-radius: var(--r-lg); }
.county-panel h3 { font-family: var(--font-sans); font-size: var(--t--1); font-weight: 700;
  letter-spacing: .1em; text-transform: uppercase; color: var(--gold-deep); margin-bottom: var(--s-4); }
.county-list { columns: 4 10rem; column-gap: var(--s-6); list-style: none; margin: 0; }
.county-list li { padding: var(--s-2) 0; border-bottom: 1px solid var(--cream-200);
  break-inside: avoid; font-weight: 600; color: var(--navy); }

/* ═══════════════════════════════════════════════════════════════════════
   13. MISC BLOCKS
   ═══════════════════════════════════════════════════════════════════════ */
.stat { position: relative; padding: var(--s-5) var(--s-5) var(--s-4); background: var(--white);
  border: 1px solid var(--cream-200); border-radius: var(--r-lg); overflow: hidden; }
.stat::before { content: ""; position: absolute; top: 0; left: var(--s-5);
  width: 38px; height: 6px; background: var(--gold);
  transform: skewX(var(--slant)); }
.stat__num { display: block; font-family: var(--font-serif); font-size: var(--t-4); font-weight: 700; color: var(--navy); line-height: 1.1; }
.stat__label { color: var(--ink-muted); font-size: var(--t--1); }
.band--navy .stat { background: var(--navy-800); border-color: rgba(255,255,255,.14); border-left-color: var(--gold); }
.band--navy .stat__num { color: var(--gold); }
.band--navy .stat__label { color: var(--navy-300); }

/* Scheduled events are blocks, not rows on a hairline: each is a card with a
   date plate, its own edge, and a marker that draws in from the left edge
   when the block is hovered or contains focus. */
.eventlist { list-style: none; margin: 0; display: grid; gap: var(--s-4); }
.event {
  position: relative; overflow: hidden;
  display: grid; grid-template-columns: 7.5rem 1fr; gap: var(--s-5);
  padding: var(--s-5);
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-radius: var(--r-lg);
  box-shadow: var(--shadow-sm);
  transition: box-shadow var(--dur) var(--ease), transform var(--dur) var(--ease);
}
.event::before {
  content: ""; position: absolute; left: 0; top: 50%;
  width: 14px; height: 34px; margin-top: -17px;
  background: var(--gold);
  transform: skewX(var(--slant)) translateX(-220%);
  transition: transform .26s var(--ease);
  pointer-events: none;
}
.event:hover { box-shadow: var(--shadow-md); transform: translateY(-3px); }
.event:hover::before, .event:focus-within::before { transform: skewX(var(--slant)) translateX(0); }
.event__date { padding: var(--s-3); text-align: center; background: var(--navy); color: var(--white); border-radius: var(--r-md); align-self: start; }
.event__month { display: block; font-size: var(--t--1); font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: var(--gold); }
.event__day { display: block; font-family: var(--font-serif); font-size: var(--t-3); font-weight: 700; line-height: 1.1; }
.event__year { display: block; font-size: var(--t--1); color: var(--navy-300); }
.event__title { font-size: var(--t-2); }
.event__meta { list-style: none; margin: var(--s-3) 0 0; display: flex; flex-wrap: wrap;
  gap: var(--s-2) var(--s-5); font-size: var(--t--1); font-weight: 600; color: var(--ink-muted); }
.event__meta li { display: inline-flex; align-items: center; gap: var(--s-2); }
.event__meta .ico { flex: 0 0 auto; color: var(--gold-deep); }
.event__desc { margin-top: var(--s-4); }
.event__foot { margin-top: var(--s-4); }
.band--navy .event, .band--navy-deep .event { background: var(--navy-800); border-color: rgba(255,255,255,.14); }
.band--navy .event__title, .band--navy-deep .event__title { color: var(--gold); }
.band--navy .event__meta, .band--navy .event__desc { color: var(--navy-300); }
.band--navy .event__meta .ico { color: var(--gold); }
@media (max-width: 560px) { .event { grid-template-columns: 1fr; } .event__date { justify-self: start; min-width: 7rem; } }
@media (prefers-reduced-motion: reduce) {
  .event, .event::before { transition: none; }
  .event:hover { transform: none; }
}

.prose > * + * { margin-top: var(--s-4); }
.prose h2 { margin-top: var(--s-6); }
.prose h3 { margin-top: var(--s-5); }
.prose ul, .prose ol { padding-left: var(--s-5); display: grid; gap: var(--s-2); max-width: var(--measure); }
.prose a { font-weight: 600; }

.note { position: relative; padding: var(--s-5); background: var(--gold-soft);
  border-top: 3px solid var(--gold); border-radius: 0 0 var(--r-md) var(--r-md); }
.note::before { content: ""; position: absolute; left: 0; right: 0; top: -3px;
  height: 2px; background: var(--navy-900); }
.note > p { max-width: none; }

.filetype { font-size: var(--t--1); color: var(--ink-muted); font-weight: 400; }
.partner-logos { display: flex; flex-wrap: wrap; align-items: center; gap: var(--s-7); }
.partner-logos img { max-height: 60px; width: auto; }

.visually-hidden {
  position: absolute !important; width: 1px; height: 1px;
  padding: 0; margin: -1px; overflow: hidden;
  clip: rect(0 0 0 0); clip-path: inset(50%); white-space: nowrap; border: 0;
}

/* ═══════════════════════════════════════════════════════════════════════
   14. HERO
   ═══════════════════════════════════════════════════════════════════════ */
.hero { position: relative; background: var(--navy-900); color: var(--white); border-bottom: 3px solid var(--gold); overflow: hidden; }
.hero__media { position: absolute; inset: 0; }
/* Each hero names its own focal point, so cover crops to the part of the
   picture that carries the subject rather than to the middle of the frame. */
.hero__media img { width: 100%; height: 100%; object-fit: cover;
  object-position: var(--hero-focus, 50% 50%); opacity: .3; }
.hero__scrim { position: absolute; inset: 0; background: linear-gradient(105deg, var(--navy-900) 12%, rgba(13,26,48,.9) 48%, rgba(13,26,48,.62) 100%); }
.hero__inner { position: relative; padding-block: clamp(var(--s-7), 5.5vw, 5rem); }
.hero__content { max-width: 58ch; }
.hero h1 { color: var(--white); max-width: 20ch; }
/* A hero is a signpost. Its heading is kept short and the paragraph under it
   is set a step smaller than a section lede, so it reads as a caption to the
   heading rather than as the opening of the page's body copy. */
.hero .lede, .page-head .lede { font-size: var(--t-0); max-width: 54ch; }
.hero .lede { color: #D9E2F2; margin-top: var(--s-4); }
.hero .breadcrumb { position: relative; }
.hero--page .hero__inner { padding-block: clamp(var(--s-5), 3.6vw, 3.25rem); }

/* A photographic hero has to actually read as a photograph. The scrim is
   angled so the left side stays dark enough to carry white text at AAA while
   the right side keeps most of the picture. */
.hero--photo .hero__media img { opacity: .68; }
.hero--photo .hero__scrim {
  background: linear-gradient(100deg,
    rgba(13,26,48,.95) 0%,
    rgba(13,26,48,.88) 38%,
    rgba(13,26,48,.55) 72%,
    rgba(13,26,48,.35) 100%);
}
.hero--photo .hero__inner { min-height: 23rem; display: grid; align-content: center; }
@media (max-width: 700px) {
  /* On a narrow screen the text sits over the middle of the picture, so the
     scrim goes flat and dark rather than angled. */
  .hero--photo .hero__scrim { background: rgba(13,26,48,.9); }
  .hero--photo .hero__media img { opacity: .5; }
}
.hero .btn-row { margin-top: var(--s-5); }

.page-head { background: var(--navy-700); color: var(--white); border-bottom: 3px solid var(--gold); padding-block: clamp(var(--s-6), 3.6vw, var(--s-7)); }
.page-head h1 { color: var(--white); }
.page-head .lede { color: #D9E2F2; margin-top: var(--s-4); }
.page-head h1 { max-width: 20ch; }

/* ── Mountain variant — an Appalachian ridgeline behind the service-area
      opener. Purely decorative (the SVG is aria-hidden); the three ridges
      stay inside the navy scale so the white heading and the breadcrumb
      keep their measured contrast wherever they overlap. ───────────────── */
.page-head--mountains { position: relative; overflow: hidden;
  padding-bottom: clamp(5rem, 10vw, 8rem); }
.page-head--mountains .container { position: relative; z-index: 1; }
.page-head__mountains { position: absolute; left: 0; right: 0; bottom: 0; pointer-events: none; }
.page-head__mountains svg { display: block; width: 100%; height: clamp(90px, 13vw, 190px); }
.page-head__mountains .ridge--far  { fill: var(--navy-600); opacity: .55; }
.page-head__mountains .ridge--mid  { fill: var(--navy-800); opacity: .85; }
.page-head__mountains .ridge--near { fill: var(--navy-900); }
.breadcrumb { margin-bottom: var(--s-4); font-size: var(--t--1); }
.breadcrumb ol { display: flex; flex-wrap: wrap; gap: var(--s-2); list-style: none; margin: 0; }
.breadcrumb a { color: #D9E2F2; }
.breadcrumb a:hover { color: var(--gold); }
.breadcrumb li + li::before { content: "/"; margin-right: var(--s-2); color: var(--navy-300); }
.breadcrumb [aria-current="page"] { color: var(--gold); font-weight: 600; }

/* ═══════════════════════════════════════════════════════════════════════
   15. FOOTER
   ═══════════════════════════════════════════════════════════════════════ */
.site-footer { background: var(--navy-900); color: #D9E2F2; border-top: 3px solid var(--gold); padding-block: var(--s-7) var(--s-5); }
.site-footer h2 { font-family: var(--font-sans); font-size: var(--t--1); font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: var(--gold); margin-bottom: var(--s-4); }
/* Footer links carry no underline at rest — the footer is a nav-style link
   list, not prose — but the underline returns on hover and focus so the
   affordance is never colour alone. */
.site-footer a { color: #D9E2F2; text-decoration: none; }
.site-footer a:hover, .site-footer a:focus-visible { color: var(--gold); text-decoration: underline; }
.site-footer__grid { display: grid; grid-template-columns: 1.5fr 1fr 1fr 1.2fr; gap: var(--s-6); }
@media (max-width: 900px) { .site-footer__grid { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); } }
.site-footer__logo img { width: 200px; margin-bottom: var(--s-4); }
.site-footer ul { list-style: none; display: grid; gap: var(--s-3); margin: 0; }
.site-footer__bottom { display: flex; flex-wrap: wrap; justify-content: space-between; gap: var(--s-4); margin-top: var(--s-5); padding-top: var(--s-4); border-top: 1px solid rgba(255,255,255,.16); font-size: var(--t--1); color: var(--navy-300); }
/* The bottom bar mixes links with plain text, so with rest-state underlines
   gone the links carry two non-colour cues of their own — a lighter tone and
   a heavier weight — to stay distinguishable (WCAG 1.4.1). */
.site-footer__bottom a { color: #D9E2F2; font-weight: 600; }
.site-footer__credit { color: var(--navy-300); }

/* ═══════════════════════════════════════════════════════════════════════
   16. PRINT
   ═══════════════════════════════════════════════════════════════════════ */
@media print {
  .site-header, .site-footer, .skip-link, .btn { display: none !important; }
  body { background: #fff; color: #000; font-size: 11pt; }
  .band { padding-block: 1rem; border: 0; }
  .band--navy, .band--navy-deep, .hero, .page-head { background: #fff !important; color: #000 !important; }
  .band--navy h2, .hero h1, .page-head h1 { color: #000 !important; }
  a[href^="http"]::after { content: " (" attr(href) ")"; font-size: 9pt; word-break: break-all; }
  .card, .event, .panel { break-inside: avoid; border: 1px solid #999; box-shadow: none; }
  .jumpnav, .slideshow__controls, .tabset__tabs, .mapcard__frame, .map-tools { display: none !important; }
  .slideshow__track { display: grid !important; }
  .slide[hidden], .tabset__panel[hidden] { display: block !important; }
}

/* ═══════════════════════════════════════════════════════════════════════
   17. FORCED COLORS (Windows High Contrast)
   ═══════════════════════════════════════════════════════════════════════ */
@media (forced-colors: active) {
  .btn { border-color: currentColor; }
  .card, .table-wrap, .nav__menu { border: 1px solid currentColor; }
  .wv-map__served path { fill: Highlight; }
  .wv-map__other path { fill: Canvas; stroke: CanvasText; }
  :focus-visible { outline: 3px solid Highlight; }
}

/* The compact .proglist signpost was replaced by .rowlist (section 20):
   five two-word tiles carried too little to justify the space. */

/* ═══════════════════════════════════════════════════════════════════════
   18. OVERFLOW GUARDS
   Grid and flex children default to min-width:auto, so an unbreakable string
   (an email address, a long URL) sets a floor the track cannot shrink below
   and pushes the page wider than the viewport. These three rules stop that.
   ═══════════════════════════════════════════════════════════════════════ */
.grid > *, .staff > *, .deflist__row > *, .rowlist__item > * { min-width: 0; }
.deflist dd, .deflist dd a { overflow-wrap: anywhere; }
.site-footer ul a { overflow-wrap: anywhere; }

/* The staff list is one column at every width now, so the old two-up
   collapse rule has nothing left to collapse. */

/* ═══════════════════════════════════════════════════════════════════════
   19. TWO-TONE RULE
   The logo stacks a navy bar directly on a gold one. Every full-width gold
   rule echoes that lockup: a dark stripe riding on top of the gold.

   Rules whose upper side already faces a navy surface — the hero and
   page-head seams, and the lower seam of every navy band — get the effect
   for free from the surface above them and need nothing added.
   ═══════════════════════════════════════════════════════════════════════ */
.site-header {
  border-bottom-width: 3px;
  box-shadow: inset 0 -2px 0 var(--navy), var(--shadow-sm);
}

/* The gold keeps its full 3px; the dark stripe is added above it, so the
   seam becomes 5px total rather than the gold losing two thirds of itself. */
.band--navy, .band--navy-deep, .site-footer { position: relative; }
.band--navy, .band--navy-deep { border-top-width: 5px; }
.site-footer { border-top-width: 5px; }
.band--navy::before,
.band--navy-deep::before,
.site-footer::before {
  content: "";
  position: absolute;
  left: 0; right: 0; top: -5px;
  height: 2px;
  background: var(--navy-900);
  pointer-events: none;
}
/* Consecutive navy bands drop their gold seam, so there is no strip to top. */
.band--navy + .band--navy::before,
.band--navy + .band--navy-deep::before,
.band--navy-deep + .band--navy::before { content: none; }

/* ═══════════════════════════════════════════════════════════════════════
   20. ROWLIST  —  the replacement for left-edged filler cards

   A table-like list where every row carries a title, a piece of meaningful
   metadata, a description and a forward affordance. Used for resource
   collections, document lists and programme signposts.

   The whole row is clickable via a stretched pseudo-element on the title
   link, so the link's accessible name stays short and specific rather than
   swallowing the entire row of text.

   The hover marker is a parallelogram cut to the logo's own slant.
   ═══════════════════════════════════════════════════════════════════════ */
.rowlist {
  list-style: none; margin: 0;
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-radius: var(--r-lg);
  overflow: hidden;
}
.rowlist__item {
  position: relative;
  display: grid;
  grid-template-columns: 1fr auto;
  align-items: center;
  gap: var(--s-3) var(--s-5);
  padding: var(--s-5) var(--s-6);
  transition: background-color var(--dur) var(--ease);
}
.rowlist__item + .rowlist__item { border-top: 1px solid var(--cream-200); }

/* Slanted gold marker, hidden off the left edge until the row is engaged.
   Deliberately a short, vertically centred bar rather than a full-height one:
   a true 32deg slant across a ~130px row would travel ~80px horizontally and
   read as a wedge, not a marker. At 30px tall the same angle stays legible
   and the travel is 19px. */
.rowlist__item::before {
  content: "";
  position: absolute; left: 0; top: 50%;
  width: 14px; height: 30px; margin-top: -15px;
  background: var(--gold);
  transform: skewX(var(--slant)) translateX(-220%);
  transition: transform .26s var(--ease);
  pointer-events: none;
}
.rowlist__item:hover, .rowlist__item:has(a:focus-visible) { background: var(--navy-050); }
.rowlist__item:hover::before,
.rowlist__item:has(a:focus-visible)::before { transform: skewX(var(--slant)) translateX(0); }

.rowlist__title { grid-column: 1; margin: 0; font-family: var(--font-serif);
  font-size: var(--t-1); font-weight: 600; line-height: 1.25; color: var(--navy); max-width: none; }
.rowlist__title a { color: inherit; text-decoration: none; }
.rowlist__title a::after { content: ""; position: absolute; inset: 0; }
.rowlist__title a:hover { text-decoration: underline; text-underline-offset: .18em; }
.rowlist__item:has(a:focus-visible) .rowlist__title a {
  outline: 3px solid var(--navy); outline-offset: 3px; border-radius: var(--r-sm); }

.rowlist__meta { grid-column: 1; margin: 0; font-size: var(--t--1); font-weight: 600;
  letter-spacing: .04em; text-transform: uppercase; color: var(--gold-deep); order: -1; }
.rowlist__desc { grid-column: 1; margin: 0; font-size: .975rem; color: var(--ink-muted); max-width: 68ch; }

.rowlist__go { grid-column: 2; grid-row: 1 / -1; display: inline-flex; align-items: center;
  gap: var(--s-2); font-size: var(--t--1); font-weight: 700; letter-spacing: .04em;
  text-transform: uppercase; color: var(--navy); white-space: nowrap; }
.rowlist__go svg { transition: transform var(--dur) var(--ease); }
.rowlist__item:hover .rowlist__go svg { transform: translateX(4px); }

@media (max-width: 640px) {
  .rowlist__item { grid-template-columns: 1fr; padding: var(--s-5); }
  .rowlist__go { grid-column: 1; grid-row: auto; }
}
@media (prefers-reduced-motion: reduce) {
  .rowlist__item::before, .rowlist__go svg { transition: none; }
}

/* Rowlist inside a navy band */
.band--navy .rowlist { background: var(--navy-800); border-color: rgba(255,255,255,.14); }
.band--navy .rowlist__item + .rowlist__item { border-top-color: rgba(255,255,255,.14); }
.band--navy .rowlist__item:hover { background: var(--navy-700); }
.band--navy .rowlist__title, .band--navy .rowlist__go { color: var(--gold); }
.band--navy .rowlist__meta { color: var(--gold); }
.band--navy .rowlist__desc { color: var(--navy-300); }

/* ═══════════════════════════════════════════════════════════════════════
   21. CARD TAB  —  angular corner flag, cut to the logo slant
   Width tracks height by --tab-ratio so the hypotenuse holds 32deg at any
   size; on hover the tab draws further down the card's edge.
   ═══════════════════════════════════════════════════════════════════════ */
.card--tab {
  --tab: 34px;
  position: relative;
  border-top-right-radius: 0;
}
.card--tab::after {
  content: "";
  position: absolute; top: 0; right: 0;
  height: var(--tab);
  width: calc(var(--tab) * var(--tab-ratio));
  background: var(--gold);
  clip-path: polygon(100% 0, 100% 100%, 0 0);
  transition: height .24s var(--ease), width .24s var(--ease);
  pointer-events: none;
}
.card--tab:hover, .card--tab:focus-within { --tab: 60px; }
@media (prefers-reduced-motion: reduce) { .card--tab::after { transition: none; } }

/* ═══════════════════════════════════════════════════════════════════════
   22. INTERACTIVE TABLES
   ═══════════════════════════════════════════════════════════════════════ */
tbody tr { transition: background-color var(--dur) var(--ease); }
tbody tr:hover { background: var(--navy-050); }
.band--navy tbody tr:hover { background: var(--navy-050); }
@media (prefers-reduced-motion: reduce) { tbody tr { transition: none; } }

/* Decorative inline icons in the rowlist meta line. Every one sits beside
   text that already carries the same information. */
.rowlist__meta { display: inline-flex; align-items: center; gap: var(--s-2); }
.rowlist__meta .ico { flex: 0 0 auto; }

/* ═══════════════════════════════════════════════════════════════════════
   23. INTERACTIVE SERVICE-AREA MAP
   Pointer affordances only. The county list carries the information, so
   none of this is required to read the page.
   ═══════════════════════════════════════════════════════════════════════ */
.map-stage { position: relative; }
.wv-map__served path,
.wv-map__other path { transition: fill .16s var(--ease), filter .16s var(--ease); }
/* Only the service-area map's counties are clickable, so only there does the
   cursor promise a click. The home map hovers a name and nothing more. */
#service-map .wv-map__served path,
#service-map .wv-map__other path { cursor: pointer; }
/* The gold highlight is only 1.59:1 against the light fill of a neighbouring
   unserved county, so the active shape carries its own dark outline rather
   than relying on fill alone to separate it from whatever it borders. */
.wv-map__served path:hover,
.wv-map__served path.is-active {
  fill: var(--gold);
  stroke: var(--navy-900);
  stroke-width: 2.5;
}
/* Hover on an unserved county. Brightness rather than a fill, because in
   the regions view each county already has a fill of its own that would win
   on specificity — and a lift works whatever colour it lands on. */
.wv-map__other path:hover,
.wv-map__other path.is-active {
  filter: brightness(1.06) saturate(1.12);
  stroke: var(--navy-900);
  stroke-width: 1.8;
}
.map-figure:not(.is-regions) .wv-map__other path:hover,
.map-figure:not(.is-regions) .wv-map__other path.is-active { fill: #DCE5F5; }
.band--navy .wv-map__other path:hover { filter: brightness(1.5); }

.map-tip {
  position: absolute; z-index: 3;
  padding: var(--s-2) var(--s-3);
  background: var(--navy-900); color: var(--white);
  font-size: var(--t--1); font-weight: 600; white-space: nowrap;
  border-radius: var(--r-sm);
  border-top: 2px solid var(--gold);
  box-shadow: var(--shadow-md);
  pointer-events: none; max-width: none;
}

.map-figure__tools {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between;
  gap: var(--s-3) var(--s-5); margin-top: var(--s-4);
}
.map-legend {
  list-style: none; margin: 0;
  display: flex; flex-wrap: wrap; align-items: center; gap: var(--s-2) var(--s-5);
  font-size: var(--t--1); color: var(--ink-muted); max-width: none;
}
.map-legend li { display: inline-flex; align-items: center; gap: var(--s-2); }
.map-legend__key { width: 22px; height: 12px; border-radius: 2px; display: inline-block; flex: 0 0 auto; }
.map-legend__key--served { background: var(--navy); }

/* The office marker and the region keys, matched to what the map draws */
.map-legend__key--office { width: 14px; height: 14px; border-radius: 50%; background: var(--gold); border: 2px solid var(--navy-900); }
.map-legend__key--center { width: 14px; height: 14px; border-radius: 50%; background: var(--map-office); border: 2px solid var(--white); box-shadow: 0 0 0 1px var(--map-office); }
.map-legend__key--program { width: 14px; height: 14px; border-radius: 50%; background: var(--white); border: 2px solid var(--navy-900); }
.map-legend__key[data-region="central"]      { background: var(--map-central); }
.map-legend__key[data-region="eastern"]      { background: var(--map-eastern); }
.map-legend__key[data-region="southern"]     { background: var(--map-southern); }
.map-legend__key[data-region="southeastern"] { background: var(--map-southeastern); }
.map-legend__key[data-region="none"]         { background: var(--map-none); border: 1px solid var(--border-strong); }
.map-legend__key[data-region="northern-map"] { background: var(--navy-600); }

/* Region keys only apply once the other locations are actually shown.
   Written as li.map-legend__region so it outranks the .map-legend li rule
   above rather than losing to it on specificity. */
.map-legend li.map-legend__region { display: none; }
.map-figure.is-regions .map-legend li.map-legend__region { display: inline-flex; }

/* ── Office markers ──────────────────────────────────────────────────
   A star sits on the county that houses the physical office. Ours is gold
   and always present; the other centres appear with the regions. */
.map-office path { stroke-width: 2; paint-order: stroke; }
.map-office--home path { fill: var(--gold); stroke: var(--navy-900); }
.map-office--center path { fill: var(--map-office); stroke: var(--white); }
.map-office--program path { fill: var(--white); stroke: var(--navy-900); }
.map-office--center, .map-office--program { display: none; }
.map-figure.is-regions .map-office--center,
.map-figure.is-regions .map-office--program { display: inline; }
/* On a navy band the served counties are gold, so a gold star would vanish
   into the county it marks: it inverts to dark with a light edge. */
.band--navy .map-office--home path { fill: var(--navy-900); stroke: var(--white); }
.band--navy .map-legend__key--office { background: var(--navy-900); border-color: var(--gold); }

/* ── The regions view ────────────────────────────────────────────────
   Off by default: the page is about our own 23 counties, and the rest of
   the state is context you ask for. */
.map-figure.is-regions .wv-map__other path[data-region="central"]      { fill: var(--map-central); }
.map-figure.is-regions .wv-map__other path[data-region="eastern"]      { fill: var(--map-eastern); }
.map-figure.is-regions .wv-map__other path[data-region="southern"]     { fill: var(--map-southern); }
.map-figure.is-regions .wv-map__other path[data-region="southeastern"] { fill: var(--map-southeastern); }
.map-figure.is-regions .wv-map__other path[data-region="none"]         { fill: var(--map-none); }
/* Northern on the statewide map, outside the 23 counties this page counts */
.map-figure.is-regions .wv-map__other path[data-region="northern-map"] { fill: var(--navy-600); }
.map-figure.is-regions .wv-map__other path { stroke: var(--navy-900); stroke-width: .8; }

/* The list of other centres sits beside the map, not under it, and is a
   list rather than a panel: no border, no ground of its own, just names
   with a bullet in the colour of the region each one belongs to. */
.map-regions h3 { font-family: var(--font-sans); font-size: var(--t--1); font-weight: 700;
  letter-spacing: .1em; text-transform: uppercase; color: var(--gold-deep); }
.map-regions__list { list-style: disc; margin: var(--s-4) 0 0; padding-left: 1.1em;
  display: grid; gap: var(--s-4); }
/* display:grid on a list item would replace display:list-item and take the
   bullet with it, so the item stays a list item and its two lines are
   blocks instead. */
.map-regions__list li { display: list-item; }
.map-regions__list strong, .map-regions__list span { display: block; }
.map-regions__list li::marker { color: var(--gold-deep); font-size: 1.1em; }
.map-regions__list li[data-region="central"]::marker      { color: var(--map-central); }
.map-regions__list li[data-region="eastern"]::marker      { color: var(--map-eastern); }
.map-regions__list li[data-region="southern"]::marker     { color: var(--map-southern); }
.map-regions__list li[data-region="southeastern"]::marker { color: var(--map-southeastern); }
.map-regions__list li[data-region="program"]::marker      { color: var(--navy); }
.map-regions__list strong { color: var(--navy); line-height: 1.3; }
.map-regions__list span { font-size: var(--t--1); color: var(--ink-muted); }
.map-regions__note { margin-top: var(--s-5); font-size: var(--t--1); color: var(--ink-muted); max-width: none; }

/* The county-by-county disclosure gives keyboard and screen-reader users the
   same per-county answer the map's pointer interactions provide. */
.map-regions__counties { margin-top: var(--s-4); font-size: var(--t--1); color: var(--ink-muted); }
.map-regions__counties summary { cursor: pointer; font-weight: 600; color: var(--navy); }
.map-regions__counties p { margin-top: var(--s-2); max-width: none; }
.map-regions__counties strong { color: var(--navy); }

/* Two columns once the regions are showing: map on the left, the list of
   the other centres on the right, level with it. */
.map-figure.is-regions {
  grid-template-columns: minmax(0, 1fr) minmax(15rem, 19rem);
  justify-items: stretch;
  column-gap: var(--s-6);
  align-items: start;
}
.map-figure.is-regions .map-figure__canvas { grid-column: 1; grid-row: 1; }
.map-figure.is-regions .map-regions { grid-column: 2; grid-row: 1; align-self: center; }
.map-figure.is-regions figcaption { grid-column: 1 / -1; }
@media (max-width: 860px) {
  .map-figure.is-regions { grid-template-columns: 1fr; }
  .map-figure.is-regions .map-regions { grid-column: 1; grid-row: auto; }
}

/* Shown only once the script that drives it is running */
.map-figure.is-ready .map-toggle { display: inline-flex; }

.county-list li { transition: background-color .16s var(--ease), color .16s var(--ease); }
.county-list li.is-active { background: var(--gold); color: var(--navy); border-radius: var(--r-sm); }
.county-list__btn { display: block; width: 100%; text-align: left;
  padding: var(--s-1) var(--s-2); background: transparent; border: 0;
  border-radius: var(--r-sm); font: inherit; font-weight: 600; color: inherit; cursor: pointer; }
.county-list__btn:hover { background: var(--navy-050); }
.county-list li[hidden] { display: none; }

@media (prefers-reduced-motion: reduce) {
  .wv-map__served path, .wv-map__other path, .county-list li { transition: none; }
}

/* ═══════════════════════════════════════════════════════════════════════
   24. PANEL  —  a sheet to stand text on

   Body copy used to be set straight onto a band with nothing around it, so
   a paragraph and the page ground had the same edge: none. A panel gives
   that text a surface, a gold top rule cut from the same stock as every
   other rule on the site, and room to breathe.
   ═══════════════════════════════════════════════════════════════════════ */
.panel {
  position: relative;
  padding: clamp(var(--s-5), 2.4vw, var(--s-6));
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-top: 4px solid var(--gold);
  border-radius: var(--r-lg);
  box-shadow: var(--shadow-sm);
}
.panel > *:first-child { margin-top: 0; }
.panel > h2:first-child { line-height: 1.12; }
.panel .btn-row { margin-top: var(--s-4); }

/* On a navy band the sheet darkens rather than punching a white hole in it */
.band--navy .panel, .band--navy-deep .panel {
  background: var(--navy-800);
  border-color: rgba(255,255,255,.14);
  border-top-color: var(--gold);
  box-shadow: none;
}
.band--navy .panel p, .band--navy-deep .panel p { color: var(--navy-300); }
.band--navy .panel strong, .band--navy-deep .panel strong { color: var(--white); }
.band--tint .panel, .band--cream .panel { box-shadow: var(--shadow-md); }

/* ═══════════════════════════════════════════════════════════════════════
   25. JUMP CONTROLS  —  section selector at the top of a long page

   Buttons, not a list of underlined links: on a page people arrive at with
   one question, the first thing they see should look pressable. They are
   still anchors underneath, so they work with JavaScript off and can be
   opened in a new tab like any other link.
   ═══════════════════════════════════════════════════════════════════════ */
.jumpnav {
  position: sticky; top: var(--header-h); z-index: 60;
  background: var(--navy-900);
  border-bottom: 2px solid var(--gold);
}
.jumpnav__inner { display: flex; flex-wrap: wrap; align-items: center; gap: var(--s-3) var(--s-5); padding-block: var(--s-3); }
.jumpnav__label {
  margin: 0; font-size: var(--t--1); font-weight: 700; letter-spacing: .08em;
  text-transform: uppercase; color: var(--gold); max-width: none;
}
.jumpnav__list { list-style: none; margin: 0; display: flex; flex-wrap: wrap; gap: var(--s-2); }
.jumpnav__list a {
  display: inline-flex; align-items: center; gap: var(--s-2);
  min-height: 44px; padding: var(--s-2) var(--s-4);
  background: var(--navy-700);
  border: 2px solid transparent;
  border-radius: var(--r-md);
  color: var(--white); font-size: .95rem; font-weight: 600; text-decoration: none;
  transition: background-color var(--dur) var(--ease), border-color var(--dur) var(--ease);
}
.jumpnav__list a:hover { background: var(--navy-600); border-color: var(--gold); color: var(--white); }
.jumpnav__list a:focus-visible { outline-color: var(--gold); }
/* The section the reader is actually in, marked by site.js */
.jumpnav__list a[aria-current="true"] { background: var(--gold); color: var(--navy); }
@media (max-width: 760px) {
  .jumpnav { position: static; }
  .jumpnav__label { flex-basis: 100%; }
}

/* ═══════════════════════════════════════════════════════════════════════
   26. FAQ  —  native disclosure widgets

   <details> rather than scripted accordions: the answers are real text in
   the page, so browser search finds them and they open with the keyboard
   without a line of JavaScript.
   ═══════════════════════════════════════════════════════════════════════ */
.faq { display: grid; gap: var(--s-2); }
.faq__item {
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-radius: var(--r-lg);
  overflow: hidden;
  transition: border-color var(--dur) var(--ease);
}
.faq__item:hover { border-color: var(--border-strong); }
.faq__item summary {
  display: flex; align-items: center; justify-content: space-between; gap: var(--s-4);
  padding: var(--s-4) var(--s-5);
  font-family: var(--font-serif); font-size: var(--t-1); font-weight: 600;
  color: var(--navy); cursor: pointer; list-style: none;
}
.faq__item summary::-webkit-details-marker { display: none; }
.faq__item summary::after {
  content: ""; flex: 0 0 auto;
  width: 11px; height: 11px;
  border-right: 2.5px solid var(--gold-deep);
  border-bottom: 2.5px solid var(--gold-deep);
  transform: translateY(-3px) rotate(45deg);
  transition: transform .2s var(--ease);
}
.faq__item[open] summary::after { transform: translateY(2px) rotate(225deg); }
.faq__item[open] summary { border-bottom: 2px solid var(--gold); }
.faq__answer { padding: var(--s-4) var(--s-5) var(--s-5); }
.faq__answer > * + * { margin-top: var(--s-3); }
.band--navy .faq__item { background: var(--navy-800); border-color: rgba(255,255,255,.14); }
.band--navy .faq__item summary { color: var(--gold); }
.band--navy .faq__answer { color: var(--navy-300); }
@media (prefers-reduced-motion: reduce) { .faq__item summary::after { transition: none; } }

/* ═══════════════════════════════════════════════════════════════════════
   27. SLIDESHOW  —  a gallery that breaks a long page in two

   With JavaScript off this is what the markup says it is: a stack of
   figures, each with its caption, in order. site.js shows one at a time and
   adds the controls. Nothing auto-advances — no one has to chase a photo.
   ═══════════════════════════════════════════════════════════════════════ */
.slideshow__track { display: grid; gap: var(--s-5); }
.slide { margin: 0; }
.slide__media {
  /* width is stated so the max-height below clamps the height only. With
     width:auto the ratio would shrink the box on both axes and the picture
     would get narrower as well as shorter. */
  width: 100%;
  aspect-ratio: 16 / 9;
  /* Capped so the heading above and the controls below stay on screen with
     the photograph: at container width, 16/9 alone is 675px of picture. */
  max-height: min(60vh, 35rem);
  border-radius: var(--r-lg);
  overflow: hidden;
  background: var(--navy-800);
  box-shadow: var(--shadow-lg);
}
.slide__media img { width: 100%; height: 100%; object-fit: cover; }
.slide__caption {
  margin-top: var(--s-3);
  font-size: var(--t-0); line-height: 1.5; color: var(--navy-300); max-width: 62ch;
}
.band--cream .slide__caption, .band--white .slide__caption, .band--tint .slide__caption { color: var(--ink-muted); }

.slideshow.is-enhanced .slideshow__track { display: block; }
.slideshow.is-enhanced .slide[hidden] { display: none; }
.slideshow__controls { display: flex; align-items: center; gap: var(--s-4); margin-top: var(--s-4); }
.slideshow__btn {
  display: inline-grid; place-items: center;
  width: 48px; height: 48px; padding: 0;
  background: var(--navy-800); color: var(--white);
  border: 2px solid var(--navy-300); border-radius: var(--r-md);
  cursor: pointer;
  transition: background-color var(--dur) var(--ease), border-color var(--dur) var(--ease);
}
.slideshow__btn:hover { background: var(--navy-600); border-color: var(--gold); }
.slideshow__btn:focus-visible { outline-color: var(--gold); }
.band--cream .slideshow__btn, .band--white .slideshow__btn, .band--tint .slideshow__btn {
  background: var(--white); color: var(--navy); border-color: var(--border-strong);
}
.band--cream .slideshow__btn:hover, .band--white .slideshow__btn:hover, .band--tint .slideshow__btn:hover {
  background: var(--navy-050); border-color: var(--navy);
}
/* Position markers cut to the logo's slant, not dots */
.slideshow__dots { display: flex; gap: var(--s-2); }
.slideshow__dot {
  width: 34px; height: 7px; padding: 0;
  background: rgba(255,255,255,.3); border: 0;
  transform: skewX(var(--slant)); cursor: pointer;
}
.band--cream .slideshow__dot, .band--white .slideshow__dot, .band--tint .slideshow__dot { background: var(--navy-100); }
.slideshow__dot[aria-current="true"] { background: var(--gold); }
.slideshow__count { margin-left: auto; font-size: var(--t--1); font-weight: 600; color: var(--navy-300); max-width: none; }
.band--cream .slideshow__count, .band--white .slideshow__count, .band--tint .slideshow__count { color: var(--ink-muted); }
@media (prefers-reduced-motion: reduce) { .slideshow__btn { transition: none; } }

/* ═══════════════════════════════════════════════════════════════════════
   28. TABSET  —  one set of rows at a time

   The tab strip is hidden until site.js has wired it up, so nobody is left
   pressing a control that does nothing. Without JavaScript the same markup
   is a plain stack of headed tables.
   ═══════════════════════════════════════════════════════════════════════ */
.tabset__tabs { display: none; }
.tabset.is-tabbed .tabset__tabs {
  display: flex; flex-wrap: wrap; gap: var(--s-2);
  margin-bottom: var(--s-5);
  border-bottom: 2px solid var(--cream-200);
}
.tab {
  min-height: 48px; padding: var(--s-3) var(--s-5);
  background: transparent;
  border: 0; border-bottom: 4px solid transparent;
  border-radius: var(--r-md) var(--r-md) 0 0;
  font-weight: 700; color: var(--ink-muted); cursor: pointer;
  transition: background-color var(--dur) var(--ease), color var(--dur) var(--ease);
}
.tab:hover { background: var(--navy-050); color: var(--navy); }
.tab[aria-selected="true"] { background: var(--white); color: var(--navy); border-bottom-color: var(--gold); }

/* A tab strip on a navy band inverts like everything else there: the muted
   label colour used on light grounds is unreadable on navy. */
.band--navy .tabset.is-tabbed .tabset__tabs,
.band--navy-deep .tabset.is-tabbed .tabset__tabs { border-bottom-color: rgba(255,255,255,.18); }
.band--navy .tab, .band--navy-deep .tab { color: var(--navy-300); }
.band--navy .tab:hover, .band--navy-deep .tab:hover { background: var(--navy-800); color: var(--white); }
.band--navy .tab[aria-selected="true"], .band--navy-deep .tab[aria-selected="true"] {
  background: var(--navy-800); color: var(--gold); border-bottom-color: var(--gold);
}
.band--navy .tab:focus-visible, .band--navy-deep .tab:focus-visible { outline-color: var(--gold); }
.tabset__panel + .tabset__panel { margin-top: var(--s-6); }
.tabset.is-tabbed .tabset__panel + .tabset__panel { margin-top: 0; }
.tabset.is-tabbed .tabset__title { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); }
.tabset__panel > .lede { margin-bottom: var(--s-5); }
.tabset__panel:focus-visible { outline-offset: 6px; }
.cell-meta { white-space: nowrap; font-size: var(--t--1); color: var(--ink-muted); }
.cell-meta .ico { display: inline-block; vertical-align: -2px; margin-right: 6px; color: var(--gold-deep); }
@media (max-width: 620px) {
  .tab { padding: var(--s-3) var(--s-4); font-size: .95rem; }
}
@media (prefers-reduced-motion: reduce) { .tab { transition: none; } }

/* ═══════════════════════════════════════════════════════════════════════
   29. MAP CARD  —  a map that is only fetched if it is wanted

   The address and the directions link are plain text and a plain link, and
   they work whether or not a map is ever loaded. Google is contacted only
   after the visitor presses the button, so simply reading the page sends
   nothing to a third party.
   ═══════════════════════════════════════════════════════════════════════ */
.mapcard { display: grid; grid-template-columns: 1.35fr 1fr; gap: var(--s-6); align-items: start; }
.mapcard__frame {
  position: relative;
  display: grid; place-content: center; justify-items: center; gap: var(--s-3);
  aspect-ratio: 4 / 3; padding: var(--s-5);
  text-align: center;
  background:
    repeating-linear-gradient(90deg, rgba(255,255,255,.05) 0 1px, transparent 1px 46px),
    repeating-linear-gradient(0deg, rgba(255,255,255,.05) 0 1px, transparent 1px 46px),
    var(--navy-900);
  border: 1px solid rgba(255,255,255,.16);
  border-radius: var(--r-lg);
  overflow: hidden;
}
/* Pinned to the frame rather than laid out inside it: centred grid content
   would leave the iframe at its own default size, sitting small in the box. */
.mapcard__frame iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; display: block; }
.mapcard__note { margin: 0; font-size: var(--t--1); color: var(--navy-300); max-width: 34ch; }
.mapcard__body > * + * { margin-top: var(--s-4); }
.mapcard__addr { font-weight: 700; color: var(--gold); max-width: 30ch; }
@media (max-width: 860px) { .mapcard { grid-template-columns: 1fr; } }

/* ═══════════════════════════════════════════════════════════════════════
   30. COUNTY SEARCH AND DETAIL
   The search filters the same list the page already carried; the detail
   card answers "and what do I do with that county?" with a real link.
   ═══════════════════════════════════════════════════════════════════════ */
.map-tools {
  display: flex; flex-wrap: wrap; align-items: flex-end; justify-content: space-between;
  gap: var(--s-4) var(--s-6); margin-bottom: var(--s-5);
}
.map-search { flex: 1 1 20rem; max-width: 26rem; }
.map-status { font-size: var(--t--1); font-weight: 600; color: var(--ink-muted); max-width: none; }
.county-detail {
  margin-top: var(--s-5); padding: var(--s-5) var(--s-6);
  background: var(--white);
  border: 1px solid var(--cream-200); border-left: 5px solid var(--gold);
  border-radius: var(--r-lg);
  box-shadow: var(--shadow-sm);
}
.county-detail__name { font-size: var(--t-2); }
.county-detail__meta { margin-top: var(--s-2); color: var(--ink-muted); }
.county-detail .btn-row { margin-top: var(--s-4); }

/* A county the reader has actually chosen stays lit after the pointer has
   moved on — unlike the hover highlight, which is momentary. */
.wv-map__served path.is-chosen {
  fill: var(--gold);
  stroke: var(--navy-900);
  stroke-width: 2.5;
}
.wv-map__other path.is-chosen { stroke: var(--navy-900); stroke-width: 2.5; filter: brightness(1.06) saturate(1.12); }
.county-list li.is-chosen { background: var(--navy-050); border-radius: var(--r-sm); }
.county-list li.is-chosen .county-list__btn { color: var(--navy); text-decoration: underline;
  text-underline-offset: .18em; }

/* Anchor targets on a page with a sticky jump bar have to clear both the
   header and the bar, or the heading lands underneath them. */
.jumpnav ~ [id] { scroll-margin-top: calc(var(--header-h) + 5rem); }
@media (max-width: 760px) { .jumpnav ~ [id] { scroll-margin-top: calc(var(--header-h) + var(--s-4)); } }

/* ═══════════════════════════════════════════════════════════════════════
   31. CALLOUT  —  one wide horizontal prompt, not a second card

   Where a band ends in a single "and if none of that fits you, ask us"
   invitation, it runs the full width of the band with its action on the
   right. Two cards of unequal height sitting beside each other look like a
   layout accident; one wide row does not.
   ═══════════════════════════════════════════════════════════════════════ */
.callout {
  display: grid; grid-template-columns: 1fr auto;
  align-items: center; gap: var(--s-4) var(--s-7);
  margin-top: var(--s-6);
  padding: var(--s-5) var(--s-6);
  background: var(--white);
  border: 1px solid var(--cream-200);
  border-left: 5px solid var(--gold);
  border-radius: var(--r-lg);
}
.callout h2, .callout h3 { font-size: var(--t-2); }
.callout p { margin-top: var(--s-2); max-width: 74ch; }
.callout__action { margin: 0; }
/* A callout that opens its band carries no top margin of its own — the band's
   padding already spaces it, and the margin is only for following content. */
.container > .callout:first-child { margin-top: 0; }
.band--navy .callout, .band--navy-deep .callout {
  background: var(--navy-800); border-color: rgba(255,255,255,.14); border-left-color: var(--gold);
}
.band--navy .callout h2, .band--navy .callout h3,
.band--navy-deep .callout h2, .band--navy-deep .callout h3 { color: var(--gold); }
.band--navy .callout p, .band--navy-deep .callout p { color: var(--navy-300); }
@media (max-width: 760px) { .callout { grid-template-columns: 1fr; } }

/* ═══════════════════════════════════════════════════════════════════════
   32. FACT STRIP  —  the break between a hero and the first body copy

   A slim band of four facts. Not stat cards: those belong to the home page
   and would put a row of boxes at the top of every page that used them.
   ═══════════════════════════════════════════════════════════════════════ */
/* No rules of its own. The hero above already ends in a gold line, and a
   second one under the strip turned it into a sandwich. */
.factstrip { padding-block: var(--s-5); border-top: 0; border-bottom: 0; }
.factstrip::before { content: none; }
.factstrip__inner { display: flex; flex-wrap: wrap; gap: var(--s-5) var(--s-8); }
.factstrip__item { display: grid; gap: 1px; margin: 0; max-width: none; }
.factstrip__item strong {
  font-family: var(--font-serif); font-size: var(--t-2); font-weight: 700;
  line-height: 1.15; color: var(--gold);
}
.factstrip__item span { font-size: var(--t--1); color: var(--navy-300); }

/* ═══════════════════════════════════════════════════════════════════════
   33. SPLIT  —  text with a photograph beside it

   A section of body copy on its own gives the eye nothing to rest on. The
   picture sits level with the text rather than being hung above it, and the
   buttons sit under the words they belong to rather than floating between
   the two columns. flip puts the picture on the left, so a run of splits
   down a page does not march in step.
   ═══════════════════════════════════════════════════════════════════════ */
.split {
  display: grid;
  grid-template-columns: minmax(0, 1.02fr) minmax(0, .98fr);
  gap: clamp(var(--s-5), 3vw, var(--s-7));
  align-items: center;
}
.split__text > * + * { margin-top: var(--s-4); }
.split__text .btn-row { margin-top: var(--s-5); }
.split__text .note { margin-top: var(--s-5); }
.split__media { margin: 0; }
.split__frame {
  aspect-ratio: 4 / 3;
  border-radius: var(--r-lg);
  overflow: hidden;
  background: var(--navy-050);
  box-shadow: var(--shadow-lg);
}
.split__frame img {
  width: 100%; height: 100%;
  object-fit: cover;
  object-position: var(--focus, 50% 50%);
}
.split__media figcaption {
  margin-top: var(--s-3);
  font-size: var(--t--1); line-height: 1.5; color: var(--ink-muted);
  max-width: 46ch;
}
.band--navy .split__media figcaption,
.band--navy-deep .split__media figcaption { color: var(--navy-300); }
.band--navy .split__frame, .band--navy-deep .split__frame { box-shadow: none; border: 1px solid rgba(255,255,255,.14); }

/* On the flipped variant the picture is first in the visual order but stays
   second in the source, so the heading is still what a screen reader meets
   first in the section. */
.split--flip .split__media { order: -1; }

@media (max-width: 900px) {
  .split { grid-template-columns: 1fr; gap: var(--s-6); }
  .split--flip .split__media { order: 0; }
}

/* ═══════════════════════════════════════════════════════════════════════
   34. REACH  —  the numbers and the map under one centred heading

   Four figures in a row and a map somewhere else were two separate claims
   about the same thing. Together, two by two beside the shape of the state,
   they read as one.
   ═══════════════════════════════════════════════════════════════════════ */
.reach {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: clamp(var(--s-6), 4vw, var(--s-8));
  align-items: center;
}
.reach__stats { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--s-4); }

/* Compact KPIs. At full size, four of these stacked two-by-two beside a map
   made the band twice as tall as it was before the map went in; the number
   still leads, it just stops shouting. */
.reach__stats .stat { padding: var(--s-5) var(--s-4) var(--s-4); }
.reach__stats .stat::before { width: 30px; height: 5px; }
.reach__stats .stat__num { font-size: var(--t-2); }
.reach__stats .stat__label { font-size: .8125rem; line-height: 1.45; }
.reach .map-figure { margin: 0; }
.reach .map-figure__canvas { max-width: 420px; margin-inline: auto; }
.reach .map-legend { justify-content: center; }
/* The home map renders at about half the width of the one on the service
   area page, so the star is scaled to stay legible at that size. */
.reach .map-office path { transform: scale(1.5); }
/* The button belongs to the numbers it sits under, so it is left-aligned
   with them rather than centred under the whole band. */
.reach__col { display: grid; gap: var(--s-5); align-content: center; }
.reach__cta { margin: 0; max-width: none; }

/* This band is a break between two long sections; it closes up at both ends
   so it reads as a strip rather than a chapter of its own. */
.reach-band { padding-block: var(--s-6) var(--s-5); }
.reach-band .band__head { margin-bottom: var(--s-4); }

/* The legend sits on navy here, not on cream */
.band--navy .map-legend, .band--navy .map-figure figcaption { color: var(--navy-300); }
.band--navy .map-legend__key--other { background: var(--navy-800); border-color: var(--navy-600); }
/* The map fills served counties with gold on navy, so the legend swatch has to
   agree with it rather than staying the navy used on light grounds. */
.band--navy .map-legend__key--served { background: var(--gold); }

@media (max-width: 900px) {
  .reach { grid-template-columns: 1fr; }
  .reach .map-figure__canvas { margin-inline: auto; }
}
@media (max-width: 520px) {
  .reach__stats { grid-template-columns: 1fr; }
}

/* An informational slide: the picture on one side, and on the other the
   name, who it is for, what it is, and the way in. Same component as the
   photo gallery — same controls, same one-at-a-time behaviour. */
.slide--info { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: clamp(var(--s-5), 3vw, var(--s-7)); align-items: center; }
.slide--info .slide__media { aspect-ratio: 4 / 3; max-height: min(52vh, 30rem); }
.slide__body > * + * { margin-top: var(--s-3); }
.slide__title { font-size: var(--t-3); }
.slide__title a { color: inherit; text-decoration: none; }
.slide__title a:hover { text-decoration: underline; text-underline-offset: .18em; }
.slide__audience { font-weight: 600; color: var(--gold-deep); }
.slide__body .btn-row { margin-top: var(--s-5); }
.band--navy .slide__audience, .band--navy-deep .slide__audience { color: var(--gold); }
@media (max-width: 820px) {
  .slide--info { grid-template-columns: 1fr; }
  .slide--info .slide__media { max-height: 42vh; }
}

/* A contact card leads with the address or the number itself, not with a
   label: the thing you came for is the thing set largest. */
.contact-pair { max-width: 56rem; }
.card__lead { font-size: var(--t-1); font-weight: 600; }
.card__lead a { text-decoration-thickness: 1px; text-underline-offset: .22em; }

/* The gold wash carries the programme signpost at the foot of a programme
   page. Its rowlist keeps a white surface, so nothing has to change inside. */
/* A gold band draws no seam of its own: the wash IS the divider. A gold rule
   sitting directly on a gold ground read as a doubled line, so the band meets
   whatever is above it with nothing but its own colour change. */
.band--gold { border-top: 0; }

/* No yellow line may touch a gold ground from above either: a navy band that
   ends against a gold band gives up its bottom gold border, since the wash
   below already does the separating. */
.band--navy:has(+ .band--gold),
.band--navy-deep:has(+ .band--gold) { border-bottom: 0; }

/* The same rule where a page meets the footer. A navy band that closes the
   page would put its gold bottom border directly against the footer's gold
   top seam — two lines with only the dark stripe between them — so the band
   yields and the footer's single seam does the work. */
main > .band--navy:last-child,
main > .band--navy-deep:last-child { border-bottom: 0; }

/* And a page that closes on a gold band hands the footer no seam at all:
   navy-900 rising out of the gold wash is already the strongest edge on the
   page, and a gold line touching the gold ground would double it. */
main:has(> .band--gold:last-child) + .site-footer { border-top: 0; }
main:has(> .band--gold:last-child) + .site-footer::before { content: none; }

.band--gold .rowlist { border-color: #E9DCB8; }
.band--gold .btn--ghost { border-color: var(--gold-deep); }
.band--gold .btn--ghost:hover { background: var(--white); border-color: var(--navy); }
/* A gold accent border would vanish into (and double) the gold wash, so the
   callout's marker goes navy on this ground — same two-tone logic as the seams. */
.band--gold .callout { border-left-color: var(--navy); }

/* ── Hero headings: let them run ─────────────────────────────────────────
   A measure limit is for reading paragraphs, not for a four-word headline.
   The lede keeps a readable 58ch; the heading is freed to sit on one line
   wherever it fits, and wraps only when it genuinely must. text-wrap: balance
   still governs the cases that do wrap, so those break evenly. */
.hero__content { max-width: min(100%, 54rem); }
.hero__content .lede { max-width: 58ch; }
.hero h1 { max-width: none; }

/* Section headings, same reasoning as the hero: the measure belongs on the
   paragraph under the heading, not on the heading itself. */
.band__head { max-width: min(100%, 60rem); }
.band__head > p { max-width: var(--measure); }
.band__head h2 { max-width: none; }

/* ═══════════════════════════════════════════════════════════════════════
   Sprint 1 additions
   ═══════════════════════════════════════════════════════════════════════ */

/* ── Partner logos, now with names ───────────────────────────────────────
   A logo alone asks the reader to recognise it. Most people will not know
   what a hospital system's mark looks like, and the ones who most need to
   know who we work with — students, their families — are the least likely
   to. The name underneath is the point; the logo is the decoration.

   Each partner is a fixed-width column so the marks sit on a common baseline
   and the names wrap under their own logo instead of running into the next. */
.partner-logos {
  align-items: flex-start;
  gap: var(--s-6) var(--s-7);
}

.partner {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--s-3);
  width: 11rem;
  text-align: center;
  text-decoration: none;
  color: inherit;
}

/* A fixed box for the mark, so a tall logo and a wide one still line their
   captions up with each other. */
.partner__mark {
  display: grid;
  place-items: center;
  height: 64px;
}
.partner__mark img {
  max-height: 64px;
  max-width: 100%;
  width: auto;
}

.partner__name {
  display: block;
  font-size: var(--t--1);
  font-weight: 600;
  line-height: 1.35;
  color: var(--navy);
  text-wrap: balance;
}

/* The launch year is context, not the name — so it sits under it, lighter,
   and never competes with the organisation it belongs to. */
.partner__since {
  display: block;
  margin-top: .2em;
  font-size: .85em;
  font-weight: 400;
  color: var(--ink-muted);
}

.partner:hover .partner__name { text-decoration: underline; }
.partner:focus-visible {
  outline: 2px solid var(--navy);
  outline-offset: 4px;
  border-radius: var(--r-sm);
}

/* ── Funding table ───────────────────────────────────────────────────────
   Figures in a table are read across a row and compared down a column, and
   this one sits on the gold wash where a borderless table dissolves. So: a
   white surface to lift it off the ground, ruled cells so the eye can hold a
   row, and the total marked as a total rather than left looking like a third
   ordinary row. */
.funding-table {
  width: 100%;
  border-collapse: collapse;
  background: var(--white);
  border: 1px solid var(--border-strong);
  border-radius: var(--r-md);
  overflow: hidden;
}

.funding-table caption {
  caption-side: top;
  text-align: left;
  padding-bottom: var(--s-3);
  font-size: var(--t--1);
  font-weight: 600;
  color: var(--ink-muted);
}

.funding-table th,
.funding-table td {
  padding: var(--s-3) var(--s-4);
  border-bottom: 1px solid var(--cream-200);
  text-align: left;
}

.funding-table thead th {
  background: var(--navy);
  color: var(--white);
  font-size: var(--t--1);
  letter-spacing: .04em;
  text-transform: uppercase;
  border-bottom: 0;
}

.funding-table tbody th {
  font-weight: 600;
  color: var(--ink);
}

/* Figures line up digit under digit, which is the whole reason to put them
   in a table rather than a sentence. */
.funding-table .num {
  text-align: right;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.funding-table tbody tr:hover { background: var(--navy-050); }

.funding-table__total th,
.funding-table__total td {
  font-weight: 700;
  color: var(--navy);
  background: var(--gold-soft);
  border-top: 2px solid var(--gold-deep);
  border-bottom: 0;
}
.funding-table__total:hover { background: var(--gold-soft); }

/* The required disclaimer that follows the table. Quieter than the statement
   above it — it is legally necessary rather than something anyone reads by
   choice — but never so quiet it fails contrast. */
.sub-note {
  margin-top: var(--s-5);
  max-width: var(--measure);
  font-size: var(--t--1);
  line-height: 1.6;
  color: var(--ink-muted);
}

@media (max-width: 40rem) {
  .partner { width: 9rem; }
  .funding-table th,
  .funding-table td { padding: var(--s-2) var(--s-3); }
}

/* ═══════════════════════════════════════════════════════════════════════
   Sprint 3 additions
   ═══════════════════════════════════════════════════════════════════════ */

/* ── Logos supplied as JPEG ──────────────────────────────────────────────
   A JPEG cannot carry transparency, so a logo saved as one arrives with a
   white box around it — obvious against the gold wash the partners sit on.
   The ICRH and Project ECHO marks are both JPEGs.

   Multiply blending drops white to nothing on a light ground: white
   multiplied by the background is the background. It costs no re-encoding
   and leaves none of the fringing that keying the white out by hand would,
   and a logo that is already transparent is unaffected by it.

   The one thing it cannot survive is a dark ground — white would go black
   there rather than away — so it is scoped to the partner strip, which is
   always the gold wash. */
.partner__mark img { mix-blend-mode: multiply; }

/* ── Cards inside a tab panel ────────────────────────────────────────────
   The programme cards carry no image, so the flat variant is right — but a
   flat card on a white band has nothing to hold it together. A hairline and
   the site's own radius give each one an edge without adding weight. */
.tabset__panel .card--flat {
  border: 1px solid var(--cream-200);
  border-radius: var(--r-md);
  background: var(--white);
}
.tabset__panel .card--flat .card__body { gap: var(--s-3); }
.tabset__panel .card--flat .card__title { font-size: var(--t-2); }

/* The button sits at the foot of the card whatever the text above it does,
   so a row of cards has its buttons on one line rather than stepping. */
.tabset__panel .card--flat .card__body { display: flex; flex-direction: column; }
.tabset__panel .card--flat .btn-row { margin-top: auto; padding-top: var(--s-2); }

@media (min-width: 48rem) {
  .grid--2 { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--s-5); }
}

/* ═══════════════════════════════════════════════════════════════════════
   Sprint 4 — the programme slideshow as a second hero
   ═══════════════════════════════════════════════════════════════════════ */

/* Full-bleed inside a centred container. The band clips horizontally so the
   100vw breakout cannot produce a sideways scrollbar — which is what usually
   goes wrong with this technique. */
.band:has(.slideshow--hero) { overflow-x: clip; }

.slideshow--hero {
  position: relative;
  width: 100vw;
  max-width: 100vw;
  margin-inline: calc(50% - 50vw);
  margin-top: var(--s-6);
}

.slide--hero {
  position: relative;
  isolation: isolate;
  min-height: clamp(22rem, 46vh, 34rem);
  display: grid;
  margin: 0;
}

/* The photograph becomes the ground rather than a panel beside the text. */
.slide--hero .slide__media {
  position: absolute;
  inset: 0;
  aspect-ratio: auto;
  max-height: none;
  border-radius: 0;
  overflow: hidden;
}
.slide--hero .slide__media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* Darkest where the words are, clearing towards the right so the photograph
   is still a photograph. White on the left third clears AA comfortably; the
   scrim is doing contrast work, not decoration. */
.slide__scrim {
  position: absolute;
  inset: 0;
  background: linear-gradient(
    90deg,
    rgba(11, 20, 40, .90) 0%,
    rgba(11, 20, 40, .78) 38%,
    rgba(11, 20, 40, .30) 72%,
    rgba(11, 20, 40, .12) 100%
  );
}

.slide__overlay {
  position: relative;
  z-index: 1;
  display: grid;
  align-content: center;
  padding-block: var(--s-7);
}

.slide__inner {
  width: min(100% - 2.5rem, var(--container, 1200px));
  margin-inline: auto;
  max-width: 46rem;
  color: var(--white);
  display: grid;
  gap: var(--s-3);
}

.slide--hero .slide__audience {
  color: var(--gold);
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  font-size: var(--t--1);
  margin: 0;
}
.slide--hero .slide__title {
  color: var(--white);
  font-size: var(--t-4);
  max-width: none;
  margin: 0;
}
.slide--hero .slide__title a { color: var(--white); text-decoration: none; }
.slide--hero .slide__title a:hover { text-decoration: underline; text-underline-offset: .18em; }
.slide--hero .slide__inner p {
  color: rgba(255, 255, 255, .93);
  max-width: 46ch;
  margin: 0;
}
.slide--hero .btn-row { margin-top: var(--s-2); }

/* ── One arrow, on the right ─────────────────────────────────────────────
   The controls layer covers the slide but lets clicks through; only the
   controls themselves take pointer events, so the photograph underneath is
   not swallowing clicks. */
.slideshow--hero .slideshow__controls {
  position: absolute;
  inset: 0;
  display: block;
  margin: 0;
  padding: 0;
  pointer-events: none;
  z-index: 2;
}

.slideshow--hero .slideshow__btn {
  pointer-events: auto;
  position: absolute;
  /* Not translateY: the theme's JS sets an inline transform: scaleX(-1) on the
     next button to flip its chevron, and an inline style would win. Centring
     with top/calc leaves that transform alone. */
  top: calc(50% - 1.625rem);
  right: clamp(.75rem, 2.5vw, 2.25rem);
  width: 3.25rem;
  height: 3.25rem;
  border-radius: 50%;
  background: rgba(255, 255, 255, .16);
  border: 1px solid rgba(255, 255, 255, .45);
  backdrop-filter: blur(6px);
  -webkit-backdrop-filter: blur(6px);
  color: #fff;
  opacity: .78;
  transition: opacity .15s ease, background .15s ease;
}
.slideshow--hero .slideshow__btn:hover,
.slideshow--hero .slideshow__btn:focus-visible {
  opacity: 1;
  background: rgba(255, 255, 255, .3);
}
.slideshow--hero .slideshow__btn:focus-visible {
  outline: 3px solid var(--gold);
  outline-offset: 3px;
}

/* One arrow was the request, so the previous button goes. The dots stay —
   they are the only way to reach a specific slide, and removing every route
   but "next" would make the ninth programme nine clicks deep. */
.slideshow--hero .slideshow__btn:first-of-type { display: none; }
.slideshow--hero .slideshow__count { display: none; }

.slideshow--hero .slideshow__dots {
  pointer-events: auto;
  position: absolute;
  left: 50%;
  transform: translateX(-50%);
  bottom: clamp(.75rem, 2vh, 1.25rem);
  gap: .5rem;
  margin: 0;
}
.slideshow--hero .slideshow__dot {
  background: rgba(255, 255, 255, .45);
  border-color: transparent;
}
.slideshow--hero .slideshow__dot[aria-current="true"] { background: var(--gold); }

/* Narrow screens: the scrim goes full-strength, because there is no longer a
   clear right-hand side for the photograph to breathe into. */
@media (max-width: 48rem) {
  .slide--hero { min-height: clamp(20rem, 62vh, 28rem); }
  .slide__scrim {
    background: linear-gradient(
      180deg,
      rgba(11, 20, 40, .55) 0%,
      rgba(11, 20, 40, .85) 55%,
      rgba(11, 20, 40, .92) 100%
    );
  }
  .slide__overlay { align-content: end; }
  .slideshow--hero .slideshow__btn {
    width: 2.75rem;
    height: 2.75rem;
    top: calc(50% - 1.375rem);
  }
}

/* A short-item list that would otherwise run down the page in a single
   column — county names, for instance. Columns are capped so the list never
   becomes wider than it is readable. */
.collist {
  columns: 3 12rem;
  column-gap: var(--s-6);
  max-width: 44rem;
}
.collist li { break-inside: avoid; }
/* ═══════════════════════════════════════════════════════════════
   Program tile directory  —  What We Do
   Replaces the carousel and tab system. Each tile is one link that
   wraps its own image and text, so there is exactly one tab stop and
   one announcement per program.
   ═══════════════════════════════════════════════════════════════ */

.ptilegroup { margin-bottom: 2.75rem; }
.ptilegroup:last-child { margin-bottom: 0; }

.ptilegroup__head { margin-bottom: 1.1rem; }
.ptilegroup__head h3 { margin: 0 0 .3rem; }
.ptilegroup__head p { margin: 0; color: #4a5568; }

.ptiles {
  display: grid;
  gap: 1.25rem;
  grid-template-columns: repeat(3, 1fr);
}
@media (max-width: 900px) { .ptiles { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 600px) { .ptiles { grid-template-columns: 1fr; } }

.ptile {
  position: relative;
  display: block;
  overflow: hidden;
  border-radius: 10px;
  aspect-ratio: 4 / 3;
  text-decoration: none;
  isolation: isolate;
  background: #0b1f3b;
  box-shadow: 0 1px 3px rgba(0, 0, 0, .16);
}

.ptile__img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  transition: transform .4s ease, filter .4s ease;
}

/* The gradient is what makes the overlaid text legible, so it is opaque
   where the text sits and clears completely at the top of the image. */
.ptile__veil {
  position: absolute;
  inset: 0;
  background: linear-gradient(
    to top,
    rgba(11, 31, 59, .95) 0%,
    rgba(11, 31, 59, .88) 30%,
    rgba(11, 31, 59, .45) 58%,
    rgba(11, 31, 59, 0) 100%
  );
}

.ptile__text {
  position: absolute;
  left: 0;
  right: 2.4rem;
  bottom: 0;
  padding: 1.1rem 1.15rem;
  z-index: 1;
}

.ptile__title {
  display: block;
  margin: 0 0 .3rem;
  font-family: inherit;
  font-size: 1.05rem;
  font-weight: 700;
  line-height: 1.25;
  color: #ffffff;
}

.ptile__line {
  display: block;
  font-size: .87rem;
  line-height: 1.4;
  color: #eef3fa;
}

.ptile__arrow {
  position: absolute;
  right: 1rem;
  bottom: 1.1rem;
  z-index: 2;
  font-size: 1.15rem;
  line-height: 1;
  color: #ffc84a;
  transition: transform .3s ease;
}

.ptile:hover .ptile__img,
.ptile:focus-visible .ptile__img {
  transform: scale(1.04);
  filter: brightness(1.07);
}
.ptile:hover .ptile__arrow { transform: translateX(3px); }

.ptile:focus-visible {
  outline: 3px solid #ffc84a;
  outline-offset: 3px;
}

@media (prefers-reduced-motion: reduce) {
  .ptile__img,
  .ptile__arrow { transition: none; }
  .ptile:hover .ptile__img,
  .ptile:focus-visible .ptile__img { transform: none; }
  .ptile:hover .ptile__arrow { transform: none; }
}

/* ═══════════════════════════════════════════════════════════════
   Footer simplified to Brand / Explore / Get in Touch.
   The nine-program directory moved out of the footer: every program
   is reachable once from What We Do, so repeating the full list here
   made the footer a second navigation of its own.
   ═══════════════════════════════════════════════════════════════ */

.site-footer__grid { grid-template-columns: 1.6fr 1fr 1.4fr; }

.site-footer__addr {
  margin: var(--s-4) 0 0;
  color: var(--navy-300);
  font-size: var(--t--1);
  line-height: 1.65;
  font-style: normal;
}

/* One restrained line rather than three separated blocks. */
.site-footer__bottom { justify-content: center; text-align: center; }
.site-footer__bottom p { margin: 0; }

/* ═══════════════════════════════════════════════════════════════
   Report list labels
   The year and the file-type tag are small text (well under 18.66px),
   so both need 4.5:1. --gold is an accent tone and does not reach it
   on a light surface; --gold-deep is the gold that does.
   ═══════════════════════════════════════════════════════════════ */

.report__year {
  color: var(--gold-deep);
  font-weight: 700;
}

.report__type {
  color: #4A5568;
}

/* ═══════════════════════════════════════════════════════════════
   What We Do — stage dividers and program sections

   Each program is a full-width section of its own. The three stage
   bands are deliberately loud so the eye reads the page as three
   groups of distinct sections rather than one long scroll.
   ═══════════════════════════════════════════════════════════════ */

/* ── The jump links in the page introduction ─────────────────── */
.stagenav {
  display: flex;
  flex-wrap: wrap;
  gap: var(--s-3);
  margin-top: var(--s-5);
}

/* ── Stage divider bands ─────────────────────────────────────── */
.stageband { text-align: center; }

.stageband__eyebrow {
  margin: 0 0 var(--s-2);
  color: var(--gold);
  font-size: var(--t--1);
  font-weight: 700;
  letter-spacing: .14em;
  text-transform: uppercase;
}

.stageband__title {
  margin: 0;
  font-size: clamp(2.4rem, 6vw, 4rem);
  line-height: 1.02;
  letter-spacing: -.02em;
  color: #fff;
}

/* A short gold rule under the stage name, so the band reads as a
   divider between groups and not as another content section. */
.stageband__title::after {
  content: "";
  display: block;
  width: 4.5rem;
  height: 4px;
  margin: var(--s-4) auto 0;
  background: var(--gold);
  border-radius: 2px;
}

.stageband__lede {
  max-width: 46ch;
  margin: var(--s-4) auto 0;
  color: var(--navy-300);
  font-size: var(--t-1);
}

/* ── Program section headings ────────────────────────────────── */
.program__title {
  margin: 0 0 var(--s-3);
  font-size: clamp(1.9rem, 3.4vw, 2.75rem);
  line-height: 1.12;
  letter-spacing: -.015em;
}

/* The one-line summary sits directly under the heading and carries
   the gold rule, tying each program back to its stage band. */
.program__title + .lede {
  position: relative;
  padding-top: var(--s-3);
  font-weight: 600;
}
.program__title + .lede::before {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  width: 3rem;
  height: 3px;
  background: var(--gold);
  border-radius: 2px;
}

/* Program sections carry more air than a standard band, which is what
   makes nine of them read as separate places rather than a list. */
.band--white  > .container > .split,
.band--cream  > .container > .split { padding-block: var(--s-3); }

@media (max-width: 700px) {
  .stageband__title::after { margin-top: var(--s-3); }
  .program__title { margin-bottom: var(--s-2); }
}

/* The eyebrow and lede are paragraphs, and the theme left-aligns paragraphs
   inside a band, which beats the centring inherited from .stageband. State the
   alignment on the children so the whole divider reads as one centred unit. */
.stageband .container > * { text-align: center; }

/* ═══════════════════════════════════════════════════════════════
   Program cards inside the What We Do tabs

   Two per row rather than three. There are only two to four programs
   in a tab, so each card can be large enough to carry a real
   description over the photograph instead of a single line.
   These rules come after the original .ptile block and replace it.
   ═══════════════════════════════════════════════════════════════ */

.ptiles {
  grid-template-columns: repeat(2, 1fr);
  gap: var(--s-6);
  margin-top: var(--s-5);
}
@media (max-width: 860px) { .ptiles { grid-template-columns: 1fr; } }

.ptile {
  aspect-ratio: 16 / 10;
  border-radius: 12px;
  box-shadow: 0 2px 10px rgba(13, 26, 48, .18);
}

/* The text sits over the lower part of the photograph, so the veil has to
   be opaque where the words are and clear where the picture matters. */
.ptile__veil {
  background: linear-gradient(
    to top,
    rgba(11, 31, 59, .96) 0%,
    rgba(11, 31, 59, .92) 38%,
    rgba(11, 31, 59, .55) 66%,
    rgba(11, 31, 59, .05) 100%
  );
}

.ptile__text {
  right: 3.4rem;
  padding: 1.5rem 1.65rem;
}

.ptile__title {
  margin-bottom: .5rem;
  font-size: clamp(1.2rem, 1.9vw, 1.5rem);
  line-height: 1.2;
}

.ptile__line {
  font-size: .95rem;
  line-height: 1.5;
}

.ptile__arrow {
  right: 1.5rem;
  bottom: 1.55rem;
  font-size: 1.4rem;
}

@media (max-width: 520px) {
  .ptile { aspect-ratio: 4 / 3; }
  .ptile__text { padding: 1.2rem 1.25rem; right: 2.8rem; }
}


/* ═══════════════════════════════════════════════════════════════
   Footer — shorter

   Four narrow columns instead of three wide ones, so the link lists
   stop stacking into a tall block. Everything is tightened: the
   bottom row is one small line rather than three stacked ones.
   ═══════════════════════════════════════════════════════════════ */

.site-footer__grid {
  grid-template-columns: 1.5fr 1fr 1fr 1.3fr;
  gap: var(--s-5) var(--s-6);
}
@media (max-width: 900px) {
  .site-footer__grid { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 520px) {
  .site-footer__grid { grid-template-columns: 1fr; }
}

.site-footer__logo img { width: 168px; margin-bottom: var(--s-3); }
.site-footer__logo p { font-size: var(--t--1); line-height: 1.55; margin: 0; }

.site-footer h2 {
  margin: 0 0 var(--s-3);
  font-size: var(--t--1);
  letter-spacing: .1em;
  text-transform: uppercase;
  color: var(--gold);
}

.site-footer ul { gap: var(--s-2); font-size: var(--t--1); }

.site-footer__addr {
  margin: var(--s-3) 0 0;
  color: var(--navy-300);
  font-size: var(--t--2, .78rem);
  line-height: 1.5;
  font-style: normal;
}

.site-footer__bottom {
  margin-top: var(--s-4);
  padding-top: var(--s-3);
  justify-content: center;
  text-align: center;
  font-size: var(--t--2, .78rem);
}
.site-footer__bottom p { margin: 0; }

/* Keep the bottom row breaking between its items rather than inside a name,
   so it never reads as "Website by Garland / Tech Consulting". */
.site-footer__bottom a { white-space: nowrap; }
.site-footer__bottom p { line-height: 1.9; }

/* The footer was tightened to bring its height down, which pushed the type
   further than it needed to go. Step it back up for legibility — the height
   saving comes from the four-column layout, not from small text. */

.site-footer__logo p { font-size: .95rem; line-height: 1.6; }

.site-footer h2 { font-size: .82rem; letter-spacing: .09em; }

.site-footer ul { font-size: .95rem; gap: var(--s-2); }

.site-footer__addr { font-size: .9rem; line-height: 1.6; }

.site-footer__bottom { font-size: .875rem; }

/* ═══════════════════════════════════════════════════════════════
   Card hover — lift the overlay off the photograph

   At rest the navy veil covers the whole image so the text reads.
   On hover (and on keyboard focus, so it is not mouse-only) the veil
   fades out and the photograph is shown properly.

   The words still have to be readable while that happens, so a short
   gradient fades IN behind just the text as the full veil fades out.
   The picture is revealed; the label never sits on bare photograph.
   ═══════════════════════════════════════════════════════════════ */

.ptile__veil {
  transition: opacity .35s ease;
}

.ptile:hover .ptile__veil,
.ptile:focus-visible .ptile__veil {
  opacity: 0;
}

/* Sits inside .ptile__text, which already establishes a stacking context
   with z-index:1, so a negative z-index here stays behind the words and
   above the image rather than escaping to the back of the card. */
.ptile__text::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  top: -2.75rem;
  z-index: -1;
  background: linear-gradient(
    to top,
    rgba(11, 31, 59, .96) 45%,
    rgba(11, 31, 59, .78) 72%,
    rgba(11, 31, 59, 0) 100%
  );
  opacity: 0;
  transition: opacity .35s ease;
  pointer-events: none;
}

.ptile:hover .ptile__text::after,
.ptile:focus-visible .ptile__text::after {
  opacity: 1;
}

@media (prefers-reduced-motion: reduce) {
  .ptile__veil,
  .ptile__text::after { transition: none; }
}

/* Footer type up another step. The four-column layout is what keeps the
   footer short, so the links can sit at a comfortable reading size rather
   than being squeezed to save height. */

.site-footer__logo p { font-size: 1rem; line-height: 1.6; }

.site-footer h2 { font-size: .88rem; letter-spacing: .08em; }

.site-footer ul { font-size: 1.02rem; gap: var(--s-3); }

.site-footer__addr { font-size: .95rem; line-height: 1.6; }

.site-footer__bottom { font-size: .95rem; }

/* Footer logo scaled up to sit better against the column of text beneath it.
   Width only — the height follows the image's own ratio, so the mark is not
   stretched out of shape. */
.site-footer__logo img { width: 250px; max-width: 100%; height: auto; }

@media (max-width: 900px) {
  .site-footer__logo img { width: 215px; }
}

/* ═══════════════════════════════════════════════════════════════
   Footer, tighter still

   The bottom row was a flex container, so its single paragraph was
   treated as a shrinkable item and broke onto two lines well before
   it ran out of room. As a block it takes the full width and the
   whole line — copyright, Accessibility, Privacy, credit — fits.

   Everything else here is padding and gaps only. The type stays at
   the size it was just raised to.
   ═══════════════════════════════════════════════════════════════ */

.site-footer { padding-block: var(--s-5) var(--s-4); }

.site-footer h2 { margin-bottom: var(--s-2); }

.site-footer ul { gap: var(--s-2); }

.site-footer__grid { gap: var(--s-4) var(--s-6); }

.site-footer__logo img { margin-bottom: var(--s-2); }
.site-footer__logo p { margin: 0; }

.site-footer__addr { margin-top: var(--s-2); }

.site-footer__bottom {
  display: block;
  text-align: center;
  margin-top: var(--s-3);
  padding-top: var(--s-3);
}
.site-footer__bottom p { margin: 0; line-height: 1.6; }

/* Keep names intact if it ever does have to wrap on a narrow screen. */
.site-footer__bottom a { white-space: nowrap; }

/* ═══════════════════════════════════════════════════════════════
   Wider reading measure

   Every paragraph on the site inherits `p { max-width: var(--measure) }`,
   which was 68ch. That is a conservative measure and left a lot of empty
   space to the right of body copy in the wide bands. Widened so text runs
   further across before it wraps.
   ═══════════════════════════════════════════════════════════════ */

:root { --measure: 92ch; }

/* The lede has its own tighter cap, which now looks narrow next to the
   body text beneath it. Bring it up in proportion. */
.lede { max-width: 78ch; }
.band__head > p { max-width: var(--measure); }

/* The hero is a different case: it sits over a photograph and its lines
   should stay short, so leave the hero caps alone and only widen the
   in-page copy. */


/* ═══════════════════════════════════════════════════════════════
   Footer bottom row

   The credit was dropping to a second line because the paragraph — like
   every other p — was capped at the reading measure and pinned left. It
   is a single centred line of navigation, not body copy, so it opts out
   of the measure entirely and centres itself in the container.
   ═══════════════════════════════════════════════════════════════ */

.site-footer__bottom p {
  max-width: none;
  margin-inline: auto;
}

/* The bottom-row separators are their own element so the gap either side is
   set once here, rather than coming from non-breaking spaces plus whatever
   whitespace the source happened to contain. */
.site-footer__bottom .sep {
  display: inline-block;
  margin: 0 .55em;
  color: var(--navy-300);
  opacity: .65;
}

/* ═══════════════════════════════════════════════════════════════
   Footer column balance

   The columns were fractional, so the last one was 1.3fr wide while its
   longest line ("Contact Form", a phone number) is short. That left a
   block of dead space inside the final column, and the whole footer read
   as pushed to the left even though it filled the container.

   Sizing each column to its own content and spreading them with
   space-between puts the last column's text against the right edge, so
   the row looks balanced without moving the logo out of alignment with
   the page content above it.
   ═══════════════════════════════════════════════════════════════ */

.site-footer__grid {
  grid-template-columns: auto auto auto auto;
  justify-content: space-between;
  gap: var(--s-4) var(--s-7);
}

/* The brand column still needs a cap, or its mission sentence would set
   the width of the whole row. */
.site-footer__logo { max-width: 30ch; }

@media (max-width: 900px) {
  .site-footer__grid {
    grid-template-columns: repeat(2, auto);
    justify-content: space-between;
  }
}

@media (max-width: 520px) {
  .site-footer__grid {
    grid-template-columns: 1fr;
    justify-content: start;
  }
  .site-footer__logo { max-width: none; }
}

/* Partner marks a step smaller. The box stays a fixed height so a tall logo
   and a wide one still line their captions up with each other — shrinking the
   box alone would break that alignment. */
.partner__mark { height: 54px; }
.partner__mark img { max-height: 54px; }

/* A little more room per partner now that there are twelve of them, so the
   longer names wrap to two lines rather than three. */
.partner { width: 12rem; }

/* WCAG: ALGEE acronym contrast on Adult MHFA */
.page-id-518 section.band--navy[aria-labelledby="algee-h"] .deflist dt {
  color: var(--gold);
}


/* WCAG 1.4.10: prevent fixed card minimums from overflowing at 320px */
@media (max-width: 360px) {
  .grid--2 { grid-template-columns: minmax(0, 1fr); }
  .grid--2 > * { min-width: 0; max-width: 100%; }
}
