/* ==========================================================================
   Tropical Wave Weather - base and components
   Depends on tokens.css. No hardcoded colours below this line.
   ========================================================================== */

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

html {
    font-size: calc(100% * var(--text-scale));
    scroll-behavior: smooth;
    -webkit-text-size-adjust: 100%;
}

body {
    margin: 0;
    background: var(--surface);
    color: var(--text);
    font-family: var(--font-body);
    font-size: var(--step-0);
    line-height: var(--leading-normal);
    -webkit-font-smoothing: antialiased;
    /* Clears the floating mobile bar so the last element is never trapped
       under it. Zero once the bar is hidden at tablet width and up. */
    padding-bottom: calc(64px + env(safe-area-inset-bottom, 0px));
}

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

h1, h2, h3, h4 {
    font-family: var(--font-display);
    font-weight: 800;
    line-height: var(--leading-tight);
    letter-spacing: var(--tracking-tight);
    /* Headings never break mid-word or hyphenate. Long storm names wrap at
       word boundaries or shrink, they do not split. */
    overflow-wrap: break-word;
    hyphens: none;
    margin: 0 0 var(--space-4);
    text-wrap: balance;
}

h1 { font-size: var(--step-5); }
h2 { font-size: var(--step-3); }
h3 { font-size: var(--step-1); }

p { margin: 0 0 var(--space-4); text-wrap: pretty; }

/* Forecast numbers get the numeric face and tabular figures so a column of
   wind speeds stays aligned as values change. */
.num, .stat__value, .storm-card__wind {
    font-family: var(--font-numeric);
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    font-feature-settings: "tnum" 1;
}

a { color: var(--text-link); text-decoration-thickness: 1px; text-underline-offset: 0.18em; }
a:hover { color: var(--text-link-hover); }

:root[data-underline="all"] a { text-decoration: underline !important; }

/* Visible focus everywhere. Never removed, only restyled. */
:focus-visible {
    outline: 3px solid var(--accent);
    outline-offset: 2px;
    border-radius: var(--radius-sm);
}

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

.skip-link {
    position: absolute;
    left: var(--space-4);
    top: -100px;
    z-index: 200;
    padding: var(--space-3) var(--space-5);
    background: var(--accent-strong);
    color: var(--text-inverse);
    border-radius: var(--radius);
    font-weight: 600;
    transition: top var(--duration-fast) var(--ease);
}
.skip-link:focus { top: var(--space-4); color: var(--text-inverse); }

.main:focus { outline: none; }

/* --------------------------------------------------------------------------
   Layout
   -------------------------------------------------------------------------- */

.section {
    max-width: var(--content-max);
    margin-inline: auto;
    padding: var(--space-8) var(--gutter);
}

.section__head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: var(--space-4);
    margin-bottom: var(--space-5);
}

.section__title { margin: 0; }
.section__link { font-weight: 600; font-size: var(--step--1); }

/* --------------------------------------------------------------------------
   Buttons. 12px radius per the brand guidelines.
   -------------------------------------------------------------------------- */

.btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-2);
    /* 44px minimum target on every button, including the icon-only ones. */
    min-height: 44px;
    min-width: 44px;
    padding: var(--space-3) var(--space-5);
    border: 1px solid transparent;
    border-radius: var(--radius);
    font-family: var(--font-body);
    font-size: var(--step-0);
    font-weight: 600;
    line-height: 1;
    text-decoration: none;
    cursor: pointer;
    transition: background var(--duration-fast) var(--ease),
                border-color var(--duration-fast) var(--ease),
                transform var(--duration-fast) var(--ease);
}
.btn:active { transform: translateY(1px); }

.btn--primary {
    background: var(--deep-ocean-blue);
    color: var(--white);
}
.btn--primary:hover { background: var(--deep-ocean-blue-90); color: var(--white); }

.btn--secondary {
    background: var(--surface);
    color: var(--text-link);
    border-color: var(--tropical-blue);
}
.btn--secondary:hover { background: var(--tropical-blue-10); }

.btn--warning { background: var(--sunrise-orange); color: var(--white); }

.btn--ghost {
    background: transparent;
    color: var(--text);
    border-color: var(--border);
}
.btn--ghost:hover { background: var(--surface-sunken); }

.btn--lg { padding: var(--space-4) var(--space-6); font-size: var(--step-1); min-height: 52px; }
.btn--sm { padding: var(--space-2) var(--space-4); font-size: var(--step--1); min-height: 40px; }

/* --------------------------------------------------------------------------
   Header and mega menu
   -------------------------------------------------------------------------- */

.site-header {
    position: sticky;
    top: 0;
    z-index: var(--z-header);
    height: var(--header-height);
    background: var(--surface);
    border-bottom: 1px solid var(--border);
    transition: box-shadow var(--duration) var(--ease);
}
.site-header[data-scrolled="true"] { box-shadow: var(--shadow-sm); }

.site-header__inner {
    max-width: var(--content-max);
    height: 100%;
    margin-inline: auto;
    padding-inline: var(--gutter);
    display: flex;
    align-items: center;
    gap: var(--space-5);
}

.site-header__brand { display: flex; align-items: center; flex: 0 0 auto; }
.site-header__logo { width: 260px; height: auto; }

.site-header__actions {
    margin-left: auto;
    display: flex;
    align-items: center;
    gap: var(--space-3);
}

.site-header__search { padding: var(--space-2); }

.mega { display: none; }
.mega__list { display: flex; gap: var(--space-2); list-style: none; margin: 0; padding: 0; }
.mega__item { position: static; }

.mega__trigger {
    display: inline-flex;
    align-items: center;
    gap: var(--space-2);
    min-height: 44px;
    padding: var(--space-2) var(--space-3);
    background: none;
    border: 0;
    border-radius: var(--radius-sm);
    color: var(--text);
    font: inherit;
    font-weight: 600;
    cursor: pointer;
}
.mega__trigger:hover { background: var(--surface-sunken); }
.mega__chevron { transition: transform var(--duration-fast) var(--ease); }
.mega__trigger[aria-expanded="true"] .mega__chevron { transform: rotate(180deg); }

.mega__panel {
    position: absolute;
    left: 0;
    right: 0;
    top: var(--header-height);
    z-index: var(--z-mega);
    background: var(--surface-raised);
    border-block: 1px solid var(--border);
    box-shadow: var(--shadow);
}
.mega__panel[hidden] { display: none; }

.mega__panel-inner {
    max-width: var(--content-max);
    margin-inline: auto;
    padding: var(--space-6) var(--gutter);
    display: grid;
    grid-template-columns: 1fr;
    gap: var(--space-6);
}

.mega__columns {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
    gap: var(--space-6);
}

.mega__heading {
    margin: 0 0 var(--space-3);
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: var(--tracking-wide);
    text-transform: uppercase;
    color: var(--text-muted);
}

.mega__links { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-1); }
.mega__links a {
    display: block;
    padding: var(--space-2) 0;
    color: var(--text);
    text-decoration: none;
    font-weight: 500;
}
.mega__links a:hover { color: var(--text-link-hover); }

.mega__feature {
    display: grid;
    align-content: start;
    gap: var(--space-2);
    padding: var(--space-5);
    background: var(--gradient-brand);
    border-radius: var(--radius-lg);
    color: var(--white);
    text-decoration: none;
}
.mega__feature-eyebrow {
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: var(--tracking-wide);
    text-transform: uppercase;
    opacity: 0.85;
}
.mega__feature-title { font-family: var(--font-display); font-size: var(--step-1); font-weight: 700; }
.mega__feature-body { font-size: var(--step--1); opacity: 0.9; }

/* Language switcher */
.lang { position: relative; display: none; align-items: center; }
.lang__icon { position: absolute; left: var(--space-3); color: var(--text-muted); pointer-events: none; }
.lang__select {
    appearance: none;
    min-height: 44px;
    padding: var(--space-2) var(--space-4) var(--space-2) calc(var(--space-3) + 22px);
    background: transparent;
    border: 1px solid var(--border);
    border-radius: var(--radius);
    color: var(--text);
    font: inherit;
    font-size: var(--step--1);
    font-weight: 600;
    cursor: pointer;
}

