@charset "utf-8";

/* N&D Brain — Unidad de Epilepsia
   The established system, on the web. Tokens, type roles and rules all come from
   DESIGN.md; nothing here invents a second identity. No third-party request is made
   from this file: the only fonts are the self-hosted Plex subsets beside it. */

/* ---------------------------------------------------------------- typeface */

@font-face {
  font-family: "IBM Plex Sans";
  src: url("../fonts/ibm-plex-sans-400.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "IBM Plex Sans";
  src: url("../fonts/ibm-plex-sans-500.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "IBM Plex Sans";
  src: url("../fonts/ibm-plex-sans-600.woff2") format("woff2");
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}

/* ---------------------------------------------------------------- tokens */

:root {
  --navy: #1b2b52;
  --navy-tint: #5d6881;
  --paper: #f8f5ee;
  --paper-line: #e8e3d6;
  --navy-line: #485373;
  --reverse-tint: #bbbfcb;
  --white: #fff;

  /* The card's 24-unit rhythm, in rem. */
  --u: 1.5rem;
  --gutter: clamp(1.25rem, 5vw, 3.5rem);
  --measure: 36rem;     /* ~68 characters at the body size */
  --page: 64rem;

  /* Type. Body never falls below 18px: this is read on a phone, often by someone
     who is frightened, sometimes by someone who has just had a seizure. */
  --t-body: clamp(1.125rem, 1.06rem + 0.3vw, 1.1875rem);
  --t-lead: clamp(1.25rem, 1.13rem + 0.55vw, 1.4375rem);
  --t-display: clamp(1.75rem, 1.1rem + 2.9vw, 3.125rem);
  --t-h2: clamp(1.4375rem, 1.19rem + 1.1vw, 2.125rem);
  --t-h3: clamp(1.1875rem, 1.12rem + 0.3vw, 1.3125rem);
  --t-small: clamp(1.0625rem, 1.02rem + 0.2vw, 1.125rem);
  --t-caps: 0.8125rem;
  /* v2: the hero's display line. Ceiling 4.75rem — 76px — the display step this
     system can carry without the wordmark above it losing the argument. Two caps sit
     under the clamp, and both only bite where they must:

       8.8vw   the longest word in the line, «Electroencefalografía», measures 9.81x
               the font size in Plex Sans 500. At 320px there are 280px of measure, so
               anything above ~28.5px puts that word through the edge of the screen.
               `hyphens: auto` on the h1 is the second net under this, for the day the
               line changes and this coefficient no longer describes it.
       10vh    the hero is one viewport tall and has to hold a wordmark, this line, a
               role line and a cue. On a 700px laptop screen the display size is what
               gives first. */
  --t-hero: min(clamp(2.25rem, 1.15rem + 4.7vw, 4.75rem), 8.8vw, 10vh);
  --t-rail: clamp(1.0625rem, 0.72rem + 0.95vw, 1.5rem);

  --nav-h: 3.25rem;
  --rail-w: 9rem;

  --lh-body: 1.65;
  --lh-display: 1.14;
}

@media (min-width: 56em) {
  :root { --nav-h: 3.75rem; }
}

/* ---------------------------------------------------------------- reset */

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

html {
  -webkit-text-size-adjust: 100%;
  scrollbar-color: var(--navy-tint) var(--paper);
}

body {
  margin: 0;
  background: var(--paper);
  color: var(--navy);
  font-family: "IBM Plex Sans", system-ui, sans-serif;
  font-size: var(--t-body);
  line-height: var(--lh-body);
  font-weight: 400;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}

h1, h2, h3 {
  font-weight: 500;
  letter-spacing: -0.01em;
  line-height: var(--lh-display);
  margin: 0;
  text-wrap: balance;
}

p, ul, ol, dl { margin: 0; }
img, svg { max-width: 100%; height: auto; }

/* Browser surfaces carry the design too. */
::selection { background: var(--navy); color: var(--paper); }
.band--navy ::selection { background: var(--paper); color: var(--navy); }

:focus-visible {
  outline: 2px solid currentColor;
  outline-offset: 3px;
  border-radius: 1px;
}

/* The action is a filled block, so its own currentColor is the colour of the field
   behind it: a currentColor ring on the CTA is drawn navy on navy, or paper on paper,
   and disappears. The ring takes the surrounding band's colour instead. */
.band--navy .cta:focus-visible,
.band--navy .skip:focus-visible { outline-color: var(--white); }
.band:not(.band--navy) .cta:focus-visible { outline-color: var(--navy); }
.skip:focus-visible { outline-color: var(--navy); }

/* ---------------------------------------------------------------- links */

a { color: inherit; text-decoration-thickness: 1px; text-underline-offset: 0.18em; }
a:hover { text-decoration-thickness: 2px; }

.band--navy a { text-decoration-color: var(--reverse-tint); }

/* ---------------------------------------------------------------- structure */

.skip {
  position: absolute;
  left: -9999px;
  top: 0;
  background: var(--paper);
  color: var(--navy);
  padding: 0.75rem 1.25rem;
  z-index: 10;
}
.skip:focus { left: 0; }

/* Readable by a screen reader, drawn for nobody. Not display:none, which removes it
   from the accessibility tree as well. */
.vh {
  position: absolute;
  width: 1px;
  height: 1px;
  margin: -1px;
  padding: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
}

.band { padding-inline: var(--gutter); }
.band--navy { background: var(--navy); color: var(--white); }
.band--navy h1, .band--navy h2, .band--navy h3 { color: var(--white); }

.wrap { max-width: var(--page); margin-inline: auto; }
.prose { max-width: var(--measure); }
.prose > * + * { margin-top: 1em; }

.section { padding-block: calc(var(--u) * 2.5); }
.section + .section { border-top: 1px solid var(--paper-line); }
.section > h2 { margin-bottom: calc(var(--u) * 1.1); }

@media (min-width: 56em) {
  .section { padding-block: calc(var(--u) * 3.25); }
}

/* ---------------------------------------------------------------- small caps
   The wordmark's own program-line setting, reused wherever the interface needs a
   label: weight 400 and +0.28em on paper, stepping up to 500 and +0.30em on navy,
   which is the light-on-dark compensation DESIGN.md applies everywhere else. */

.caps {
  font-size: var(--t-caps);
  font-weight: 400;
  letter-spacing: 0.28em;
  text-transform: uppercase;
  color: var(--navy-tint);
  margin: 0;
}
.band--navy .caps { font-weight: 500; letter-spacing: 0.3em; color: var(--reverse-tint); }

/* ---------------------------------------------------------------- the stage

   v2, 2026-10-20. The hero is a fixed layer and the page is lifted over it. The
   mechanism is one sticky element, not `background-attachment: fixed`, which is the
   version of this effect that fails on iOS. `.stage` pins at the top of the viewport
   and stays pinned for the whole document, because its containing block is the body;
   `main` and the footer carry an opaque ground and a higher stacking level, so they
   travel up over it. Nothing moves that the reader did not move themselves: there is
   no scroll handler, no transform, no timeline here — only two stacking levels and a
   sticky box, which is why it stays smooth on a phone.

   The one authored moment on this site. Reduced motion gets the static page instead:
   the hero scrolls away like any other block, and nothing else changes. */

.stage {
  position: sticky;
  top: 0;
  z-index: 0;
}

@media (prefers-reduced-motion: reduce) {
  .stage { position: static; }
}

.hero {
  position: relative;
  display: flex;
  flex-direction: column;
  justify-content: center;
  /* The hero and the nav bar together are exactly one viewport, which puts the bar on
     the hero's bottom edge at rest and the phone number inside the first screen. The
     bar is --nav-h of content between two hairlines, so the hairlines come out of the
     hero's height too: without them it overshot by 2px at every size and the bar sat
     just under the fold. */
  min-height: calc(100svh - var(--nav-h) - 2px);
  overflow: clip;
  /* vh-based, because this block has to fit a viewport it does not control. Fixed rem
     padding is what pushed the nav bar — and with it the phone number — below the fold
     on a 700px laptop screen. */
  padding-block: clamp(1.5rem, 4.5vh, 3.25rem) calc(clamp(1.75rem, 5vh, 3.75rem) + 3.5rem);
}

/* Variant A's figure. Offset right and bled off the edge so the measure stays clean;
   it sits under the text, never between the reader and it. */
.hero__fig {
  position: absolute;
  z-index: 0;
  top: 50%;
  right: -14vw;
  translate: 0 -50%;
  width: min(92vw, 34rem);
  height: auto;
  pointer-events: none;
}

.hero__inner,
.hero__down { position: relative; z-index: 1; }
/* A column flex item sizes to min-content by default, so the h1's longest word set the
   width of this box and carried it straight through the side of a 320px screen. */
.hero__inner { width: 100%; min-width: 0; }

.hero__mark {
  display: block;
  /* 2.5x v1, which set this at 9.5-13rem. The master bakes in its own clear space, so
     the margin below is the remainder of the gap, not the whole of it. */
  width: min(clamp(14rem, 42vw, 32.5rem), 58vh);
  height: auto;
  margin-bottom: clamp(0.9rem, 2.6vh, 1.65rem);
}

.hero h1 {
  font-size: var(--t-hero);
  line-height: 1.08;
  /* 19ch sets the line in three at the desktop size. At 15ch it broke into four, and
     the fourth line was what pushed the nav below the first viewport. */
  max-width: 19ch;
  text-wrap: balance;
  hyphens: auto;
}

.hero__role {
  margin-top: clamp(0.7rem, 2.2vh, 1.35rem);
  max-width: var(--measure);
  color: var(--reverse-tint);
  font-size: var(--t-lead);
}
/* The name steps up by weight, the system's own emphasis device, rather than by size
   or colour. `b` carries no extra announcement in a screen reader. */
.hero__role b {
  font-weight: 500;
  color: var(--white);
  /* the name is one unit: it never breaks across lines, the same rule the card's
     specifics line follows */
  white-space: nowrap;
}

/* The cue sits on the hero's bottom edge and on the page's own left margin, not the
   band's: absolute inside the hero, but still inside a .wrap so it lines up under the
   display line rather than floating out at the screen edge. */
.hero__foot {
  position: absolute;
  z-index: 1;
  left: 0;
  right: 0;
  bottom: clamp(0.75rem, 2.4vh, 1.5rem);
  padding-inline: var(--gutter);
}
.hero__down {
  display: inline-block;
  color: var(--reverse-tint);
  /* 44px of target around a 20px mark */
  padding: 0.65rem 1.1rem 0.65rem 0;
  line-height: 0;
}
.hero__down:hover { color: var(--white); }

@media (min-width: 56em) {
  .hero__fig {
    right: clamp(-6rem, -4vw, 0rem);
    width: min(62vw, 47rem);
  }
}

/* ---------------------------------------------------------------- the nav bar

   At rest it is the hero's bottom edge; from the first scroll it is the top of the
   page. One element doing both, so the phone number never leaves the screen. */

.nav {
  position: sticky;
  top: 0;
  z-index: 3;
  background: var(--navy);
  color: var(--white);
  border-top: 1px solid var(--navy-line);
  border-bottom: 1px solid var(--navy-line);
  padding-inline: var(--gutter);
}

/* Wider than the 64rem page. The bar is full-bleed navy anyway, and eight items plus
   the action do not fit in 64rem at a size this system is allowed to set them. */
.nav__inner {
  display: flex;
  align-items: stretch;
  gap: 1rem;
  min-height: var(--nav-h);
  max-width: 78rem;
}

.nav__list {
  display: flex;
  align-items: stretch;
  gap: clamp(0.7rem, 1.25vw, 1.45rem);
  margin: 0;
  padding: 0;
  list-style: none;
  flex: 1 1 auto;
  min-width: 0;
  /* Below the desktop breakpoint the row scrolls rather than collapsing into a
     disclosure: a <details> panel inside a sticky bar depends on how a browser renders
     its slot when closed, and this has to behave the same everywhere. The last item is
     cut by the edge, which is the affordance — no gradient, which this system bans. */
  overflow-x: auto;
  overscroll-behavior-x: contain;
  scrollbar-width: none;
}
.nav__list::-webkit-scrollbar { display: none; }

.nav__list a,
.nav__cta {
  display: flex;
  align-items: center;
  white-space: nowrap;
  font-size: var(--t-small);
  text-decoration: none;
}
.nav__list a {
  color: var(--reverse-tint);
  border-bottom: 2px solid transparent;
}
.nav__list a:hover { color: var(--white); border-bottom-color: var(--navy-line); }

.nav__cta {
  flex: 0 0 auto;
  /* the markup's space between the number and the note is a flex gap now: two flex
     items have no whitespace between them */
  gap: 0.3em;
  margin-left: auto;
  padding-inline: clamp(0.7rem, 1.6vw, 1.15rem);
  background: var(--paper);
  color: var(--navy);
  font-weight: 500;
}
.nav__cta:hover { background: var(--white); }
.nav .cta__note { font-weight: 400; }
.nav__cta:focus-visible { outline-color: var(--white); }
.nav__list a:focus-visible { outline-color: var(--white); outline-offset: -2px; }

/* The number is the action and stays at every width; the qualifier it carries is the
   first thing to go when the bar runs out of room on a 320px screen. */
@media (max-width: 25.99em) {
  .nav .cta__note { display: none; }
}

/* An anchor must not land under the docked bar. */
[id] { scroll-margin-top: calc(var(--nav-h) + 1.25rem); }

/* The page travels over the stage: opaque ground, higher level. */
main,
.footer { position: relative; z-index: 2; background: var(--paper); }
.footer { background: var(--navy); }


/* ---------------------------------------------------------------- the action */

.cta {
  display: inline-flex;
  align-items: baseline;
  /* The longer second channel does not fit one line on a 320px screen, and an
     inline-flex block will not shrink below its content: let the note wrap instead
     of pushing a pixel of horizontal scroll onto the whole page. */
  flex-wrap: wrap;
  max-width: 100%;
  gap: 0.15rem 0.6ch;
  min-height: 3.25rem;
  padding: 0.95rem 1.6rem;
  background: var(--paper);
  color: var(--navy);
  font-weight: 500;
  font-size: var(--t-lead);
  letter-spacing: 0.01em;
  text-decoration: none;
  border: 1px solid transparent;
  transition: background-color 120ms ease-out, color 120ms ease-out;
}
.cta:hover { background: var(--white); }
.cta__note { font-size: var(--t-small); font-weight: 400; color: var(--navy-tint); }

/* On paper the action inverts: navy field, paper text. */
.band:not(.band--navy) .cta { background: var(--navy); color: var(--paper); }
.band:not(.band--navy) .cta:hover { background: #16233f; }
.band:not(.band--navy) .cta__note { color: var(--reverse-tint); }

/* ---------------------------------------------------------------- divider
   The badge trace, the identity's one pictorial element, at a uniform scale and
   once on this page. Never redrawn, never replaced by a rule.

   It is deliberately not animated. A scroll-driven draw was built and removed: any
   reveal that starts from an undrawn state leaves the mark blank wherever the
   timeline never advances — printing, a full-page capture, a reader view — and the
   one pictorial element in this identity must be present in every rendering of the
   page. Restraint is also the right register for the audience. */

.trace {
  display: block;
  width: clamp(9rem, 24vw, 12.5rem);
  margin: 0 0 calc(var(--u) * 1.6);
  color: var(--navy);
  overflow: visible;
}

/* ---------------------------------------------------------------- services */

.services { margin-top: calc(var(--u) * 0.5); }

.service {
  padding-block: calc(var(--u) * 1.4);
  border-top: 1px solid var(--paper-line);
}
.service h3 { margin-bottom: 0.5em; }
.service p + p { margin-top: 0.8em; }
.service__includes {
  margin-top: 0.9em;
  color: var(--navy-tint);
  font-size: var(--t-small);
}

@media (min-width: 56em) {
  .service {
    display: grid;
    grid-template-columns: 15rem 1fr;
    column-gap: calc(var(--u) * 2);
    padding-block: calc(var(--u) * 1.8);
  }
  .service h3 { grid-column: 1; margin-bottom: 0; }
  .service__body { grid-column: 2; max-width: var(--measure); }
}

/* ---------------------------------------------------------------- checklist
   No glyph bullets. The marker is a hairline, drawn, in the system's own
   vocabulary — the same rule that divides everything else on the page. */

.checklist { list-style: none; padding: 0; }
.checklist li {
  display: grid;
  grid-template-columns: 1.5rem 1fr;
  column-gap: 1rem;
  padding-block: 0.8rem;
  border-top: 1px solid var(--paper-line);
}
.checklist li::before {
  content: "";
  display: block;
  height: 1px;
  background: var(--navy-tint);
  margin-top: 0.82em;
}

@media (min-width: 56em) {
  .checklist {
    columns: 2;
    column-gap: calc(var(--u) * 2.5);
  }
  .checklist li { break-inside: avoid; }
}

/* ---------------------------------------------------------------- process
   The steps are numbered because the sequence is the information: this is the order
   a visit actually happens in. The services list above is deliberately unnumbered —
   those are offerings, not a sequence. */

.steps { list-style: none; padding: 0; counter-reset: step; margin-top: calc(var(--u) * 1.2); }
.steps li {
  counter-increment: step;
  display: grid;
  grid-template-columns: 2.25rem 1fr;
  column-gap: 1rem;
  padding-block: calc(var(--u) * 0.9);
  border-top: 1px solid var(--paper-line);
  max-width: calc(var(--measure) + 3.25rem);
}
.steps li::before {
  content: counter(step);
  font-variant-numeric: lining-nums tabular-nums;
  color: var(--navy-tint);
  font-size: var(--t-small);
  line-height: inherit;
}
.steps b { font-weight: 500; }

/* ---------------------------------------------------------------- questions */

.faq { margin-top: calc(var(--u) * 0.4); }
.faq__item {
  padding-block: calc(var(--u) * 1.1);
  border-top: 1px solid var(--paper-line);
  max-width: var(--measure);
}
.faq__item h3 { margin-bottom: 0.55em; }
/* The sheet FAQ 2 promises, reachable before the reader calls rather than only after.
   No `download` attribute: the answer is meant to be read, and a phone browser shows
   a one-page PDF faster than it saves one. */
.faq__file { margin-top: 0.9em; }
.faq__file a { display: inline-flex; align-items: center; min-height: 2.75rem; }

/* ---------------------------------------------------------------- doctor, place */

/* The doctor block keeps the card's order — name, specialty, registration — and the
   unit's own paragraphs sit below it. */
.doctor { display: grid; gap: calc(var(--u) * 1.3); }
.doctor__body { max-width: var(--measure); }
.doctor__body > * + * { margin-top: 1em; }
.doctor__name { font-size: var(--t-h3); font-weight: 500; }
.doctor__role { color: var(--navy-tint); }
.doctor__role + .doctor__reg { margin-top: 0.3em; }
.doctor__reg + p { margin-top: calc(var(--u) * 1.1); }
.doctor__reg, .place__line--muted { color: var(--navy-tint); font-size: var(--t-small); }

/* The long biography folds away behind a native disclosure, so the section stays
   scannable without a line of JavaScript. The marker is drawn from borders, not a
   glyph lifted out of some other font. */
.trayectoria { margin-top: calc(var(--u) * 1.2); border-top: 1px solid var(--paper-line); }
.trayectoria > summary {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  min-height: 2.75rem;
  padding-block: 0.85rem;
  font-weight: 500;
  cursor: pointer;
  list-style: none;
}
.trayectoria > summary::-webkit-details-marker { display: none; }
.trayectoria > summary::after {
  content: "";
  flex: none;
  width: 0.5rem;
  height: 0.5rem;
  border-right: 1.5px solid var(--navy-tint);
  border-bottom: 1.5px solid var(--navy-tint);
  transform: translateY(-0.15em) rotate(45deg);
  transition: transform 150ms ease-out;
}
.trayectoria[open] > summary::after { transform: translateY(0.1em) rotate(-135deg); }
@media (prefers-reduced-motion: reduce) {
  .trayectoria > summary::after { transition: none; }
}
.trayectoria ul { list-style: none; padding: 0; margin: 0 0 calc(var(--u) * 0.9); }
.trayectoria li { padding-block: calc(var(--u) * 0.75); border-top: 1px solid var(--paper-line); }
.trayectoria li:first-child { border-top: 0; }
.trayectoria b { font-weight: 500; }

.doctor__links { display: flex; flex-wrap: wrap; gap: 0.4rem 1.75rem; margin-top: calc(var(--u) * 1.1); }
.doctor__links a { min-height: 2.75rem; display: inline-flex; align-items: center; font-size: var(--t-small); }

/* Where and how to get an appointment. */
.place__meta { margin-top: calc(var(--u) * 1.2); max-width: var(--measure); }
.place__meta dt { color: var(--navy-tint); font-size: var(--t-small); }
.place__meta dd { margin: 0.15em 0 0; }
.place__meta div + div { margin-top: calc(var(--u) * 0.8); }
.place__channels { display: flex; flex-wrap: wrap; gap: 0.9rem 1rem; margin-top: calc(var(--u) * 1.3); }

/* The second channel is a counterpart to the phone, not a rival: same block, outlined. */
.band:not(.band--navy) .cta--secondary {
  background: transparent;
  color: var(--navy);
  border-color: var(--navy);
}
.band:not(.band--navy) .cta--secondary:hover { background: var(--paper-line); }
.band:not(.band--navy) .cta--secondary .cta__note { color: var(--navy-tint); }

/* Portrait. The section becomes two columns only when a portrait is actually in it,
   so a page without one is not a page with a hole in it. The image carries no fixed
   aspect ratio and no object-fit: it ships at the photograph's own proportions, so
   nothing is cropped here that the photographer did not crop. */
.doctor__portrait { max-width: 15rem; }
.doctor__portrait img { display: block; width: 100%; height: auto; }
@media (min-width: 56em) {
  .doctor:has(.doctor__portrait) {
    grid-template-columns: 15rem 1fr;
    column-gap: calc(var(--u) * 2);
    align-items: start;
  }
}
.place__line { font-size: var(--t-lead); font-weight: 500; }
.place address { font-style: normal; }

/* ---------------------------------------------------------------- figures */

.figpair {
  --fig-ref: 440;
  display: grid;
  gap: calc(var(--u) * 1.2);
  margin-top: calc(var(--u) * 1.2);
  align-items: start;
}
@media (min-width: 40em) {
  .figpair { grid-template-columns: 1fr 1fr; gap: calc(var(--u) * 1.6); }
}

.figpair figure {
  margin: 0;
  display: grid;
  grid-template-rows: 1fr auto;   /* renders share a row, captions land on one line */
}
/* --fig-ref is the widest render in the set; --w is each render's own 1x width.
   The per-render widths below are written by build/prepare_assets.py from
   figures.json — they live in the stylesheet rather than in a style attribute so the
   Content-Security-Policy can refuse inline styles outright. Do not edit by hand. */

/* figure-widths:begin */
.figpair img.fig-19-lateral { --w: 344; }
.figpair img.fig-19-superior { --w: 397; }
.figpair img.fig-37-lateral { --w: 440; }
.figpair img.fig-37-superior { --w: 427; }
.figpair img.fig-47-lateral { --w: 440; }
.figpair img.fig-47-superior { --w: 427; }
/* figure-widths:end */
.figpair img {
  display: block;
  width: calc(var(--w) / var(--fig-ref) * 100%);
  max-width: 100%;
  height: auto;
  align-self: end;
}
.figpair figcaption {
  margin-top: 0.7rem;
  color: var(--navy-tint);
  font-size: var(--t-small);
  line-height: 1.45;
}

.montage { padding-block: calc(var(--u) * 2); border-top: 1px solid var(--paper-line); }
.montage h2 { font-size: var(--t-h2); }
.montage__composition { margin-top: 0.6em; color: var(--navy-tint); max-width: var(--measure); }
.montage__measure { margin-top: 0.8em; max-width: var(--measure); }
.montage__measure b { font-weight: 600; }

/* The figures' own category colours encode electrode groups. They are data, exempt
   from the palette, and are never restyled to match it. */
.legend { list-style: none; padding: 0; margin-top: calc(var(--u) * 1.1); display: flex; flex-wrap: wrap; gap: 0.6rem 1.75rem; }
.legend li { display: flex; align-items: center; gap: 0.6rem; font-size: var(--t-small); color: var(--navy-tint); }
.legend i { display: block; width: 0.9rem; height: 0.9rem; flex: none; }
/* The renders' own category colours, named once. Data, not palette. */
.legend i.is-standard { background: #6b7d9e; }
.legend i.is-ifcn     { background: #219942; }
.legend i.is-extra    { background: #ed780f; }

.notes { margin-top: calc(var(--u) * 0.9); color: var(--navy-tint); font-size: var(--t-small); line-height: 1.5; }
.notes p + p { margin-top: 0.35em; }

/* A column of measured values, so magnitudes compare by eye. Plex Sans's figures
   are lining and tabular by construction, so the column aligns without changing face. */
.coverage { width: 100%; border-collapse: collapse; margin-top: calc(var(--u) * 1.2); max-width: var(--measure); }
.coverage th, .coverage td { text-align: left; padding: 0.7rem 1rem 0.7rem 0; border-top: 1px solid var(--paper-line); }
.coverage thead th { border-top: 0; font-weight: 400; color: var(--navy-tint); font-size: var(--t-small); }
.coverage td { font-variant-numeric: tabular-nums lining-nums; }
.coverage td:first-child { font-weight: 500; }
.coverage .num { text-align: right; width: 7rem; }

/* ---------------------------------------------------------------- footer */

.footer { padding-block: calc(var(--u) * 2.5); border-top: 1px solid var(--navy-line); }
.footer__badge { display: block; width: 6.5rem; margin-bottom: calc(var(--u) * 1.3); }
.footer__grid { display: grid; gap: calc(var(--u) * 1.2); }
.footer nav ul { list-style: none; padding: 0; display: flex; flex-wrap: wrap; gap: 0.8rem 1.75rem; }
.footer a { min-height: 2.75rem; display: inline-flex; align-items: center; }
.footer__legal { color: var(--reverse-tint); font-size: var(--t-small); }
.footer__legal p + p { margin-top: 0.4em; }
/* Inline links in a sentence are exempt from WCAG 2.2 target size, but the phone
   number is a contact action: vertical padding enlarges the hit area on an inline
   box without disturbing the line it sits in. */
.footer__legal a { padding-block: 0.7rem; }

@media (min-width: 56em) {
  .footer__grid { grid-template-columns: 1fr auto; align-items: start; column-gap: calc(var(--u) * 2); }
}

/* ---------------------------------------------------------------- legal pages */

.doc { padding-block: calc(var(--u) * 2); }
.doc h2 { font-size: var(--t-h3); margin-top: calc(var(--u) * 1.6); margin-bottom: 0.5em; }
.doc .prose { max-width: var(--measure); }
.updated {
  margin-top: calc(var(--u) * 1.6);
  padding-top: calc(var(--u) * 0.8);
  border-top: 1px solid var(--paper-line);
  color: var(--navy-tint);
  font-size: var(--t-small);
  max-width: var(--measure);
}

/* Unused since the asesor's sign-off on 2026-10-19 removed both BORRADOR banners.
   Kept, not deleted: six lines of the two legal pages are still unreviewed (see
   LEGAL.md), so a banner may be asked for again. 190 bytes, ~60 gzipped. */
.draft {
  border: 1px solid var(--paper-line);
  border-left: 1px solid var(--paper-line);
  padding: 1rem 1.25rem;
  margin-bottom: calc(var(--u) * 1.4);
  color: var(--navy-tint);
  font-size: var(--t-small);
  max-width: var(--measure);
}

/* ---------------------------------------------------------------- page head
   Every page but the first opens with the wordmark as the way back to it. */

.pagehead {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.6rem 2rem;
  margin: 0;
  padding-block: calc(var(--u) * 1.1);
  border-bottom: 1px solid var(--paper-line);
}
.pagehead a { display: inline-block; }
.pagehead img { display: block; width: clamp(8.5rem, 26vw, 11rem); }

.page-title { font-size: var(--t-display); }
.standfirst { margin-top: var(--u); }
.hero-figure { margin-top: calc(var(--u) * 1.4); }
.hero-figure img { display: block; width: min(100%, 22rem); }
.after-table { margin-top: calc(var(--u) * 1.4); }
.doc h1 { font-size: var(--t-h2); }

/* ---------------------------------------------------------------- utilities */

.lead { font-size: var(--t-lead); }
.muted { color: var(--navy-tint); }
.vh {
  position: absolute;
  width: 1px; height: 1px;
  margin: -1px; padding: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
}

/* ---------------------------------------------------------------- the reading rail

   One word per section, down the page's right edge, from 64em up. It is a second,
   quieter table of contents: it says where the reader is without asking them to look
   away from what they are reading. Below 64em it does not exist and the nav bar
   carries the job — a rail on a phone would be furniture, not orientation.

   Three states, and the words are English by the AD's decision (recorded in DESIGN.md
   under Website):

     not yet reached   not rendered at all, so a keyboard cannot land on an invisible
                       link and no contrast rule applies to something nobody can see
     reached           navy-tint, 5.1:1 on paper
     current           navy, 12.6:1, the system's own weight step with it

   Driven three ways, in order of preference: a CSS scroll timeline where the browser
   has one, a 1.3 KB IntersectionObserver where it does not, and — with neither — every
   word visible from the start. The degraded state is the honest one: a rail that shows
   all seven words is still a working table of contents. A script that fails never
   leaves the page with its navigation hidden. */

.rail { display: none; }

@media (min-width: 64em) {
  .rail {
    display: block;
    position: fixed;
    /* above main, which carries the opaque ground the page scrolls up on; equal
       levels would let main paint over the rail, since it comes later in the DOM */
    z-index: 4;
    top: calc(var(--nav-h) + var(--u) * 2);
    /* the page is 64rem and centred: the rail's right edge is the page's right edge */
    right: max(1.25rem, (100% - var(--page)) / 2);
    width: var(--rail-w);
    text-align: right;
  }
  /* The text gives up the width the rail takes, so the two never overlap. Scoped to
     the sibling that actually has a rail: /montajes carries none and keeps its full
     measure. */
  .rail ~ main .wrap { padding-right: calc(var(--rail-w) + 1.5rem); }

  .rail__list {
    margin: 0;
    padding: 0;
    list-style: none;
    display: grid;
    gap: calc(var(--u) * 0.45);
  }
  .rail__link {
    display: block;
    font-size: var(--t-rail);
    font-weight: 500;
    letter-spacing: 0.06em;
    line-height: 1.1;
    color: var(--navy-tint);
    text-decoration: none;
    /* the mark is small; the target is not */
    padding-block: 0.3rem;
  }
  .rail__link:hover { color: var(--navy); }
  .rail__link:focus-visible { outline-color: var(--navy); }
}

/* --- driven by the browser's own scroll timeline, where there is one --------- */

@supports (animation-timeline: view()) {
  @media (min-width: 64em) {
    body {
      timeline-scope: --sec-2, --sec-3, --sec-4, --sec-5, --sec-6, --sec-7, --sec-end;
    }
    .section[data-sec="2"] { view-timeline-name: --sec-2; }
    .section[data-sec="3"] { view-timeline-name: --sec-3; }
    .section[data-sec="4"] { view-timeline-name: --sec-4; }
    .section[data-sec="5"] { view-timeline-name: --sec-5; }
    .section[data-sec="6"] { view-timeline-name: --sec-6; }
    .section[data-sec="7"] { view-timeline-name: --sec-7; }
    [data-sec="end"] { view-timeline-name: --sec-end; }

    /* The rail retires when the closing argument arrives. Two reasons, and the second
       is the one that matters: the reading it tracks is over, and its navy words would
       otherwise be invisible on a navy field and sit on top of it. */
    .rail {
      animation: rail-retire linear both;
      animation-timeline: --sec-end;
      animation-range: entry 0% entry 35%;
    }

    .rail__link {
      animation: rail-arrive linear both;
      animation-range: entry 0% entry 45%;
    }
    .rail--2 { animation-timeline: --sec-2; }
    .rail--3 { animation-timeline: --sec-3; }
    .rail--4 { animation-timeline: --sec-4; }
    .rail--5 { animation-timeline: --sec-5; }
    .rail--6 { animation-timeline: --sec-6; }
    .rail--7 { animation-timeline: --sec-7; }

    .rail__ink {
      animation: rail-current linear both;
      animation-range: entry 70% exit 30%;
    }
    .ink--2 { animation-timeline: --sec-2; }
    .ink--3 { animation-timeline: --sec-3; }
    .ink--4 { animation-timeline: --sec-4; }
    .ink--5 { animation-timeline: --sec-5; }
    .ink--6 { animation-timeline: --sec-6; }
    .ink--7 { animation-timeline: --sec-7; }
  }
}

/* --- the script's path, only taken when the timeline is missing -------------- */

@media (min-width: 64em) {
  .rail--js .rail__link { visibility: hidden; opacity: 0; }
  .rail--js .rail__link.is-seen {
    visibility: visible;
    opacity: 1;
    transition: opacity 320ms cubic-bezier(0.16, 1, 0.3, 1);
  }
  .rail--js .rail__ink.is-current { color: var(--navy); }
  .rail--js.rail--done { opacity: 0; visibility: hidden; transition: opacity 240ms linear; }
}

@keyframes rail-arrive {
  0%   { visibility: hidden; opacity: 0; }
  1%   { visibility: visible; opacity: 0; }
  100% { visibility: visible; opacity: 1; }
}
@keyframes rail-retire {
  0%   { opacity: 1; visibility: visible; }
  99%  { opacity: 0; visibility: visible; }
  100% { opacity: 0; visibility: hidden; }
}
@keyframes rail-current {
  0%, 100% { color: var(--navy-tint); }
  18%, 82% { color: var(--navy); }
}

/* Reduced motion keeps every state and drops the fade: the rail still says where the
   reader is, it just stops easing. State is information here, not decoration. */
@media (prefers-reduced-motion: reduce) {
  .rail--js .rail__link.is-seen { transition: none; }
  @supports (animation-timeline: view()) {
    .rail__link { animation-range: entry 0% entry 1%; }
  }
}
