/* --- ALS Hope Foundation stylesheet ----------------------------------------
   One stylesheet, hand-editable.

   Order: fonts, tokens, global, the daybreak overrides, then what used to be
   each component's scoped <style>, base components first. Astro's :global()
   wrappers are stripped, since nothing here is scoped.
   ------------------------------------------------------------------------ */


/* --- Fonts -------------------------------------------------------------- */

/* --- Poppins: the single family --------------------------------------------
   This is the foundation's own type: its printed identity embeds Poppins and
   nothing else (verified with pdffonts, not by eye).

   It has no width axis, so every display style comes from size and weight
   alone, and every font-variation-settings declaration is a plain
   font-weight.

   Six static cuts rather than a variable file: Google does not publish a
   variable Poppins, and 400/500/600/700 plus two italics is 48KB total.

   Latin subset only. This site is English; latin-ext would roughly double the
   payload for glyphs no page uses.

   Paths carry the site's base-path prefix because /public assets are not
   rewritten by Astro's base handling.
   ------------------------------------------------------------------------ */

/* Poppins Light, for standfirsts. NOT for body text: at 16px this weight
   loses legibility, and this site is read mostly by older patients and
   families. Only used from --step-1 up. */
@font-face {
  font-family: 'Poppins';
  font-style: normal;
  font-weight: 300;
  font-display: swap;
  src: url(../assets/fonts/poppins-300.woff2) format('woff2');
}

@font-face {
  font-family: 'Poppins';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url(../assets/fonts/poppins-400.woff2) format('woff2');
}

@font-face {
  font-family: 'Poppins';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url(../assets/fonts/poppins-500.woff2) format('woff2');
}

@font-face {
  font-family: 'Poppins';
  font-style: normal;
  font-weight: 600;
  font-display: swap;
  src: url(../assets/fonts/poppins-600.woff2) format('woff2');
}

@font-face {
  font-family: 'Poppins';
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url(../assets/fonts/poppins-700.woff2) format('woff2');
}

/* Job titles are set in italic ("President", "Executive Director") and pull
   quotes in bold italic, so both cuts earn their place. */
@font-face {
  font-family: 'Poppins';
  font-style: italic;
  font-weight: 400;
  font-display: swap;
  src: url(../assets/fonts/poppins-400-italic.woff2) format('woff2');
}

@font-face {
  font-family: 'Poppins';
  font-style: italic;
  font-weight: 700;
  font-display: swap;
  src: url(../assets/fonts/poppins-700-italic.woff2) format('woff2');
}

/* --- Tokens ------------------------------------------------------------- */

/* --- ALS Hope Foundation design tokens -------------------------------------
   Color strategy: DRENCHED. The surface is the color. The logo's deep blue is
   the ground and the logo's yellow half-sun is the light inside it. Not a
   white page with blue accents, which reads as a template.

   Theme chosen by scene, not category: a daughter in her forties, 11pm, in
   bed with her phone, working out what to do after her father's ALS
   diagnosis. At that hour a bright white page is an assault.

   OKLCH throughout, hue 262 on the logo blue. Every neutral tinted toward it.
   No pure black, no pure white. Ratios below were measured on the rendered
   DOM, not estimated.
   ------------------------------------------------------------------------ */

:root {
  /* --- the ground ----------------------------------------------------------
     THE PALETTE IS THE FOUNDATION'S OWN, sampled from its printed identity.

     Sampled off the rendered cover at 150dpi, then converted:   navy
     #001C58   oklch(0.255 0.114 261.5)   yellow      #FFC93C   oklch(0.861
     0.159 86.4)   yellow deep #E1AF2C   oklch(0.779 0.148 85.9)   grey
     #ECEDEF   oklch(0.946 0.003 264.5)

     Hue 262 matches the sampled 261.5; the navy is lighter and considerably
     more saturated than a value derived from a PNG of the logo.

     Measured pairs, all AA or better: white on navy 16.07, yellow on navy
     10.46, navy on yellow 10.46, navy on grey 13.72. The one that fails is
     yellow on white at 1.54, which is why yellow is only ever a surface on
     this site and never a text colour on a light one.
     ---------------------------------------------------------------------- */
  --ground: oklch(0.255 0.114 261.5); /* #001C58, dominant dark surface */
  /* One step down for the hero and footer, which need to sit under a scrim
     and read as the deepest point. The brand has a single navy; this stays
     within it rather than introducing a second colour. */
  --ground-deep: oklch(0.205 0.098 261.5);
  --ground-raised: oklch(0.315 0.11 261.5); /* raised surfaces on dark */

  /* --- light sections, used for rhythm, never as the default ------------- */
  --paper: oklch(0.97 0.008 262);
  --paper-warm: oklch(0.955 0.015 95);

  /* The light scale. Three steps that do the separating a dark layout gets
     from --ground / --ground-raised / --ground-deep.

     Anchored on --paper and tinted toward hue 262, the logo blue: every
     neutral leans toward the brand hue.

     A warm cream scale on hue 95 (the sun's own hue) was dropped: beige reads
     as 2005, and it broke the tint rule. The warmth belongs to the sun
     itself, in the hero gradient and the giving band, not to the paper
     underneath everything. */
  --paper-1: oklch(0.942 0.011 262); /* raised surface on --paper */
  --paper-2: oklch(0.908 0.014 262); /* the plane inside that surface */
  --ink: oklch(0.2 0.035 262);
  --ink-soft: oklch(0.44 0.03 262);

  /* --- the light in it -----------------------------------------------------
     Both taken from the foundation's palette. --sun-deep is the same yellow
     one step darker, at hue 86. Orange does not appear anywhere in the
     palette, so the orange of the logo's outer rays is not used.

     The hero's glow keeps its orange, deliberately: that gradient is sunlight
     falling through a photograph, not a graphic plane, and a sunrise that is
     pure yellow looks like a filter.
     ---------------------------------------------------------------------- */
  --sun: oklch(0.861 0.159 86.4); /* #FFC93C */
  --sun-deep: oklch(0.779 0.148 85.9); /* #E1AF2C */

  /* Logo blue. NEVER on a --ground token: it measures 2.46:1 and fails.
     In this direction the blue became the surface, so as an accent it only
     has a job on light sections (6.61:1 on --paper). */
  --brand-blue: oklch(0.48 0.27 264);

  /* --- text on the drenched ground -------------------------------------- */
  --on-ground: oklch(0.975 0.01 262); /* 16.49:1 */
  --on-ground-soft: oklch(0.8 0.035 262); /* 9.47:1 */
  --on-ground-dim: oklch(0.68 0.04 262); /* 6.16:1, still AA */

  /* --- type ------------------------------------------------------------- */
  --font: 'Poppins', 'Helvetica Neue', Arial, sans-serif;

  /* Ratio 1.33 between steps. Flat scales read as uncommitted. */
  --step--1: clamp(0.875rem, 0.85rem + 0.1vw, 0.9375rem);
  --step-0: clamp(1rem, 0.97rem + 0.15vw, 1.125rem);
  --step-1: clamp(1.33rem, 1.26rem + 0.35vw, 1.6rem);
  --step-2: clamp(1.77rem, 1.62rem + 0.75vw, 2.4rem);
  --step-3: clamp(2.36rem, 2.02rem + 1.7vw, 3.6rem);
  --step-4: clamp(3.15rem, 2.4rem + 3.7vw, 5.4rem);
  --step-5: clamp(3.1rem, 1.9rem + 6.4vw, 7.4rem);

  /* Held at their neutral values so the font-variation-settings declarations
     left in the codebase are inert rather than wrong. Poppins has no width
     axis and no weight axis: it ships as static cuts, so display contrast now
     comes from size and weight, not from stretching the letterforms.

     Anything genuinely display-scale sets --wght-display as a font-weight. 700
     is Poppins' heaviest cut in use here; 750 was an Archivo axis value and
     rounds to nothing available. */
  --wdth-display: 100;
  --wdth-body: 100;
  --wght-display: 700;
  /* Heavy headline against thin letters. Only for large text; body stays at
     400. */
  --wght-lede: 300;

  /* --- space ------------------------------------------------------------ */
  --space-2xs: 0.375rem;
  --space-xs: 0.625rem;
  --space-s: 1rem;
  --space-m: 1.5rem;
  --space-l: 2.5rem;
  --space-xl: 4rem;
  --space-2xl: 6rem;
  --space-3xl: 9rem;

  /* Deliberately not one uniform section rhythm: uniform padding everywhere
     is monotonous. */
  --section-tight: clamp(3rem, 2.4rem + 3vw, 5rem);
  --section-y: clamp(4.5rem, 3.4rem + 5.5vw, 8rem);
  --section-loose: clamp(6rem, 4.4rem + 8vw, 11rem);

  /* Consumed by the hero, which pulls up behind the transparent masthead by
     exactly this much.

     It has to equal the masthead's real height or the hero starts late and a
     strip of body shows above it. Measured, not chosen: 58px of logo (the mark
     is 200px wide and its own ratio sets the height) plus 16px of padding top
     and bottom. It read 76px, which left a 14px gap that was invisible only
     because the body used to be navy too. On a white page it is a white band
     across the top of the photograph.

     If the masthead's padding or the logo width changes, this changes with it. */
  --masthead-h: 90px;

  --measure: 68ch;
  --shell: 78rem;
  --gutter: clamp(1.25rem, 0.85rem + 2vw, 3rem);

  /* --- shape ------------------------------------------------------------ */
  /* The rejected arch was `50% 50% 0 0`: round on top, flat on the base. That
     asymmetry is what read as a headstone, not the radius itself. A uniform
     radius on all four corners, and a capsule (round top AND bottom), carry no
     such reading. So radius is back, generously, as the surface language:
     panels and media are rounded, and separation comes from a step in
     luminance rather than from hairlines. */
  /* Kept at 14: a large radius reads as soft on a 500px card and as a bubble
     on a small one, and this page runs both: the Center of Hope panels are
     large, the figure plates are 56px. 14 holds at either size. */
  --radius-card: 14px;
  --radius-media: 12px;
  /* Controls get less than panels, not the same. A button is a small object
     and the radius is a proportion of what it sits on: 14px on a 47px-tall
     button is a quarter of its height and still reads as a pill, where the
     same 14 on a 500px panel is a soft corner. */
  --radius-control: 8px;
  --radius-pill: 999px;
  --radius-tight: 4px;

  --hairline: 1px solid oklch(0.975 0.01 262 / 0.16);
  --hairline-ink: 1px solid oklch(0.2 0.035 262 / 0.16);

  /* Custom curves; the CSS built-ins are too weak to read as intentional.
     --ease-out for anything entering or responding to input, --ease for
     colour and hover changes. No bounce, no elastic anywhere. */
  --ease: cubic-bezier(0.4, 0, 0.2, 1);
  --ease-out: cubic-bezier(0.23, 1, 0.32, 1);

  /* The menu curve. It is the one iOS drawers use: it starts with body and
     brakes long, which is what is wanted when something has to feel smooth
     rather than fast. The dropdowns use it on entry. */
  --ease-menu: cubic-bezier(0.32, 0.72, 0, 1);

  /* The menu underline, which travels from one item to the next.

     It starts decisive and brakes long. The "correct" curve for something
     travelling across the screen would be an ease-in-out (0.77, 0, 0.175, 1),
     and it was tried: measured, 60ms after the pointer entered the bar had
     travelled 6px of 204. An ease-in-out starts like an ease-in, and this
     responds to a user gesture, where the eye is on the start. The long
     braking is kept. */
  --ease-travel: cubic-bezier(0.3, 0.8, 0.25, 1);
}

/* The logo drops to 158px below this width (see Header.astro), so the masthead
   loses 12px of height and the hero has to stop pulling up as far. */
@media (max-width: 63rem) {
  :root {
    --masthead-h: 78px;
  }
}

/* --- Global ------------------------------------------------------------- */


/* ==========================================================================
   Reset
   ========================================================================== */

*,
*::before,
*::after {
  box-sizing: border-box;
}

* {
  margin: 0;
}

html {
  -webkit-text-size-adjust: 100%;
  /* Was `dark`, so that scrollbars, autofill and native controls match a dark
     page. White is the dominant ground now, and a dark scrollbar and a dark
     autofill panel on a white page are the browser's defaults contradicting
     the design. The tone class carries it, so a future dark tone can set its
     own. */
  background: var(--ground-deep);
  /* No scroll-behavior: smooth. Lenis owns smooth scrolling and the two fight. */
}