/* Hide the Google Translate chrome. The site's own control drives it. */
.goog-te-banner-frame, .skiptranslate iframe { display: none !important; }
body { top: 0 !important; }

/* Burger and drawer */
.site-header__burger {
    display: grid;
    gap: 5px;
    width: 44px;
    height: 44px;
    place-content: center;
    padding: 0;
    background: none;
    border: 0;
    cursor: pointer;
}
.site-header__burger span {
    display: block;
    width: 22px;
    height: 2px;
    background: var(--text);
    border-radius: 2px;
    transition: transform var(--duration-fast) var(--ease), opacity var(--duration-fast) var(--ease);
}
.site-header__burger[aria-expanded="true"] span:nth-child(1) { transform: translateY(7px) rotate(45deg); }
.site-header__burger[aria-expanded="true"] span:nth-child(2) { opacity: 0; }
.site-header__burger[aria-expanded="true"] span:nth-child(3) { transform: translateY(-7px) rotate(-45deg); }

.drawer {
    position: fixed;
    inset: var(--header-height) 0 0;
    z-index: var(--z-mega);
    padding: var(--space-5) var(--gutter) calc(96px + env(safe-area-inset-bottom, 0px));
    background: var(--surface);
    overflow-y: auto;
    overscroll-behavior: contain;
}
.drawer[hidden] { display: none; }
.drawer__group { border-bottom: 1px solid var(--border); }
.drawer__group summary {
    display: flex;
    align-items: center;
    min-height: 52px;
    font-family: var(--font-display);
    font-size: var(--step-1);
    font-weight: 700;
    cursor: pointer;
}
.drawer__group ul { list-style: none; margin: 0 0 var(--space-4); padding: 0; display: grid; gap: var(--space-1); }
.drawer__group a { display: block; padding: var(--space-3) 0; text-decoration: none; color: var(--text); }

/* --------------------------------------------------------------------------
   Hero
   -------------------------------------------------------------------------- */

.hero {
    position: relative;
    isolation: isolate;
    /* Poster sits on the hero itself, not only on the video element, so it is
     * still the backdrop when the video is hidden or never plays. The gradient
     * stays beneath it as the final fallback. */
    background-image: url('../video/hero-home-poster.jpg'), var(--gradient-brand);
    background-size: cover, auto;
    background-position: center, center;
    color: var(--white);
}

/* Background loop.
 *
 * The brand gradient stays underneath rather than being replaced, so the hero
 * looks deliberate for the entire time the video is loading, and permanently
 * on any browser that refuses to play it.
 *
 * The scrim is not decoration. The footage is a bright radar screen and the
 * headline sits directly over it, so without a wash the white type drops below
 * readable contrast wherever the storm's green and orange land. It is angled
 * to stay heaviest on the left, where the text is.
 */
.hero__media {
    position: absolute;
    inset: 0;
    z-index: -2;
    width: 100%;
    height: 100%;
    object-fit: cover;
}
.hero__scrim {
    position: absolute;
    inset: 0;
    z-index: -1;
    background:
        linear-gradient(90deg, rgba(7, 27, 61, 0.92) 0%, rgba(7, 27, 61, 0.78) 45%, rgba(7, 27, 61, 0.45) 100%),
        linear-gradient(180deg, rgba(7, 27, 61, 0.35) 0%, rgba(7, 27, 61, 0.6) 100%);
}

/* Readers who have asked their OS for less motion get the still poster that is
 * already on .hero. This hides the player rather than preventing the fetch, so
 * it is an accessibility fix and not a bandwidth one.
 */
@media (prefers-reduced-motion: reduce) {
    .hero__media { display: none; }
}

.hero__inner {
    position: relative;
    max-width: var(--content-max);
    margin-inline: auto;
    padding: var(--space-9) var(--gutter);
}
.hero__eyebrow {
    margin: 0 0 var(--space-3);
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: var(--tracking-wide);
    text-transform: uppercase;
    opacity: 0.85;
}
.hero__title { max-width: 20ch; margin-bottom: var(--space-5); }
.hero__lede { max-width: 60ch; font-size: var(--step-1); opacity: 0.94; }
.hero__actions { display: flex; flex-wrap: wrap; gap: var(--space-3); margin-top: var(--space-6); }
.hero .btn--secondary { background: transparent; border-color: rgba(255,255,255,0.6); color: var(--white); }
.hero .btn--secondary:hover { background: rgba(255,255,255,0.12); }
.hero__promise {
    margin: var(--space-7) 0 0;
    font-style: italic;
    font-size: var(--step--1);
    opacity: 0.8;
}

/* --------------------------------------------------------------------------
   Cards and panels
   -------------------------------------------------------------------------- */

.card-grid, .storm-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
    gap: var(--space-4);
}

.card {
    display: block;
    padding: var(--space-5);
    background: var(--surface-raised);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    box-shadow: var(--shadow-sm);
    color: inherit;
    text-decoration: none;
    transition: transform var(--duration) var(--ease), box-shadow var(--duration) var(--ease);
}
.card:hover { transform: translateY(-3px); box-shadow: var(--shadow); color: inherit; }
.card__title { font-size: var(--step-1); margin-bottom: var(--space-2); }
.card__body { margin: 0; color: var(--text-muted); font-size: var(--step--1); }

.panel {
    padding: var(--space-5);
    background: var(--surface-sunken);
    border: 1px dashed var(--border-strong);
    border-radius: var(--radius);
}
.panel__title { margin: 0 0 var(--space-2); font-weight: 700; }
.panel__body { margin: 0; color: var(--text-muted); font-size: var(--step--1); }

/* Category chips. Colour plus the category text, never colour alone. */
.cat { display: inline-flex; align-items: center; gap: var(--space-2); padding: var(--space-1) var(--space-3); border-radius: var(--radius-pill); font-size: var(--step--1); font-weight: 700; color: var(--midnight-navy); }
.cat--td { background: var(--cat-td); }
.cat--ts { background: var(--cat-ts); }
.cat--cat-1 { background: var(--cat-1); }
.cat--cat-2 { background: var(--cat-2); }
.cat--cat-3 { background: var(--cat-3); }
.cat--cat-4 { background: var(--cat-4); color: var(--white); }
.cat--cat-5 { background: var(--cat-5); color: var(--white); }

/* --------------------------------------------------------------------------
   Error page
   -------------------------------------------------------------------------- */

.error-page {
    max-width: var(--content-narrow);
    margin-inline: auto;
    padding: var(--space-9) var(--gutter);
    text-align: center;
}
.error-page__code {
    font-family: var(--font-numeric);
    font-size: var(--step-5);
    font-weight: 800;
    color: var(--border-strong);
    margin: 0;
}
.error-page__body { color: var(--text-muted); }
.error-page__actions { display: flex; flex-wrap: wrap; gap: var(--space-3); justify-content: center; margin-top: var(--space-6); }

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

.site-footer {
    background: var(--surface-inverse);
    color: var(--text-inverse);
    margin-top: var(--space-9);
}
.site-footer__inner {
    max-width: var(--content-max);
    margin-inline: auto;
    padding: var(--space-8) var(--gutter);
    display: grid;
    gap: var(--space-7);
}
.site-footer__logo { width: 220px; filter: brightness(0) invert(1); }
.site-footer__promise { margin-top: var(--space-4); font-style: italic; opacity: 0.75; max-width: 34ch; }
.site-footer__columns {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
    gap: var(--space-6);
}
.site-footer__heading {
    margin: 0 0 var(--space-3);
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: var(--tracking-wide);
    text-transform: uppercase;
    opacity: 0.7;
}
.site-footer__columns ul { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-2); }
.site-footer__columns a { color: var(--text-inverse); opacity: 0.85; text-decoration: none; font-size: var(--step--1); }
.site-footer__columns a:hover { opacity: 1; color: var(--hurricane-cyan); }

.site-footer__legal {
    border-top: 1px solid rgba(255,255,255,0.15);
    padding: var(--space-5) var(--gutter) var(--space-7);
    max-width: var(--content-max);
    margin-inline: auto;
}
.site-footer__attribution { font-size: var(--step--1); opacity: 0.7; max-width: 90ch; }
.site-footer__copyright { font-size: var(--step--1); opacity: 0.6; margin: 0; }

/* --------------------------------------------------------------------------
   Floating mobile action bar
   -------------------------------------------------------------------------- */

.mobile-bar {
    position: fixed;
    left: 0; right: 0; bottom: 0;
    z-index: var(--z-mobile-bar);
    display: grid;
    grid-auto-flow: column;
    grid-auto-columns: 1fr;
    background: var(--surface-raised);
    border-top: 1px solid var(--border);
    padding-bottom: env(safe-area-inset-bottom, 0px);
    box-shadow: 0 -2px 16px rgba(7, 27, 61, 0.10);
}
.mobile-bar__item {
    display: grid;
    justify-items: center;
    align-content: center;
    gap: 3px;
    min-height: 56px;
    padding: var(--space-2);
    color: var(--text-muted);
    text-decoration: none;
}
.mobile-bar__item:hover, .mobile-bar__item[aria-current="page"] { color: var(--accent); }
.mobile-bar__label { font-size: 0.72rem; font-weight: 600; }

/* --------------------------------------------------------------------------
   Accessibility panel
   -------------------------------------------------------------------------- */

.a11y__launcher {
    position: fixed;
    right: var(--space-4);
    bottom: calc(72px + env(safe-area-inset-bottom, 0px));
    z-index: var(--z-a11y);
    display: grid;
    place-content: center;
    width: 48px; height: 48px;
    background: var(--deep-ocean-blue);
    color: var(--white);
    border: 2px solid var(--white);
    border-radius: 50%;
    box-shadow: var(--shadow);
    cursor: pointer;
}

.a11y__panel {
    position: fixed;
    right: var(--space-4);
    bottom: calc(130px + env(safe-area-inset-bottom, 0px));
    z-index: var(--z-a11y);
    width: min(340px, calc(100vw - 2 * var(--space-4)));
    max-height: min(70vh, 620px);
    overflow-y: auto;
    padding: var(--space-5);
    background: var(--surface-raised);
    border: 1px solid var(--border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow-lg);
}
.a11y__panel[hidden] { display: none; }
.a11y__header { display: flex; align-items: center; justify-content: space-between; margin-bottom: var(--space-4); }
.a11y__title { font-size: var(--step-1); margin: 0; }
.a11y__close { width: 36px; height: 36px; background: none; border: 0; font-size: 1.5rem; line-height: 1; color: var(--text-muted); cursor: pointer; }
.a11y__group { border: 0; padding: 0; margin: 0 0 var(--space-5); }
.a11y__group legend { padding: 0; margin-bottom: var(--space-2); font-size: var(--step--1); font-weight: 700; letter-spacing: var(--tracking-wide); text-transform: uppercase; color: var(--text-muted); }
.a11y__row { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.a11y__chip {
    min-height: 40px;
    padding: var(--space-2) var(--space-4);
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius-pill);
    color: var(--text);
    font: inherit;
    font-size: var(--step--1);
    font-weight: 600;
    cursor: pointer;
}
.a11y__chip[aria-pressed="true"] { background: var(--deep-ocean-blue); border-color: var(--deep-ocean-blue); color: var(--white); }
.a11y__switch { display: flex; align-items: center; gap: var(--space-3); min-height: 44px; cursor: pointer; }
.a11y__switch input { width: 20px; height: 20px; accent-color: var(--tropical-blue); }
.a11y__note { margin: var(--space-2) 0 0; font-size: var(--step--1); color: var(--text-muted); }
.a11y__footer { display: flex; align-items: center; justify-content: space-between; gap: var(--space-3); padding-top: var(--space-4); border-top: 1px solid var(--border); }
.a11y__link { font-size: var(--step--1); font-weight: 600; }

/* --------------------------------------------------------------------------
   Breakpoints. Mobile is the base; these are the additions for wider screens.
   -------------------------------------------------------------------------- */

@media (min-width: 48rem) {
    body { padding-bottom: 0; }
    .mobile-bar { display: none; }
    .lang { display: flex; }
    .a11y__launcher { bottom: var(--space-5); }
    .a11y__panel { bottom: calc(var(--space-5) + 60px); }
    .site-footer__inner { grid-template-columns: minmax(220px, 1fr) 2.4fr; }
}

@media (min-width: 64rem) {
    .mega { display: block; }
    .site-header__burger { display: none; }
    .drawer { display: none !important; }
    .mega__panel-inner { grid-template-columns: 2.6fr 1fr; }
}

/* --------------------------------------------------------------------------
   Reduced motion. Honours the OS setting and the in-panel toggle.
   -------------------------------------------------------------------------- */

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

:root[data-motion="reduced"] * {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
}

/* --------------------------------------------------------------------------
   Print. People print evacuation checklists.
   -------------------------------------------------------------------------- */

@media print {
    .site-header, .mobile-bar, .a11y, .site-footer__columns { display: none !important; }
    body { padding: 0; color: #000; background: #fff; }
    a[href^="/"]::after { content: " (tropicalwaveweather.com" attr(href) ")"; font-size: 0.8em; }
}

/* ==========================================================================
   Page components
   ========================================================================== */

.section--tight { padding-block: var(--space-7) var(--space-5); }
.section--sunken { background: var(--surface-sunken); max-width: none; }
.section--sunken > * { max-width: var(--content-max); margin-inline: auto; }
.section__source, .section__note { font-size: var(--step--1); color: var(--text-muted); }
.section__note { max-width: 80ch; margin-bottom: var(--space-4); }

.breadcrumbs {
    max-width: var(--content-max);
    margin-inline: auto;
    padding: var(--space-4) var(--gutter) 0;
    font-size: var(--step--1);
}
.breadcrumbs ol { display: flex; flex-wrap: wrap; gap: var(--space-2); list-style: none; margin: 0; padding: 0; color: var(--text-muted); }
.breadcrumbs li + li::before { content: "/"; margin-right: var(--space-2); opacity: .5; }
.breadcrumbs a { color: var(--text-muted); text-decoration: none; }
.breadcrumbs a:hover { color: var(--text-link); }
.breadcrumbs [aria-current] { color: var(--text); font-weight: 600; }

.page-head { max-width: 78ch; }
.page-head__eyebrow {
    margin: 0 0 var(--space-3);
    font-size: var(--step--1);
    font-weight: 700;
    letter-spacing: var(--tracking-wide);
    text-transform: uppercase;
    color: var(--text-muted);
}
.page-head__title { font-size: var(--step-4); margin-bottom: var(--space-4); }
.page-head__lede { font-size: var(--step-1); color: var(--text-muted); margin: 0; }

.prose { max-width: var(--content-narrow); }
.prose h2 { font-size: var(--step-2); margin-top: var(--space-6); }
.prose h3 { font-size: var(--step-1); margin-top: var(--space-5); }
.prose p { color: var(--text-muted); }
.prose > :first-child { margin-top: 0; }

/* Quiet state. Most of the year nothing is active, so this is a designed
   state rather than an empty container. */
.quiet-state {
    display: flex;
    gap: var(--space-5);
    align-items: flex-start;
    padding: var(--space-6);
    background: var(--surface-sunken);
    border: 1px solid var(--border);
    border-radius: var(--radius-lg);
}
.quiet-state__mark { color: var(--accent); flex: 0 0 auto; }
.quiet-state__title { font-size: var(--step-1); margin-bottom: var(--space-2); }
.quiet-state__body { color: var(--text-muted); max-width: 60ch; margin-bottom: var(--space-2); }
.quiet-state__meta { font-size: var(--step--1); color: var(--text-muted); margin: 0; }

/* Storm cards */
.storm-grid--detail { grid-template-columns: repeat(auto-fit, minmax(320px, 1fr)); }
.storm-card {
    display: block;
    padding: var(--space-5);
    background: var(--surface-raised);
    border: 1px solid var(--border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow-sm);
    color: inherit;
    text-decoration: none;
    transition: transform var(--duration) var(--ease), box-shadow var(--duration) var(--ease);
}
a.storm-card:hover { transform: translateY(-3px); box-shadow: var(--shadow); }
.storm-card__head { display: flex; align-items: center; justify-content: space-between; gap: var(--space-3); margin-bottom: var(--space-4); }
.storm-card__basin { font-size: var(--step--1); color: var(--text-muted); font-weight: 600; }
.storm-card__name { font-size: var(--step-2); margin-bottom: var(--space-4); }
.storm-card__name a { color: inherit; text-decoration: none; }
.storm-card__stats { display: grid; grid-template-columns: repeat(2, 1fr); gap: var(--space-4); margin: 0 0 var(--space-4); }
.storm-card__stats dt { font-size: var(--step--1); color: var(--text-muted); margin-bottom: 2px; }
.storm-card__stats dd { margin: 0; font-size: var(--step-1); font-weight: 600; }
.storm-card__stats dd span { font-size: var(--step--1); color: var(--text-muted); font-weight: 500; }
.storm-card__wind { font-size: var(--step-2) !important; }
.storm-card__actions { display: flex; flex-wrap: wrap; gap: var(--space-2); }
.storm-card__updated { margin: var(--space-4) 0 0; font-size: var(--step--1); color: var(--text-muted); }

/* Fact strip */
.fact-strip {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(160px, 1fr));
    gap: var(--space-4);
    margin: var(--space-6) 0 0;
    padding: var(--space-5);
    background: var(--surface-sunken);
    border-radius: var(--radius-lg);
}
.fact-strip dt { font-size: var(--step--1); color: var(--text-muted); margin-bottom: var(--space-1); }
.fact-strip dd { margin: 0; font-size: var(--step-1); font-weight: 600; }
.fact-strip dd span { font-size: var(--step--1); color: var(--text-muted); font-weight: 500; }