body {
  /* Deepest point by default so the transparent masthead reads as continuous
     with the hero instead of as a bar sitting on a lighter surface. Sections
     that want the mid ground opt in with .on-ground. */
  background: var(--ground-deep);
  color: var(--on-ground);
  font-family: var(--font);
  font-size: var(--step-0);
  /* Light type on dark reads lighter, so it gets extra leading. */
  line-height: 1.65;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

img,
picture,
svg,
video {
  display: block;
  max-width: 100%;
}

input,
button,
textarea,
select {
  font: inherit;
  color: inherit;
}

button {
  cursor: pointer;
}

/* ==========================================================================
   Typography
   ========================================================================== */

/* Poppins is a geometric sans with a large x-height and circular bowls. Two
   consequences for display type: tracking of -0.03em closes Poppins' round
   letters into each other, and uppercase display does not hold, since Poppins
   caps are wide and even a short heading runs past the measure. Every heading
   is set in sentence case for exactly that reason. */
h1,
h2,
h3,
.display {
  font-family: var(--font);
  font-weight: var(--wght-display);
  letter-spacing: -0.02em;
  line-height: 1.05;
  text-wrap: balance;
  /* Long single words at display size overflow narrow grid columns and get
     clipped silently. A broken word is bad; a clipped headline is worse. */
  overflow-wrap: break-word;
}

h1 {
  font-size: var(--step-5);
  line-height: 0.92;
}

h2 {
  font-size: var(--step-4);
}

h3 {
  font-size: var(--step-2);
  letter-spacing: -0.02em;
  line-height: 1.02;
}

p {
  text-wrap: pretty;
}

a {
  color: var(--sun);
  text-decoration-thickness: 1px;
  text-underline-offset: 0.2em;
}

.lede {
  font-size: var(--step-1);
  line-height: 1.45;
  color: var(--on-ground-soft);
  max-width: 32ch;
}

.prose {
  max-width: var(--measure);
  color: var(--on-ground-soft);
}

.prose > * + * {
  margin-top: var(--space-s);
}

/* ==========================================================================
   Focus and skip link
   --------------------------------------------------------------------------
   The audience includes keyboard-only and assistive-technology users, so the
   focus ring is loud on purpose and never removed.
   ========================================================================== */

:focus-visible {
  outline: 3px solid var(--sun);
  outline-offset: 3px;
  border-radius: var(--radius-tight);
}

.on-light :focus-visible {
  outline-color: var(--brand-blue);
}

.skip-link {
  position: absolute;
  top: 0;
  left: var(--gutter);
  z-index: 100;
  transform: translateY(-120%);
  padding: var(--space-xs) var(--space-s);
  background: var(--sun);
  color: var(--ink);
  font-weight: 700;
  text-decoration: none;
  transition: transform 0.16s var(--ease);
}

.skip-link:focus-visible {
  transform: translateY(0);
  color: var(--ink);
  /* The ring goes INSIDE the button, not outside.

     With `outline-offset: 3px` it was painted over the navy masthead, where
     the brand blue measures 1.49:1 against the 3:1 minimum (2.54:1 over the
     hero photograph). It is the first focus on every page: the first Tab of
     any keyboard visit.

     Inside, ink on the button's own gold gives 11.79:1, and the white halo
     separates it from the navy and from the photograph without depending on
     either background. */
  outline: 3px solid var(--ink);
  outline-offset: -3px;
  box-shadow: 0 0 0 3px #fff;
}

/* Specificity: `body.daybreak :focus-visible` is (0,2,1) and
   `.skip-link:focus-visible` (0,2,0), so the brand blue beat the ink and the
   ring was still the one that measures 1.49:1. With `html body.daybreak` in
   front this is (0,3,1) and wins. */
html body.daybreak .skip-link:focus-visible {
  outline-color: var(--ink);
}

/* ==========================================================================
   Layout
   ========================================================================== */

.shell {
  width: 100%;
  max-width: var(--shell);
  margin-inline: auto;
  /* Safe-area aware: the hero runs full bleed, so on notched devices in
     landscape the copy would otherwise sit under the inset. */
  padding-inline:
    max(var(--gutter), env(safe-area-inset-left))
    max(var(--gutter), env(safe-area-inset-right));
}

/* Sections carry their own rhythm rather than one uniform padding. */
.section {
  padding-block: var(--section-y);
}

/* In-page anchors land with room above the heading rather than flush against
   the viewport edge. More noticeable under Lenis, whose easing makes an abrupt
   stop obvious. */
[id] {
  scroll-margin-top: clamp(1.5rem, 1rem + 2vw, 3rem);
}

.section--tight {
  padding-block: var(--section-tight);
}

.section--loose {
  padding-block: var(--section-loose);
}

.on-ground {
  background: var(--ground);
}

/* Light sections are the exception, used for rhythm, not the default ground. */
.on-light {
  background: var(--paper);
  color: var(--ink);
}

.on-light .lede,
.on-light .prose {
  color: var(--ink-soft);
}

/* :not(.btn) matters. Without it these rules win on specificity over
   .btn--ink and paint ink text on an ink fill, which makes the "Make a
   donation" button invisible. */
.on-light a:not(.btn) {
  color: var(--brand-blue);
}

.on-sun {
  background: var(--sun);
  color: var(--ink);
}

.on-sun a:not(.btn) {
  color: var(--ink);
}

/* ==========================================================================
   Buttons
   --------------------------------------------------------------------------
   Measured: sun fill + ink text 12.67:1. Outline on ground 9.47:1.
   ========================================================================== */

.btn {
  display: inline-flex;
  align-items: center;
  gap: 0.5em;
  min-height: 44px; /* touch target */
  padding: 0.75em 1.5em;
  border: 1px solid transparent;
  border-radius: var(--radius-pill);
  font-size: var(--step-0);
  font-weight: 600;
  line-height: 1.1;
  text-decoration: none;
  white-space: nowrap;
  /* Explicit properties, never `all`. */
  transition:
    background-color 0.2s var(--ease),
    border-color 0.2s var(--ease),
    color 0.2s var(--ease),
    transform 0.14s var(--ease-out);
  /* Removes the 300ms tap delay and the grey flash on iOS. */
  touch-action: manipulation;
  -webkit-tap-highlight-color: transparent;
}

/* Scale, not translate: a press should read as pressure, not as a nudge. Kept
   subtle, and it scales the label with it, which is the point. */
.btn:active {
  transform: scale(0.97);
}

/* nowrap is right on a wide viewport, where a two-line button looks broken. On
   a narrow one it is what pushes the page sideways: a label like "Fundraise or
   volunteer" cannot shrink below its own line, so the button overflows and
   takes the document with it. This surfaced with the move to Poppins, which is
   materially wider than the condensable Archivo it replaced, and it was a
   horizontal scrollbar on a 375px screen. */
@media (max-width: 34rem) {
  .btn {
    white-space: normal;
    text-align: center;
  }
}

.btn--sun {
  background: var(--sun);
  color: var(--ink);
}

.btn--outline {
  background: transparent;
  border-color: var(--on-ground-soft);
  color: var(--on-ground);
}

.on-light .btn--outline,
.on-sun .btn--outline {
  /* 55%, not 35%. The border is the ONLY thing that delimits this control,
     and at 35% ink over the brand gold it measured 2.11:1, below the 3:1 WCAG
     asks for a UI element. */
  border-color: oklch(0.2 0.035 262 / 0.55);
  color: var(--ink);
}

.btn--ink {
  background: var(--ink);
  color: var(--sun);
}

/* Underline that grows, rather than an arrow appended to every block. */
.link-line {
  display: inline-block;
  font-weight: 650;
  text-decoration: none;
  padding-bottom: 2px;
  background-image: linear-gradient(currentColor, currentColor);
  background-repeat: no-repeat;
  background-position: 0 100%;
  background-size: 100% 1px;
  transition: background-size 0.3s var(--ease);
}

/* ==========================================================================
   Photography
   --------------------------------------------------------------------------
   Square corners, no masking.

   An arch (border-radius: 50% 50% 0 0) was tried and rejected: rounded top on
   a flat base, over a dark ground, reads as a HEADSTONE. On a site about a
   terminal illness the shape was saying death while the copy said hope. It
   also split the brand's grammar in two, since the hero had already
   established the sun as light rather than as a frame.

   So the brand appears on imagery as warm light (.shot--lit), never as a
   contour. One motif, one grammar.
   ========================================================================== */

.shot {
  position: relative;
  overflow: hidden;
}

/* Plain `img`, NOT :global(img). This is a regular stylesheet, where :global
   is not valid CSS: lightningcss drops the whole rule, which silently stripped
   object-fit from every image and left them showing their top-left corner at
   natural size. */
.shot > img {
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* The sun as light falling on the photograph, echoing the hero. */
.shot--lit::after {
  content: '';
  position: absolute;
  inset: 0;
  background: radial-gradient(
    120% 80% at 88% 12%,
    oklch(0.88 0.18 95 / 0.34) 0%,
    oklch(0.8 0.19 75 / 0.16) 34%,
    transparent 62%
  );
  mix-blend-mode: screen;
  pointer-events: none;
}

/* ==========================================================================
   Motion
   ========================================================================== */

@media (prefers-reduced-motion: no-preference) {
  html.js-motion [data-reveal],
  html.js-motion [data-reveal-row],
  html.js-motion [data-hero-in] {
    opacity: 0;
    transform: translateY(20px);
  }
}

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
}

/* ==========================================================================
   Utilities
   ========================================================================== */

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

/* ==========================================================================
   Hover states
   --------------------------------------------------------------------------
   Gated behind a capability query. On touch devices :hover fires on tap and
   then sticks, leaving buttons stuck in a hovered state after the finger
   lifts. Every hover on this site lives in here.
   ========================================================================== */

@media (hover: hover) and (pointer: fine) {
  .btn--sun:hover {
    background: oklch(0.93 0.17 95);
    color: var(--ink);
  }

  .btn--outline:hover {
    border-color: var(--sun);
    color: var(--sun);
  }

  .on-light .btn--outline:hover,
  .on-sun .btn--outline:hover {
    border-color: var(--ink);
    background: oklch(0.2 0.035 262 / 0.06);
    color: var(--ink);
  }

  .btn--ink:hover {
    background: var(--ground-deep);
    color: var(--sun);
  }

  .link-line:hover {
    background-size: 100% 3px;
  }
}

/* --- Daybreak ----------------------------------------------------------- */

/* --- Daybreak: the light layout --------------------------------------------
   A change of temperature, not of structure: nothing here reorders the page.

   The type must not be "in your face", and the page must not be very dark: it
   has to lean into hope.

   White plus a timid blue accent is the wrong reading: it is a generic
   template. What separates this is the third colour: the foundation's printed
   identity is white AND navy AND yellow, with the yellow carrying every
   badge, pill and figure. So the surfaces invert and the yellow's job grows;
   the navy does not merely shrink into an accent, it stops being the ground.

   One deliberate departure remains: the hero stays dark. A sunrise needs a
   night before it, and the horizon is the brand's own metaphor, drawn in its
   logo. Lighten everything and the motif disappears along with the one
   genuinely good photograph in the archive. The banner gradient is lightened
   so the image is more visible.

   Also: not everything shrinks. A page where nothing is large is not calm, it
   is bland. What shouts is the section heading repeating at 86px uppercase
   five times on the way down, not the hero. So the h2 drops hard, the h1 only
   one step, and uppercase goes everywhere.
   ------------------------------------------------------------------------ */

/* --- the diagonal ----------------------------------------------------------
   The brand's printed identity is not "white with accents": it is built on
   diagonal planes of navy and yellow slicing across the page, cut corners,
   bleeding blocks of colour. White background with small yellow pills is the
   timidest reading of that layout, with no rhythm and the yellow reduced to
   decoration.

   So the diagonal is the system here. One angle everywhere, one variable.

   DIRECTION IS NOT A FREE CHOICE: the diagonal DESCENDS to the right (on the
   cover the navy holds the top right and the edge falls away toward the
   bottom right corner), and every interior page repeats it. A diagonal rising
   to the right, on the reasoning that a sunrise reads upward, contradicts it.

   The planes BLEED: a shape enters at one edge of the page and leaves at
   another, and they usually travel in pairs, a navy plane with a yellow one
   running parallel and offset from it. Nothing is a floating card with a cut
   corner.
   ------------------------------------------------------------------------ */

/* The angle, measured off the cover rather than guessed. The printed diagonal
   drops about 320px over a 935px page, which is 34% of the width, or roughly
   19 degrees. 3.5rem to 5.5rem on a 1440px viewport is 6% and about 3.5
   degrees: on paper it reads as a diagonal, on screen as a line that has gone
   slightly crooked.

   Full 34% is not transferable. A page is 1.3 times taller than it is wide
   and a section is not, so a 490px drop on a desktop viewport would eat an
   entire band of content.

   Set at 7vw: about 100px at 1440, near 4 degrees. Kept as one variable for
   the whole page rather than a hero-only override: two angles on one page
   read as a mistake, and the hero sets the expectation for the rest. */
body.daybreak {
  --cut: clamp(2.25rem, 7vw, 9rem);
  /* Thickness of the yellow plane that runs parallel to a navy edge. */
  --band: clamp(0.6rem, 0.9vw, 1.15rem);
}

/* --- surface inversion -----------------------------------------------------
   The page is light and the dark is the exception.

   Done by remapping tokens on the body rather than by rewriting the sections.
   Every section was written against --on-ground-*, so pointing those at the
   ink scale makes several hundred lines of existing CSS correct on white with
   no per-rule edits. The same trick .on-light already used locally, applied
   one level up.

   --paper becomes true white here. A 0.97 blue-tinted white is right for a
   light section inside a dark page (pure white next to navy glares) and wrong
   for the dominant surface of the site. The tinted near-white survives as
   --paper-1, which does the separating.
   ------------------------------------------------------------------------ */

html:has(body.daybreak) {
  /* Was dark, set globally for a navy page. Scrollbars, autofill and native
     controls would otherwise render dark on a white page. */
  color-scheme: light;
  background: var(--paper);
}

body.daybreak {
  --paper: oklch(1 0 0);
  /* #ECEDEF, the second surface of the foundation's palette, which pages
     alternate with white. */
  --paper-1: oklch(0.946 0.003 264.5);
  --paper-2: oklch(0.905 0.005 264.5);

  --on-ground: var(--ink);
  --on-ground-soft: var(--ink-soft);
  --on-ground-dim: var(--ink-soft);
  --hairline: var(--hairline-ink);

  background: var(--paper);
  color: var(--ink);
  /* Dark type on white needs less leading than light type on navy. */
  line-height: 1.6;
}

/* .on-ground was the navy mid surface. On white it is the faint step up, so
   the page still alternates rather than running as one flat sheet. */
body.daybreak .on-ground {
  background: var(--paper-1);
}

/* Body links are INK with a gold underline, not the logo blue.

   The blue passed contrast (6.61:1 on paper) but does not belong to this
   system: the palette is navy, gold and paper, and the logo blue appears in
   one other place. Measured, 88 links across 17 pages were 88 patches of a
   colour that is not in the design.

   What distinguishes the link is the UNDERLINE, not the colour, so dropping
   the blue does not break WCAG 1.4.1: the gold underline is always there,
   thickens on hover, and the text stays in ink at 18.11:1 instead of 6.61:1.

   Gold works as an underline on paper even though not as a text colour: --sun
   measures 1.43:1 on white, which is why the links were not gold. A 1px line
   does not have to meet the text threshold. */
body.daybreak a:not(.btn) {
  color: var(--ink);
  text-decoration-line: underline;
  /* 2px: the deep gold measures 2.03:1 on paper, so a 1px line looked weak.
     At 2px it reads without raising the tone, which keeps the underline an
     accent and not a second text colour. */
  text-decoration-thickness: 2px;
  text-underline-offset: 0.18em;
  text-decoration-color: var(--sun-deep);
  transition: text-decoration-thickness 0.18s var(--ease),
              text-decoration-color 0.18s var(--ease);
}

@media (hover: hover) and (pointer: fine) {
  body.daybreak a:not(.btn):hover {
    text-decoration-thickness: 3px;
    text-decoration-color: var(--sun);
  }
}

/* The underline is for links IN THE TEXT. Navigation is not underlined: the
   top menu, the phone panel menu, the footer, the section rail and components
   that already have their own way of signalling (the resource list with its
   chevron, downloads with their PDF chip, the cards). Without this exception
   the six menu items came out underlined. */
body.daybreak :is(.masthead, .masthead__panel, .footer, .sectionnav) a:not(.btn),
body.daybreak a.links__link:not(.btn),
body.daybreak a.docs__link:not(.btn),
body.daybreak .card a:not(.btn):where(.btn) {
  text-decoration-line: none;
}

body.daybreak :focus-visible {
  outline-color: var(--brand-blue);
}

/* --- rounded corners -------------------------------------------------------
   Everything is rounded, rather than leaving one round section among flat
   ones: a single rounded block on a squared page reads as an accident.

   The angles do not go anywhere. They live in the planes (the hero's horizon,
   the section seams, the corner wedges): shapes that bleed off the page,
   never boxes sitting on it. So the page keeps the diagonals in its
   backgrounds and rounds every object that sits on top of them.
   ------------------------------------------------------------------------ */

html body.daybreak .btn {
  border-radius: var(--radius-control);
}

html body.daybreak .frame,
html body.daybreak .frame__inner,
html body.daybreak .event__shot,
html body.daybreak figcaption {
  border-radius: var(--radius-card);
  overflow: hidden;
}

/* The icon plates lose their chamfer with everything else. */
html body.daybreak .figure__icon {
  clip-path: none;
  border-radius: var(--radius-media);
}

/* --- the surfaces that stay dark -------------------------------------------
   The hero and the footer keep the drenched ground, so they need the token
   scale the rest of the page gave up. Restored locally rather than by
   excluding them from the remap, which would mean listing every section that
   IS light instead of the three that are not.

   The masthead is the third, and the easy one to miss: it is transparent, it
   sits OUTSIDE .hero in the DOM, and the hero pulls up behind it. So it
   inherited the light-page token scale and painted navy nav links onto a navy
   photograph. Its ground is whatever is behind it, which here is always the
   hero, so it belongs with the dark surfaces. The mobile panel it opens is
   --ground-deep for the same reason.
   ------------------------------------------------------------------------ */

body.daybreak .masthead,
body.daybreak .hero,
body.daybreak .footer {
  --on-ground: oklch(0.975 0.01 262);
  --on-ground-soft: oklch(0.8 0.035 262);
  --on-ground-dim: oklch(0.68 0.04 262);
  --hairline: 1px solid oklch(0.975 0.01 262 / 0.16);

  color: var(--on-ground);
}

body.daybreak .footer {
  background: var(--ground-deep);
}

/* Back to the sun inside the dark surfaces, where it carries at 12.67:1. */
body.daybreak .hero a:not(.btn),
body.daybreak .footer a:not(.btn) {
  color: var(--sun);
}

/* The masthead's links are the navigation, not links-as-accent, so they take
   the plain light ink rather than the sun; a row of yellow nav items would
   compete with the Donate button, which is the one thing in there that should
   be yellow. The gold underline that grows on hover already does the
   accenting. */
body.daybreak .masthead a:not(.btn) {
  color: var(--on-ground);
}

/* Every navy surface, and `.is-dark` so a new one only has to say so instead
   of being remembered in two separate lists. Enumerated by hand, both lists
   had holes (`.mission`, which is navy, and the Standard template's CTA),
   which gave a 2.23:1 focus ring on the page's two primary actions, against
   WCAG 1.4.11's 3:1. This blue on navy is never allowed. */
body.daybreak .masthead :focus-visible,
body.daybreak .hero :focus-visible,
body.daybreak .mission :focus-visible,
body.daybreak .footer :focus-visible,
body.daybreak .is-dark :focus-visible {
  outline-color: var(--sun);
}

/* global.css hovers the outline button to yellow-on-yellow-border, which was
   written for a page whose ground is navy. On white that is a 1.43:1 label,
   so on the light page it hovers to ink instead.

   Scoped by ANCESTOR, not by direct parent. `*:not(.hero):not(.footer) >
   .btn--outline` only checks the immediate parent: the hero's buttons sit
   inside .hero__actions, so the exclusion never reached them and "Ways to
   give" hovered to navy text on a dark photograph.

   Inside the hover capability query on purpose: on touch, :hover fires on tap
   and sticks, which is what every hover in this project is gated against. */
@media (hover: hover) and (pointer: fine) {
  html body.daybreak .btn--outline:hover {
    border-color: var(--ink);
    background: oklch(0.2 0.035 262 / 0.06);
    color: var(--ink);
  }

  /* Every dark surface on the page, plus `.is-dark` for any new one. Without
     it the Standard template's CTA hovered its outline button to ink on navy:
     1.13:1 for both the label and the border, so the control vanished. */
  html body.daybreak .masthead .btn--outline:hover,
  html body.daybreak .hero .btn--outline:hover,
  html body.daybreak .mission .btn--outline:hover,
  html body.daybreak .footer .btn--outline:hover,
  html body.daybreak .is-dark .btn--outline:hover {
    border-color: var(--sun);
    background: transparent;
    color: var(--sun);
  }
}

body.daybreak .hero :focus-visible,
body.daybreak .footer :focus-visible {
  outline-color: var(--sun);
}

/* --- type ------------------------------------------------------------------
   Three amplifiers were stacked on display type: uppercase, the width axis at
   112, and weight 750. Removing the first two changes the character as much
   as the size does.

   `html body.daybreak` on purpose: the component's own scoped rules land at
   the same specificity as `body.daybreak`, and a tie would be settled by
   stylesheet order, which is not something to leave to chance.
   ------------------------------------------------------------------------ */

/* 700, not 600: the --wght-display token already said 700 and these rules
   contradicted it, so the system had two answers to the same question. It is
   half the weight contrast, heavy headline against thin letters; the other
   half is --wght-lede on standfirsts. */
html body.daybreak h1,
html body.daybreak h2,
html body.daybreak h3,
html body.daybreak .display {
  text-transform: none;
  font-weight: var(--wght-display);
  letter-spacing: -0.02em;
  line-height: 1.08;
}

/* Sizes are their own curves here, not steps borrowed from the scale.

   The scale's steps reach their cap at roughly 1470px, so a 1280 or 1440
   laptop is already served the maximum: lowering the cap alone would not move
   laptops, the slope has to come down too. Values below are the rendered size
   at 1440, measured, not the clamp arguments read off the page. */

/* 118 to 61 at 1440. Still the largest thing on the page, which it should be:
   a page where nothing is big is not calm, it is bland. */
html body.daybreak h1 {
  font-size: clamp(2.6rem, 2.1rem + 1.9vw, 4.5rem);
  line-height: 1.02;
}

/* --- the hero, edge to edge ------------------------------------------------
   The hero is the photograph, full screen, with nothing laid over its foot.
   The angle still runs the commitments' bottom seam, the giving section and
   the corner wedge, where it reads as a system rather than as a lid on the
   hero.

   The extra bottom padding went with the planes that used to end the hero: it
   existed only to keep the buttons clear of the wedge that was about to cover
   them.
   ------------------------------------------------------------------------ */
html body.daybreak .hero {
  /* Full screen. The hero already pulls up behind the transparent masthead by
     --masthead-h, so it starts at the top of the viewport and 100dvh takes it
     exactly to the bottom.

     dvh, not vh: on mobile browsers vh is the tallest possible viewport, which
     means the foot of the hero sits under the address bar until the user
     scrolls. */
  min-height: 100dvh;
  position: relative;
}

/* Above both planes. Was 3, which the navy band now occupies. */
html body.daybreak .hero .hero__inner {
  z-index: 5;
}

/* The yellow plane that runs parallel to the navy one, offset. That pairing
   is the identity's signature: on the cover a yellow slab crosses behind the
   navy one at the same angle, and every interior page repeats it at the top
   corner.

   It lives on the section BELOW the hero rather than inside it, because the
   hero is clipped and a clip-path applies to an element's pseudo-elements
   too: the band would have been sliced off along the very edge it is meant to
   follow. Here it sits in the white, tucked under the hero's edge and running
   parallel to it. */
html body.daybreak .mission {
  position: relative;
  isolation: isolate;
}

/* --- the corner wedge ------------------------------------------------------
   Two bands entering at the top edge and running down to the right, the
   yellow one wider and behind, the navy one in front, with the yellow showing
   past it on both sides.

   PARALLEL IS THE WHOLE POINT. Two triangles sharing the top right corner do
   not give it: with different bases the hypotenuses have different slopes, so
   the two planes cross instead of running together.

   Built with skewX. Skewing two rectangles by the same angle guarantees their
   edges are parallel no matter what width or height each takes, so the
   proportions can be tuned freely without the geometry drifting.
   ------------------------------------------------------------------------ */

html body.daybreak .wedge-tr {
  position: relative;
  isolation: isolate;
  overflow: hidden;
}

html body.daybreak .wedge-tr::before,
html body.daybreak .wedge-tr::after {
  content: '';
  position: absolute;
  /* Starts above the section and runs off the right edge: the planes always
     bleed rather than sit inside the page. */
  top: calc(-1 * var(--wedge-h));
  height: calc(var(--wedge-h) * 2);
  /* Positive, so the bands lean down and to the RIGHT, which is also the
     direction of the hero's horizon and every seam on the page. Negative
     leans them the other way and reads as a mirror. */
  transform: skewX(24deg);
  transform-origin: top right;
  pointer-events: none;
  --wedge-h: clamp(8rem, 17vw, 17rem);
}

/* The gold band, behind and wider so it shows past the navy on BOTH sides.
   Offsets are measured from the right edge: the gold must overlap the navy,
   or the navy falls off the right edge of the viewport and the gold becomes
   the figure, the inverse of the intended layering (navy plane in front). */
html body.daybreak .wedge-tr::before {
  right: clamp(0.75rem, 2.5vw, 2.5rem);
  width: clamp(10rem, 19vw, 18rem);
  background: var(--sun);
  z-index: -2;
}

/* The navy band in front of it, inside the viewport, with the gold running
   2.5rem past it on each side. */
html body.daybreak .wedge-tr::after {
  right: clamp(2rem, 5vw, 5rem);
  width: clamp(7rem, 14vw, 13rem);
  background: var(--ground);
  z-index: -1;
}

/* --- the corner wedge, bottom left -----------------------------------------
   The mirror of .wedge-tr, for a section that wants the figure at its foot.
   Same angle, same plane order (gold behind and wider, navy in front),
   entering from the bottom edge instead of the top.
   ------------------------------------------------------------------------ */

html body.daybreak .wedge-bl {
  position: relative;
  isolation: isolate;
  overflow: hidden;
}

html body.daybreak .wedge-bl::before,
html body.daybreak .wedge-bl::after {
  content: '';
  position: absolute;
  bottom: calc(-1 * var(--wedge-h));
  height: calc(var(--wedge-h) * 2);
  transform: skewX(24deg);
  transform-origin: bottom left;
  pointer-events: none;
  --wedge-h: clamp(7rem, 16vw, 16rem);
}

/* The gold band: wider, further right, reaching higher. */
html body.daybreak .wedge-bl::before {
  left: clamp(0.75rem, 2.5vw, 2.5rem);
  width: clamp(9rem, 17vw, 16rem);
  background: var(--sun);
  z-index: -2;
}

/* The navy band in front, offset left, so the gold survives on both sides. */
html body.daybreak .wedge-bl::after {
  left: clamp(2rem, 5vw, 5rem);
  width: clamp(6.5rem, 12vw, 11.5rem);
  background: var(--ground);
  z-index: -1;
}

/* --- the commitments' bottom seam ------------------------------------------
   Navy meeting grey on a dead straight line would be flat, while the seam at
   the top of the same section is a diagonal with a gold plane riding it.

   Same construction as the hero, and for the same reason. The planes are
   built INSIDE the section rather than by clipping it: a clip-path applies to
   an element's pseudo-elements too, so a band drawn here would be sliced off
   along the very edge it is meant to follow, and a clip on the section below
   would only ever reveal the white page rather than this grey.

   So the foot of the section carries the next section's grey with a diagonal
   top edge, and the gold line rides that edge. Both anchored at bottom: 0 so
   their edges share an origin and stay parallel; the gold box is taller by
   exactly --band, which is what keeps them together at every x.
   ------------------------------------------------------------------------ */

html body.daybreak .mission {
  --seam: clamp(1.25rem, 1.8vw, 2.25rem);
  padding-bottom: calc(var(--section-y) + var(--cut) + var(--seam));
  overflow: hidden;
}

/* The grey plane, which is what the next section is painted in. */
html body.daybreak .mission::after {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: calc(var(--cut) + var(--seam));
  background: var(--paper-1);
  clip-path: polygon(0 0, 100% var(--cut), 100% 100%, 0 100%);
  z-index: -1;
  pointer-events: none;
}

/* The gold line on that edge. */
html body.daybreak .mission::before {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: calc(var(--cut) + var(--seam) + var(--band));
  background: var(--sun);
  clip-path: polygon(0 0, 100% var(--cut), 100% calc(var(--cut) + var(--band)), 0 var(--band));
  z-index: -1;
  pointer-events: none;
}

/* --- the grey line across the top of the numbers ---------------------------
   A hairline ran the full width of the page under the diagonal. It is a
   rounding artefact.

   .mission is painted navy and its grey plane is a ::after anchored to
   bottom: 0 with a height of calc(--cut + --seam). When that height lands on
   a fraction of a pixel, the plane stops a sliver short of the section's own
   bottom edge and the navy behind it shows through as one row of pixels.
   Measured off a screenshot: at 1920 wide, row 119 came back rgb(177,185,201)
   between rows of rgb(236,237,239), navy mixed into grey, exactly one pixel
   tall.

   The plane cannot simply be extended downwards: .mission carries overflow:
   hidden, so anything past its box is clipped. So the section below covers
   the seam instead. It is the same grey, so there is nothing to see.
   ------------------------------------------------------------------------ */
html body.daybreak .mission + .section {
  margin-top: -1px;
  /* The overlap alone does nothing: .mission is position: relative, so it
     paints over a static sibling and the sliver survived the pull-up (the row
     had simply moved down by one). The section below has to be in the
     stacking order too. Its box starts one pixel inside .mission and nowhere
     else, so this covers the seam and nothing else. */
  position: relative;
  z-index: 1;
}

/* --- give: diagonals opposite the commitments' -----------------------------
   Mirrors the angle from Three Commitments, and swaps the accent to navy
   since give's own ground is already the colour commitments uses for its
   line. Where mission's seams descend left to right and carry a gold line,
   give's ascend left to right and carry a navy one: same technique, same
   shared --cut, run in the other direction, so the two read as a matched
   pair.

   Unlike mission, give does not need a fake "next section" plane behind the
   line: give's own background IS the colour, so clip-path goes directly on
   .give itself, and the true white page shows through the cut on both sides.
   That is also why this needs only two pseudo-elements (one line per edge)
   where mission needed a plane-plus-line pair: mission's seam borrows a
   colour it does not own.

   The "clip-path applies to pseudo-elements too" warning above applies here
   as well, but harmlessly: both navy lines sit entirely inside the area
   .give's own clip-path already keeps visible.
   ------------------------------------------------------------------------ */

html body.daybreak .give {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  /* --section-loose's own padding, plus room for the cut and the line riding
     it, at both the top and the foot. */
  padding-block: calc(var(--section-loose) + var(--cut) + var(--band));
  clip-path: polygon(
    0 var(--cut),
    100% 0,
    100% calc(100% - var(--cut)),
    0 100%
  );
}

/* The navy line just inside the top cut. */
html body.daybreak .give::before {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  top: 0;
  height: calc(var(--cut) + var(--band));
  background: var(--ground);
  clip-path: polygon(
    0 var(--cut),
    100% 0,
    100% var(--band),
    0 calc(var(--cut) + var(--band))
  );
  z-index: -1;
  pointer-events: none;
}

/* Mirrored at the foot. */
html body.daybreak .give::after {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  height: calc(var(--cut) + var(--band));
  background: var(--ground);
  clip-path: polygon(
    0 calc(var(--cut) + var(--band)),
    100% var(--band),
    100% 0,
    0 var(--cut)
  );
  z-index: -1;
  pointer-events: none;
}

/* A light-weight headline for "Hope is on the Horizon": the tagline should
   read as a phrase, not as a slab. The weight drops from 680 to 380, the
   difference between a headline and a sentence, and the tracking opens
   slightly because thin type at display size closes up.

   Only the h1. The section headings keep their weight; taking the whole page
   thin would leave nothing anchoring it. */
html body.daybreak .hero h1 {
  font-weight: 400;
  letter-spacing: -0.005em;
}

/* 86 to 40 at 1440. This is the one that was doing the shouting: five section
   headings on the way down, each at poster scale. */
html body.daybreak h2,
html body.daybreak .mission .mission__head h2,
html body.daybreak .give__head {
  font-size: clamp(1.9rem, 1.55rem + 1.05vw, 2.8rem);
}

html body.daybreak h3 {
  font-size: var(--step-1);
}

/* The three consequences of the diagnosis are the most scannable thing on the
   page and they stay a step above body copy, just not at poster scale. */
html body.daybreak .explain .consequences li {
  font-size: var(--step-2);
  text-transform: none;
  font-weight: 600;
}

html body.daybreak .footer__tagline {
  font-size: var(--step-3);
  text-transform: none;
  font-weight: 600;
}

html body.daybreak .masthead__panel a:not(.btn) {
  font-size: var(--step-1);
  text-transform: none;
  font-weight: 600;
}

/* --- the light sections ----------------------------------------------------
   Three commitments and The Center of Hope carry `on-light` in this tone,
   which global.css already knows how to style. Two adjustments on top of it.

   What is ALS stays dark: it is the heaviest section on the page, the three
   consequences of the diagnosis over a motor neuron under a microscope. The
   microscopy is a black frame that integrates on navy and cuts out hard on
   cream, and gravity belongs on the dark ground. The page alternates rather
   than splitting in half.
   ------------------------------------------------------------------------ */

/* Cool paper, tinted toward the logo blue (not --paper-warm: cream reads as
   old). */
html body.daybreak .on-light {
  background: var(--paper);

  /* Remap the semantic tokens locally instead of rewriting every rule that
     uses them. Everything inside these sections was written against
     --on-ground-*, so pointing those at the ink scale makes the existing
     styles correct on cream with no per-rule overrides. */
  --on-ground: var(--ink);
  --on-ground-soft: var(--ink-soft);
  --on-ground-dim: var(--ink-soft);
  --hairline: var(--hairline-ink);
}

/* Hardcoded rather than tokenised, so the remap above cannot reach it. Kept
   even though What is ALS is dark: the rule is scoped to .on-light, so it
   simply stops matching, and it is correct again if that section moves back. */
html body.daybreak .on-light .explain__figure img {
  border-color: oklch(0.2 0.035 262 / 0.16);
}

/* The sun carries no text on light: it measures 1.43:1 on paper. On these
   sections the logo blue finally has a job again, at 6.61:1, which it does not
   have anywhere on the dark ground. global.css already routes links this way;
   this only covers the underline the link-line draws from currentColor. */
html body.daybreak .on-light .link-line {
  color: var(--brand-blue);
}

/* --- the commitments, on navy ----------------------------------------------
   This section goes on a blue ground. The component marks it `.on-light` in
   this tone, so the surface and the whole ink token scale are overridden back
   here.

   It also continues the hero: the hero ends on a navy plane, so with this
   section navy too the colour runs unbroken from the gold line down through
   the commitments before the page turns white. That is the cover's
   proportion, where the navy field is the largest thing on the page.
   ------------------------------------------------------------------------ */

html body.daybreak .mission.on-light {
  background: var(--ground);
  color: var(--on-ground);

  --on-ground: oklch(0.975 0.01 262);
  --on-ground-soft: oklch(0.8 0.035 262);
  --on-ground-dim: oklch(0.68 0.04 262);
  --hairline: 1px solid oklch(0.975 0.01 262 / 0.16);
}

/* --brand-blue is 2.46:1 on this ground. Links take the sun, as they do in the
   hero and the footer. */
html body.daybreak .mission.on-light a:not(.btn) {
  color: var(--sun);
}

html body.daybreak .mission.on-light :focus-visible {
  outline-color: var(--sun);
}

/* --- the commitments' column -----------------------------------------------
   The column runs on navy:

     RESEARCH          name, caps, white, on top
       [pillar]        the gold column beneath the name
     Dr. Robert        the programmes, white, beneath that
     Sinnott Lab

   The pillar goes below the name, not above it (icon over label is the
   reflex, not the pattern). And there are no boxes: chamfered navy cards and
   yellow squares were both tried, and the yellow squares put text on a yellow
   plane, which the identity only does in small pills.
   ------------------------------------------------------------------------ */

html body.daybreak .mission .panel {
  background: none;
  border-radius: 0;
  clip-path: none;
  padding: 0;
  aspect-ratio: auto;
  color: var(--on-ground);
  --panel-surface: var(--ground);
}

/* Caps, white, and tracked out a little: at this size Poppins' capitals close
   up on each other.

   The larger size goes here rather than on `.panel h3`, which is where you
   would look for it: `html body.daybreak h3` sets --step-1 at (0,1,2) and
   outweighs it, so the panel rule was never the one on screen.

   Between --step-1 and --step-2 as this tone redefines them at the foot of
   the file (19.2/22.4px and 24.8/32px), not as they are declared at the top.
   --step-2 is what section headings use, and three panel headings at that
   size read as three sections stacked in a row rather than as one. */
html body.daybreak .mission .panel h3 {
  font-size: clamp(1.35rem, 1.25rem + 0.4vw, 1.7rem);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  font-weight: 700;
  color: var(--on-ground);
}

/* The gold column, at the size it holds on the page: large enough to be the
   figure in the column rather than an icon beside a heading. */
html body.daybreak .mission .panel__pillar {
  width: clamp(3.5rem, 5vw, 5rem);
  height: auto;
  color: var(--sun);
  margin-block: clamp(1.25rem, 2vw, 2rem);
}

html body.daybreak .mission .panel p {
  color: var(--on-ground);
}

/* The three CTAs are buttons. Outline rather than a solid yellow fill: three
   solid buttons in a row would carry more weight than Donate in the masthead
   and Find care in the hero, and these are the third-level action on the
   page, not the first.

   Pushed to the foot of the column so the three land on one line however much
   copy sits above them. */
html body.daybreak .mission .panel__cta {
  align-self: center;
  margin-top: var(--space-m);
}

/* The section still carries .on-light from the component, so global.css hands
   these the light-ground outline: ink text and an ink border, both invisible
   on navy. Same trap as the links, one level further in. */
html body.daybreak .mission.on-light .panel__cta {
  border-color: oklch(0.975 0.01 262 / 0.45);
  color: var(--on-ground);
  background: transparent;
}

/* The commitment CTAs need their hover re-stated, and it is a cascade problem
   rather than a colour one. Their resting rule is `.mission.on-light
   .panel__cta`, which ties with `.mission .btn--outline:hover` on specificity
   and sits later in the file, so it wins even while hovered: the button never
   changes. Matching the same chain plus :hover settles it. */
@media (hover: hover) and (pointer: fine) {
  html body.daybreak .mission.on-light .panel__cta:hover {
    border-color: var(--sun);
    background: transparent;
    color: var(--sun);
  }
}

html body.daybreak .mission .panels {
  gap: clamp(2rem, 1rem + 4vw, 4.5rem);
}

/* --- consequences of the smaller heading -----------------------------------
   The giving section aligns its two columns to their bottoms. That was right
   when the heading was three lines of 86px display and roughly matched the
   column beside it. At 40px the heading is 83px tall against a 230px column,
   so bottom alignment opened 148px of dead space above it.
   ------------------------------------------------------------------------ */
html body.daybreak .give__grid {
  align-items: start;
}

/* The tight rhythm this section used to set here now lives with the clip-path
   further up, as `--section-tight + --cut`, because a clipped section has to
   pad itself back by the wedge it removes.

   A leftover rule with identical specificity and later in the file quietly
   won: the section went back to --section-tight, the padding that kept
   content clear of the diagonal disappeared, and the bottom right corner
   sliced through "Fundraise or volunteer". Two rules for one property on one
   selector is the whole bug. */

/* The columns were 1.2fr and 0.8fr, sized when the heading was three lines of
   display type and needed the wider half. Holding a 13ch heading, that ratio
   put a wide band of empty yellow between the two columns. The heading column
   now takes only what it needs.

   Gated above 63rem, and that gate fixes a real bug rather than being
   tidiness. HomeSections collapses this grid to one column below 63rem from
   its own scoped stylesheet; this rule is `html body.daybreak ...`, which
   outweighs it and carried the two-column track down to 375px: a 49px content
   column, buttons that could not fit inside it, and a page that scrolled
   sideways on a phone. Any override of a component's layout has to respect
   the breakpoints that component defines. */
@media (min-width: 63.0625em) {
  html body.daybreak .give__grid {
    grid-template-columns: auto minmax(0, 1fr);
    gap: clamp(1.5rem, 1rem + 3vw, 4rem);
    align-items: baseline;
  }
}

html body.daybreak .give__head {
  max-width: 13ch;
}

html body.daybreak .give__body p {
  font-size: var(--step-0);
  max-width: 42ch;
}

html body.daybreak .give__actions {
  margin-top: var(--space-m);
}

/* --- Frame -------------------------------------------------------------- */


  .frame {
    position: relative;
    padding: var(--frame-rule);
    /* Only paints when a rule is asked for; at 0 the padding is nothing and
       this never shows. */
    background: var(--sun);
  }

  .frame__inner {
    width: 100%;
    height: 100%;
    overflow: hidden;
    background: var(--frame-fill, transparent);
  }

  /* Images fill the frame. Anything else (a logo, a slideshow) sizes itself. */
  .frame__inner img {
    display: block;
    width: 100%;
    height: 100%;
    object-fit: cover;
  }

/* --- Pillar ------------------------------------------------------------- */


  /* --sun-deep, not --sun. The pale yellow measures 1.43:1 on white and
     washes out to nothing; the sun's outer ray holds at graphic-object
     contrast and is the tone the foundation's printed pillars are drawn in. */
  .pillar {
    display: block;
    color: var(--sun-deep);
  }

  /* Cut from the shaft rather than drawn over it, so the grooves show whatever
     surface the icon sits on and the mark stays correct on any panel. */
  .pillar__flutes rect {
    fill: var(--panel-surface, var(--paper-1));
  }

/* --- Glyph -------------------------------------------------------------- */


  .glyph {
    display: block;
    color: var(--sun);
  }

/* --- Header ------------------------------------------------------------- */


  /* Transparent over the hero, so the drenched ground runs edge to edge and
     the masthead does not read as a separate bar sitting on top of it. */
  .masthead {
    position: relative;
    z-index: 20;
    background: transparent;
  }

  /* With text enlarged to double, the six-section menu plus logo plus button
     does not fit in 1440px: measured, the document grew to 1882px and the
     Donate button sat entirely off-screen, on all 25 pages. `wrap` makes it
     drop to the next line instead of overflowing, and `min-width: 0` stops
     the nav refusing to shrink to its content width. */
.masthead__inner {
  flex-wrap: wrap;
}

.masthead__inner > * {
  min-width: 0;
}

/* The menu list wraps too. With text at double size at 1280px, the last item
   ("Ways to help") overflowed by 47px: the masthead already wrapped, but the
   list inside stayed on one rigid line. Measured after: 0px of overflow at
   1440 and 1280, with the Donate button inside the screen. */
.masthead__nav > ul {
  flex-wrap: wrap;
}

.masthead__inner {
    display: flex;
    align-items: center;
    /* Fixed, not `--space-l`. See the note on the list gap: `.shell` loses
       content width as the screen grows, so the bar's spacing cannot grow
       with it. */
    gap: 2rem;
    min-height: 76px;
    padding-block: var(--space-s);
  }

  .masthead__brand {
    flex: none;
    display: block;
    line-height: 0;
  }

  .masthead__brand img {
    width: 200px;
    height: auto;
  }

  /* The bar runs to the edge with six labels, five chevrons and the Donate
     button, and 24px of logo is the cheapest thing to give up: the logotype
     stays legible and the full menu fits on one line. */
  @media (min-width: 63.0625em) {
    .masthead__brand img {
      width: 176px;
    }
  }

  .masthead__nav {
    margin-inline-start: auto;
  }

  .masthead__nav > ul {
    display: flex;
    align-items: center;
    gap: 1.125rem;
    list-style: none;
    padding: 0;
  }

  .masthead__nav a {
    color: var(--on-ground);
    font-size: var(--step--1);
    font-weight: 600;
    letter-spacing: 0.01em;
    text-decoration: none;
    white-space: nowrap;
    padding-block: 0.4rem;
    /* Grows on hover rather than adding an arrow or a permanent underline. */
    background-image: linear-gradient(var(--sun), var(--sun));
    background-repeat: no-repeat;
    background-position: 0 100%;
    background-size: 0 2px;
    transition: background-size 0.28s var(--ease-out), color 0.2s var(--ease);
    touch-action: manipulation;
    -webkit-tap-highlight-color: transparent;
  }

  /* Gated: on touch, :hover fires on tap and then sticks. */
  @media (hover: hover) and (pointer: fine) {
    .masthead__nav a:hover {
      color: var(--sun);
      background-size: 100% 2px;
    }
  }


  .masthead__donate {
    flex: none;
    min-height: 40px;
    padding: 0.55em 1.3em;
    font-size: var(--step--1);
  }

  /* --- mobile ----------------------------------------------------------- */

  .masthead__toggle {
    display: none;
    flex: none;
    margin-inline-start: auto;
    width: 44px;
    height: 44px;
    align-items: center;
    justify-content: center;
    background: transparent;
    border: 1px solid oklch(0.975 0.01 262 / 0.3);
    border-radius: var(--radius-tight);
    touch-action: manipulation;
    -webkit-tap-highlight-color: transparent;
    transition: transform 0.14s var(--ease-out);
  }

  .masthead__toggle:active {
    transform: scale(0.94);
  }

  .masthead__bars {
    display: grid;
    gap: 4px;
    width: 18px;
  }

  .masthead__bars i {
    display: block;
    height: 2px;
    background: var(--on-ground);
    transition: transform 0.2s var(--ease), opacity 0.2s var(--ease);
  }

  .masthead__toggle[aria-expanded='true'] .masthead__bars i:nth-child(1) {
    transform: translateY(6px) rotate(45deg);
  }

  .masthead__toggle[aria-expanded='true'] .masthead__bars i:nth-child(2) {
    opacity: 0;
  }

  .masthead__toggle[aria-expanded='true'] .masthead__bars i:nth-child(3) {
    transform: translateY(-6px) rotate(-45deg);
  }

  .masthead__panel {
    background: var(--ground-deep);
    padding-block: var(--space-s) var(--space-l);
  }

  /* With the panel open, the bar takes the same navy as the panel.

     On the homepage the masthead is transparent and reads over the hero
     photograph. When the menu opens, the panel pushes the hero down and
     leaves the bar over white paper: there the logo (the white version) and
     the close X disappear. Measured on a phone at 390px: invisible.

     The navy goes on .masthead.masthead--open and not on body.daybreak so as
     not to depend on the theme: the only thing it has to beat is the
     `background: transparent` of .masthead, which is (0,1,0). */
  .masthead.masthead--open {
    background: var(--ground-deep);
  }

  .masthead__panel ul {
    list-style: none;
    padding: 0;
    margin-bottom: var(--space-m);
  }

  .masthead__panel li + li {
    border-top: var(--hairline);
  }

  .masthead__panel a:not(.btn) {
    display: block;
    padding-block: 0.85rem;
    color: var(--on-ground);
    font-weight: 700;
    font-size: var(--step-2);
    letter-spacing: -0.02em;
    text-transform: uppercase;
    text-decoration: none;
  }

  @media (max-width: 63rem) {
    .masthead__nav,
    .masthead__donate {
      display: none;
    }

    .masthead__toggle {
      display: flex;
    }

    .masthead__brand img {
      width: 158px;
    }
  }

  /* The masthead switches to the menu BEFORE the rest of the layout, so it
     carries its own breakpoint instead of sharing the site's 63rem.

     Measured in the browser: the nav has six destinations with real names
     ("Care and Support", "Events and News"), and at 1010px the Donate button
     overflowed the viewport by 74px, with the whole page scrolling
     horizontally. At 1024px it overflowed by 62px.

     The alternative was squeezing body text and spacing until it "fit", which
     is how an illegible navigation is made. Between 63rem and 75rem the menu
     wins: there is plenty of room for the full logo and the menu button. */
  @media (min-width: 63.0625em) and (max-width: 79.9375rem) {
    .masthead__nav,
    .masthead__donate {
      display: none;
    }

    .masthead__toggle {
      display: flex;
    }
  }


/* --- dropdowns -------------------------------------------------------------
   The nav links to the individual pages, not only the six hubs.

   The top-level label stays a LINK to the hub and the chevron is a separate
   BUTTON. A single control cannot announce "go to About" and "expand four
   pages" at once, and here half of the visitors arrive looking for one
   specific care page.

   The chamfer does not use `--plate-chamfer`: that variable lives in
   standard.css and the homepage only loads styles.css, so the undefined
   `var()` there would silently drop the whole property. Local value, scoped
   to this block.
   ------------------------------------------------------------------------ */

.masthead__nav > ul {
  /* the anchor for the travelling underline */
  position: relative;
}

.masthead__nav > ul > li {
  display: flex;
  align-items: center;
}

/* --- the travelling underline ----------------------------------------------
   One bar that moves to the item being pointed at and returns to the open
   section's item on release, instead of six independent underlines growing
   from 0 to 100%.

   It uses `transform`, so no layout, and a TRANSITION rather than keyframes:
   crossing the menu end to end retargets the animation from wherever it is
   instead of restarting it on each item.

   Progressive: without JavaScript there is no bar, and each link's gradient
   (which stays in its rule) does the job. So the gradient is only turned off
   when the script declares `has-ink`.
   ------------------------------------------------------------------------ */
.masthead__ink {
  position: absolute;
  top: 0;
  left: 0;
  width: 1px;      /* el ancho real lo pone scaleX */
  height: 2px;
  background: var(--sun);
  transform-origin: 0 0;
  opacity: 0;
  pointer-events: none;
  transition: transform 0.24s var(--ease-travel),
              opacity 0.18s var(--ease);
}

/* The first appearance does not travel: it is placed and shown. An underline
   sliding in from the menu's left edge reads as a glitch. */
.masthead__ink[data-colocando] {
  transition: opacity 0.18s var(--ease);
}

.masthead__nav.has-ink a {
  background-image: none;
}

.masthead__group {
  position: relative;
  display: flex;
  align-items: center;
  gap: 0.1rem;
}

.masthead__disc {
  flex: none;
  display: grid;
  place-items: center;
  width: 22px;
  height: 22px;
  padding: 0;
  background: transparent;
  border: 0;
  border-radius: var(--radius-tight);
  color: inherit;
  cursor: pointer;
  touch-action: manipulation;
  -webkit-tap-highlight-color: transparent;
}

.masthead__chev {
  width: 11px;
  height: auto;
  transition: transform 0.24s var(--ease-out);
}

.masthead__group.is-open > .masthead__disc .masthead__chev {
  transform: rotate(180deg);
}

/* The open page's section carries the permanent gold underline, as the single
   link did before there were dropdowns. */
.masthead__nav .masthead__group[data-section='current'] > a {
  background-size: 100% 2px;
}

.masthead__sub {
  list-style: none;
  margin: 0;
  padding: 0;
}

.masthead .masthead__sub[hidden] {
  /* Explicit, and with the specificity to beat any `display` that comes
     later: `hidden` is only a `display: none` from the browser stylesheet and
     the first author rule saying otherwise overrides it. The same mistake
     already cost a 197px phantom gap in this site's tabs. */
  display: none;
}

@media (min-width: 80rem) {
  .masthead__nav .masthead__sub {
    position: absolute;
    top: calc(100% + 0.65rem);
    inset-inline-start: -1rem;
    z-index: 30;
    /* One column per .masthead__col. The panel is as wide as its columns, so a
       two-column section (Care & Support) is just a wider panel: no second
       component, and the flush-end measurement in the inline script still
       works because it reads the panel's own width. */
    display: grid;
    grid-auto-flow: column;
    grid-auto-columns: minmax(15rem, 22rem);
    padding: 0.5rem 0;
    background: var(--ground-deep);
    border-top: 2px solid var(--sun);
    box-shadow: 0 18px 40px oklch(0.12 0.05 261 / 0.38);
    --menu-chamfer: 0.9rem;
    clip-path: polygon(0 0, 100% 0,
                       100% calc(100% - var(--menu-chamfer)),
                       calc(100% - var(--menu-chamfer)) 100%,
                       0 100%);
    /* Transition, not keyframes: if it closes halfway through opening, it
       returns from where it is instead of jumping to the start.

       The panel hangs off the label, so it grows FROM the label: origin top
       left, or top right when anchored to that side.

       Scale from 0.985, not from 0: nothing in the real world appears from
       nothing, and a panel growing from a point reads as a trick. */
    transform-origin: top left;
    opacity: 0;
    transform: translateY(-6px) scale(0.985);
    /* EXIT: faster than the entry. On close the user has already chosen and
       only waits for it to get out of the way. */
    transition: opacity 0.15s var(--ease),
                transform 0.15s var(--ease-menu),
                visibility 0s linear 0.15s;
    visibility: hidden;
  }

  /* ENTRY: longer and with the menu curve, for a softer ease. 260ms, within
     the 300ms ceiling a navigation control should not exceed. */
  .masthead__nav .masthead__group.is-open .masthead__sub {
    opacity: 1;
    transform: none;
    visibility: visible;
    transition: opacity 0.26s var(--ease-menu),
                transform 0.26s var(--ease-menu),
                visibility 0s linear;
  }

  .masthead__nav .masthead__group.is-flush-end .masthead__sub {
    inset-inline-start: auto;
    inset-inline-end: -1rem;
    transform-origin: top right;
    /* The chamfer changes corner with the anchoring, so it is always on the
       outside. */
    clip-path: polygon(0 0, 100% 0, 100% 100%,
                       var(--menu-chamfer) 100%,
                       0 calc(100% - var(--menu-chamfer)));
  }

  /* The bridge between the label and the panel: without it the pointer
     crosses the 0.65rem of air and mouseleave closes the menu before it
     arrives. */
  .masthead__nav .masthead__group.is-open::after {
    content: '';
    position: absolute;
    top: 100%;
    inset-inline: -1rem;
    height: 0.8rem;
  }

  /* Columns of a sectioned panel. A hairline between them, not a card each:
     the panel is already one surface. */
  .masthead__nav .masthead__col + .masthead__col {
    border-inline-start: var(--hairline);
  }

  /* A header is a label, not a destination: smaller, uppercase, the soft ink
     instead of the link ink, no underline, no hover, default cursor. Its
     links sit one step in so the group reads as a group. */
  .masthead__nav .masthead__label {
    display: block;
    padding: 0.7rem 1.25rem 0.2rem;
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: 0.08em;
    line-height: 1.3;
    text-transform: uppercase;
    white-space: nowrap;
    color: var(--on-ground-soft);
    cursor: default;
  }

  .masthead__nav .masthead__sub a {
    display: block;
    padding: 0.5rem 1.25rem;
    font-size: var(--step--1);
    font-weight: 500;
    letter-spacing: 0;
    white-space: nowrap;
    background-image: none;
  }

  .masthead__nav .masthead__sub a[aria-current='page'] {
    color: var(--sun);
  }

  .masthead__nav .masthead__grp > ul a {
    padding-inline-start: 2rem;
  }

  .masthead__nav .masthead__deep {
    list-style: none;
    margin: 0.1rem 0 0.35rem;
    padding: 0;
    border-inline-start: 1px solid oklch(0.975 0.01 262 / 0.18);
    margin-inline-start: 1.6rem;
  }

  .masthead__nav .masthead__deep a {
    padding-inline-start: 0.85rem;
    font-size: var(--step--1);
    line-height: 1.35;
    white-space: normal;
    color: var(--on-ground-soft, inherit);
  }
}

@media (prefers-reduced-motion: reduce) {
  /* The fade is kept, which explains that something appeared, and the
     movement is removed, which is what causes nausea. */
  .masthead__nav .masthead__sub,
  .masthead__nav .masthead__group.is-open .masthead__sub {
    transform: none;
    transition-property: opacity, visibility;
  }

  .masthead__chev { transition: none; }

  .masthead__ink {
    transition-property: opacity;
  }
}

/* The lists inside a panel are plain: the nav's top-level list and the mobile
   panel's `ul` rule would otherwise give them bullets, padding and a bottom
   margin. */
.masthead__sub ul {
  list-style: none;
  margin: 0;
  padding: 0;
}

/* --- the same tree inside the panel, as an accordion -------------------- */

.masthead__panel .masthead__group {
  display: grid;
  grid-template-columns: 1fr auto;
  align-items: center;
  gap: 0;
}

.masthead__panel .masthead__disc {
  width: 44px;   /* objetivo tactil completo */
  height: 44px;
}

.masthead__panel .masthead__chev {
  width: 14px;
}

.masthead__panel .masthead__sub {
  grid-column: 1 / -1;
  padding-block: 0.15rem 0.65rem;
}

.masthead__panel .masthead__sub a:not(.btn) {
  padding-block: 0.6rem;
  padding-inline-start: 0.9rem;
  font-size: var(--step-0);
  font-weight: 500;
  text-transform: none;
  letter-spacing: 0;
  border-inline-start: 2px solid oklch(0.975 0.01 262 / 0.18);
}

.masthead__panel .masthead__sub a[aria-current='page'] {
  color: var(--sun);
  border-inline-start-color: var(--sun);
}

.masthead__panel .masthead__deep {
  list-style: none;
  margin: 0;
  padding: 0;
}

/* Two columns stack in the panel; a small gap keeps them from reading as one
   list. */
.masthead__panel .masthead__col + .masthead__col {
  margin-top: 0.5rem;
}

.masthead__panel .masthead__label {
  display: block;
  padding: 0.85rem 0 0.25rem 0.9rem;
  font-size: var(--step--1);
  font-weight: 700;
  letter-spacing: 0.08em;
  line-height: 1.3;
  text-transform: uppercase;
  color: var(--on-ground-soft);
  border-inline-start: 2px solid oklch(0.975 0.01 262 / 0.18);
}

.masthead__panel .masthead__grp > ul a:not(.btn) {
  padding-inline-start: 1.6rem;
}

.masthead__panel .masthead__grp > ul .masthead__deep a:not(.btn) {
  padding-inline-start: 2.6rem;
}

.masthead__panel .masthead__deep a:not(.btn) {
  padding-inline-start: 2rem;
  font-size: var(--step--1);
}

/* The panel separator was drawn with `li + li`, which would now also fall
   between the children of a dropdown and split the group into stripes. */
.masthead__panel .masthead__sub li + li {
  border-top: 0;
}

/* --- HomeSections ------------------------------------------------------- */


  /* --- 1. hero ---------------------------------------------------------- */

  .hero {
    position: relative;
    isolation: isolate;
    overflow: hidden;
    min-height: min(88dvh, 48rem);
    display: flex;
    align-items: flex-end;
    /* The masthead sits on top of the photograph, so the hero pulls up behind
       it and pads the copy back down clear of the nav. */
    margin-top: calc(-1 * var(--masthead-h, 76px));
    padding-block: calc(var(--masthead-h, 76px) + clamp(4rem, 3rem + 6vw, 9rem))
      clamp(3rem, 2.2rem + 4vw, 5.5rem);
  }

  .hero__media {
    position: absolute;
    inset: 0;
    z-index: -1;
  }

  .hero__slides {
    list-style: none;
    padding: 0;
    margin: 0;
    position: absolute;
    inset: 0;
  }

  /* 21s cycle over three slides: 7s each, which is slow enough that the hero
     is not flickering behind someone trying to read the heading. The first
     slide is the one that holds on load, so it needs no delay. */
  .hero__slide {
    position: absolute;
    inset: 0;
    opacity: 0;
    animation: hero-cycle 21s infinite;
    animation-delay: calc(var(--slide) * 7s);
  }

  @keyframes hero-cycle {
    0%,
    30% {
      opacity: 1;
    }
    36%,
    94% {
      opacity: 0;
    }
    100% {
      opacity: 1;
    }
  }

  .hero__media img {
    width: 100%;
    height: 100%;
    object-fit: cover;
    /* Frames the group and the path they are walking toward. */
    object-position: 52% 42%;
  }

  /* The sun as light behind the group rather than a shape in a corner. Sits
     under the photograph and reads through it via the scrim's transparency. */
  /* Sunlight behind the group. Pulled back hard from where it started, because
     with the slideshow the frame underneath it changes: on the walking shot it
     falls on trees and reads as light, and on the group portrait it landed
     squarely on a woman's face and dyed it yellow. Any effect painted over a
     photograph has to survive every photograph that can appear under it.

     Also raised and pushed further right, off the centre of the frame where
     the faces are. */
  .hero__glow {
    position: absolute;
    right: 2%;
    bottom: 34%;
    width: clamp(16rem, 34vw, 34rem);
    aspect-ratio: 1;
    border-radius: 50%;
    background: radial-gradient(
      circle,
      oklch(0.88 0.18 95 / 0.42) 0%,
      oklch(0.8 0.19 75 / 0.24) 38%,
      oklch(0.7 0.17 52 / 0.08) 62%,
      transparent 72%
    );
    z-index: 1;
    pointer-events: none;
  }

  /* Guarantees text contrast over the photograph, and lightened so the image
     is more visible.

     Every stop came down, but not uniformly, because they do different jobs.
     The band under the copy is load-bearing: the h1, the lede and the outline
     button all sit on it, and at 0.95 the effective background is the ground
     token, which is where the measured 16.49:1 comes from. Taking that to
     0.80 keeps the text over an effective luminance still dark enough to pass
     AA with margin, and it is the largest cut the copy can carry.

     Where nothing sits on it the scrim can afford to go much further, so the
     right-hand side drops to 0.18 and the photograph reads nearly clean
     there.

     The top band stays comparatively heavy at 0.72. It protects the nav,
     which crosses the brightest part of the frame and measured 4.90:1
     unprotected, and it is the one stop where a lighter value would fail
     rather than just look flatter. */
  .hero__scrim {
    position: absolute;
    inset: 0;
    z-index: 2;
    /* The overlay is lightened by 10%, which is NOT a number picked by eye:
       it is the maximum the headline contrast tolerates.

       Measured on all THREE carousel photos, sampling the real pixel under
       the text (the worst case, not the average). The headline is large text,
       so its AA minimum is 3:1:

         current 4.11    -10%  3.60    -18%  3.22 (borderline)    -25%  2.98 (fails)

       Lightening only the right half, where there is no text, was also tried:
       it does NOT work. The headline reaches 63% of the width and the
       gradient is diagonal (100deg), so the 66% stop already lands on it:
       that variant measured 2.80 and fails.

       Lightening MORE would need a design change (a local box or gradient
       behind the text, which counts as background for WCAG; a `text-shadow`
       does not). */
    background:
      linear-gradient(to bottom, oklch(0.155 0.075 262 / 0.7) 0%, transparent 22%),
      linear-gradient(
        100deg,
        oklch(0.155 0.075 262 / 0.72) 0%,
        oklch(0.155 0.075 262 / 0.61) 38%,
        oklch(0.155 0.075 262 / 0.29) 66%,
        oklch(0.155 0.075 262 / 0.16) 100%
      ),
      linear-gradient(to top, oklch(0.155 0.075 262 / 0.63) 0%, transparent 52%);
    pointer-events: none;
  }

  .hero__inner {
    position: relative;
    z-index: 3;
    width: 100%;
  }

  /* Manual slide controls. One chevron, drawn once as a <polyline> rather
     than borrowed from an icon set that is not loaded; "next" is the same SVG
     mirrored with scaleX(-1), so there is one shape to get right, not two
     that have to match.

     Semi-transparent navy plus blur, the overlay treatment used elsewhere on
     this page for content floating on unpredictable photographs (the panel
     photo captions): a flat colour would look wrong against some part of at
     least one of the three photos, blur keeps it legible against all of them.

     --radius-control, not a circle. Every other control on this page (the
     donate button, the newsletter field, the date badges) is unified on that
     one token; a fully round icon button would be a second, competing
     "control" language for no reason beyond carousel convention. */
  .hero__nav {
    position: absolute;
    top: 50%;
    transform: translateY(-50%);
    z-index: 4;
    display: grid;
    place-items: center;
    width: 2.75rem;
    height: 2.75rem;
    border: none;
    border-radius: var(--radius-control);
    background: oklch(0.155 0.075 262 / 0.45);
    backdrop-filter: blur(6px);
    color: var(--on-ground);
    cursor: pointer;
    transition: background-color 0.2s var(--ease), color 0.2s var(--ease),
      transform 0.14s var(--ease-out);
    touch-action: manipulation;
    -webkit-tap-highlight-color: transparent;
  }

  .hero__nav svg {
    width: 1.15rem;
    height: 1.15rem;
  }

  .hero__nav--prev {
    left: var(--gutter);
  }

  /* The drawn chevron always points left; flipping it is cheaper and more
     reliably symmetric than hand-drawing a mirror-image path. */
  .hero__nav--next {
    right: var(--gutter);
  }

  .hero__nav--next svg {
    transform: scaleX(-1);
  }

  .hero__nav:active {
    transform: translateY(-50%) scale(0.97);
  }

  @media (hover: hover) and (pointer: fine) {
    .hero__nav:hover {
      background: oklch(0.155 0.075 262 / 0.68);
      color: var(--sun);
    }
  }

  /* Nothing to navigate to: under reduced motion the other two slides are
     display:none (see the reduced-motion block below), so a control that can
     only ever point at the one slide already showing is a dead end rather
     than a feature. */
  @media (prefers-reduced-motion: reduce) {
    .hero__nav {
      display: none;
    }
  }

  @media (max-width: 34rem) {
    .hero__nav {
      width: 2.25rem;
      height: 2.25rem;
    }

    .hero__nav svg {
      width: 1rem;
      height: 1rem;
    }
  }

  .hero h1 {
    margin-inline-start: -0.055em;
    max-width: 20ch;
  }

  .hero__foot {
    /* Copy stays on the scrimmed side, clear of the glow. */
    max-width: 54%;
    margin-top: clamp(1.5rem, 1.2rem + 2vw, 2.75rem);
  }

  .hero__actions {
    display: flex;
    flex-wrap: wrap;
    gap: var(--space-s);
    margin-top: var(--space-l);
  }

  /* --- 2. mission ------------------------------------------------------- */

  /* Centred, unlike the reading blocks further down. Centring a heading that
     opens a set of panels is the gesture that stops this reading as another
     left/right split; centring body copy as well would just be tiring. */
  .mission__head {
    text-align: center;
    margin-bottom: var(--space-xl);
  }

  /* Steps down harder than --step-4 at the small end. "COMMITMENTS" is eleven
     characters at wght 750 / wdth 112, which does not fit 375px at the
     default display minimum, and the global overflow-wrap safety net then
     split it mid-word. Measured against the rendered word width, not
     estimated. */
  .mission__head h2 {
    font-size: clamp(2.3rem, 8.4vw, 5.4rem);
  }

  /* The measure goes on the paragraph only. Putting it on the wrapper
     strangled the display heading, which then broke mid-word ("COMMI / TMEN /
     TS"): a display size inside a box measured for body text. */
  .mission__head p {
    max-width: 38ch;
    margin-top: var(--space-s);
    margin-inline: auto;
    color: var(--on-ground-soft);
  }

  /* The panels end level. Ragged bottoms with nothing under them look
     unfinished: where one panel is shorter, a second tile beneath it closes
     the column. The variety belongs inside the panel, not at its edge. */
  /* Two rows, shared by all three panels through subgrid: heads occupy one
     band and feet another, so the panels finish level AND the visual matter
     starts on the same line. Equal outer height alone was not enough; the
     heads carry different amounts of copy, which left the photograph, the
     geometry and the name each beginning at a different height. */
  .panels {
    display: grid;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    grid-template-rows: auto 1fr;
    grid-auto-rows: auto 1fr;
    gap: var(--space-m);
  }

  /* Four rows for four children, with the copy row taking the slack, so the
     three links land on one line however much text sits above them. */
  .panel {
    background: var(--ground-raised);
    border-radius: var(--radius-card);
    /* No border. Separation is the step in luminance from --ground, which is
       why the ground and raised tokens exist. */
    padding: var(--space-l) var(--space-m);
    display: grid;
    grid-template-rows: auto auto 1fr auto;
    justify-items: center;
    text-align: center;
    gap: var(--space-2xs);
    /* Read by Pillar.astro, which cuts its flutes in this colour so the icon
       is correct on whatever surface it lands on. */
    --panel-surface: var(--ground-raised);
  }

  .panel__pillar {
    margin-bottom: var(--space-s);
  }

  /* The size that ships is NOT set here. `html body.daybreak h3` (0,1,2)
     beats `.panel h3` (0,1,1), so this declaration never reaches the page in
     the daybreak tone; the live value is in the daybreak block, with the caps
     and the tracking. */
  .panel h3 {
    font-size: var(--step-1);
    font-weight: 600;
    text-transform: none;
    letter-spacing: -0.01em;
    line-height: 1.15;
    color: var(--on-ground);
  }

  /* The body was --step--1, the smallest size on the page, on the one block
     that carries what the foundation actually does, read by patients and
     families who are frequently older. Up one step, and the measure widens
     with it so the column does not turn into four short lines. */
  .panel p {
    color: var(--on-ground-soft);
    font-size: var(--step-0);
    line-height: 1.55;
    max-width: 32ch;
  }

  .panel .link-line {
    margin-top: var(--space-xs);
  }

  /* --- 3. what is ALS --------------------------------------------------- */

  /* A section stripped down to a heading, one sentence and a button, centred
     on a narrow measure, reads as empty.

     A photograph in the hexagon of the foundation's printed identity fills
     it. It is also the only way that identity places an image: never bled
     behind copy, always framed. Copy left, frame right, which does not repeat
     the Center of Hope composition further down because that one runs the
     other way. */
  .explain__inner {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 0.72fr);
    gap: clamp(2rem, 1rem + 5vw, 5rem);
    align-items: center;
  }

  .explain__copy {
    display: grid;
    justify-items: start;
    gap: var(--space-m);
  }

  .explain__glyph {
    margin-bottom: calc(-1 * var(--space-xs));
  }

  .explain__body {
    font-size: var(--step-1);
    line-height: 1.45;
    max-width: 46ch;
    color: var(--on-ground-soft);
  }

  .explain__shot {
    max-width: 30rem;
    width: 100%;
    margin-inline-start: auto;
  }

  /* --- 4. clinic -------------------------------------------------------- */

  /* Two equal panels side by side: a filled card holding the copy, a
     photograph filling the other, both the same size and both heavily
     rounded.

     Equal columns and `stretch`, so the panels match height whatever the copy
     does. The photograph sets that height through its aspect-ratio and the
     text panel follows. */
  .clinic__grid {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: clamp(1rem, 0.5rem + 1.5vw, 2rem);
    align-items: stretch;
  }

  /* The radius is local to this section and deliberately at odds with the
     rest of the page, whose other corners are squared off. If this
     composition stays, the squaring needs revisiting page-wide rather than
     leaving one round section among flat ones. */
  /* Flex, not grid: the CTA is pinned to the foot with `margin-top: auto`,
     and in a grid with `align-content: start` that does nothing, because
     align-content has already fixed where the rows sit. */
  .clinic__copy {
    background: var(--paper-1);
    border-radius: var(--radius-card);
    padding: clamp(1.75rem, 1rem + 3vw, 3.5rem);
    display: flex;
    flex-direction: column;
    align-items: flex-start;
  }

  /* Somebody else's mark, so it is given room and left alone: no tint, no
     radius, no attempt to make its green agree with the page. Height-capped
     rather than width-capped because it is nearly square. */
  .clinic__logo {
    width: auto;
    height: auto;
    max-height: 5.5rem;
    max-width: 13.75rem;
    object-fit: contain;
    margin-bottom: var(--space-m);
  }

  .clinic__copy p {
    margin-top: var(--space-m);
    color: var(--on-ground-soft);
    max-width: 48ch;
  }

  /* Pinned to the foot of the panel rather than sitting directly under the
     last paragraph.

     `margin-top: auto` only. Adding padding-top to hold it clear of the copy
     pads the BUTTON rather than the space above it: the control grows into a
     tall block that swallows the paragraph behind it. Space above a pinned
     element is margin, never padding. */
  .clinic__cta {
    margin-top: auto;
  }

  /* A floor under that `auto`: when the copy nearly fills the panel there is
     no free space left to push with, and the button ends up against the last
     line. This is the minimum gap; the auto takes over whenever there is
     room. */
  .clinic__copy p:last-of-type {
    margin-bottom: var(--space-l);
  }

  .clinic__figure {
    margin: 0;
  }

  /* Fills its half of the row and sets the height for both panels.

     Note: this photograph is 665px wide and roughly 2010. It is the weakest
     asset on the page and the first to replace when new photography is
     available. */
  .clinic__shot {
    width: 100%;
    aspect-ratio: 1;
    border-radius: var(--radius-card);
    overflow: hidden;
  }

  .clinic__shot img {
    /* Framed on the two faces, the only part worth showing at this
       resolution. */
    object-position: 56% 24%;
  }

  /* --- 5. events -------------------------------------------------------- */

  /* Three tiles, photograph first, copy under it. Matches the commitments
     row, and drops the hairline table this section was. */
  .events__list {
    list-style: none;
    padding: 0;
    margin-top: var(--space-xl);
    display: grid;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    gap: var(--space-l) var(--space-m);
  }

  .event {
    display: grid;
    align-content: start;
    gap: var(--space-2xs);
  }

  .event__shot {
    position: relative;
    margin-bottom: var(--space-s);
  }

  /* Events need a visible date. None of the three has a confirmed one: the
     archived event pages carry Squarespace PUBLISH dates, not event dates,
     and every one already fell in the past. Inventing a specific date for a
     nonprofit's public events is not something to do quietly; this is the
     honest placeholder, styled as the real thing so the layout needs no
     rework once confirmed dates arrive.

     Positioned as a corner badge on the photo rather than as the plain text
     line it replaces. */
  .event__badge {
    position: absolute;
    top: var(--space-s);
    left: var(--space-s);
    z-index: 1;
    padding: 0.45em 0.85em;
    background: var(--sun);
    color: var(--ink);
    font-weight: 700;
    font-size: var(--step--1);
    letter-spacing: 0.04em;
    text-transform: uppercase;
    border-radius: var(--radius-control);
  }

  .event__name {
    font-size: var(--step-1);
    font-weight: 600;
    text-transform: none;
    letter-spacing: -0.01em;
    line-height: 1.15;
    color: var(--on-ground);
  }

  .event__note {
    color: var(--on-ground-soft);
    font-size: var(--step--1);
    line-height: 1.5;
  }

  .events__all {
    margin-top: var(--space-xl);
  }

  /* The logo carousel pauses on focus of anything inside, and for that to be
     possible the viewport has to be able to receive focus.

     `:focus-within` does not work here: there is not one focusable element
     inside (18 <li> with only an <img>), so it never fired and the pause was
     hover-only, useless with a keyboard and on touch screens. WCAG 2.2.2
     requires that any automatic movement lasting more than five seconds can
     be paused, and this one loops for 44 seconds, forever. */