/* Alerts */
.alert-group { margin-bottom: var(--space-7); }
.alert-group__title { display: flex; align-items: center; gap: var(--space-3); font-size: var(--step-1); }
.alert-group__dot { width: 12px; height: 12px; border-radius: 50%; }
.alert-group__dot--extreme { background: var(--cat-5); }
.alert-group__dot--severe { background: var(--cat-3); }
.alert-group__dot--moderate { background: var(--sunrise-orange); }
.alert-group__dot--minor { background: var(--cat-1); }
.alert-group__dot--unknown { background: var(--storm-gray-30); }

.alert-list { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-3); }
.alert-row {
    display: flex;
    flex-wrap: wrap;
    gap: var(--space-4);
    align-items: flex-start;
    padding: var(--space-4) var(--space-5);
    background: var(--surface-raised);
    border: 1px solid var(--border);
    border-left: 4px solid var(--border-strong);
    border-radius: var(--radius);
}
.alert-row--extreme { border-left-color: var(--cat-5); }
.alert-row--severe { border-left-color: var(--cat-3); }
.alert-row--moderate { border-left-color: var(--sunrise-orange); }
.alert-row--minor { border-left-color: var(--cat-1); }
.alert-row__severity { font-size: var(--step--1); font-weight: 700; text-transform: uppercase; letter-spacing: var(--tracking-wide); color: var(--text-muted); }
.alert-row__body { flex: 1 1 300px; }
.alert-row__event { font-weight: 700; margin: 0 0 var(--space-1); }
.alert-row__headline { margin: 0 0 var(--space-1); font-size: var(--step--1); }
.alert-row__area { margin: 0; font-size: var(--step--1); color: var(--text-muted); }
.alert-row__meta, .alert-row__expires { font-size: var(--step--1); color: var(--text-muted); text-align: right; }
.alert-row__urgency { display: block; font-weight: 600; }
.alert-row__storm { margin-left: var(--space-2); font-size: var(--step--1); }

.badge { display: inline-flex; align-items: center; padding: 2px var(--space-2); border-radius: var(--radius-pill); font-size: var(--step--1); font-weight: 700; }
.badge--count { background: var(--accent-strong); color: var(--white); }
.badge--hit { background: var(--sunrise-orange-10); color: var(--sunrise-orange); margin-left: var(--space-2); }

.tag { display: inline-block; padding: 1px var(--space-2); border-radius: var(--radius-sm); font-size: 0.72rem; font-weight: 700; text-transform: uppercase; letter-spacing: .04em; }
.tag--tide { background: var(--tropical-blue-10); color: var(--tropical-blue); }
.tag--nws { background: var(--hurricane-cyan-10); color: var(--deep-ocean-blue); }
.tag--draft { background: var(--storm-gray-15); color: var(--storm-gray); }
.tag--archive { background: var(--storm-gray-15); color: var(--storm-gray); }

.notice { padding: var(--space-4) var(--space-5); border-radius: var(--radius); font-size: var(--step--1); margin: 0 0 var(--space-5); }
.notice--info { background: var(--tropical-blue-10); color: var(--deep-ocean-blue); }
.notice--warning { background: var(--sunrise-orange-10); color: #8a4508; }

/* Tables */
.table-scroll { overflow-x: auto; -webkit-overflow-scrolling: touch; }
.data-table { width: 100%; border-collapse: collapse; font-size: var(--step-0); }
.data-table th, .data-table td { padding: var(--space-3) var(--space-4); text-align: left; border-bottom: 1px solid var(--border); }
.data-table thead th { font-size: var(--step--1); text-transform: uppercase; letter-spacing: var(--tracking-wide); color: var(--text-muted); font-weight: 700; }
.data-table tbody tr:hover { background: var(--surface-sunken); }
.data-table__day { white-space: nowrap; }
.data-table__weekday { display: block; font-weight: 700; }
.data-table__date { display: block; font-size: var(--step--1); color: var(--text-muted); font-weight: 500; }

/* Tides */
.tide-next {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(160px, 1fr));
    gap: var(--space-5);
    margin-top: var(--space-6);
    padding: var(--space-5);
    background: var(--gradient-brand);
    border-radius: var(--radius-lg);
    color: var(--white);
}
.tide-next__label { margin: 0 0 var(--space-1); font-size: var(--step--1); text-transform: uppercase; letter-spacing: var(--tracking-wide); opacity: .8; }
.tide-next__time, .tide-next__value { margin: 0; font-size: var(--step-3); font-weight: 700; line-height: 1.05; }
.tide-next__value span, .tide-next__time span { font-size: var(--step-0); opacity: .8; margin-left: 2px; }
.tide-next__date { margin: var(--space-1) 0 0; font-size: var(--step--1); opacity: .85; }
.tide-next__residual--high .tide-next__value { color: #ffd8a8; }

.tide-row { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: var(--space-4); }
.tide-row__item { display: flex; align-items: baseline; gap: var(--space-2); padding: var(--space-1) var(--space-3); border-radius: var(--radius-sm); background: var(--surface-sunken); }
.tide-row__item--high { border-left: 3px solid var(--tropical-blue); }
.tide-row__item--low { border-left: 3px solid var(--storm-gray-30); }
.tide-row__type { font-size: var(--step--1); font-weight: 700; color: var(--text-muted); }
.tide-row__height { font-size: var(--step--1); color: var(--text-muted); }

.tide-strip { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: var(--space-3); }
.tide-strip__item { display: grid; gap: 2px; padding: var(--space-4); background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius); }
.tide-strip__item--high { border-top: 3px solid var(--tropical-blue); }
.tide-strip__item--low { border-top: 3px solid var(--storm-gray-30); }
.tide-strip__type { font-size: var(--step--1); font-weight: 700; text-transform: uppercase; color: var(--text-muted); }
.tide-strip__time { font-size: var(--step-1); font-weight: 700; }
.tide-strip__day, .tide-strip__height { font-size: var(--step--1); color: var(--text-muted); }

.station-group { margin-bottom: var(--space-6); }
.station-group__title { font-size: var(--step-1); padding-bottom: var(--space-2); border-bottom: 1px solid var(--border); }
.station-list, .location-list { list-style: none; margin: 0; padding: 0; display: grid; grid-template-columns: repeat(auto-fill, minmax(260px, 1fr)); gap: var(--space-2); }
.station-list__item, .location-list__item {
    display: flex; align-items: center; justify-content: space-between; gap: var(--space-3);
    padding: var(--space-3) var(--space-4);
    border: 1px solid var(--border); border-radius: var(--radius);
    background: var(--surface-raised); color: inherit; text-decoration: none;
}
.station-list__item:hover, .location-list__item:hover { border-color: var(--accent); color: inherit; }
.station-list__name, .location-list__name { font-weight: 600; }
.station-list__meta { font-size: var(--step--1); color: var(--text-muted); }
.location-list__meta { display: flex; gap: var(--space-1); }

/* Column count comes from the template via --area-cols, because auto-fill
 * derives its columns from the available width and knows nothing about how
 * many cards there are. Sixteen states across five columns stranded Virginia
 * on a row by itself; the helper picks four so the rows come out square.
 * The narrower breakpoints use fixed divisors that keep rows full at counts
 * the desktop value would leave ragged. */
.area-grid {
    list-style: none;
    margin: 0;
    padding: 0;
    display: grid;
    grid-template-columns: repeat(var(--area-cols, 4), minmax(0, 1fr));
    gap: var(--space-3);
}
@media (max-width: 62rem) {
    .area-grid { grid-template-columns: repeat(3, minmax(0, 1fr)); }
    /* Fifteen cards divide by three, sixteen do not. A last card that would sit
     * alone takes the whole row instead, so the block still ends on a straight
     * edge rather than a gap. */
    .area-grid > li:last-child:nth-child(3n + 1) { grid-column: 1 / -1; }
}
@media (max-width: 40rem) {
    .area-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .area-grid > li:last-child:nth-child(odd) { grid-column: 1 / -1; }
}
.area-card { display: grid; gap: var(--space-1); padding: var(--space-4); background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius); text-decoration: none; color: inherit; }
.area-card:hover { border-color: var(--accent); color: inherit; }
.area-card__code { font-family: var(--font-numeric); font-weight: 700; font-size: var(--step-1); color: var(--accent-strong); }
.area-card__name { font-weight: 600; }
.area-card__count { font-size: var(--step--1); color: var(--text-muted); }

.chip-list { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: var(--space-2); }
.chip { display: inline-flex; align-items: center; gap: var(--space-2); padding: var(--space-2) var(--space-4); background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius-pill); font-size: var(--step--1); font-weight: 600; text-decoration: none; color: inherit; }
.chip:hover { border-color: var(--accent); color: inherit; }
.chip__meta { color: var(--text-muted); font-weight: 500; }

/* Forecast
 *
 * The controller hands over exactly eight NWS periods: four days as day/night
 * pairs. They are a sequence, so they belong on one line. auto-fit fitted
 * seven and dropped the eighth onto a row of its own, where "Sunday Night"
 * stopped reading as the end of the run and started reading as a separate
 * card that had lost its neighbours.
 *
 * Eight explicit tracks with a floor instead. Above roughly 1050px they share
 * the width; below it the row overflows and scrolls sideways, which keeps the
 * sequence intact on a phone rather than reflowing it into an arbitrary grid.
 */
.forecast-grid {
    display: grid;
    grid-template-columns: repeat(8, minmax(120px, 1fr));
    gap: var(--space-3);
    overflow-x: auto;
    overscroll-behavior-x: contain;
    scroll-snap-type: x proximity;
    padding-bottom: var(--space-2);
}
.forecast-card { padding: var(--space-4); background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius); scroll-snap-align: start; }
.forecast-card__name { margin: 0 0 var(--space-2); font-size: var(--step--1); font-weight: 700; color: var(--text-muted); }
.forecast-card__temp { margin: 0 0 var(--space-2); font-size: var(--step-3); font-weight: 700; line-height: 1; }
.forecast-card__temp span { font-size: var(--step-0); color: var(--text-muted); }
.forecast-card__summary { margin: 0; font-size: var(--step--1); }
.forecast-card__precip { margin: var(--space-2) 0 0; font-size: var(--step--1); color: var(--tropical-blue); font-weight: 600; }

/* Spaghetti plot */
.plot-header { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-4); margin-bottom: var(--space-5); }
.plot-header__title { margin: 0; font-size: var(--step-2); }
.plot-header__meta { margin: var(--space-1) 0 0; font-size: var(--step--1); color: var(--text-muted); }

.spread { padding: var(--space-3) var(--space-5); border-radius: var(--radius); text-align: right; }
.spread--tight { background: rgba(53, 214, 194, .15); }
.spread--moderate { background: var(--sunrise-orange-10); }
.spread--wide { background: rgba(242, 68, 92, .12); }
.spread__label { margin: 0; font-size: var(--step--1); font-weight: 700; text-transform: uppercase; letter-spacing: var(--tracking-wide); color: var(--text-muted); }
.spread__value { margin: 0; font-size: var(--step-3); font-weight: 700; line-height: 1.05; }
.spread__value span { font-size: var(--step-0); color: var(--text-muted); margin-left: 2px; }
.spread__note { margin: 0; font-size: var(--step--1); color: var(--text-muted); }

.plot { margin: 0; }
.plot__svg { width: 100%; height: auto; border: 1px solid var(--border); border-radius: var(--radius-lg); display: block; }
.plot__bg { fill: var(--surface-sunken); }
.plot__grid line { stroke: var(--border); stroke-width: 1; }
.plot__grid text { fill: var(--text-muted); font-size: 11px; font-family: var(--font-numeric); }
.plot__track { stroke-width: 1.75; stroke-linecap: round; stroke-linejoin: round; opacity: .85; }
.plot__track--ensemble { stroke-width: 1; opacity: .38; }
.plot__track--official { stroke-width: 4; opacity: 1; }
.plot__origin-halo { fill: var(--hurricane-cyan); opacity: .35; }
.plot__origin-dot { fill: var(--deep-ocean-blue); }
.plot__caption { margin-top: var(--space-3); font-size: var(--step--1); color: var(--text-muted); max-width: 80ch; }

.legend { list-style: none; margin: var(--space-4) 0 0; padding: 0; display: flex; flex-wrap: wrap; gap: var(--space-2) var(--space-4); }
.legend__item { display: inline-flex; align-items: center; gap: var(--space-2); font-size: var(--step--1); }
.legend__swatch { width: 18px; height: 3px; border-radius: 2px; }
.legend__code { color: var(--text-muted); font-family: var(--font-numeric); }

.storm-switch { display: flex; flex-wrap: wrap; gap: var(--space-2); margin-bottom: var(--space-5); }
.storm-switch__item { padding: var(--space-2) var(--space-4); border: 1px solid var(--border); border-radius: var(--radius-pill); text-decoration: none; color: inherit; font-weight: 600; font-size: var(--step--1); }
.storm-switch__item.is-active { background: var(--deep-ocean-blue); border-color: var(--deep-ocean-blue); color: var(--white); }

.hero--active { background: linear-gradient(135deg, var(--midnight-navy) 0%, var(--deep-ocean-blue) 60%, var(--tropical-blue) 100%); }

/* --------------------------------------------------------------------------
   Header fixes found while reviewing the rendered page
   -------------------------------------------------------------------------- */