.partners__viewport:focus-visible {
  outline: 3px solid var(--sun);
  outline-offset: 4px;
}

/* --- 5b. partners ----------------------------------------------------- */

  /* Not a boxed slideshow in a side column, but a full-width strip with the
     copy above it and the button below: heading, marquee, action, stacked and
     each spanning the section on its own terms.

     .partners__viewport sits OUTSIDE both .shell wrappers, at the section's
     own full width. Partners is the one row that moves. */
  .partners__head {
    text-align: center;
    max-width: 52ch;
    margin-inline: auto;
  }

  .partners__head p {
    margin-top: var(--space-m);
    color: var(--on-ground-soft);
  }

  .partners__viewport {
    margin-top: var(--space-xl);
    overflow: hidden;
    mask-image: linear-gradient(
      to right,
      transparent,
      black 8%,
      black 92%,
      transparent
    );
  }

  .partners__track {
    list-style: none;
    padding: 0;
    margin: 0;
    display: flex;
    align-items: center;
    gap: clamp(2.5rem, 1.5rem + 4vw, 5rem);
    width: max-content;
    /* 44s: the logos grew (roughly another 23%) and the track grew with them,
       so the same duration over a longer single-copy distance would have sped
       the scroll up. Duration tracks single-copy width, not how many copies
       are duplicated for the loop. */
    animation: marquee-scroll 44s linear infinite;
  }

  /* Exactly a third of the track now that it holds three copies, which is
     where the second copy begins. Two copies were not enough width: on a wide
     screen a single copy's logos did not reach the far edge, so the strip ran
     out and showed a gap of bare white before the loop reset. A third copy
     guarantees there is always at least one full set of logos ahead of the
     visible edge, whatever the viewport width. */
  @keyframes marquee-scroll {
    to {
      transform: translateX(-33.3334%);
    }
  }

  /* No longer boxed inside a small frame, so there is no ceiling from a
     fixed-height card to respect here. */
  .partners__item img {
    width: auto;
    height: auto;
    max-height: 6rem;
    max-width: 20rem;
    object-fit: contain;
  }

  /* Pause on hover and on focus. A moving target is unusable for anyone with
     a tremor or a motor impairment, which on this site is a large share of
     the audience, not an edge case. */
  .partners__viewport:hover .partners__track,
  .partners__viewport:focus-within .partners__track {
    animation-play-state: paused;
  }

  .partners__cta {
    display: block;
    width: fit-content;
    margin: var(--space-xl) auto 0;
  }

  /* --- 5c. by the numbers ----------------------------------------------- */

  .figures__head {
    display: grid;
    justify-items: center;
    text-align: center;
    margin-bottom: var(--space-xl);
  }

  .figures__glyph {
    margin-bottom: var(--space-s);
  }

  .figures__head p {
    max-width: 46ch;
    margin-top: var(--space-s);
    margin-inline: auto;
    color: var(--on-ground-soft);
  }

  /* Two columns, not three: with six figures three columns give two thin rows
     where two give a block. */
  .figures__grid {
    list-style: none;
    padding: 0;
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: var(--space-xl) var(--space-2xl);
  }

  .figure__head {
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    align-items: center;
    gap: var(--space-s);
  }

  /* The icon plate: a navy square with two corners cut.

     The chamfer is a fixed length, NOT a fraction of --cut. At --cut/3 it was
     53px, which on a 56px square clipped the plate down to a diagonal sliver
     with the icon gone. A shape this small cannot be driven by a page-scale
     variable. */
  .figure__icon {
    --plate-chamfer: 0.9rem;
    display: grid;
    place-items: center;
    width: 3.5rem;
    height: 3.5rem;
    background: var(--ground);
    color: var(--sun);
    font-size: 1.75rem;
    clip-path: polygon(
      var(--plate-chamfer) 0,
      100% 0,
      100% calc(100% - var(--plate-chamfer)),
      calc(100% - var(--plate-chamfer)) 100%,
      0 100%,
      0 var(--plate-chamfer)
    );
  }

  .figure__value {
    font-weight: 700;
    font-size: var(--step-3);
    line-height: 1;
    letter-spacing: -0.03em;
    color: var(--ink, var(--on-ground));
  }

  /* The yellow pill. This is the one place on a light page where the sun can
     carry text: ink on sun is 10.46:1. */
  .figure__label {
    justify-self: start;
    margin-top: 0.35rem;
    padding: 0.25em 0.8em;
    background: var(--sun);
    color: var(--ink);
    font-size: var(--step--1);
    font-weight: 600;
    line-height: 1.35;
  }

  .figure__note {
    margin-top: var(--space-s);
    font-size: var(--step--1);
    line-height: 1.5;
    color: var(--on-ground-soft);
    max-width: 38ch;
  }

  /* --- 6b. sponsors ----------------------------------------------------- */

  .sponsors__head {
    font-size: var(--step-1);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.14em;
    text-align: center;
    color: var(--on-ground-dim);
  }

  /* This row holds still: a plain wrapped row inside the shell, same width as
     every other section instead of running full bleed. Partners and alliances
     carries the marquee, so the page has one row of logos in motion rather
     than two. */
  .sponsors__track {
    list-style: none;
    padding: 0;
    margin-top: var(--space-l);
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    align-items: center;
    gap: clamp(1.5rem, 1rem + 2vw, 3rem);
  }

  /* Full colour, which is not the reflex. Desaturating a sponsor row is the
     usual move, but it fails on this set: three of these logos are white type
     on a solid colour plate, and grayscale turns them into grey blocks with
     the wordmark gone. It is also the wrong courtesy: these companies funded
     the walk, and their marks are how they are thanked.

     Levelling comes from geometry instead: one height cap for every logo, and
     generous even spacing, so a nine-brand row still reads as one band. */
  .sponsors__item img {
    width: auto;
    height: auto;
    max-height: 3.25rem;
    max-width: 11.25rem;
    object-fit: contain;
  }

  @media (prefers-reduced-motion: reduce) {
    .hero__slide {
      animation: none;
    }

    .hero__slide:first-child {
      opacity: 1;
    }

    /* The other two would otherwise sit at opacity 0 over the first one,
       which is harmless, but they are also downloads nobody will ever see. */
    .hero__slide:not(:first-child) {
      display: none;
    }

    /* Sponsors is a plain wrapped row by default and never moves, so it needs
       nothing here. Partners is the one that marquees. */
    .partners__track {
      animation: none;
      width: 100%;
      flex-wrap: wrap;
      justify-content: center;
      gap: var(--space-m);
    }

    /* The duplicate exists only to make the loop seamless. Standing still it
       is six logos printed twice. */
    .partners__item[aria-hidden='true'] {
      display: none;
    }
  }

  /* --- 6. giving -------------------------------------------------------- */

  .give__grid {
    display: grid;
    grid-template-columns: minmax(0, 1.2fr) minmax(0, 0.8fr);
    gap: clamp(1.5rem, 1rem + 4vw, 4rem);
    align-items: end;
  }

  .give__head {
    max-width: 16ch;
  }

  .give__body p {
    font-size: var(--step-1);
    line-height: 1.45;
    max-width: 34ch;
  }

  .give__actions {
    display: flex;
    flex-wrap: wrap;
    gap: var(--space-s);
    margin-top: var(--space-l);
  }

  /* --- responsive ------------------------------------------------------- */

  @media (max-width: 63rem) {
    /* Was clamp(9rem, 8rem + 18vw, 16rem), reserving the bottom of the screen
       for the diagonal planes. With those gone the copy would float a sixth
       of a viewport above the fold for no reason. */
    .hero {
      min-height: 0;
      padding-bottom: clamp(3rem, 2.2rem + 4vw, 5.5rem);
    }

    /* Full screen here too. The 40rem cap made the hero 640px on a phone
       whose viewport is 844, so the seam landed mid-screen with white under
       it. daybreak.css sets 100dvh; this override sits below it in the
       cascade and would win. */
    .hero {
      min-height: 100dvh;
    }

    .hero__foot {
      max-width: none;
    }

    /* Narrow viewports put copy across the full width, so the horizontal
       scrim cannot protect it. It goes vertical and heavier instead.

       Lightened with the desktop scrim, and by less. There is no empty half
       of the frame to give back here: the copy runs the full width, so the
       bottom two thirds stay load-bearing. What can open up is the top, where
       only the photograph lives, and it drops from 0.45 to 0.24. */
    .hero__scrim {
      background:
        /* Same nav guard as desktop. Without it the white wordmark and the
           menu button sit directly on whichever slide is up, and one of the
           three opens on bright sky. With a slideshow the worst case is not a
           crop that can be chosen, it arrives on a timer. */
        linear-gradient(to bottom, oklch(0.155 0.075 262 / 0.6) 0%, transparent 18%),
        /* The same 10% as on desktop. On mobile the text falls over the
           bottom band, so the `to top` gradient is the one that rules here;
           measured separately at 390px. */
        linear-gradient(
          to top,
          oklch(0.155 0.075 262 / 0.6) 0%,
          oklch(0.155 0.075 262 / 0.54) 48%,
          oklch(0.155 0.075 262 / 0.26) 78%,
          oklch(0.155 0.075 262 / 0.12) 100%
        );
    }

    .hero__glow {
      right: -10%;
      bottom: 52%;
      width: clamp(16rem, 70vw, 26rem);
    }

    .explain__inner,
    .clinic__grid,
    .give__grid {
      grid-template-columns: 1fr;
    }

    .figures__grid {
      grid-template-columns: repeat(2, minmax(0, 1fr));
      gap: var(--space-l) var(--space-m);
    }

    /* Two up rather than one: at this width a single column of panels turns
       the section into a long scroll of near-identical blocks. The third
       wraps and sits wide, which reads as intentional rather than as a
       leftover. */
    .panels {
      grid-template-columns: repeat(2, minmax(0, 1fr));
    }

    .explain__head {
      grid-template-columns: 1fr;
    }

    .explain__figure {
      order: -1;
      width: clamp(8rem, 34vw, 11rem);
    }

    .clinic__shot {
      max-width: 20rem;
      margin-inline: 0;
    }

    /* Two up, third wraps wide, same as the commitments row. */
    .events__list {
      grid-template-columns: repeat(2, minmax(0, 1fr));
    }

    .give__grid {
      align-items: start;
    }
  }

  @media (max-width: 34rem) {
    .panels,
    .events__list {
      grid-template-columns: 1fr;
    }

    .hero__actions .btn,
    .give__actions .btn {
      flex: 1 1 auto;
      justify-content: center;
    }
  }

/* --- Footer ------------------------------------------------------------- */


  .footer {
    background: var(--ground-deep);
    color: var(--on-ground);
    padding-block: var(--section-y) var(--space-l);
  }

  .footer__tagline {
    font-weight: 700;
    font-size: var(--step-4);
    line-height: 0.95;
    letter-spacing: -0.03em;
    text-transform: uppercase;
    color: var(--sun);
    max-width: 18ch;
    margin-bottom: var(--space-2xl);
  }

  .footer__grid {
    display: grid;
    /* Contact carries more, so the columns are not equal. */
    grid-template-columns: 1.5fr 1fr 1fr;
    gap: var(--space-xl) var(--space-l);
    padding-top: var(--space-l);
    border-top: var(--hairline);
  }

  /* `html body.daybreak h2` sets a size at (0,1,3) and outweighs this at
     (0,1,1), so these shipped at 39.92px against an intended 15px: 2.6x off,
     and the largest heading on any page after the h1. The tone goes in front
     of the selector so the intended size actually lands. */
  body.daybreak .footer__col h2,
  .footer__col h2 {
    font-weight: 600;
    font-size: var(--step--1);
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: var(--on-ground-dim);
    margin-bottom: var(--space-m);
  }

  .footer__col ul {
    list-style: none;
    padding: 0;
    display: grid;
    gap: 0.6rem;
  }

  .footer a {
    color: var(--on-ground);
    text-decoration: none;
    touch-action: manipulation;
    -webkit-tap-highlight-color: transparent;
  }

  @media (hover: hover) and (pointer: fine) {
    .footer a:hover {
      color: var(--sun);
      text-decoration: underline;
      text-underline-offset: 0.2em;
    }
  }

  .footer address {
    font-style: normal;
    display: grid;
    gap: var(--space-s);
    color: var(--on-ground-soft);
  }

  .footer__social a {
    display: inline-flex;
    align-items: center;
    gap: 0.6rem;
  }

  .footer__social svg {
    width: 1.05rem;
    height: 1.05rem;
    color: var(--sun);
  }

  .footer__legal {
    margin-top: var(--space-2xl);
    padding-top: var(--space-m);
    border-top: var(--hairline);
    display: grid;
    gap: 0.4rem;
    font-size: var(--step--1);
    /* 6.16:1 against this ground, past AA for small text. */
    color: var(--on-ground-dim);
  }

  /* The measure goes on the text lines, not on the block: with the max-width
     on `.footer__legal` its hairline came out shorter than the logos'. */
  .footer__legal > * {
    max-width: 66rem;
  }

  @media (max-width: 63rem) {
    .footer__grid {
      grid-template-columns: 1fr 1fr;
    }

    .footer__col--contact {
      grid-column: 1 / -1;
    }
  }

  @media (max-width: 30rem) {
    .footer__grid {
      grid-template-columns: 1fr;
    }
  }