/* Nav labels and buttons must never wrap. A wrapped label breaks the fixed
   72px header height and pushes the bar over the hero. */
.mega__trigger, .btn, .site-header__cta { white-space: nowrap; }

.site-header__logo { width: clamp(180px, 16vw, 240px); }
.site-header__inner { gap: var(--space-4); }
.mega__list { gap: 2px; }
.mega__trigger { padding-inline: var(--space-2); }

/* The logo artwork is dark navy, which disappears against the dark theme
   header. Until a light logo asset exists, render it as a white silhouette in
   dark mode. That loses the orange arc, so exporting a proper light variant is
   the real fix, noted in docs. */
:root[data-theme="dark"] .site-header__logo { filter: brightness(0) invert(1); }

@media (prefers-color-scheme: dark) {
    :root[data-theme="auto"] .site-header__logo { filter: brightness(0) invert(1); }
}

/* At the narrower end of desktop the six top level items plus the actions do
   not fit. Drop the language selector first, since it is the least used. */
@media (min-width: 64rem) and (max-width: 78rem) {
    .lang { display: none; }
    .site-header__cta { display: none; }
}

/* --------------------------------------------------------------------------
   Mobile overflow fix
   --------------------------------------------------------------------------
   Measured at 375px: the header row was 472px wide, so the whole page slid
   sideways. Cause was the logo at its 180px floor plus the Storm Alerts CTA,
   the search button, the language select, and the burger all competing for
   343px of content width.

   Fixed by removing what is duplicated elsewhere on mobile rather than by
   setting overflow-x: hidden on the body. That property hides the symptom,
   leaves the layout genuinely too wide, and breaks position: sticky in some
   browsers, so it is the wrong tool here.
   -------------------------------------------------------------------------- */

@media (max-width: 47.99rem) {
    /* Alerts already has a permanent slot in the floating mobile bar, so the
       header CTA is redundant and is the widest thing competing for space. */
    .site-header__cta { display: none; }

    .site-header__logo { width: clamp(140px, 42vw, 200px); }
    .site-header__inner { gap: var(--space-3); }
    .site-header__actions { gap: var(--space-1); }
}

/* --------------------------------------------------------------------------
   Archive blocks on the area hubs: fact strip lede, recent storms, and the
   hardest-hit ranking bars.
   -------------------------------------------------------------------------- */

.section__head--stacked { display: block; }
.section__head--stacked .section__title { margin-bottom: var(--space-2); }
.section__lede { margin: 0; max-width: 65ch; color: var(--text-muted); font-size: var(--step-0); }

.strike-rank { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-4); }
.strike-rank li { display: grid; gap: var(--space-1); }
.strike-rank__name { font-weight: 700; }
.strike-rank__bar {
    display: block;
    height: 10px;
    border-radius: 999px;
    background: var(--surface-sunken);
    overflow: hidden;
}
.strike-rank__fill {
    display: block;
    height: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--tropical-blue), var(--alert-red, #c0392b));
}
.strike-rank__stats { font-size: var(--step--1); color: var(--text-muted); }

@media (min-width: 720px) {
    .strike-rank li {
        grid-template-columns: 220px 1fr;
        align-items: center;
        column-gap: var(--space-4);
    }
    .strike-rank__stats { grid-column: 2; }
}

/* Belt and braces against a future regression: no descendant may force the
   page wider than the viewport. Scoped to the layout containers rather than
   applied globally so it cannot clip a deliberately scrollable table. */
.site-header__inner,
.hero__inner,
.section,
.site-footer__inner {
    max-width: min(var(--content-max), 100%);
}

/* ==========================================================================
   Model viewer
   ========================================================================== */

.viewer-bar {
    display: flex; flex-wrap: wrap; gap: var(--space-5);
    align-items: flex-end; margin-bottom: var(--space-4);
}
.viewer-bar__group { display: grid; gap: var(--space-2); }
.viewer-bar__label {
    font-size: var(--step--1); font-weight: 700; text-transform: uppercase;
    letter-spacing: var(--tracking-wide); color: var(--text-muted);
}
.viewer-tabs { display: flex; flex-wrap: wrap; gap: var(--space-1); }
.viewer-tabs__item {
    padding: var(--space-2) var(--space-4); border: 1px solid var(--border);
    border-radius: var(--radius-sm); text-decoration: none; color: inherit;
    font-weight: 600; font-size: var(--step--1); background: var(--surface-raised);
    white-space: nowrap;
}
.viewer-tabs__item.is-active { background: var(--deep-ocean-blue); border-color: var(--deep-ocean-blue); color: var(--white); }
.viewer-select {
    min-height: 44px; padding: var(--space-2) var(--space-4);
    border: 1px solid var(--border); border-radius: var(--radius-sm);
    background: var(--surface-raised); color: var(--text); font: inherit; font-weight: 600;
}

/* Timeline */
.timeline {
    display: grid; gap: var(--space-4); align-items: center;
    grid-template-columns: auto 1fr auto auto;
    padding: var(--space-4);
    background: var(--surface-sunken);
    border: 1px solid var(--border);
    border-radius: var(--radius-lg) var(--radius-lg) 0 0;
    border-bottom: 0;
}
.timeline__controls { display: flex; gap: var(--space-2); }
.timeline__btn {
    display: inline-flex; align-items: center; gap: var(--space-2);
    min-height: 44px; min-width: 44px; justify-content: center;
    padding: var(--space-2) var(--space-3);
    background: var(--surface-raised); color: var(--text);
    border: 1px solid var(--border); border-radius: var(--radius-sm);
    font: inherit; font-weight: 600; font-size: var(--step--1); cursor: pointer;
}
.timeline__btn:hover { border-color: var(--accent); }
.timeline__btn--play { padding-inline: var(--space-4); }
.timeline__btn--play[aria-pressed="true"] { background: var(--deep-ocean-blue); color: var(--white); border-color: var(--deep-ocean-blue); }

.timeline__slider { min-width: 0; }
.timeline__slider input[type="range"] {
    width: 100%; height: 44px; accent-color: var(--tropical-blue); cursor: pointer;
}
.timeline__readout { text-align: right; min-width: 96px; }
.timeline__tau { margin: 0; font-size: var(--step-2); font-weight: 700; line-height: 1; }
.timeline__valid { margin: 2px 0 0; font-size: var(--step--1); color: var(--text-muted); white-space: nowrap; }
.timeline__spread { text-align: right; min-width: 110px; padding-left: var(--space-4); border-left: 1px solid var(--border); }
.timeline__spread-label { margin: 0; font-size: var(--step--1); text-transform: uppercase; letter-spacing: var(--tracking-wide); color: var(--text-muted); }
.timeline__spread-value { margin: 0; font-size: var(--step-2); font-weight: 700; line-height: 1; }
.timeline__spread-value span:last-child { font-size: var(--step--1); color: var(--text-muted); margin-left: 2px; }
.timeline__spread-count { margin: 0; font-size: var(--step--1); color: var(--text-muted); white-space: nowrap; }

/* Hour grid */
.hour-grid {
    display: flex; flex-wrap: wrap; gap: 3px;
    padding: var(--space-3) var(--space-4);
    background: var(--surface-sunken);
    border-inline: 1px solid var(--border);
}
.hour-grid__item {
    min-width: 46px; min-height: 32px; padding: 2px var(--space-2);
    background: var(--surface-raised); border: 1px solid var(--border);
    border-radius: var(--radius-sm); color: var(--text-muted);
    font-family: var(--font-numeric); font-size: 0.76rem; font-weight: 700; cursor: pointer;
}
.hour-grid__item:hover { border-color: var(--accent); color: var(--text); }
.hour-grid__item[aria-pressed="true"] { background: var(--deep-ocean-blue); border-color: var(--deep-ocean-blue); color: var(--white); }