/* --- What is ALS + The Center of Hope, as a pair ---------------------------
   Two full-width sections became one row of two panels, each with its copy on
   the left and a photograph on the right, meeting on a diagonal.

   The diagonal is the reason this exists. Everywhere else on the page the
   angle lives in section backgrounds, where enough of it turns into
   wallpaper. Here it is the seam between the photograph and the colour: an
   image is never a rectangle dropped on a page, it is cut against the colour
   beside it.
   ------------------------------------------------------------------------ */

.duo__grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: clamp(1rem, 0.5rem + 1.5vw, 1.75rem);
  align-items: stretch;
}

/* The panel is the clipping context: `overflow: hidden` plus the radius is
   what keeps the photograph inside the rounded corner, since the image itself
   is clipped by a polygon and a polygon has no radius. */
/* The copy column carries more weight than the photograph. At 1fr / 0.82fr
   the text column was narrower than its own button, so "Understand the
   diagnosis" ran under the image and got sliced by the diagonal. A button is
   a hard minimum: the column cannot be narrower than the widest control in
   it. */
.duo__panel {
  display: grid;
  /* The chevron cuts a wedge out of the image column, so it is given back
     some width: at 0.75fr the visible photograph was a sliver. */
  grid-template-columns: minmax(0, 1.1fr) minmax(0, 0.9fr);
  align-items: stretch;
  background: var(--paper-1);
  border-radius: var(--radius-card);
  overflow: hidden;
  /* Was clamp(18rem, 26vw, 24rem), which on a wide screen pinned the panel at
     384px of minimum before any content, and with the copy on top of that the
     pair filled most of a viewport for two short paragraphs. The panel should
     be sized by what is in it, with the minimum only stopping it collapsing. */
  min-height: clamp(14rem, 17vw, 18rem);
}

.duo__copy {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  padding: clamp(1.35rem, 0.9rem + 1.4vw, 2rem);
}

/* One step down from a section heading. These are two panels sharing a row,
   not two sections: at --step-2 "The Center of Hope" took three lines in its
   own column and set the height of the pair. */
.duo__copy h2 {
  font-size: var(--step-1);
  line-height: 1.15;
}

.duo__copy p {
  margin-top: var(--space-s);
  color: var(--on-ground-soft);
  font-size: var(--step--1);
  line-height: 1.55;
}

/* Pinned to the foot so the two buttons land on one line across both panels,
   whatever the copy above them does. margin, never padding: padding would
   inflate the button instead of the space above it. */
/* Smaller than a page-level button. These are the third action in a panel
   that is itself half a row, and at the default size "Understand the
   diagnosis" broke onto two lines, which reads as a button that did not fit
   rather than as one that was meant to be there. */
.duo__cta {
  margin-top: auto;
  padding-top: 0;
  font-size: var(--step--1);
  padding: 0.7em 1.15em;
  /* Never wider than the column it sits in. */
  max-width: 100%;
  text-align: center;
}

.duo__copy p:last-of-type {
  margin-bottom: var(--space-l);
}

/* Somebody else's mark: given room and left alone, no tint and no radius.

   It sits below the words "The Center of Hope" so the two panel headings sit
   on one line. Opening the column, it pushed its heading down by the height
   of the mark and left "What is ALS?" alone at the top of the row. So the
   spacing moves with it: the margin is above now, and the paragraph below
   brings its own. */