/* Plot stage */
.plot-stage { position: relative; }
.plot-stage .plot__svg { border-radius: 0 0 var(--radius-lg) var(--radius-lg); border-top: 0; }
.plot-canvas {
    display: block; width: 100%; aspect-ratio: 16 / 10;
    border: 1px solid var(--border); border-top: 0;
    border-radius: 0 0 var(--radius-lg) var(--radius-lg);
    background: var(--surface-sunken);
}

/* Model toggles */
.model-groups {
    display: grid; grid-template-columns: repeat(auto-fit, minmax(230px, 1fr));
    gap: var(--space-4); margin-top: var(--space-5);
}
.model-group { border: 1px solid var(--border); border-radius: var(--radius); padding: var(--space-4); background: var(--surface-raised); }
.model-group__head { display: flex; align-items: center; justify-content: space-between; gap: var(--space-2); margin-bottom: var(--space-3); }
.model-group__title { margin: 0; font-size: var(--step-0); }
.model-group__toggle {
    padding: 2px var(--space-2); border: 1px solid var(--border); border-radius: var(--radius-pill);
    background: transparent; color: var(--text-muted); font: inherit; font-size: 0.72rem; font-weight: 700; cursor: pointer;
}
.model-group__toggle[aria-pressed="true"] { background: var(--tropical-blue-10); color: var(--tropical-blue); border-color: var(--tropical-blue); }
.model-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 2px; max-height: 220px; overflow-y: auto; }
.model-list__item label { display: flex; align-items: center; gap: var(--space-2); padding: var(--space-1) 0; cursor: pointer; font-size: var(--step--1); }
.model-list__item input { width: 16px; height: 16px; accent-color: var(--tropical-blue); flex: 0 0 auto; }
.model-list__swatch { width: 16px; height: 3px; border-radius: 2px; flex: 0 0 auto; }
.model-list__name { flex: 1 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.model-list__code { color: var(--text-muted); font-family: var(--font-numeric); font-size: 0.7rem; }

/* Externally added archive components */
.section__head--stacked { display: block; }
.section__lede { margin: var(--space-2) 0 0; color: var(--text-muted); max-width: 70ch; font-size: var(--step--1); }
.strike-rank { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-3); }
.strike-rank li { display: grid; grid-template-columns: minmax(120px, 1fr) 2fr; gap: var(--space-2) var(--space-4); align-items: center; }
.strike-rank__name { font-weight: 600; text-decoration: none; color: inherit; }
.strike-rank__name:hover { color: var(--text-link); }
.strike-rank__bar { display: block; height: 10px; background: var(--storm-gray-15); border-radius: var(--radius-pill); overflow: hidden; }
.strike-rank__fill { display: block; height: 100%; background: var(--gradient-brand); }
.strike-rank__stats { grid-column: 1 / -1; font-size: var(--step--1); color: var(--text-muted); }

@media (max-width: 47.99rem) {
    .timeline { grid-template-columns: 1fr auto; }
    .timeline__controls { grid-column: 1 / -1; justify-content: center; }
    .timeline__slider { grid-column: 1 / -1; }
    .timeline__spread { border-left: 0; padding-left: 0; text-align: left; }
    .timeline__readout { text-align: left; }
    .strike-rank li { grid-template-columns: 1fr; }
}

/* ==========================================================================
   Radar and satellite
   ========================================================================== */

.radar-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(280px, 1fr)); gap: var(--space-4); }
.radar-figure { margin: 0; background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius-lg); overflow: hidden; }
.radar-figure img { width: 100%; height: auto; display: block; background: var(--surface-sunken); }
.radar-figure figcaption { padding: var(--space-3) var(--space-4); font-size: var(--step--1); color: var(--text-muted); }
.radar-figure--feature { max-width: 780px; margin-inline: auto; }

.radar-sites { display: grid; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); gap: var(--space-5); }
.radar-sites__area { font-size: var(--step-0); margin-bottom: var(--space-2); padding-bottom: var(--space-2); border-bottom: 1px solid var(--border); }
.radar-sites__list { list-style: none; margin: 0; padding: 0; display: grid; gap: 2px; }
.radar-sites__link { display: flex; align-items: center; justify-content: space-between; gap: var(--space-2); padding: var(--space-2) var(--space-3); border-radius: var(--radius-sm); text-decoration: none; color: inherit; font-size: var(--step--1); min-height: 40px; }
.radar-sites__link:hover { background: var(--surface-raised); color: inherit; }
.radar-sites__link.is-active { background: var(--deep-ocean-blue); color: var(--white); }
.radar-sites__name { font-weight: 600; }
.radar-sites__code { font-family: var(--font-numeric); color: var(--text-muted); font-size: 0.72rem; }
.radar-sites__link.is-active .radar-sites__code { color: rgba(255,255,255,.7); }

.radar-thumbs { display: grid; grid-template-columns: repeat(auto-fill, minmax(180px, 1fr)); gap: var(--space-3); }
.radar-thumb { display: block; border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; text-decoration: none; color: inherit; background: var(--surface-raised); }
.radar-thumb:hover { border-color: var(--accent); color: inherit; }
.radar-thumb img { width: 100%; height: auto; display: block; background: var(--surface-sunken); }
.radar-thumb__label { display: block; padding: var(--space-2) var(--space-3); font-size: var(--step--1); font-weight: 600; }
.radar-thumb__label span { display: block; color: var(--text-muted); font-family: var(--font-numeric); font-size: 0.7rem; font-weight: 500; }

.viewer-tabs--wide { margin-bottom: var(--space-5); }

/* ==========================================================================
   Page hero with imagery
   --------------------------------------------------------------------------
   Backgrounds are GOES-19 stills committed as static assets. A scrim sits
   between image and text because legibility is not negotiable on a page
   someone reads during a storm: the gradient guarantees contrast regardless
   of how bright that day's cloud cover happens to be.
   ========================================================================== */

.page-hero {
    position: relative;
    isolation: isolate;
    background: var(--midnight-navy);
    color: var(--white);
    overflow: hidden;
}
.page-hero__media {
    position: absolute; inset: 0; z-index: -2;
    width: 100%; height: 100%; object-fit: cover;
    opacity: .55;
}
.page-hero::after {
    content: "";
    position: absolute; inset: 0; z-index: -1;
    background:
        linear-gradient(100deg, rgba(7,27,61,.94) 0%, rgba(7,27,61,.75) 45%, rgba(7,27,61,.35) 100%),
        linear-gradient(to top, rgba(7,27,61,.9), rgba(7,27,61,0) 60%);
}
.page-hero__inner {
    max-width: min(var(--content-max), 100%);
    margin-inline: auto;
    padding: var(--space-8) var(--gutter) var(--space-7);
}
.page-hero .page-head__eyebrow { color: var(--hurricane-cyan); opacity: 1; }
.page-hero .page-head__title { color: var(--white); }
.page-hero .page-head__lede { color: rgba(255,255,255,.86); }
.page-hero__credit {
    margin: var(--space-5) 0 0;
    font-size: 0.72rem;
    letter-spacing: .04em;
    text-transform: uppercase;
    color: rgba(255,255,255,.55);
}

/* Breadcrumbs sitting on the hero need light text. */
.page-hero .breadcrumbs { padding-inline: 0; }
.page-hero .breadcrumbs ol,
.page-hero .breadcrumbs a { color: rgba(255,255,255,.7); }
.page-hero .breadcrumbs [aria-current] { color: var(--white); }

@media (prefers-reduced-motion: no-preference) {
    .page-hero__media { transition: opacity var(--duration-slow) var(--ease); }
}

/* Breadcrumbs inside the hero need breathing room from the eyebrow below. */
.page-hero .breadcrumbs { margin-bottom: var(--space-5); }

.plot__land path { fill: var(--plot-land); stroke: var(--plot-coast); stroke-width: 1.2; }
.plot__borders path { fill: none; stroke: var(--plot-border-line); stroke-width: 0.8; }