.duo__copy img.clinic__logo,
.duo__copy > img {
  width: auto;
  height: auto;
  /* A little larger than when it opened the column: on its own line under the
     heading it is read as the clinic's mark rather than glanced past, and at
     2.5rem the wordmark inside it was not legible at all. */
  max-height: 3.25rem;
  max-width: 10rem;
  object-fit: contain;
  margin-top: var(--space-s);
  margin-bottom: 0;
}

/* The photograph, cut against the copy.

   NOT a straight diagonal. The edge is a CHEVRON: it runs down and to the
   left to a point at roughly three fifths height, then opens back out to the
   right. It is what makes the image read as a shape rather than as a
   rectangle someone sheared.

   Five points, and only two numbers drive it: how far in the top and bottom
   edges start, and where the point sits vertically. */
.duo__shot {
  position: relative;
  --duo-in: 26%;   /* how far in from the left the top edge begins */
  --duo-tip: 58%;  /* height of the point */
  clip-path: polygon(
    var(--duo-in) 0,
    100% 0,
    100% 100%,
    calc(var(--duo-in) * 0.72) 100%,
    0 var(--duo-tip)
  );
}

.duo__shot img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* Both photographs are wide and the panel is not, so the crop determines what
   survives. Chosen per image rather than shared: one is two people at a
   gathering, the other is a clinician and a patient. */
.duo__panel:first-child .duo__shot img {
  object-position: 50% 45%;
}

.duo__panel:last-child .duo__shot img {
  object-position: 56% 30%;
}

@media (max-width: 63rem) {
  /* One panel per row, and inside each the photograph goes under the copy: at
     half a phone's width the diagonal has nothing to cut against and the
     image becomes a sliver. */
  .duo__grid,
  .duo__panel {
    grid-template-columns: 1fr;
  }

  /* Stacked, the chevron would cut across the top of the photograph instead
     of down its side, which is not the same shape at all. Straight edges
     below the breakpoint. */
  .duo__shot {
    clip-path: none;
    aspect-ratio: 16 / 9;
  }

  .duo__panel {
    min-height: 0;
  }
}

/* --- 2025 in numbers, as one row -------------------------------------------
   Six figures on a single line, divided by hairlines, which reads at a
   glance. A two-column grid with a sentence under each figure was taller than
   the whole of What is ALS, for six numbers.

   The yellow pill goes with it. It was right when each figure was a block
   with room around it; on one line six pills read as a row of tags, and the
   label is doing plain labelling work here.
   ------------------------------------------------------------------------ */

.figures__eyebrow {
  font-size: var(--step--1);
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--on-ground-soft);
  margin-bottom: var(--space-l);
}

.figures__row {
  list-style: none;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(6, minmax(0, 1fr));
  align-items: start;

  /* The dividers between figures: one pixel of ink at 16%. (The grey seam
     across the top of this section is a different line.) */
  --figure-rule: var(--hairline);
}

/* Divided by rules between items, not around them: a border on every item
   would close the row into a box. */
.figures__row .figure + .figure {
  border-left: var(--figure-rule);
}

.figures__row .figure {
  display: grid;
  justify-items: center;
  text-align: center;
  gap: 0.5rem;
  padding-inline: clamp(0.5rem, 1.2vw, 1.25rem);
}

.figures__row .figure__icon {
  width: 3.5rem;
  height: 3.5rem;
  display: grid;
  place-items: center;
  background: none;
  clip-path: none;
  color: var(--sun-deep);
  font-size: 3rem;
}