/* Archive banner. Loud on purpose: out-of-season guidance shown under a live
   heading reads as fabricated, which is worse than showing nothing. */
.archive-banner {
    display: flex; gap: var(--space-4); align-items: flex-start;
    padding: var(--space-5);
    margin-bottom: var(--space-5);
    background: var(--sunrise-orange-10);
    border: 1px solid var(--sunrise-orange);
    border-left: 5px solid var(--sunrise-orange);
    border-radius: var(--radius);
    color: #7a3d06;
}
.archive-banner__tag {
    flex: 0 0 auto;
    padding: 3px var(--space-3);
    background: var(--sunrise-orange); color: var(--white);
    border-radius: var(--radius-pill);
    font-size: 0.7rem; font-weight: 800; letter-spacing: .06em; text-transform: uppercase;
}
.archive-banner__title { margin: 0 0 var(--space-2); font-weight: 700; }
.archive-banner__body { margin: 0; font-size: var(--step--1); }

:root[data-theme="dark"] .archive-banner { color: #ffd9b0; background: rgba(244,123,32,.14); }

@media (prefers-color-scheme: dark) {
    :root[data-theme="auto"] .archive-banner { color: #ffd9b0; background: rgba(244,123,32,.14); }
}

/* Plot zoom controls, floated over the canvas. */
.plot-stage { position: relative; }
.plot-zoom {
    position: absolute; top: var(--space-3); right: var(--space-3); z-index: 2;
    display: flex; flex-direction: column; align-items: stretch; gap: 2px;
    padding: 4px;
    background: var(--surface-raised);
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    box-shadow: var(--shadow-sm);
}
.plot-zoom__btn {
    display: grid; place-content: center;
    min-width: 36px; min-height: 36px; padding: 0 var(--space-2);
    background: transparent; border: 0; border-radius: var(--radius-sm);
    color: var(--text); font: inherit; font-size: var(--step--1); font-weight: 700; cursor: pointer;
}
.plot-zoom__btn:hover:not(:disabled) { background: var(--surface-sunken); }
.plot-zoom__btn:disabled { opacity: .4; cursor: default; }
.plot-zoom__btn--reset { min-height: 30px; font-size: 0.72rem; text-transform: uppercase; letter-spacing: .04em; color: var(--text-muted); }
.plot-zoom__level { text-align: center; font-size: 0.72rem; color: var(--text-muted); padding: 2px 0; }

.plot-canvas { cursor: grab; touch-action: none; }
.plot-canvas.is-grabbing { cursor: grabbing; }

.plot-hint { margin: var(--space-2) 0 0; font-size: var(--step--1); color: var(--text-muted); }

/* ==========================================================================
   Full-width headings
   --------------------------------------------------------------------------
   The brief calls for headings to fill 100% of their parent, and I had capped
   them at a readable measure instead. Caps removed here, and the display
   headings opt into the JS fitter in app.js which binary-searches font-size
   until the longest line exactly meets the container edge. clamp() alone
   cannot do this: it knows the viewport, not the container.

   Body paragraphs inside .prose keep a measure, because a 1240px line of
   running text is genuinely hard to read. Headings, ledes, and standalone
   statements go full width.
   ========================================================================== */

.page-head,
.page-head__lede,
.hero__title,
.hero__lede,
.section__lede,
.quiet-state__body,
.site-footer__attribution,
.site-footer__promise,
.plot__caption,
.section__note {
    max-width: 100%;
}

/* Headings that fill the container exactly. The fitter overrides font-size
   inline, so the clamp below is only the pre-JS and no-JS appearance. */
/* No nowrap here. The fitter applies it itself before measuring, so that in the
 * gap before the font loads and the script runs, the heading simply wraps
 * inside its box. With nowrap set up front, the pre-JS paint pushed the
 * homepage headline off the right edge of the screen. */
[data-fit] {
    display: block;
    width: 100%;
    overflow: hidden;
}

/* A nowrap heading must still behave on a phone, where filling the width
   would leave text unreadably small. Below tablet the fitter is skipped and
   normal wrapping returns. */
@media (max-width: 47.99rem) {
    [data-fit] {
        white-space: normal;
        overflow: visible;
        font-size: var(--step-4) !important;
    }
}

/* ==========================================================================
   Local alerts on a location page
   --------------------------------------------------------------------------
   Sits above the page heading. If someone opens their town's page during a
   warning, the warning is the page.
   ========================================================================== */

.local-alert {
    border: 1px solid var(--border);
    border-left: 6px solid var(--border-strong);
    border-radius: var(--radius-lg);
    padding: var(--space-5);
    background: var(--surface-raised);
}
.local-alert--extreme { border-left-color: var(--cat-5); background: rgba(194,54,127,.08); }
.local-alert--severe  { border-left-color: var(--cat-3); background: rgba(255,122,69,.09); }
.local-alert--moderate{ border-left-color: var(--sunrise-orange); background: var(--sunrise-orange-10); }
.local-alert--minor   { border-left-color: var(--cat-1); }

.local-alert__head { display: flex; align-items: center; gap: var(--space-3); flex-wrap: wrap; margin-bottom: var(--space-4); }
.local-alert__tag {
    padding: 3px var(--space-3); border-radius: var(--radius-pill);
    background: var(--deep-ocean-blue); color: var(--white);
    font-size: 0.7rem; font-weight: 800; letter-spacing: .06em; text-transform: uppercase;
}
.local-alert--extreme .local-alert__tag { background: var(--cat-5); }
.local-alert--severe  .local-alert__tag { background: var(--cat-3); color: var(--midnight-navy); }
.local-alert--moderate .local-alert__tag { background: var(--sunrise-orange); }
.local-alert__title { margin: 0; font-size: var(--step-1); }

.local-alert__list { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--space-4); }
.local-alert__item { padding-left: var(--space-4); border-left: 3px solid var(--border); }
.local-alert__item--extreme { border-left-color: var(--cat-5); }
.local-alert__item--severe { border-left-color: var(--cat-3); }
.local-alert__item--moderate { border-left-color: var(--sunrise-orange); }
.local-alert__event { margin: 0 0 var(--space-1); font-weight: 700; font-size: var(--step-1); }
.local-alert__headline { margin: 0 0 var(--space-2); }
.local-alert__instruction { margin: 0 0 var(--space-2); font-size: var(--step--1); color: var(--text-muted); }
.local-alert__meta { margin: 0; font-size: var(--step--1); color: var(--text-muted); }
.local-alert__official {
    margin: var(--space-4) 0 0; padding-top: var(--space-4);
    border-top: 1px solid var(--border);
    font-size: var(--step--1); color: var(--text-muted);
}

.alert-row__places { margin: var(--space-2) 0 0; font-size: var(--step--1); }
.alert-row__places a { font-weight: 600; }

/* Alert map */
.alert-map__halo { fill: var(--sunrise-orange); opacity: .22; }
.alert-map__dot { fill: var(--sunrise-orange); }
.alert-map__point text { fill: var(--text); font-size: 13px; font-weight: 600; font-family: var(--font-body); paint-order: stroke; stroke: var(--surface-sunken); stroke-width: 3px; }
.alert-map__point--extreme .alert-map__halo { fill: var(--cat-5); opacity: .3; }
.alert-map__point--extreme .alert-map__dot { fill: var(--cat-5); }
.alert-map__point--severe .alert-map__halo { fill: var(--cat-3); opacity: .28; }
.alert-map__point--severe .alert-map__dot { fill: var(--cat-3); }
.alert-map__point--minor .alert-map__halo,
.alert-map__point--unknown .alert-map__halo { fill: var(--storm-gray); opacity: .2; }
.alert-map__point--minor .alert-map__dot,
.alert-map__point--unknown .alert-map__dot { fill: var(--storm-gray); }

.chip--extreme { border-color: var(--cat-5); }
.chip--severe { border-color: var(--cat-3); }
.chip--moderate { border-color: var(--sunrise-orange); }