/* The figures are the section: they should be the largest thing in it, and
   nothing else in this row competes for the size. Not on the type scale on
   purpose: --step-3 is a heading size and this is a number, which reads
   larger than letters at the same value because it is all cap height. */
.figures__row .figure__value {
  font-weight: 700;
  font-size: clamp(2.4rem, 1.9rem + 2.2vw, 3.6rem);
  line-height: 1;
  letter-spacing: -0.03em;
  color: var(--ink);
  /* Tabular figures: while the number counts, proportional digits change the
     element's width on every frame and the row jitters sideways. This pins
     every digit to the same advance width. */
  font-variant-numeric: tabular-nums;
}

.figures__row .figure__label {
  background: none;
  color: var(--on-ground-soft);
  font-size: var(--step--1);
  font-weight: 400;
  line-height: 1.35;
  padding: 0;
  margin: 0;
  justify-self: center;
}

/* Six across stops working long before a phone: three, then two. */
@media (max-width: 63rem) {
  .figures__row {
    grid-template-columns: repeat(3, minmax(0, 1fr));
    gap: var(--space-l) 0;
  }

  /* With three per row the rule belongs between columns, not before every
     item, or the first of each row gets one hanging off its left edge. */
  .figures__row .figure + .figure {
    border-left: var(--figure-rule);
  }

  .figures__row .figure:nth-child(3n + 1) {
    border-left: 0;
  }
}

@media (max-width: 34rem) {
  .figures__row {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .figures__row .figure:nth-child(3n + 1) {
    border-left: var(--figure-rule);
  }

  .figures__row .figure:nth-child(odd) {
    border-left: 0;
  }
}

/* --- Scale -----------------------------------------------------------------
   Everything felt too big, specifically at the top end.

   The type scale and the section rhythm were both built for the drenched navy
   layout, where a section held one idea and could afford to shout. This page
   now runs ten sections, several of them side-by-side panels, and the same
   maximums make a 1900px screen feel like a poster.

   Only the CAPS come down. The minimums are untouched, so nothing changes on
   a phone: on a 375px screen every one of these clamps was already sitting at
   its floor.
   ------------------------------------------------------------------------ */

body.daybreak {
  --step-1: clamp(1.2rem, 1.14rem + 0.28vw, 1.4rem);
  --step-2: clamp(1.55rem, 1.42rem + 0.6vw, 2rem);
  --step-3: clamp(2rem, 1.75rem + 1.2vw, 2.9rem);
  --step-4: clamp(2.6rem, 2.1rem + 2.6vw, 4rem);
  --step-5: clamp(2.8rem, 1.9rem + 4.6vw, 5.2rem);

  /* Sections were up to 173px top and bottom. Against panels that are
     themselves only 230px tall, that is more air between blocks than inside
     them. */
  --section-tight: clamp(2.5rem, 2rem + 2vw, 3.5rem);
  --section-y: clamp(3.5rem, 2.8rem + 3.4vw, 5.5rem);
  --section-loose: clamp(4.5rem, 3.4rem + 5vw, 7.5rem);
}

/* --- Browser surfaces ------------------------------------------------------
   The parts nobody draws still ship with the browser's own design: the
   selection highlight, the caret, the scrollbars, the autofill panel. Left
   alone they belong to no design system (see the color-scheme note further
   up).
   ------------------------------------------------------------------------ */

/* The tone owns the scheme. daybreak is a light page with two navy sections,
   so light is correct for the chrome the browser paints. */
html:has(body.daybreak) {
  color-scheme: light;
}

/* Selection in the brand's gold, with ink on top: 11.79:1, and the one
   pairing the system already uses for a filled control. */
::selection {
  background: var(--sun);
  color: var(--ink);
}

/* No per-surface rule needed: keying off `.on-ground` is wrong, since in this
   tone that is the grey section, not a navy one. The single rule above holds
   everywhere, because gold reads at 10.46:1 on navy and the ink on top of it
   at 11.79:1. */

body.daybreak {
  /* The caret is a brand surface too. Logo blue on white, at 7.22:1. */
  caret-color: var(--brand-blue);
}

/* The privacy policy link, in the footer.

   The original site has it there, and without it no page linked the one
   document of the ten that is a privacy policy. On a health foundation with
   contact and donation forms, that is not cosmetic.

   The text is the literal footer text of the source ("ALS Hope Foundation
   Privacy Policy"), and the PDF stays hosted at alshf.org until it is
   uploaded to the new hosting, like the other nine. */
.footer__privacy {
  margin: 0 0 var(--space-s);
}

/* Top row of the footer: the newsletter on the left and, on the right, the
   recognitions block (three logos without links) with its title. The two
   labels share style and start at the same height. Below the footer
   breakpoint (63rem) the block moves under the newsletter. The two squares
   (Charity Navigator and Morris) share height; the Alliance one is landscape
   and is vertically centred, at a width that gives it comparable weight.
   Morris is opaque, with its own background, so it is not shown larger than
   this: the logo text loses sharpness. */
.footer__top {
  display: grid;
  gap: var(--space-l);
}

@media (min-width: 63.0625rem) {
  .footer__top {
    grid-template-columns: 1fr 1fr;
    gap: var(--space-xl) var(--space-l);
  }
}

.footer__recognition {
  padding-bottom: var(--space-xl);
}

.footer__logos {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  align-items: center;
  /* Always in one row: instead of wrapping, the three shrink together. The
     gap also shrinks, down to --space-s on mobile. */
  gap: clamp(var(--space-s), 3vw, var(--space-l));
}

/* The base is the maximum size and `flex-shrink` shares out the missing space
   in proportion to that base, so the three keep their 1:2:1 ratio. */
.footer__logos li {
  flex: 0 1 7.5rem;
  min-width: 0;
}

.footer__logos li:nth-child(2) {
  flex-basis: 15rem;
}

.footer__logos img {
  display: block;
  width: 100%;
  height: auto;
  object-fit: contain;
}

/* On hover the logo grows a little. It enters with --ease-out (it responds to
   a gesture) in 250ms; it leaves with the same curve, so releasing halfway
   returns it from where it was, without a jump. Only with a fine pointer and
   without reduced-motion: on touch there is no hover and the effect would
   stick. */
@media (hover: hover) and (pointer: fine) and (prefers-reduced-motion: no-preference) {
  .footer__logos img {
    transition: transform 250ms var(--ease-out);
  }

  .footer__logos li:hover img {
    transform: scale(1.08);
  }
}

.footer__privacy a {
  color: var(--on-ground-soft);
  font-size: var(--step--1);
  text-decoration-color: color-mix(in oklab, currentColor 45%, transparent);
  text-underline-offset: 0.2em;
}

@media (hover: hover) and (pointer: fine) {
  .footer__privacy a:hover {
    color: var(--on-ground);
    text-decoration-color: currentColor;
  }
}

/* The menu hover declared `color: var(--sun)` in `.masthead__nav a:hover`,
   but `body.daybreak .masthead a:not(.btn)` is more specific (`:not()` adds
   the specificity of its argument) and kept the base colour: the underline
   animated and the colour never changed. */
@media (hover: hover) and (pointer: fine) {
  body.daybreak .masthead__nav a:not(.btn):hover {
    color: var(--sun);
  }
}

/* Same specificity trap for the dropdowns: `body.daybreak .masthead
   a:not(.btn)` sets the colour and without this rule the submenu hover
   changed nothing. It carries a background, not only a colour, because in a
   list of seven destinations colour alone does not say which one is under the
   cursor. */
@media (hover: hover) and (pointer: fine) {
  body.daybreak .masthead .masthead__sub a:not(.btn):hover,
  .masthead .masthead__sub a:not(.btn):hover {
    color: var(--sun);
    background-color: oklch(0.975 0.01 262 / 0.07);
  }

  .masthead__disc:hover .masthead__chev {
    color: var(--sun);
  }
}

/* Same reason as the hover: `body.daybreak .masthead a:not(.btn)` sets the
   colour and beat the current destination inside a dropdown, which stayed
   white like the rest. In the panel the gold bar in the margin already marked
   it; on desktop nothing did. */
body.daybreak .masthead .masthead__sub a[aria-current='page'],
.masthead .masthead__sub a[aria-current='page'] {
  color: var(--sun);
}

/* --- 12. newsletter: subscriber sign-up ------------------------------------
   The original site has NO form: it collects subscribers with Mailchimp's
   "connected site" script, the popup configured in the Mailchimp dashboard.
   Repeating it was ruled out (third-party design, third-party JS, and a popup
   on a site for people with ALS and their families) in favour of an own block
   that posts to the SAME list.

   The list belongs to the foundation: the `u` comes from the links of its own
   campaign archives in the source (703e2261cc5f64a68d7d52c28, datacenter
   us9).

   It goes in the footer and not on the home because the popup had site-wide
   reach, and this is the honest way to keep that reach without a popup.
   ------------------------------------------------------------------------ */

/* `display: grid` beats the `display: none` that the `hidden` attribute
   brings, so without this line the hidden form kept 197px of empty space in
   the footer of all 25 pages. */
.news[hidden] { display: none; }

/* One column, left-aligned like the rest of the footer.

   Two columns (label on one side, field on the other) looked wrong once the
   copy was removed: the left side was left with the label floating alone
   against a huge gap. The block depended on text that does not exist yet.

   This way it holds with what exists today, and when the copy arrives it goes
   under the label without touching the structure. */
.news {
  display: grid;
  max-width: 30rem;
  padding-bottom: var(--space-xl);
}

.news__title,
.footer__label {
  /* The same label as Contact, Explore and Follow: it is a system label, not
     brand copy. */
  margin-top: 0;
  font-weight: 600;
  font-size: var(--step--1);
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--on-ground-dim);
  margin-bottom: var(--space-xs);
}

.news__lead {
  color: var(--on-ground);
  max-width: 34rem;
  /* Space between the text and the field. Without it the field label starts
     flush against the end of the paragraph and the two read as a single
     block. */
  margin: 0 0 var(--space-m);
}

.news__label {
  /* Visible, not a placeholder. A hidden label with the text only in the
     placeholder disappears as soon as the person starts typing, which is
     exactly when it is needed. */
  display: block;
  font-size: var(--step--1);
  color: var(--on-ground-dim);
  margin-bottom: var(--space-xs);
}

.news__row {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-xs);
}

.news__input {
  flex: 1 1 12rem;
  min-width: 0;
  min-height: 2.75rem;
  padding: 0 var(--space-s);
  font: inherit;
  color: var(--ink);
  background: #fff;
  border: 2px solid transparent;
  border-radius: var(--radius-control);
}

.news__input::placeholder { color: #6b7280; }

.news__input:focus-visible {
  outline: 3px solid var(--sun);
  outline-offset: 2px;
  border-color: var(--ink);
}

.news__input[aria-invalid='true'] { border-color: #b42318; }

.news__submit {
  flex: 0 0 auto;
  min-height: 2.75rem;
}

/* The Mailchimp honeypot. Off-screen, not `display: none`: some bots ignore
   what is hidden that way. */
.news__bot {
  position: absolute;
  left: -5000px;
}



/* The new-tab note. The form posts to Mailchimp with `target="_blank"`, and
   saying so beforehand is right: a tab that appears without warning
   disorients, even more with a screen reader. It is tied to the button by
   `aria-describedby`, so it is announced on arrival. */
.news__note {
  margin: var(--space-xs) 0 0;
  font-size: var(--step--1);
  color: var(--on-ground-dim);
}


/* --- Resource tiles with a logo (programs, partners) -----------------------
   Extends the `.resource` tile that /clinical-trials already uses (defined in
   standard.css): same panel, same whole-tile link, same host line. The only
   addition is an optional logo frame above the name, because a program or a
   partner is recognised by its mark before its name.

   The frame is a fixed height with the logo contained, so tiles with a logo
   of any proportion (a wide wordmark next to a tall emblem) keep one row
   height. The logos come with a white ground, so the frame is white too: they
   sit on the panel as the plates they were drawn as, not as cut-outs.
   ------------------------------------------------------------------------ */
.resource__media {
  height: 8rem;
  margin-bottom: var(--space-2xs);
  overflow: hidden;
  padding: var(--space-xs);
  background: #fff;
  border-radius: var(--radius-media);
}

.resource__media img {
  display: block;
  width: 100%;
  height: 100%;
  object-fit: contain;
}


/* ==========================================================================
   Presentation slideshow (VAAC photos)
   --------------------------------------------------------------------------
   A presentation, not a banner: it does not advance on its own and it holds
   one photo at a time, with the controls underneath so they never cover the
   picture. The hero's arrows (`.hero__nav`) float over a photograph and are
   tuned for that; here the same chevron and the same square control shape sit
   on a solid navy button instead.

   Without JavaScript the slides are all in the page, stacked, so nothing is
   hidden from anyone. `.is-ready` (set by main.js) turns them into a stage.
   ========================================================================== */
.slideshow {
  margin: var(--space-l) 0;
}

.slideshow__slides {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  gap: var(--space-s);
}

.slideshow__slide img {
  display: block;
  width: 100%;
  height: auto;
  border-radius: var(--radius-media);
  background: var(--paper-1);
}

.slideshow__bar {
  display: none;
}

.slideshow.is-ready .slideshow__slides {
  /* Every slide in the same cell: the stage takes the height of the tallest,
     so the controls below never jump when the photo changes. */
  gap: 0;
}

.slideshow.is-ready .slideshow__slide {
  grid-area: 1 / 1;
  opacity: 0;
  visibility: hidden;
  transition: opacity 0.35s var(--ease), visibility 0s linear 0.35s;
}

.slideshow.is-ready .slideshow__slide.is-current {
  opacity: 1;
  visibility: visible;
  transition: opacity 0.35s var(--ease), visibility 0s;
}

.slideshow.is-ready .slideshow__slide img {
  /* Photos arrive in slightly different proportions: contain keeps every one
     whole inside the stage instead of cropping it. */
  height: 100%;
  object-fit: contain;
}

.slideshow.is-ready .slideshow__bar {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-s);
  margin-top: var(--space-s);
}

.slideshow__nav {
  display: grid;
  place-items: center;
  width: 2.75rem;
  height: 2.75rem;
  border: none;
  border-radius: var(--radius-control);
  background: var(--ground);
  /* Literal light, not --on-ground: on a daybreak (light) page that token is
     remapped to the ink colour, which would draw a dark chevron on navy. */
  color: oklch(0.975 0.01 262);
  cursor: pointer;
  transition: background-color 0.2s var(--ease), color 0.2s var(--ease),
    transform 0.14s var(--ease-out);
  touch-action: manipulation;
  -webkit-tap-highlight-color: transparent;
}

.slideshow__nav svg {
  width: 1.15rem;
  height: 1.15rem;
}

/* One chevron drawn pointing left, mirrored for "next", as in the hero. */
.slideshow__nav--next svg {
  transform: scaleX(-1);
}

.slideshow__nav:active {
  transform: scale(0.97);
}

@media (hover: hover) and (pointer: fine) {
  .slideshow__nav:hover {
    background: var(--ground-raised);
    color: var(--sun);
  }
}

.slideshow__nav:focus-visible {
  outline: 3px solid var(--brand-blue);
  outline-offset: 3px;
}

.slideshow__count {
  margin: 0;
  min-width: 5.5rem;
  text-align: center;
  font-size: var(--step--1);
  font-variant-numeric: tabular-nums;
  color: var(--ink-soft);
}

@media (prefers-reduced-motion: reduce) {
  .slideshow.is-ready .slideshow__slide,
  .slideshow.is-ready .slideshow__slide.is-current,
  .slideshow__nav {
    transition: none;
  }
}
