:root {
    --primary-color: #6C8E7F;
    --primary-dark: #5a7a6d;
    --primary-light: #8fa89d;
    --secondary-color: #d4b483;
    --text-color: #333;
    /* Muted secondary text. Replaces the old light grays (hex 999/aaa/bbb/888),
       which all failed WCAG AA (1.9-3.5:1); this passes at 5.6:1 on white. */
    --text-muted: #5f6b63;
    /* Section-header green — darker than --primary-dark so headings read as
       headings; unifies the old #2e3e2e/#2f3a36 one-offs. */
    --heading-color: #2f3a36;
    --light-gray: #f5f5f5;
    --border-color: #ddd;
    --shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
    /* Spacing scale — the standard rungs for new and refactored rules, so the
       file stops accumulating one-off padding/margin values. */
    --space-xs: 0.25rem;
    --space-sm: 0.5rem;
    --space-md: 1rem;
    --space-lg: 1.5rem;
    --space-xl: 2rem;
    /* Type scale — likewise the standard font-size rungs. */
    --fs-xs: 0.75rem;
    --fs-sm: 0.8125rem;
    --fs-md: 0.875rem;
    --fs-base: 1rem;
    --fs-lg: 1.125rem;
    --fs-xl: 1.25rem;
    --fs-2xl: 1.5rem;
}

/* Budget fallback styles */
.budget-fallback {
    display: none;
}

/* Hide budget amounts and labels in summary stats */
.budget-report-container .summary-stats,
.summary-stats .budget-amount,
.summary-stats .budget-label {
    display: none;
}

* {
    margin: 0;
    padding: 0;
    box-sizing: border-box;
}

body {
    font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
    line-height: 1.6;
    color: var(--text-color);
    background-color: #f9f9f9;
    /* Clamp page width to the viewport so nothing creates a horizontal scroll.
       Tables/timeline scroll inside their own panes, so this is safe — and it
       keeps the absolutely-positioned header scope toggle on-screen on phones. */
    overflow-x: hidden;
}

.app-container {
    display: flex;
    flex-direction: column;
    min-height: 100vh;
    max-width: 1440px;
    margin: 0 auto;
    background: white;
    box-shadow: var(--shadow);
}

/* === Header — Editorial cover treatment ===
   Layered sage gradient with a low-opacity topographic line pattern,
   curved bottom edge (SVG sibling), three-tier typographic hierarchy
   (eyebrow / title / subtitle), and pill-style nav. */
.app-header {
    background:
        /* Faint topographic contour pattern — sense of place without
           literal imagery. Inline SVG, ~5% opacity, repeats horizontally. */
        url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='600' height='200' viewBox='0 0 600 200'><g fill='none' stroke='%23ffffff' stroke-width='0.6' stroke-opacity='0.08'><path d='M0,40 Q150,10 300,40 T600,40'/><path d='M0,70 Q150,40 300,70 T600,70'/><path d='M0,100 Q150,70 300,100 T600,100'/><path d='M0,130 Q150,100 300,130 T600,130'/><path d='M0,160 Q150,130 300,160 T600,160'/></g></svg>"),
        linear-gradient(135deg, #5a7468 0%, #6c8e7f 45%, #7a9a8c 100%);
    color: #fff;
    padding: 2.4rem 2rem 4.4rem;        /* extra bottom space for the curve */
    text-align: center;
    position: relative;
    overflow: hidden;
}
.app-header-inner {
    position: relative;
    z-index: 1;
    max-width: 960px;
    margin: 0 auto;
}
/* Soft curved bottom edge — sits flush against the bottom of the sage
   band so the white content area peeks through in a shallow arc.
   Drawn as a sibling SVG with a white fill matching the page below. */
.app-header-curve {
    position: absolute;
    left: 0;
    right: 0;
    bottom: -1px;                       /* -1 hides anti-aliasing seam */
    width: 100%;
    height: 48px;
    display: block;
    z-index: 0;
}
/* Eyebrow — small, uppercase, letter-spaced. Sets context above the
   title without competing for attention. */
.app-header-eyebrow {
    font-size: 0.72rem;
    font-weight: 600;
    letter-spacing: 0.18em;
    text-transform: uppercase;
    color: rgba(255, 255, 255, 0.7);
    margin: 0 0 0.85rem;
}
/* Subtitle — light, single sentence, breathing room below title. */
.app-header-subtitle {
    font-size: 0.95rem;
    font-weight: 400;
    color: rgba(255, 255, 255, 0.75);
    margin: 0.85rem 0 0;
    letter-spacing: 0.005em;
    line-height: 1.45;
    /* Reserve two lines and vertically center the text, so the nav below keeps
       a fixed position no matter how long each tab's tagline is — a 1-line vs
       2-line tagline used to shove the nav up/down when switching tabs. The
       grid item stays full-width (so the text still wraps); align-items only
       centers it vertically within the reserved height. */
    min-height: 2.9em;            /* 2 × line-height (1.45) */
    display: grid;
    align-items: center;
}
/* Year mark inside the title — refined editorial treatment: thin pipe
   separator + lighter-weight white. No tint, no badge — just a quiet
   date anchor that sits beside the headline. */
.app-header-year {
    color: rgba(255, 255, 255, 0.78);
    font-weight: 300;
    margin-left: 0.55em;
    padding-left: 0.65em;
    border-left: 1px solid rgba(255, 255, 255, 0.28);
    letter-spacing: 0.01em;
}

/* "Open ↗" button — only visible when the page is embedded in an
   iframe. Lets the user pop the tracker out into a full tab. Pinned top-LEFT
   so it never collides with the scope toggle in the top-right corner. */
.open-fullpage-btn {
    position: absolute;
    top: 0.9rem;
    left: 1rem;
    display: inline-block;
    padding: 6px 12px;
    background: rgba(255,255,255,0.14);
    border: 1px solid rgba(255,255,255,0.35);
    border-radius: 4px;
    color: #fff;
    text-decoration: none;
    font-size: 0.82rem;
    font-weight: 500;
    letter-spacing: 0.02em;
    transition: background 0.15s ease;
}
.open-fullpage-btn:hover {
    background: rgba(255,255,255,0.26);
    border-color: rgba(255,255,255,0.55);
}
.open-fullpage-btn[hidden] { display: none; }

/* Animated WebGL ocean (header-ocean.js) — a faint living version of the
   swell mark, drifting across the lower band behind the masthead content.
   Created by JS only when WebGL + motion are available; absent otherwise, so
   the static gradient/swell remain the fallback. Sits above the gradient but
   below both the white shore curve (z-index 0, later in the DOM) and the
   title content (.app-header-inner, z-index 1). Non-interactive. */
.app-header-ocean {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    z-index: 0;
    pointer-events: none;
    display: block;
}

/* Stacked-wave mark — three soft swells above the title. Reads as
   the Pacific without leaning on a specific landmark. Sized as a
   refined anchor rather than a banner. */
.app-header-mark {
    display: block;
    width: 72px;
    height: 21px;
    margin: 0 auto 0.7rem;
    opacity: 0.95;
}

/* Editorial serif headline. Newsreader pairs warmth with restraint and
   gives the masthead a publication feel rather than a web-app one.
   Falls back gracefully to system serifs if the webfont fails. */
.app-header h1 {
    margin: 0;
    font-family: 'Newsreader', 'Source Serif Pro', Georgia, 'Times New Roman', serif;
    font-weight: 500;
    font-size: clamp(2rem, 4vw, 2.85rem);
    letter-spacing: -0.012em;
    line-height: 1.04;
}
/* "Hawaiʻi" gets a warm ivory tint and small caps — architectural
   wordmark treatment that distinguishes the place name from the
   function noun ("Budget") without leaning the glyph (italic ʻokina
   read as drifted punctuation). */
.app-header-place {
    color: #f4ead5;
    font-variant: small-caps;
    font-weight: 500;
    letter-spacing: 0.02em;
}
/* "Tracker" demoted to a small-caps tagline beneath the headline.
   A short ivory hairline above acts as masthead chrome, locking the
   tagline into deliberate publication rhythm rather than floating. */
.app-header-tag {
    display: block;
    position: relative;
    margin-top: 0.4rem;
    font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
    font-size: 0.98rem;
    font-weight: 600;
    letter-spacing: 0.22em;
    text-transform: uppercase;
    color: rgba(255, 255, 255, 0.78);
}
.app-header-tag::before {
    content: '';
    display: block;
    width: 28px;
    height: 1px;
    background: rgba(244, 234, 213, 0.40);
    margin: 0 auto 0.45rem;
}

/* Nav — segmented-control pattern. The nav strip itself is a darker sage
   chip that hosts the pills, so inactive tabs read clearly without needing
   their own border/fill, and the active white pill pops as a true
   "selected segment." */
.main-nav {
    display: inline-flex;
    /* Never wrap to a second line. Combined with the responsive sub-label
       collapse below 960px (where the short labels easily fit), this keeps the
       nav a single row at every width — the sub-label version is trimmed to sit
       comfortably under the 880px header cap, with nowrap as the hard guarantee
       so a sub-pixel tip-over can never break it onto two lines. */
    flex-wrap: nowrap;
    gap: 0.2rem;
    margin: 1.5rem auto 0;
    padding: 5px;
    max-width: 100%;
    background: rgba(0, 0, 0, 0.18);
    border-radius: 999px;
    border: 1px solid rgba(255, 255, 255, 0.08);
    box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.12);
}

.nav-link {
    color: #ffffff;
    text-decoration: none;
    padding: 0.55rem 1.05rem;
    border-radius: 999px;
    white-space: nowrap;
    border: 1px solid transparent;
    background: transparent;
    /* Center single-line links (About) against the taller stacked
       sub-label links so the pill row stays vertically aligned. */
    display: inline-flex;
    align-items: center;
    justify-content: center;
    /* Smooth crossfade across every property the active state touches.
       Material-style standard easing gives a settling, polished feel. */
    transition:
        background 0.28s cubic-bezier(0.2, 0, 0.2, 1),
        color 0.22s ease,
        box-shadow 0.32s ease,
        transform 0.18s cubic-bezier(0.2, 0, 0.2, 1);
    font-size: 1.15rem;
    font-weight: 650;
    letter-spacing: 0.005em;
    will-change: transform, background;
}

.nav-link:hover {
    background: rgba(255, 255, 255, 0.1);
}
.nav-link.active {
    background: #fff;
    color: #3d5249;                     /* deep sage on white pill */
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.18);
    font-weight: 600;
}

/* Stacked nav variants — bill label on top, descriptive sub-label beneath
   ("HB1800" / "2026 budget bill"). Stacking keeps each item narrow so the
   four-item row still fits under the 960px header cap (inline sub-labels
   overflowed it). The sub-labels collapse on phones (≤640px) — see .nav-sub. */
.nav-link-stacked,
.nav-link-hb300,
.nav-link-actuals {
    display: inline-flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 0.15em;
    line-height: 1.15;
}
/* HB300 differentiates by label only — same white text as siblings so
   contrast stays high on the sage background. */
.nav-link-hb300 { color: #ffffff; }
.nav-link-hb300:hover { color: #ffffff; }
.nav-link-hb300.active { color: #3d5249; }

/* Sub-labels ("2026 budget bill" …) sit beneath each bill label as a readable
   caption. Hidden on phones (≤640px), where the no-wrap row has no room to
   spare, and shown from 641px up — stacked they stay within the 960px header
   cap. The text also lives on as each link's `title` tooltip. */
.nav-sub {
    display: none;
    font-size: 0.8rem;
    color: rgba(255, 255, 255, 0.85);
    font-weight: 500;
    letter-spacing: 0.01em;
    transition: color 0.22s ease, opacity 0.22s ease;
}
@media (min-width: 680px) {
    .nav-sub { display: block; }
}
.nav-link.active .nav-sub {
    color: #8aa595;                     /* sage tint, readable on white pill */
    opacity: 1;
    font-weight: 500;
}
/* HD1/SD1 links in draft comparison title */
.draft-title-link {
    color: inherit;
    text-decoration: none;
    border-bottom: 2px solid #a8d5b9;
}
.draft-title-link:hover {
    border-bottom-color: #2c6e49;
    color: #2c6e49;
}

/* Draft comparison meta bar */
.draft-meta-bar {
    display: flex;
    align-items: center;
    gap: 0.5rem;
    font-size: 0.88rem;
    color: #555;
    margin-bottom: 1.25rem;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
.draft-meta-bar a {
    color: #2c6e49;
    text-decoration: none;
    border-bottom: 1px solid #a8d5b9;
}
.draft-meta-bar a:hover {
    color: #1a4a31;
    border-bottom-color: #2c6e49;
}
.draft-meta-divider {
    color: var(--text-muted);
    font-size: 1rem;
    flex-shrink: 0;
}

/* Main Content */
#app {
    flex: 1;
    padding: 2rem;
    position: relative;
    min-height: 400px;
}

/* Loading State */
.loading {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    text-align: center;
}

.spinner {
    width: 40px;
    height: 40px;
    border: 4px solid #f3f3f3;
    border-top: 4px solid var(--primary-dark);
    border-radius: 50%;
    animation: spin 1s linear infinite;
    margin: 0 auto 1rem;
}
@keyframes spin {
    0% { transform: rotate(0deg); }
    100% { transform: rotate(360deg); }
}

/* Summary Cards Grid */
.summary-cards-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
    gap: var(--space-lg);
    margin: var(--space-xl) 0;
}

/* Canonical summary card. A second, near-identical .summary-card block used to
   live further down (the .summary-cards grid); it was redundant — its only
   effective difference was overriding .amount to 1.8rem, folded in here. */
.summary-card {
    background: white;
    border-radius: 8px;
    padding: var(--space-lg);
    text-align: center;
    box-shadow: var(--shadow);
    border: 1px solid var(--border-color);
    transition: transform 0.2s, box-shadow 0.2s;
}

.summary-card:hover {
    transform: translateY(-2px);
    box-shadow: 0 6px 12px rgba(0, 0, 0, 0.15);
}

.summary-card .amount {
    font-size: 1.8rem;
    font-weight: bold;
    color: var(--primary-color);
    margin-bottom: 0.5rem;
    display: block;
}

.summary-card .amount .fmt-num {
    font-size: 1em;
    font-weight: 700;
    color: inherit;
}

.summary-card .amount .fmt-unit {
    font-size: 0.68em;
    font-weight: 500;
    color: #7a8fa6;
    letter-spacing: 0.03em;
    vertical-align: 0.1em;
    margin-left: 0.2em;
}

.summary-card .label {
    color: #666;
    font-size: 0.9rem;
    font-weight: 500;
    text-transform: uppercase;
    letter-spacing: 0.5px;
}

.summary-card .label-sub {
    color: var(--text-muted);
    font-size: 0.78rem;
    font-weight: 400;
    margin-top: 0.15rem;
}

/* Make first summary card label bold */
.summary-cards-grid .summary-card:first-child .label {
    font-weight: 700;
}

/* Sort controls */
.sort-controls {
    margin: 20px 0;
    padding: 15px;
    background: #f8f9fa;
    border-radius: 6px;
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: 10px;
}

.sort-controls span {
    margin-right: 10px;
    font-weight: 500;
    color: #495057;
}

.sort-btn {
    background: #e9ecef;
    border: 1px solid #dee2e6;
    border-radius: 4px;
    padding: 6px 12px;
    font-size: 0.9em;
    cursor: pointer;
    transition: all 0.2s;
    color: #495057;
}

.sort-btn:hover {
    background: #dee2e6;
}

.sort-btn.active {
    background: #2c3e50;
    color: white;
    border-color: #2c3e50;
}

/* Department cards */
.department-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
    gap: 20px;
    margin-top: 20px;
}

.department-card {
    background: white;
    border-radius: 8px;
    box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
    padding: 20px;
    text-decoration: none;
    color: #333;
    transition: transform 0.2s, box-shadow 0.2s;
    display: block;
}

.department-card:hover {
    transform: translateY(-5px);
    box-shadow: 0 6px 12px rgba(0, 0, 0, 0.15);
    text-decoration: none;
}

/* County grant pass-through codes (CCH/COH/COK/COM): shown for total accuracy
   but not clickable — they have no department drill-in page. */
.department-card-static {
    cursor: default;
    opacity: 0.9;
}
.department-card-static:hover {
    transform: none;
    box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}

.department-card h3 {
    margin: 0 0 15px 0;
    color: var(--heading-color);
    font-size: var(--fs-xl);
}

.budget-total {
    background: #f8f9fa;
    padding: 15px;
    border-radius: 6px;
    margin-bottom: 15px;
    text-align: center;
}

.budget-total span {
    display: block;
    font-size: 0.9em;
    color: #6c757d;
    margin-bottom: 5px;
}

.budget-total strong {
    font-size: 1.5em;
    color: #2c3e50;
}

.budget-breakdown {
    font-size: 0.9em;
}

.budget-row {
    display: flex;
    justify-content: space-between;
    padding: 8px 0;
    border-bottom: 1px solid #eee;
}

.budget-row:last-child {
    border-bottom: none;
}
.budget-row span:first-child {
    color: #666;
}

.budget-row span:last-child {
    font-weight: 500;
}

.budget-table th,
.budget-table td {
    padding: 0.75rem 1rem;
    text-align: left;
    border-bottom: 1px solid var(--border-color);
}

.budget-table th {
    background-color: var(--light-gray);
    color: var(--primary-color);
    font-weight: 600;
}

.budget-table tr:nth-child(even) {
    background-color: var(--light-gray);
}

/* Footer */

/* Responsive Design */
@media (max-width: 768px) {
    .app-container {
        box-shadow: none;
    }
    
    #app {
        padding: 1rem;
    }
    
    .department-grid {
        grid-template-columns: 1fr;
    }
}

/* Chart Container */
.chart-container {
    position: relative;
    margin: 2rem 0;
    width: 100%;
    max-width: 800px;
    margin-left: auto;
    margin-right: auto;
    overflow: hidden;
}

.chart-wrapper {
    width: 100%;
    text-align: center;
}

.chart-wrapper img {
    max-width: 100%;
    height: auto;
    border: 1px solid var(--border-color);
    border-radius: 4px;
}

/* Department Detail Page */
.department-detail {
    padding: 2rem;
    max-width: 1000px;
    margin: 0 auto;
}

.department-detail .department-content {
    width: 100%;
    overflow: hidden;
}

/* Department Description Formatting */
.dept-description {
    background-color: var(--light-gray);
    padding: 1.5rem;
    margin: 1.5rem 0;
    border-radius: 8px;
    border-left: 4px solid var(--primary-color);
}

.dept-description h3 {
    margin-top: 0;
    margin-bottom: 1rem;
    color: var(--primary-color);
}

.dept-description p {
    line-height: 1.6;
    margin-bottom: 1rem;
    text-align: justify;
}

.department-detail table {
    width: 100%;
    table-layout: fixed;
    border-collapse: collapse;
}

.department-detail th,
.department-detail td {
    padding: 0.75rem;
    text-align: left;
    border-bottom: 1px solid var(--border-color);
}

.department-detail th {
    background-color: var(--light-gray);
    font-weight: 600;
}

/* Back Button */
.back-button {
    display: inline-block;
    margin-bottom: 1.5rem;
    color: var(--primary-color);
    text-decoration: none;
    font-weight: 500;
}

.back-button:hover {
    text-decoration: underline;
}

/* Department Header */
.department-header {
    margin-bottom: 2rem;
    padding-bottom: 1rem;
    border-bottom: 2px solid var(--border-color);
}

.department-header h2 {
    color: var(--heading-color);
    margin-bottom: 0.5rem;
}

/* Summary Cards */
/* Alternate grid container (auto-fill vs the -grid variant's auto-fit). The
   .summary-card / .amount rules that used to sit here were duplicates of the
   canonical block above and have been removed; only .label was unique. */
.summary-cards {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
    gap: var(--space-lg);
    margin: var(--space-xl) 0;
}

.summary-card .label {
    color: #666;
    font-size: 0.9rem;
}

/* Override for department page embedded styles */
.budget-amount {
    color: var(--primary-color) !important;
}


/* ===== Controls Bar ===== */
.controls-bar {
    display: flex;
    justify-content: space-between;
    align-items: center;
    flex-wrap: wrap;
    gap: 10px;
    margin: 20px 0;
    padding: 15px;
    background: #f8f9fa;
    border-radius: 6px;
}

.action-links {
    display: flex;
    gap: 10px;
    align-items: center;
    flex-wrap: wrap;
}

.action-link {
    background: none;
    border: 1px solid var(--primary-color);
    color: var(--primary-color);
    padding: 6px 12px;
    border-radius: 4px;
    font-size: 0.9em;
    cursor: pointer;
    text-decoration: none;
    transition: all 0.2s;
}

.action-link:hover {
    background: var(--primary-color);
    color: white;
}

.export-btn {
    font-family: inherit;
}

/* ===== Data Tables ===== */
.data-table {
    width: 100%;
    border-collapse: collapse;
    margin: 0.25rem 0 0.5rem;
    font-size: 0.99em;
}

.data-table th,
.data-table td {
    padding: 10px 13px;
    text-align: left;
    border-bottom: 1px solid rgba(16, 24, 40, 0.06);
}

/* Editorial column headers — quiet, uppercase, letter-spaced. Data leads, chrome follows.
   Bumped size so labels remain legible at small caps; thead gets its own subtle tint +
   a firm bottom edge + small drop-shadow so it stays visually distinct from the sticky
   dept-group-row that pins immediately below it. */
.data-table th {
    background: linear-gradient(to bottom, #f7f9fb, #eef2f6);
    border-bottom: 1px solid rgba(16, 24, 40, 0.12);
    /* 1px keyline + a soft falloff beneath, so the pinned header reads as
       floating above the rows that scroll under it. */
    box-shadow: 0 1px 0 rgba(16, 24, 40, 0.04),
                0 3px 5px -3px rgba(16, 24, 40, 0.10);
    font-size: 0.78rem;
    font-weight: 600;
    color: #5b6570;
    letter-spacing: 0.065em;
    text-transform: uppercase;
    position: sticky;
    top: 0;
    z-index: 2;                           /* above dept-group-row.open which is z-index 1 */
}
/* Round the outer thead corners to echo the white card's 12px radius. The
   table itself sits inside a card with rounded corners but the table cells
   are rectangular by default — corner-rounding the first/last th lets the
   header tint flow into the card's curve instead of meeting it as a hard edge. */
.data-table thead th:first-child {
    border-top-left-radius: 8px;
}
.data-table thead th:last-child {
    border-top-right-radius: 8px;
}

/* Scope sub-label under a column header ("Gov. → CD1") — same micro-kicker
   voice as the summary bar's connector/net kickers, so the table and the bar
   mark the same data relationship with the same signature. */
.th-sub {
    display: block;
    font-size: 0.6rem;
    font-weight: 600;
    color: #9aa5ad;
    white-space: nowrap;
    line-height: 1.3;
    text-transform: uppercase;
    letter-spacing: 0.07em;
    margin-top: 2px;
}

/* Row hover — neutral, subtle */
.data-table tbody tr:hover {
    background: rgba(16, 24, 40, 0.025);
}

.amount-cell {
    text-align: right !important;
    font-variant-numeric: tabular-nums;
}

/* Pill/chip around HD1 & SD1 numbers — subtle neutral container */
.figure-chip {
    display: inline-block;
    padding: 2px 9px;
    background: #f4f6f8;
    border: 1px solid #e3e7eb;
    border-radius: 4px;
    font-variant-numeric: tabular-nums;
    min-width: 3.85rem;
    text-align: right;
    white-space: nowrap;
}
.figure-chip .fmt-num {
    font-size: 0.99rem;
    font-weight: 600;
    color: #1a1a1a;
    letter-spacing: -0.01em;
}
.figure-chip .fmt-unit {
    font-size: 0.79rem;
    font-weight: 600;
    color: #6b7d8f;
    letter-spacing: 0.02em;
    margin-left: 3px;
}
/* Per-stage position count — permanent/temporary breakdown under each dollar chip */
.pos-sub {
    display: block;
    margin-top: 3px;
    text-align: right;
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
}
.pos-sub .pos-perm,
.pos-sub .pos-temp {
    font-size: 0.92rem;
    font-weight: 600;
    letter-spacing: -0.01em;
}
.pos-sub .pos-perm { color: #4a6b86; }
.pos-sub .pos-temp { color: #9a7b3a; }
.pos-sub .pos-sep { color: #b8c2cc; margin: 0 4px; font-weight: 600; }
.pos-sub .pos-unit {
    font-size: 0.72rem;
    font-weight: 600;
    color: #8aa0b2;
    letter-spacing: 0.02em;
    margin-left: 2px;
}
.pos-sub .pos-temp .pos-unit { color: #c0a566; }

/* Governor's Message detail — hint + "not funded" chip on the Gov's Request cell */
.amount-cell.has-gov { cursor: help; }
.gov-msg-hint {
    margin-left: 5px;
    color: #6e8aa5;
    font-size: 0.82rem;
    cursor: help;
}
.amount-cell.has-gov:hover .gov-msg-hint,
.amount-cell.has-gov:focus .gov-msg-hint { color: #3d5a76; }
/* CD1 "crossed out" hint — items the Legislature declined to fund */
.amount-cell.has-govcut { cursor: help; }
.gov-cut-hint {
    display: block;
    margin-top: 3px;
    font-size: 0.7rem;
    font-weight: 700;
    color: #8a2b2b;
    letter-spacing: 0.02em;
    white-space: nowrap;
}
.amount-cell.has-govcut:hover .gov-cut-hint,
.amount-cell.has-govcut:focus .gov-cut-hint { color: #6a1f1f; }
/* Governor's Message / cut popover cards */
.reason-popover .gov-pop-title {
    margin: 0 0 6px;
    font-weight: 600;
    color: #2b3a4a;
    font-size: 0.9rem;
}
.reason-popover .gov-cut-label { color: #8a2b2b; }
.reason-popover .gov-cut-note {
    margin: 0 0 6px;
    font-size: 0.82rem;
    color: #6b7280;
}
.reason-popover .gov-cut-list s,
.reason-popover .gov-pop-title s {
    text-decoration: line-through;
    text-decoration-color: #c0606a;
    color: #8a2b2b;
}

/* ── Actuals tab (FY2025 spending) ───────────────────────────────────── */
.actuals-caveat {
    margin: 0.5rem 0 1.1rem;
    font-size: 0.86rem;
    color: #6b7280;
    line-height: 1.5;
}
.actuals-caveat a { color: #2b4a38; font-weight: 600; text-decoration: underline; }
.actuals-caveat a:hover { color: #5a7b68; }
.actuals-table td:first-child { font-weight: 500; }
/* Variance tint — under budget (money left) green, over budget red.
   Reuses the comparison table's positive/negative chip palette. */
.amount-cell.variance-under .figure-chip { background: #e8f5ec; border-color: #c7e5d0; }
.amount-cell.variance-over  .figure-chip { background: #fbecee; border-color: #f2c9ce; }
.var-word {
    display: block;
    margin-top: 3px;
    text-align: right;
    font-size: 0.72rem;
    font-weight: 600;
    color: #8aa0b2;
    letter-spacing: 0.02em;
    white-space: nowrap;
}
.amount-cell.variance-under .var-word { color: #1f6b3a; }
.amount-cell.variance-over  .var-word { color: #8a2b2b; }

/* ── School Food Service ─────────────────────────────────────────────── */
/* Highlighted entry card on the DOE department page */
.sfs-link-card {
    display: flex;
    align-items: center;
    gap: 14px;
    margin: 0 0 1.25rem;
    padding: 14px 18px;
    background: linear-gradient(to right, #eef4ef, #f7f9f7);
    border: 1px solid #cfe0d4;
    border-left: 4px solid #5a7b68;
    border-radius: 10px;
    text-decoration: none;
    color: inherit;
    transition: background 0.18s ease, box-shadow 0.18s ease, transform 0.18s ease;
}
.sfs-link-card:hover {
    background: linear-gradient(to right, #e6f0e9, #f0f5f1);
    box-shadow: 0 2px 10px rgba(16, 24, 40, 0.08);
    transform: translateY(-1px);
}
.sfs-link-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 38px;
    height: 38px;
    flex: 0 0 38px;
    border-radius: 8px;
    background: #ffffff;
    border: 1px solid #cfe0d4;
    color: #5a7b68;
}
.sfs-link-text { display: flex; flex-direction: column; gap: 2px; flex: 1; }
.sfs-link-text strong { color: #2b3a4a; font-size: 1.02rem; }
.sfs-link-sub { font-size: 0.86rem; color: #6b7280; }
.sfs-link-arrow { font-size: 1.3rem; color: #5a7b68; font-weight: 700; }

/* Payroll/Other sub-line under a revenue/expenditure figure */
.sfs-sub {
    display: block;
    margin-top: 3px;
    text-align: right;
    font-size: 0.78rem;
    color: #8aa0b2;
    white-space: nowrap;
}
.sfs-page .summary-card.sfs-net-card.positive .amount { color: #1f6b3a; }
.sfs-page .summary-card.sfs-net-card.negative .amount { color: #8a2b2b; }

/* Payroll / Other breakdown — small labeled badges under a figure */
.sfs-breakdown {
    display: flex;
    flex-wrap: wrap;
    gap: 4px;
    justify-content: flex-end;
    margin-top: 5px;
}
.sfs-mini-badge {
    display: inline-flex;
    align-items: baseline;
    gap: 4px;
    padding: 2px 7px;
    background: #f4f6f8;
    border: 1px solid #e1e7ec;
    border-radius: 6px;
    font-size: 0.72rem;
    line-height: 1.3;
    white-space: nowrap;
}
.sfs-mini-label {
    color: #8aa0b2;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.03em;
    font-size: 0.64rem;
}
.sfs-mini-val { color: #3d5247; font-weight: 600; }

/* ── Cash Rollforward ────────────────────────────────────────────────── */
.sfs-cash-block { margin-top: 1.75rem; }
.sfs-cash-head { margin: 0 0 0.3rem; font-size: 1.05rem; color: #2b3a4a; }
.sfs-cash-intro {
    margin: 0 0 1rem;
    font-size: 0.86rem;
    color: #6b7280;
    line-height: 1.5;
    max-width: 60ch;
}
.sfs-cash-intro strong { color: #3d5247; }
.sfs-cf-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
    gap: 1rem;
}
.sfs-cf-card {
    border: 1px solid #e1e7ec;
    border-radius: 12px;
    overflow: hidden;
    background: #fff;
}
.sfs-cf-card-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 0.75rem;
    padding: 0.8rem 1rem;
    background: linear-gradient(135deg, #f4f8f5 0%, #eef3f7 100%);
    border-bottom: 1px solid #e1e7ec;
}
.sfs-cf-fund { font-size: 1rem; font-weight: 700; color: #2b4a38; }
.sfs-cf-avail-block { display: flex; flex-direction: column; align-items: flex-end; gap: 1px; }
.sfs-cf-avail-label {
    font-size: 0.64rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: #8aa0b2;
}
.sfs-cf-avail-val { font-size: 1.05rem; font-weight: 700; }
.sfs-cf-avail-val.positive { color: #1f6b3a; }
.sfs-cf-avail-val.negative { color: #8a2b2b; }

.sfs-cf-steps-head,
.sfs-cf-step {
    display: grid;
    grid-template-columns: 1fr 1.1fr 1.1fr;
    align-items: center;
    gap: 0.5rem;
    padding: 0.5rem 1rem;
}
.sfs-cf-steps-head {
    font-size: 0.64rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: #8aa0b2;
    padding-top: 0.7rem;
    padding-bottom: 0.4rem;
}
.sfs-cf-steps-head .sfs-cf-net,
.sfs-cf-steps-head .sfs-cf-end { text-align: right; }
.sfs-cf-step { border-top: 1px solid #f0f3f5; }
.sfs-cf-step:nth-child(even) { background: #fafbfc; }
.sfs-cf-fy { font-weight: 600; color: #3d5247; font-size: 0.86rem; }
.sfs-cf-net { text-align: right; font-size: 0.86rem; font-weight: 600; font-variant-numeric: tabular-nums; }
.sfs-cf-net.positive { color: #1f6b3a; }
.sfs-cf-net.negative { color: #b06a4a; }
.sfs-cf-end {
    text-align: right;
    font-size: 0.9rem;
    font-weight: 700;
    font-variant-numeric: tabular-nums;
}
.sfs-cf-end.positive { color: #1f6b3a; }
.sfs-cf-end.negative { color: #8a2b2b; }
/* Prominent source attribution card on the School Food Service page —
   replaces the old inline "Source: …" sentence with an icon + linked
   source name + metadata badges. */
.sfs-source-card {
    display: flex;
    align-items: flex-start;
    gap: 0.85rem;
    margin-top: 0.9rem;
    padding: 0.85rem 1rem;
    background: linear-gradient(135deg, #f4f8f5 0%, #eef3f7 100%);
    border: 1px solid #d8e3dc;
    border-left: 4px solid #5a7b68;
    border-radius: 10px;
}
.sfs-source-icon {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 38px;
    height: 38px;
    flex-shrink: 0;
    border-radius: 9px;
    background: #5a7b68;
    color: #fff;
}
.sfs-source-body { display: flex; flex-direction: column; gap: 0.35rem; min-width: 0; }
.sfs-source-label {
    font-size: 0.7rem;
    font-weight: 700;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: #6b7280;
}
.sfs-source-name {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
    font-size: 1.05rem;
    font-weight: 700;
    color: #2b4a38;
    text-decoration: none;
    line-height: 1.2;
}
.sfs-source-name:hover { color: #5a7b68; text-decoration: underline; }
.sfs-source-ext { opacity: 0.7; flex-shrink: 0; }
.sfs-source-badges { display: flex; flex-wrap: wrap; gap: 0.4rem; margin-top: 0.15rem; }
.sfs-badge {
    display: inline-flex;
    align-items: center;
    padding: 0.18rem 0.6rem;
    font-size: 0.78rem;
    font-weight: 600;
    color: #3d5247;
    background: #ffffff;
    border: 1px solid #cdddd2;
    border-radius: 999px;
}

.sfs-notes {
    margin: 1.25rem 0 0;
    padding-left: 1.1rem;
    font-size: 0.82rem;
    color: #6b7280;
    line-height: 1.5;
}
/* Segmented control that works for any number of buttons — the active button
   carries its own background (no fixed-width sliding thumb like .fy-seg-ctrl). */
.seg-ctrl {
    display: inline-flex;
    background: #f1f3f5;
    border-radius: 999px;
    padding: 3px;
    gap: 2px;
    font-size: 0.86rem;
    line-height: 1;
}
.seg-ctrl button {
    border: 0;
    background: transparent;
    padding: 7px 16px;
    font-size: inherit;
    font-weight: 500;
    color: #6b7280;
    cursor: pointer;
    border-radius: 999px;
    transition: background 160ms ease, color 160ms ease;
}
.seg-ctrl button:hover:not(.active) { color: #374151; }
.seg-ctrl button.active {
    background: #ffffff;
    color: #1e7e34;
    font-weight: 600;
    box-shadow: 0 1px 2px rgba(16, 24, 40, 0.08);
}
.sfs-page .seg-ctrl { margin: 0.5rem 0 1rem; }
/* N/A chip — used when gov amount is unavailable for a project */
.figure-chip.fig-na {
    color: var(--text-muted);
    font-style: italic;
    background: #fafafa;
    border-color: #e8e8e8;
    min-width: 2rem;
}
/* Tinted chip for the Change column based on direction */
.amount-cell.positive .figure-chip {
    background: #e8f5ec;
    border-color: #c7e5d0;
}
.amount-cell.negative .figure-chip {
    background: #fbecee;
    border-color: #f2c9ce;
}
/* Transferred: amber — money moved between depts, not cut or added */
.amount-cell.transferred .figure-chip {
    color: #7a5c0a;
    background: #fef8e7;
    border-color: #f5df96;
}
/* Small "→ AGS" annotation rendered below the delta chip in the change cell */
.change-transfer-dest {
    display: block;
    font-size: 0.72rem;
    font-weight: 500;
    color: #8b6914;
    letter-spacing: 0.01em;
    margin-top: 3px;
    line-height: 1.2;
}

/* ── Unified Change cell: dollar delta + inline pct on a second line ── */
.change-cell {
    white-space: nowrap;
    line-height: 1.2;
}
.change-cell .change-main {
    display: inline-flex;
    align-items: center;
    gap: 4px;
    justify-content: flex-end;
}
.change-cell .change-arrow {
    font-size: 0.72rem;
    line-height: 1;
    opacity: 0.85;
}
.change-cell .change-pct {
    display: block;
    font-size: 0.73rem;
    font-weight: 500;
    opacity: 0.7;
    margin-top: 2px;
    letter-spacing: -0.005em;
}
.change-cell.positive { color: #1e7e34; }
.change-cell.negative { color: #c62828; }

/* ── Indent guide lines (#10): thin vertical rules showing hierarchy in expanded rows.
   Painted via linear-gradient at specific x positions so they sit at the indent-start
   (aligned with the parent row's content), not at the table edge. */
.dept-detail-row .detail-indent,
.fund-detail-row .detail-indent {
    background-image: linear-gradient(
        to right,
        transparent 0.8rem,
        rgba(16, 24, 40, 0.10) 0.8rem,
        rgba(16, 24, 40, 0.10) calc(0.8rem + 1px),
        transparent calc(0.8rem + 1px)
    );
    background-repeat: no-repeat;
}
.prog-section-row .section-indent {
    background-image: linear-gradient(
        to right,
        transparent 0.8rem,
        rgba(16, 24, 40, 0.10) 0.8rem,
        rgba(16, 24, 40, 0.10) calc(0.8rem + 1px),
        transparent calc(0.8rem + 1px),
        transparent 2.5rem,
        rgba(16, 24, 40, 0.08) 2.5rem,
        rgba(16, 24, 40, 0.08) calc(2.5rem + 1px),
        transparent calc(2.5rem + 1px)
    );
    background-repeat: no-repeat;
}
.prog-fund-row .fund-indent {
    background-image: linear-gradient(
        to right,
        transparent 0.8rem,
        rgba(16, 24, 40, 0.10) 0.8rem,
        rgba(16, 24, 40, 0.10) calc(0.8rem + 1px),
        transparent calc(0.8rem + 1px),
        transparent 2.5rem,
        rgba(16, 24, 40, 0.08) 2.5rem,
        rgba(16, 24, 40, 0.08) calc(2.5rem + 1px),
        transparent
    );
    background-repeat: no-repeat;
}

/* Pill/chip around section labels (Operating, Capital Improvement, Mixed, etc.) */
.section-chip {
    display: inline-block;
    padding: 2px 9px;
    background: #eef3f6;
    border: 1px solid #d5dfe6;
    border-radius: 10px;
    font-size: 0.86rem;
    font-weight: 500;
    color: #3a5260;
    letter-spacing: 0.01em;
}
/* Pill/chip around fund category names (General, Federal, GO Bond, etc.) */
.fund-chip-multi {
    cursor: help;
    text-decoration: underline dotted #9b7fbf;
}
/* JS-rendered fund tooltip (appended to body to escape table overflow clipping) */
.fund-tooltip {
    display: none;
    position: absolute;
    background: #2e3e2e;
    color: #fff;
    font-size: 0.78rem;
    line-height: 1.6;
    padding: 6px 12px;
    border-radius: 6px;
    white-space: pre;
    box-shadow: 0 3px 10px rgba(0,0,0,0.25);
    pointer-events: none;
    z-index: 9999;
}
.fund-chip {
    display: inline-block;
    padding: 2px 9px;
    background: #f3eff6;
    border: 1px solid #ddd1e3;
    border-radius: 10px;
    font-size: 0.86rem;
    font-weight: 500;
    color: #4e3a60;
    letter-spacing: 0.01em;
    white-space: nowrap;
}

/* Fund-category colour variants — applied via data-fund-cat="<full category name>".
   Documented semantic mapping by source-of-money: each chip's color encodes
   *where the dollars come from*, so the user can scan the page and learn the
   rough composition at a glance. Five groups, each with its own hue family:

     • State General  (sage green) — A
         General Funds: state tax revenue, flexible spending
     • State Dedicated (teal-sage) — B, T, W
         State-collected money set aside for a specific purpose
     • Federal       (warm tan)   — N, P
         Money from the US government
     • Borrowed      (slate blue) — C, E
         State takes on debt (general-obligation or revenue bonds)
     • Transfers / Other (neutral grey) — U, S, R, X
         Inter-gov, county, private, miscellaneous

   Multi-fund chips (no data-fund-cat) fall back to the default treatment
   in .fund-chip above. The mapping is repeated in the Fund Detail tooltip
   and the reading-guide panel so users can decode it inline. */

/* — State General — */
.fund-chip[data-fund-cat="General Funds"] {
    background: #e8f0e8;
    border-color: #c4d8c4;
    color: #2d4a2d;
}

/* — State Dedicated — */
.fund-chip[data-fund-cat="Special Funds"],
.fund-chip[data-fund-cat="Trust Funds"],
.fund-chip[data-fund-cat="Revolving Funds"] {
    background: #e3eef0;
    border-color: #bcd2d6;
    color: #2a4a4f;
}

/* — Federal — */
.fund-chip[data-fund-cat="Federal Funds"],
.fund-chip[data-fund-cat="Other Federal Funds"] {
    background: #f4ebd9;
    border-color: #dcc59a;
    color: #6b4818;
}

/* — Borrowed — */
.fund-chip[data-fund-cat="General Obligation Bond Fund"],
.fund-chip[data-fund-cat="Revenue Bond Funds"] {
    background: #ebeef5;
    border-color: #c8d0e0;
    color: #364266;
}

/* — Transfers & Other — */
.fund-chip[data-fund-cat="Interdepartmental Transfers"],
.fund-chip[data-fund-cat="County Funds"],
.fund-chip[data-fund-cat="Private Contributions"],
.fund-chip[data-fund-cat="Other Funds"] {
    background: #ecedf0;
    border-color: #d2d4dc;
    color: #3c4452;
}

/* Department code chip — small monospace badge with the 3-letter dept code.
   Replaces the old <strong>DEPT</strong> treatment to distinguish the code
   from the department name that follows it. */
.dept-chip {
    display: inline-block;
    padding: 1px 7px;
    background: #f1f3f5;
    border: 1px solid #dde1e5;
    border-radius: 5px;
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 0.78rem;
    font-weight: 600;
    color: #3a4754;
    letter-spacing: 0.02em;
    vertical-align: 1px;
}
.project-dept-row .dept-chip,
.dept-group-row .dept-chip {
    margin-right: 4px;
}

/* Inline sparkline — shows Gov → HD1 → SD1 trajectory in program cells.
   Vertically centered with the surrounding text; muted so it doesn't compete. */
.row-sparkline {
    display: inline-block;
    vertical-align: -4px;
    margin-left: 8px;
    opacity: 0.85;
}
.row-sparkline:hover {
    opacity: 1;
}

/* Stacked bar — composition of programs within a fund group, shown inline
   in the fund group-header row. The bar itself (14px, with hairline gaps
   and a sage outline) sits below a small leader caption that names the
   largest contributing program (e.g. "Largest: HMS401 53%"). Hover or
   focus reveals a popover with the full segment legend.

   The previous "SHARE BY PROGRAM" kicker was dropped because it repeated
   identical text on every fund row — its purpose is now communicated by
   the bar's visual presence and the leader caption naming the top program. */
.stacked-bar-wrap {
    position: relative;
    display: inline-flex;
    align-items: center;
    margin-left: 10px;
    padding: 1px 2px;
    vertical-align: -8px;
    cursor: default;
    outline: none;
}
.stacked-bar-stack {
    display: inline-flex;
    flex-direction: column;
    align-items: flex-start;
    gap: 2px;
    line-height: 1;
}
.stacked-bar-caption {
    font-size: 0.72rem;
    font-weight: 500;
    color: #6b7773;
    letter-spacing: 0.01em;
    white-space: nowrap;
}
.stacked-bar-caption-id {
    font-weight: 700;
    color: #2c3e35;
    letter-spacing: 0.02em;
    margin-left: 1px;
}
.stacked-bar-caption-pct {
    color: #6f9184;
    font-weight: 600;
    margin-left: 3px;
}
.stacked-bar-track {
    display: inline-flex;
    border-radius: 3px;
    overflow: hidden;
    box-shadow: 0 0 0 1px #d8e4dd;
    background: #ffffff;
    line-height: 0;
}
.stacked-bar {
    display: block;
}

/* Hover/focus popover legend */
.stacked-bar-popover {
    position: absolute;
    bottom: calc(100% + 8px);
    left: 0;
    z-index: 1000;
    min-width: 240px;
    max-width: 320px;
    padding: 10px 12px 11px;
    background: #ffffff;
    border: 1px solid #d8e4dd;
    border-radius: 6px;
    box-shadow: 0 8px 24px rgba(40, 60, 52, 0.14),
                0 2px 4px rgba(40, 60, 52, 0.06);
    opacity: 0;
    visibility: hidden;
    transform: translateY(2px);
    transition: opacity 120ms ease, visibility 120ms ease, transform 120ms ease;
    pointer-events: none;
    font-weight: 400;
}
/* Flip below the bar when the default position would clip the sticky
   table header. Toggled via JS on pointerenter/focusin. */
.stacked-bar-popover--below {
    bottom: auto;
    top: calc(100% + 8px);
    transform: translateY(-2px);
}
.stacked-bar-wrap:hover .stacked-bar-popover--below,
.stacked-bar-wrap:focus-visible .stacked-bar-popover--below,
.stacked-bar-wrap:focus-within .stacked-bar-popover--below {
    transform: translateY(0);
}
.stacked-bar-wrap:hover .stacked-bar-popover,
.stacked-bar-wrap:focus-visible .stacked-bar-popover,
.stacked-bar-wrap:focus-within .stacked-bar-popover {
    opacity: 1;
    visibility: visible;
    transform: translateY(0);
}
.stacked-bar-popover-title {
    font-size: 0.72rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.07em;
    color: #6f9184;
    margin-bottom: 7px;
    padding-bottom: 6px;
    border-bottom: 1px solid #eef2ef;
}
.stacked-bar-legend {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 4px;
}
.stacked-bar-legend-row {
    display: grid;
    grid-template-columns: 10px 1fr auto auto;
    gap: 6px 10px;
    align-items: center;
    font-size: 0.82rem;
    line-height: 1.35;
    color: #2c3e35;
}
.legend-swatch {
    display: inline-block;
    width: 10px;
    height: 10px;
    border-radius: 2px;
    box-shadow: inset 0 0 0 1px rgba(16, 24, 40, 0.10);
}
.legend-label {
    color: #2c3e35;
    font-weight: 500;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.legend-pct {
    color: #6f9184;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    text-align: right;
}
.legend-amt {
    color: #5a6e66;
    font-weight: 500;
    font-variant-numeric: tabular-nums;
    text-align: right;
}

/* Search highlight — muted yellow tint with slight rounding, no harsh neon.
   Used when the search input has a query. */
mark {
    background: #fff6c2;
    color: inherit;
    padding: 0 2px;
    border-radius: 2px;
    box-shadow: 0 0 0 1px rgba(209, 180, 40, 0.3);
}

/* === Totals Row — sage-aligned summary footer ===
   Pulled into the same family as the timeline pills, net change pill, and
   reading-guide pill: soft sage background, sage rule above, sage left
   accent on the label cell, and positive/negative chips that mirror the
   net change pill so the table footer and the headline summary read as
   one consistent component. */
.totals-block .totals-row td {
    border-top: 1px solid #dde7e1;             /* very soft sage rule — divider, not a frame */
    background: #f1f5f3;                       /* lighter sage tint, gentler contrast against zebra rows */
    color: #1f2937;
    font-weight: 700;
    padding: 16px 13px;
}
.totals-block .totals-row td:first-child {
    text-transform: uppercase;
    letter-spacing: 0.05em;
    font-size: 0.95rem;
    color: #4b5563;
    /* No left accent bar — its hard vertical edge fights the soft top
       rule. The uppercase label and tinted background already mark this
       row as the summary without an additional vertical anchor. */
    box-shadow: inset 3px 0 0 #e3ede7;          /* whisper-soft sage shoulder; reads as a tint, not an edge */
}
/* Count info shown after the "Total" label — smaller, lighter, and reset
   from the cell's uppercase styling so it reads as supplementary info
   rather than competing with the primary label. */
.totals-block .totals-row .totals-meta {
    font-size: 0.85rem;
    font-weight: 500;
    color: #8a9492;
    margin-left: 0.55em;
    text-transform: none;
    letter-spacing: 0.02em;
    font-variant: normal;
}
.totals-block .totals-row td:last-child {
    /* matched whisper-soft shoulder on the right edge for symmetry */
    box-shadow: inset -3px 0 0 #e3ede7;
}
/* Number chips — shared muted slate base. Padding, unit margin, and unit
   font-size MATCH the base .figure-chip rule so totals row digits sit at
   the exact same right anchor as body row digits in every column. Only
   colors, weight, and number font-size change for emphasis. */
.totals-block .totals-row .figure-chip {
    background: #e9ecf0;
    border-color: #d5dae0;
    font-weight: 700;
    /* padding, min-width inherited from .figure-chip — DO NOT override */
}
.totals-block .totals-row .figure-chip .fmt-num {
    color: #1f2937;
    font-size: 1.1rem;
    font-weight: 700;
    letter-spacing: -0.015em;
}
.totals-block .totals-row .figure-chip .fmt-unit {
    color: #8a9492;
    font-weight: 500;
    /* font-size and margin-left inherited from .figure-chip .fmt-unit so
       the unit suffix sits at the identical right anchor as body rows */
}
/* Change cell: re-skinned to match the net change pill exactly (deep sage
   for positive, warm clay for negative). Same hue, same border family,
   so the totals delta and the headline net pill encode direction
   identically across the page. */
.totals-block .totals-row .change-cell.positive .figure-chip {
    background: #eaf2ec;
    border-color: #9fc0ad;
}
.totals-block .totals-row .change-cell.negative .figure-chip {
    background: #f5ece8;
    border-color: #d2b1a8;
}
.totals-block .totals-row .change-cell.positive .figure-chip .fmt-num {
    color: #2f6b48;
}
.totals-block .totals-row .change-cell.negative .figure-chip .fmt-num {
    color: #8e3f3a;
}
.totals-block .totals-row .change-cell .change-arrow {
    font-size: 0.95rem;
    margin-right: 3px;
}
/* Hide the percentage in the totals row — the absolute delta is the
   anchor for the summary, and the % adds noise without aiding scanning. */
.totals-block .totals-row .change-pct {
    display: none;
}
/* Force all amount cells (including the change cell's inner content) to
   vertical-align: middle so every chip sits on the same horizontal axis. */
.totals-block .totals-row td {
    vertical-align: middle;
}

/* Clickable Capital Improvement chip that scrolls to the projects section */
a.section-chip-link {
    text-decoration: none;
    cursor: pointer;
    background: #e2eef7;
    border-color: #b7d2e5;
    color: #1f4e71;
    transition: background 0.15s ease, border-color 0.15s ease;
}
a.section-chip-link:hover {
    background: #cfe3f2;
    border-color: #85b4d1;
    text-decoration: none;
}

/* Section 14 capital projects list */
.projects-section {
    margin-top: 1.25rem;
    padding: 20px 22px;
    border-top: none;
}
.projects-section h3 {
    margin: 0 0 6px 0;
    font-size: var(--fs-xl);
    color: var(--heading-color);
}
.projects-section .section-desc {
    font-size: 0.97rem;
    color: #6a6a6a;
    margin: 0 0 16px 0;
}
/* ── Capital Projects table ── */
.project-table {
    font-size: 0.935rem;
}
/* Inherit the standard grey gradient + neutral border from .data-table th
   for visual consistency with all other tables on the page. Only the
   compact padding remains project-specific. */
.project-table thead th {
    padding: 7px 11px;
}
.project-table td {
    padding: 9px 11px;
    vertical-align: top;
}
/* Dept group rows inside the project table — match the chrome of .dept-group-row */
.project-table .project-dept-row {
    cursor: pointer;
    user-select: none;
    border-bottom: 1px solid rgba(16, 24, 40, 0.08);
}
.project-table .project-dept-row td {
    background: linear-gradient(to bottom, #fafbfc, #f1f4f7);
    transition: background 0.18s ease, box-shadow 0.18s ease;
    padding-top: 12px;
    padding-bottom: 12px;
}
.project-table .project-dept-row td:first-child {
    box-shadow: inset 3px 0 0 #c8d1d9;
    border-top-left-radius: 6px;
    border-bottom-left-radius: 6px;
}
.project-table .project-dept-row td:last-child {
    border-top-right-radius: 6px;
    border-bottom-right-radius: 6px;
}
.project-table .project-dept-row:hover td {
    background: linear-gradient(to bottom, #f3f6f9, #e7ecf1);
}
.project-table .project-dept-row:hover td:first-child {
    box-shadow: inset 3px 0 0 #8aa595;
}
.project-table .project-dept-row.open td {
    background: linear-gradient(to bottom, #eef3ef, #e2eae4);
    color: #2a3d33;
}
.project-table .project-dept-row.open td:first-child {
    box-shadow: inset 3px 0 0 #6f8e7c;
}
.project-dept-cell {
    padding: 11px 15px !important;
}
.project-dept-cell .project-totals {
    float: right;
    font-size: 0.90rem;
    color: #556;
    font-variant-numeric: tabular-nums;
}
.project-dept-cell .project-totals .positive { color: #28a745; }
.project-dept-cell .project-totals .negative { color: #dc3545; }
/* Program column inside project rows */
.project-program-cell {
    white-space: nowrap;
    min-width: 80px;
}
.project-prog-name {
    font-size: 0.81rem;
    color: #7a8a85;
    font-weight: 400;
    margin-top: 2px;
    white-space: normal;
    max-width: 132px;
}
.project-table .project-num {
    font-variant-numeric: tabular-nums;
    color: #6a6a6a;
    width: 48px;
    white-space: nowrap;
}
.project-table .project-name {
    font-weight: 500;
    color: #2e3e2e;
}
.project-table .project-scope {
    font-size: 0.86rem;
    color: #7a7a7a;
    line-height: 1.4;
    margin-top: 3px;
    max-width: 500px;
}
.project-table .project-row.change-added { border-left: 3px solid #28a745; }
.project-table .project-row.change-removed { border-left: 3px solid #dc3545; }
.project-table .project-row.change-modified { border-left: 3px solid #e0b341; }
.project-table .project-row.change-unchanged { border-left: 3px solid transparent; }
/* Change-type left-edge treatment on main comparison rows (mirrors project table) */
.dept-detail-row.change-removed {
    border-left: 3px solid rgba(220,53,69,0.55);
    background: rgba(248,215,218,0.18);
}
.dept-detail-row.change-added {
    border-left: 3px solid rgba(40,167,69,0.55);
    background: rgba(212,237,218,0.18);
}
.proj-gov-label, .proj-draft-label {
    font-size: 0.79rem;
    font-weight: 400;
    opacity: 0.7;
    margin-left: 1px;
}

.positive { color: #28a745; }
.negative { color: #dc3545; }
.muted { color: var(--text-muted); font-size: 0.85em; margin-top: 10px; }

.badge {
    display: inline-block;
    padding: 2px 9px;
    border-radius: 10px;
    font-size: 0.83em;
    font-weight: 600;
    text-transform: uppercase;
}
.badge-add { background: #d4edda; color: #155724; }
.badge-remove { background: #f8d7da; color: #721c24; }

.draft-stats {
    margin: 0.5rem 0 1rem;
    font-size: 0.95em;
}

.empty-state {
    text-align: center;
    padding: 3rem 1rem;
    color: #666;
}
.empty-state pre {
    display: inline-block;
    text-align: left;
    background: #f4f4f4;
    padding: 1rem;
    border-radius: 6px;
    margin-top: 1rem;
    font-size: 0.85em;
}

/* ===== Filter Bar ===== */
.filter-bar {
    display: flex;
    gap: 10px;
    flex-wrap: wrap;
    margin-bottom: 1rem;
    align-items: center;
}

.search-input {
    flex: 1;
    min-width: 200px;
    padding: 9px 13px;
    border: 1px solid #ddd;
    border-radius: 4px;
    font-size: 1.05em;
}

.filter-select {
    padding: 9px 13px;
    border: 1px solid #ddd;
    border-radius: 4px;
    font-size: 0.99em;
    background: white;
}

.search-summary {
    margin: 0.5rem 0 1rem;
    color: #666;
}

/* ===== Department Detail Enhancements ===== */
.dept-desc {
    color: #555;
    line-height: 1.7;
    margin: 0.5rem 0 1.5rem;
    padding: 1rem;
    background: #f8f9fa;
    border-left: 3px solid var(--primary-color);
    border-radius: 4px;
}

.programs-table {
    font-size: 0.85em;
}

/* ===== FY Toggle ===== */
.fy-toggle {
    display: flex;
    gap: 8px;
    margin-bottom: 1rem;
}

/* ===== Compact Summary Cards ===== */
.summary-cards-grid.compact {
    grid-template-columns: 1fr auto 1fr auto 1fr;
    gap: 0.5rem 0.6rem;
    margin: 1rem 0;
    max-width: 580px;
}
.summary-cards-grid.compact.triple {
    grid-template-columns: 1fr auto 1fr auto 1fr auto 1fr;
    max-width: 820px;
}
.summary-cards-grid.compact .summary-card {
    padding: 0.6rem 0.75rem;
    min-width: 0;
}
.summary-cards-grid.compact .summary-card .amount {
    font-size: 1.15rem;
    margin-bottom: 0.15rem;
}
.summary-cards-grid.compact .summary-card .label {
    font-size: 0.72rem;
}
.card-arrow {
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--text-muted);
    font-size: 1.1rem;
    padding: 0 2px;
    align-self: center;
}

/* ===== Change Card Accent ===== */
.summary-card.change-card {
    background: #eaf5ee;
    box-shadow: none;
    border-top: 3px solid #2e7d32;
}
.summary-card.change-card:hover {
    transform: none;
    box-shadow: none;
}
.summary-card.change-card.change-negative {
    background: #fdecea;
    border-top-color: #c62828;
}

/* ===== Section Label Row ===== */
.card-section-label {
    grid-column: 1 / -1;
    font-weight: 600;
    font-size: 0.75rem;
    text-transform: uppercase;
    letter-spacing: 0.5px;
    color: var(--text-muted);
    margin: 0.25rem 0 -0.25rem;
    padding-left: 2px;
    cursor: default;
}
.card-section-label:first-child {
    margin-top: 0;
}
.card-section-label.card-section-total {
    font-weight: 700;
    font-size: 0.8rem;
    color: var(--primary-dark);
    margin-bottom: 0.1rem;
    padding-bottom: 0.35rem;
    border-bottom: 1px solid #ddd;
}
.card-section-label.card-section-toggle {
    cursor: pointer;
    user-select: none;
    padding-left: 0.85rem;
    font-size: 0.7rem;
    font-weight: 500;
    color: var(--text-muted);
    margin-top: 0.4rem;
}
.card-section-label.card-section-toggle:hover {
    color: var(--primary-color);
}

.toggle-arrow {
    display: inline-block;
    font-size: 0.6rem;
    vertical-align: middle;
    transition: transform 0.15s;
}
.card-row-collapsible {
    grid-column: 1 / -1;
    margin: 0 0 0.25rem;
    padding-left: 0.85rem;
}
.card-row-collapsible .summary-cards-grid.compact {
    margin: 0.25rem 0 0;
}

/* ===== Table Header Dropdown (Section / Fund) ===== */
.th-dropdown {
    position: relative;
    cursor: pointer;
    user-select: none;
}
/* Filter dropdowns read differently from sortable headers: a quiet rounded
   chip appears on hover (sort columns just swap their ▲▼), and the label
   tints sage while a filter is applied. */
.th-dropdown-btn {
    white-space: nowrap;
    display: inline-block;
    padding: 2px 7px;
    margin: -2px -7px;          /* chip grows around the label, no layout shift */
    border-radius: 999px;
    transition: background 0.12s ease, color 0.12s ease;
}
.th-dropdown-btn:hover {
    color: var(--primary-color);
    background: rgba(111, 145, 132, 0.10);
}
.th-dropdown-btn.th-filtered {
    color: #4a7a6a;
}
.th-dropdown-menu {
    display: none;
    position: absolute;
    top: 100%;
    left: 0;
    background: white;
    border: 1px solid #ddd;
    border-radius: 4px;
    box-shadow: 0 4px 12px rgba(0,0,0,0.15);
    z-index: 20;
    min-width: 220px;
    max-height: 300px;
    overflow-y: auto;
    padding: 4px 0;
    margin-top: 2px;
    font-weight: 400;
}
.th-dropdown.open .th-dropdown-menu {
    display: block;
}
.th-dropdown-menu label {
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 7px 13px;
    cursor: pointer;
    font-size: 0.94em;
    white-space: nowrap;
    color: #333;
}
.th-dropdown-menu label:hover {
    background: #f0f8f4;
}
.th-dropdown-menu input[type="checkbox"] {
    margin: 0;
}

/* ===== Sortable Columns ===== */
/* NOTE: do NOT set position here — parent .data-table th is position: sticky,
   and any override (like position: relative) breaks the sticky column header. */
th.sortable {
    cursor: pointer;
    user-select: none;
    white-space: nowrap;
    transition: color 0.15s;
}
th.sortable:hover {
    color: #1f2937;
    /* Must be OPAQUE — th is position:sticky, so a semi-transparent hover
       background lets the rows scrolling behind it bleed through. Slightly
       darker variant of the default thead gradient. */
    background: linear-gradient(to bottom, #eef2f6, #e4e9ee);
}
/* Active sort arrow — inline, bold, using the sage accent for consistency */
th.sortable .sort-ind {
    display: inline-block;
    margin-left: 4px;
    color: #1e7e34;
    font-size: 0.68rem;
    font-weight: 700;
    vertical-align: baseline;
}
/* Faint arrow hint on any sortable header hover (even when not active) */
th.sortable:not(:hover):not(.sort-active) .sort-hint { opacity: 0; }
th.sortable .sort-hint {
    display: inline-block;
    margin-left: 4px;
    color: #c0c6cc;
    font-size: 0.65rem;
    opacity: 0.6;
    transition: opacity 0.15s;
}

/* Department group rows — soft warm-grey gradient with a sage accent bar
   on the left when collapsed, deepening to a stronger sage when open. The
   gradient adds dimension that flat fills lack; the accent bar gives each
   dept block a subtle "you are entering a section" cue without shouting. */
.dept-group-row {
    cursor: pointer;
    font-weight: 500;
    border-bottom: 1px solid rgba(16, 24, 40, 0.08);
}
.dept-group-row td {
    padding-top: 12px;
    padding-bottom: 12px;
    background: linear-gradient(to bottom, #fafbfc, #f1f4f7);
    transition: background 0.18s ease, box-shadow 0.18s ease;
}
.dept-group-row td:first-child {
    box-shadow: inset 3px 0 0 #c8d1d9;
    border-top-left-radius: 6px;
    border-bottom-left-radius: 6px;
}
.dept-group-row td:last-child {
    border-top-right-radius: 6px;
    border-bottom-right-radius: 6px;
}
.dept-group-row:hover td {
    background: linear-gradient(to bottom, #f3f6f9, #e7ecf1);
}
.dept-group-row:hover td:first-child {
    box-shadow: inset 3px 0 0 #8aa595;
}
/* When expanded: deeper sage tint + stronger left bar so it reads as the
   active context for the child rows below it. */
.dept-group-row.open td {
    background: linear-gradient(to bottom, #eef3ef, #e2eae4);
    color: #2a3d33;
}
.dept-group-row.open td:first-child {
    box-shadow: inset 3px 0 0 #6f8e7c;
}
/* Only sticky when expanded — keeps the dept label pinned below the
   thead while scrolling through its children. Collapsed rows stay in
   the normal flow so they don't queue up at the top. Background must
   be on the td because sticky cells leave their row's background behind. */
.dept-group-row.open td {
    position: sticky;
    top: 39px;
    z-index: 1;
}
/* Visual breathing room between dept blocks: a transparent gap created via
   negative-bottom border + box-shadow trick. Cleaner than per-tbody
   margins which break the table layout. */
.dept-block + .dept-block .dept-group-row td {
    /* Adds a 6px "white space" gap above each subsequent dept block by
       pushing the gradient down slightly via padding. */
    padding-top: 16px;
}
.dept-arrow {
    display: inline-block;
    width: 1em;
    font-size: 0.88em;
    color: #666;
    transition: transform 0.18s ease;
}
/* Expand carets render a fixed ▶ glyph and rotate to point down when open,
   so the open/close gesture animates instead of swapping characters.
   (The tax-calculator table still swaps glyphs — it never gets .open.) */
.dept-arrow.open {
    transform: rotate(90deg);
}
.dept-count {
    font-weight: 400;
    color: var(--text-muted);
    font-size: 0.935em;
}
.dept-detail-row.hidden,
.project-row.hidden {
    display: none;
}
/* Entrance fade for compare-page table rows. JS sets --ri (0–14) on the
   first screenful after each render, cascading them in; rows revealed later
   by expand/collapse replay the animation at --ri 0 (display:none → shown
   restarts CSS animations), which is what eases expanded children in. */
@keyframes row-enter {
    from { opacity: 0; }
}
.compare-page .data-table tbody tr {
    animation: row-enter 0.22s ease-out backwards;
    animation-delay: calc(var(--ri, 0) * 18ms);
}
.dept-detail-row .detail-indent,
.fund-detail-row .detail-indent {
    padding-left: 2.2rem;
}
.prog-group-row {
    cursor: pointer;
}
.prog-section-row.hidden {
    display: none;
}
.prog-section-row .section-indent {
    padding-left: 3.85rem;
    font-style: italic;
    color: #555;
}
.fund-detail-heading {
    margin: 2rem 0 0.75rem;
    font-size: 1.21rem;
    color: var(--text-color);
    cursor: help;
}
.fund-detail-heading .has-tooltip:hover {
    color: var(--primary-color);
}
.fund-detail-heading .has-tooltip::after {
    white-space: pre-line;
    width: 340px;
    font-size: 0.82rem;
    line-height: 1.7;
    padding: 10px 14px;
}
/* Fund group rows — same visual language as dept-group-row for consistency. */
.fund-group-row {
    cursor: pointer;
    font-weight: 500;
    border-bottom: 1px solid rgba(16, 24, 40, 0.08);
}
.fund-group-row td {
    padding-top: 12px;
    padding-bottom: 12px;
    background: linear-gradient(to bottom, #fafbfc, #f1f4f7);
    transition: background 0.18s ease, box-shadow 0.18s ease;
}
.fund-group-row td:first-child {
    box-shadow: inset 3px 0 0 #c8d1d9;
    border-top-left-radius: 6px;
    border-bottom-left-radius: 6px;
}
.fund-group-row td:last-child {
    border-top-right-radius: 6px;
    border-bottom-right-radius: 6px;
}
.fund-group-row:hover td {
    background: linear-gradient(to bottom, #f3f6f9, #e7ecf1);
}
.fund-group-row:hover td:first-child {
    box-shadow: inset 3px 0 0 #8aa595;
}
.fund-group-row.open td {
    background: linear-gradient(to bottom, #eef3ef, #e2eae4);
    color: #2a3d33;
    position: sticky;
    top: 39px;
    z-index: 1;
}
.fund-group-row.open td:first-child {
    box-shadow: inset 3px 0 0 #6f8e7c;
}
.fund-block + .fund-block .fund-group-row td {
    padding-top: 16px;
}
.fund-detail-row.hidden {
    display: none;
}

/* ===== Responsive ===== */
@media (max-width: 768px) {
    .filter-bar {
        flex-direction: column;
    }
    .search-input, .filter-select {
        width: 100%;
    }
    .controls-bar {
        flex-direction: column;
        align-items: stretch;
    }
    .data-table {
        font-size: 0.8em;
    }
    .data-table th, .data-table td {
        padding: 6px 8px;
    }
}

/* Split-department cross-reference note */
.split-note {
    font-size: 0.83rem;
    font-weight: 400;
    color: var(--text-muted);
    margin-left: 0.5rem;
    font-style: italic;
}
.split-link {
    color: var(--primary-color);
    text-decoration: underline dotted;
    font-style: normal;
}
.split-link:hover {
    color: var(--primary-dark);
}

/* Reallocation warning note */
.realloc-note {
    display: inline-block;
    font-size: 0.79rem;
    font-weight: 500;
    font-style: normal;
    color: #7a5c00;
    background: #fff8e1;
    border: 1px solid #ffe082;
    border-radius: 4px;
    padding: 1px 7px;
    margin-left: 0.4rem;
    cursor: help;
    white-space: nowrap;
}
.realloc-note .split-link {
    color: #7a5c00;
    text-decoration: underline dotted;
}
.realloc-note .split-link:hover {
    color: #4a3800;
}
/* Pure reallocation (no net change) — blue/neutral */
.realloc-note.realloc-pure {
    color: #1a5276;
    background: #eaf4fb;
    border-color: #aed6f1;
}
.realloc-note.realloc-pure .split-link {
    color: #1a5276;
}
.realloc-note.realloc-pure .split-link:hover {
    color: #0d2c47;
}

/* Transfer indicator — shown on collapsed department rows that contain inter-dept transfers */
.dept-transfer-note {
    display: inline-block;
    font-size: 0.74rem;
    font-weight: 500;
    color: #1a5276;
    background: #eaf4fb;
    border: 1px solid #aed6f1;
    border-radius: 3px;
    padding: 1px 7px;
    margin-left: 6px;
    cursor: help;
    vertical-align: middle;
}

/* Transfer badge — shown in the Change cell when a program is split across depts */
.transfer-badge {
    display: block;
    font-size: 0.74rem;
    font-weight: 500;
    font-style: normal;
    margin-top: 4px;
    border-radius: 4px;
    padding: 1px 6px;
    cursor: help;
    white-space: nowrap;
    line-height: 1.4;
}
.transfer-pure {
    color: #1a5276;
    background: #eaf4fb;
    border: 1px solid #aed6f1;
}
.transfer-partial {
    color: #7a5c00;
    background: #fff8e1;
    border: 1px solid #ffe082;
}
.transfer-link {
    color: inherit;
    text-decoration: underline dotted;
    font-style: normal;
}
.transfer-link:hover {
    text-decoration: underline;
}

/* Paired-dept chip — the unified cross-dept signal replacing .split-note,
   .dept-transfer-note, and .transfer-badge. Renders next to the program name
   as a compact "↔ DEPT" pill (or "→" / "←" for directional transfers). */
.pair-chip {
    display: inline-block;
    font-size: 0.76rem;
    font-weight: 500;
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    text-decoration: none;
    border-radius: 4px;
    padding: 1px 6px;
    margin-left: 5px;
    vertical-align: 1px;
    white-space: nowrap;
    cursor: pointer;
    transition: background 0.12s ease, color 0.12s ease, border-color 0.12s ease;
}
.pair-chip + .pair-chip { margin-left: 3px; }
.pair-chip-neutral {
    color: #4a5763;
    background: #eef1f4;
    border: 1px solid #d4d9df;
}
.pair-chip-neutral:hover {
    background: #dfe4e9;
    color: #2b3640;
}
.pair-chip-out {       /* dept LOST dollars — moving OUT to sibling */
    color: #7a2e2e;
    background: #fcecec;
    border: 1px solid #f3c5c5;
}
.pair-chip-out:hover {
    background: #f6d6d6;
    color: #5a1f1f;
}
.pair-chip-in {        /* dept GAINED dollars — moving IN from sibling */
    color: #1f5c35;
    background: #e7f3eb;
    border: 1px solid #bfd9c8;
}
.pair-chip-in:hover {
    background: #d4ebdb;
    color: #0f3f21;
}

/* Hover-highlight: all rows sharing a program_id pair key glow together.
   Treat the entire row as one continuous tinted band — accent bars only on
   the outermost cells so it reads as a single seamless highlight (no
   per-cell vertical "breaks" or left-edge stripes between cells). */
.pair-highlight > td {
    background: #fef7d6 !important;
    transition: background 0.15s ease, box-shadow 0.15s ease;
}
.pair-highlight > td:first-child {
    box-shadow: inset 3px 0 0 #d9a800;
}
.pair-highlight > td:last-child {
    box-shadow: inset -3px 0 0 #d9a800;
}

/* Inline FY year toggle in the Program column header */
.th-program-inner {
    display: flex;
    align-items: center;
    gap: 0.5rem;
    white-space: nowrap;
}
.th-program-label {
    flex: 1;
    white-space: nowrap;
}
.fy-inline-toggle {
    display: inline-flex;
    border: 1px solid #b0bfb0;
    border-radius: 5px;
    overflow: hidden;
    flex-shrink: 0;
}
.fy-inline-btn {
    padding: 1px 8px;
    background: none;
    border: none;
    border-right: 1px solid #b0bfb0;
    cursor: pointer;
    font-size: 0.78rem;
    font-weight: 500;
    color: #5b6570;
    line-height: 1.5;
    letter-spacing: 0.01em;
}
.fy-inline-btn:last-child {
    border-right: none;
}
.fy-inline-btn.active {
    background: var(--primary-color);
    color: #fff;
}
.fy-inline-btn:not(.active):hover {
    background: #edf2ed;
}

/* Fund-type sub-rows (drill-down inside a multi-fund program/section row) */
.prog-fund-row.hidden {
    display: none;
}
.prog-fund-row, .fund-sub-row {
    background: #f9fafb;
}
.prog-fund-row td, .fund-sub-row td {
    border-top: none;
    padding-top: 3px;
    padding-bottom: 3px;
}
.fund-indent {
    padding-left: 3.3rem !important;
    font-size: 0.90rem;
    color: #444;
}
.fund-indent-deep {
    padding-left: 4.4rem !important;
}
.fund-name-full {
    color: var(--text-muted);
    font-size: 0.86rem;
    margin-left: 4px;
}

/* Fund type info note (e.g. GO Bond explanation) */
.fund-note {
    font-size: 0.79rem;
    font-weight: 500;
    font-style: normal;
    color: #1a5276;
    background: #eaf4fb;
    border: 1px solid #aed6f1;
    border-radius: 4px;
    padding: 1px 6px;
    margin-left: 0.4rem;
    cursor: help;
    white-space: nowrap;
}

/* Data-quality annotation badge (bill-drafting anomalies, rollup notes) */
.data-note {
    display: inline-block;
    font-size: 0.78rem;
    font-weight: 600;
    color: #7d5a00;
    background: #fff8e1;
    border: 1px solid #f0c040;
    border-radius: 3px;
    padding: 0px 4px;
    margin-left: 0.35rem;
    cursor: help;
    white-space: nowrap;
    vertical-align: middle;
    line-height: 1.6;
}
.data-note:hover {
    background: #fff3b0;
    border-color: #e6a800;
}

/* Reading guide callout box */
.reading-guide {
    background: #fff;
    border: 1px solid #d0dbd5;
    border-left: 4px solid var(--primary-color);
    border-radius: 8px;
    padding: 0.85rem 1.1rem;
    margin: 1rem 0 1.25rem;
    font-size: 0.875rem;
    line-height: 1.55;
    box-shadow: 0 1px 4px rgba(0,0,0,0.06);
    max-width: 480px;
}
/* Compact single-row pill with hover tooltip panel (next to search bar).
   Uses the project's sage palette so it sits in-family with the timeline
   pills and header chrome rather than reading as a generic info banner. */
.reading-guide-pill {
    position: relative;
    display: inline-flex;
    align-items: center;
    gap: 0.5rem;
    height: 32px;
    padding: 0 14px;
    margin-left: auto;
    background: linear-gradient(180deg, #eaf2ec 0%, #d8e6dd 100%);
    border: 1px solid #9fc0ad;
    border-radius: 16px;
    font-size: 0.92rem;
    color: #3d5249;
    cursor: help;
    outline: none;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.55),
                0 1px 3px rgba(60, 82, 73, 0.12);
    transition: background 0.18s ease, border-color 0.18s ease,
                box-shadow 0.18s ease, transform 0.18s ease;
}
.reading-guide-pill:hover,
.reading-guide-pill:focus-within {
    background: linear-gradient(180deg, #e0ece4 0%, #cadcd1 100%);
    border-color: #6f9184;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.55),
                0 2px 6px rgba(60, 82, 73, 0.18);
}
.reading-guide-pill .rg-info-svg {
    width: 14px;
    height: 14px;
    flex-shrink: 0;
    color: #5a7468;
    /* Cancel flex gap so the icon sits tight with the label */
    margin-right: -0.25rem;
}
.reading-guide-pill .reading-guide-icon {
    width: 1.2rem;
    height: 1.2rem;
    font-size: 0.79rem;
    background: linear-gradient(135deg, #84a89c 0%, #6f9184 100%);
    color: #fff;
    border-radius: 50%;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    line-height: 1;
    flex-shrink: 0;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.22);
}
.reading-guide-pill strong {
    font-weight: 600;
    font-size: 0.92rem;
    white-space: nowrap;
    letter-spacing: 0.01em;
}
/* Panel text must be allowed to wrap regardless of the pill's nowrap rule */
.reading-guide-panel strong {
    white-space: normal;
}
.reading-guide-panel {
    position: absolute;
    top: calc(100% + 8px);
    right: 0;
    min-width: 0;
    width: min(380px, calc(100vw - 32px));
    max-width: calc(100vw - 32px);
    background: #fff;
    border: 1px solid #d0dbd5;
    border-left: 4px solid var(--primary-color);
    border-radius: 8px;
    padding: 0.85rem 1.1rem;
    box-shadow: 0 4px 14px rgba(0,0,0,0.15);
    font-size: 0.85rem;
    line-height: 1.55;
    color: #444;
    opacity: 0;
    visibility: hidden;
    transform: translateY(-4px);
    transition: opacity 0.15s, transform 0.15s, visibility 0.15s;
    z-index: 1000;
    pointer-events: none;
    white-space: normal;
    /* Never taller than the viewport allows — scroll internally instead of
       forcing the user to scroll the page to read the bottom of the panel. */
    max-height: min(380px, 70vh);
    overflow-y: auto;
    overscroll-behavior: contain;   /* don't bubble scroll to page */
}
/* Slim scrollbar, matching .reason-popover */
.reading-guide-panel::-webkit-scrollbar { width: 8px; }
.reading-guide-panel::-webkit-scrollbar-thumb {
    background: rgba(0, 0, 0, 0.18);
    border-radius: 4px;
}
.reading-guide-pill:hover .reading-guide-panel,
.reading-guide-pill:focus .reading-guide-panel,
.reading-guide-pill:focus-within .reading-guide-panel {
    opacity: 1;
    visibility: visible;
    transform: translateY(0);
    pointer-events: auto;
}
/* Typography reset — the parent pill sets font-weight: 600 on its label,
   which cascades into the panel and makes ALL the panel text render bold.
   Reset to normal weight; <strong> is reserved for true emphasis. */
.reading-guide-panel {
    font-weight: 400;
}
.reading-guide-panel p {
    margin: 0 0 0.7rem;
    font-weight: 400;
    line-height: 1.55;
    color: #3d4a47;
}
.reading-guide-panel p:first-child {
    margin-top: 0;
}
.reading-guide-panel p:last-child {
    margin-bottom: 0;
}
.reading-guide-panel strong {
    font-weight: 600;
    color: #2c3e35;
    white-space: normal;
}
.reading-guide-panel em {
    font-style: italic;
    font-weight: 500;
    color: #6f9184;             /* sage tint for emphasis (in/out direction) */
}
/* Chip definitions — clean two-column grid replacing the dense
   <br>-separated list. Chip on the left, description on the right,
   so each entry reads as a labeled definition rather than a run-on. */
.reading-guide-panel .rg-chips {
    margin-top: 0.85rem;
    padding-top: 0.75rem;
    border-top: 1px solid #e1eae5;
}
.reading-guide-panel .rg-chips-title {
    margin: 0 0 0.6rem;
    font-size: 0.82rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    color: #6f9184;
    line-height: 1.2;
}
.reading-guide-panel .rg-chips-defs {
    display: grid;
    grid-template-columns: auto 1fr;
    gap: 0.5rem 0.75rem;
    margin: 0;
    align-items: center;
}
.reading-guide-panel .rg-chips-defs dt {
    margin: 0;
    text-align: left;
    white-space: nowrap;
}
.reading-guide-panel .rg-chips-defs dd {
    margin: 0;
    color: #4a5e57;
    font-size: 0.85rem;
    line-height: 1.4;
    font-weight: 400;
}
.reading-guide-panel .rg-chips-help {
    margin: 0.75rem 0 0;
    font-size: 0.82rem;
    color: #7a8590;
    font-style: italic;
    font-weight: 400;
    line-height: 1.4;
}
/* Fund-color reference inside the reading-guide panel. The dt column is
   widened (6rem) to accommodate multi-letter chip swatches like "B T W"
   and "U S R X" without wrapping. The dd entries keep the chip colors
   tight against the prose so the user can map color → meaning at a glance. */
.reading-guide-panel .rg-funds {
    margin-top: 0.85rem;
    padding-top: 0.75rem;
    border-top: 1px solid #e1eae5;
}
.reading-guide-panel .rg-funds-defs {
    grid-template-columns: 5.5rem 1fr;
    gap: 0.55rem 0.75rem;
}
.reading-guide-panel .rg-funds-defs dt .fund-chip {
    font-size: 0.78rem;
    letter-spacing: 0.06em;
    padding: 1px 8px;
}
/* On narrow viewports anchor the panel to the screen edges via fixed
   positioning so it can never overflow the viewport on either side. */
@media (max-width: 720px) {
    .reading-guide-panel {
        position: fixed;
        top: auto;
        left: 0.75rem;
        right: 0.75rem;
        min-width: 0;
        max-width: none;
        width: auto;
    }
}
/* Collapsed fund-color section — keeps the default panel short, expands
   only when the user wants the fund-color reference. */
.reading-guide-panel details.rg-funds {
    margin-top: 0.6rem;
    padding-top: 0.5rem;
}
.reading-guide-panel details.rg-funds > summary {
    cursor: pointer;
    font-size: 0.8rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    color: #6f9184;
    list-style: none;
    padding: 0.25rem 0;
    user-select: none;
}
.reading-guide-panel details.rg-funds > summary::-webkit-details-marker {
    display: none;
}
.reading-guide-panel details.rg-funds > summary::before {
    content: '▸ ';
    display: inline-block;
    width: 0.9em;
    transition: transform 0.12s;
}
.reading-guide-panel details.rg-funds[open] > summary::before {
    transform: rotate(90deg);
}
.reading-guide-panel details.rg-funds > .rg-chips-defs {
    margin-top: 0.5rem;
}
.reading-guide-panel .reading-guide-summary {
    margin: 0 0 0.6rem;
    padding-bottom: 0.55rem;
    border-bottom: 1px solid #eee;
    color: #2c3e50;
    font-size: 0.87rem;
}
.reading-guide-header {
    display: flex;
    align-items: center;
    gap: 0.6rem;
}
.reading-guide-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 1.5rem;
    height: 1.5rem;
    background: var(--primary-color);
    color: #fff;
    border-radius: 50%;
    font-size: 0.95rem;
    font-weight: 500;
    flex-shrink: 0;
    line-height: 1;
    user-select: none;
}
.reading-guide-header strong {
    flex: 1;
    font-size: 0.88rem;
    color: #2c3e50;
    letter-spacing: 0.01em;
}
.reading-guide-toggle {
    flex-shrink: 0;
    background: #f0f4f2;
    border: 1px solid #c5d5cc;
    border-radius: 20px;
    color: var(--primary-dark);
    font-weight: 600;
    font-size: 0.74rem;
    padding: 2px 10px;
    cursor: pointer;
    transition: background 0.15s, color 0.15s, border-color 0.15s;
    letter-spacing: 0.03em;
    text-transform: uppercase;
}
.reading-guide-toggle:hover {
    background: var(--primary-color);
    color: #fff;
    border-color: var(--primary-color);
}
.reading-guide-content {
    margin-top: 0.7rem;
    padding-top: 0.65rem;
    padding-left: 2.05rem;
    border-top: 1px solid #e6eeea;
    animation: slideDown 0.18s ease-out;
}
@keyframes slideDown {
    from { opacity: 0; transform: translateY(-4px); }
    to   { opacity: 1; transform: translateY(0); }
}
.reading-guide-summary {
    margin: 0.75rem 0 0;
    color: #444;
    font-size: 0.875rem;
}
.reading-guide-content p {
    margin: 0 0 0.45rem;
    color: #444;
}
.reading-guide-content p:last-child {
    margin-bottom: 0;
}

/* Context banner for cross-navigation */
.context-banner {
    background: #f0f8f4;
    border: 1px solid #d4edda;
    border-radius: 6px;
    padding: 0.75rem 1rem;
    margin-bottom: 1rem;
    font-size: 0.9rem;
}
.context-banner a { font-weight: 500; }

/* CSS tooltip */
.has-tooltip {
    position: relative;
}
.has-tooltip::after {
    content: attr(data-tooltip);
    position: absolute;
    top: calc(100% + 6px);
    left: 0;
    background: var(--primary-dark);
    color: #fff;
    font-size: 0.78rem;
    font-weight: 400;
    text-transform: none;
    letter-spacing: 0;
    line-height: 1.4;
    padding: 6px 10px;
    border-radius: 5px;
    white-space: normal;
    width: 280px;
    box-shadow: 0 3px 8px rgba(0,0,0,0.25);
    pointer-events: none;
    opacity: 0;
    transition: opacity 0.15s;
    z-index: 100;
}
.has-tooltip:hover::after {
    opacity: 1;
}

/* Wider + table-safe tooltip for program-purpose hovers on HB1800 rows.
   Objectives run 1–3 sentences; the default 280px card wraps too tightly
   and the default z-index can lose to sticky header/shadow layers on the
   compare table. */
.prog-purpose-tip::after {
    width: 340px;
    max-width: min(340px, 90vw);
    /* `pre-line` honors the `\n` between bulleted "To [verb]…" goals
       that purposeTooltipAttrs() injects for multi-objective programs.
       For single-objective programs the absent newlines just render as
       a normal wrapped paragraph. */
    white-space: pre-line;
    z-index: 50;
}

/* Program-objective popover trigger (replaces the old .prog-purpose-tip
   data-tooltip pattern).  Same dotted-underline affordance; now routes
   through the shared #reason-popover element for rich formatting. */
.has-purpose {
    cursor: help;
    text-decoration: underline dotted rgba(47, 58, 54, 0.35);
    text-underline-offset: 3px;
}
.has-purpose:focus {
    outline: 2px solid rgba(70, 110, 95, 0.45);
    outline-offset: 1px;
    border-radius: 2px;
}

/* Purpose popover — same card geometry as the change-reason popover but
   with an earthy-green accent instead of the chamber red/blue.  The
   background tint (#f7f9f7) and border colour (#466e5f → 20% opacity)
   read as "reference material" vs the chamber cards which read as
   "political comparison".  Width is narrower (380px) because objectives
   are prose, not two-column comparisons. */
#reason-popover[data-pop-type="purpose"] {
    width: 380px;
    max-width: min(380px, calc(100vw - 24px));
}
.purpose-pop-header {
    background: #f0f4f1;
    border-bottom-color: rgba(70, 110, 95, 0.18);
}
.reason-section.reason-purpose {
    border-left-color: #466e5f;    /* site forest-green — distinct from blue/red */
    background: #fafcfa;
}
.reason-section.reason-purpose .reason-chamber-label {
    color: #466e5f;
    font-size: 0.68rem;
    letter-spacing: 0.1em;
}

/* Objective bullet list — slightly tighter than the change-reason bullets
   since objective sentences are often longer prose.  Line-height bumped
   for readability on multi-line items. */
.purpose-list {
    list-style: none;
    margin: 0;
    padding: 0;
}
.purpose-list li {
    position: relative;
    padding-left: 14px;
    margin: 0 0 6px;
    font-size: 0.86rem;
    line-height: 1.5;
    color: #2f3a36;
}
.purpose-list li::before {
    content: "›";
    position: absolute;
    left: 0;
    color: #466e5f;
    font-weight: 700;
}
.purpose-list li:last-child { margin-bottom: 0; }

/* Single-sentence / short objectives */
.purpose-text {
    margin: 0;
    font-size: 0.86rem;
    line-height: 1.5;
    color: #2f3a36;
}

/* Truncation notice — subdued, italic */
.purpose-truncated {
    margin: 8px 0 0;
    font-size: 0.74rem;
    font-style: italic;
    color: #7a8c85;
}

/* Change-reason tooltip on the HB1800 delta cell.  The text is a
   one-line summary of the legislature's stated reason for changing the
   program's funding (sourced from EXEC + DISAGREE worksheet PDFs).
   When both chambers' reasons exist they're labelled "Senate: …" /
   "House: …" with a blank-line separator — `pre-line` preserves that
   visual break inside the tooltip card. */
/* Change-cell affordance: the dotted underline tells the user there's a
   tooltip on hover, mirroring the program-id objective tooltip pattern. */
.has-reason {
    cursor: help;
    position: relative;
}
.has-reason .figure-chip {
    text-decoration: underline dotted rgba(47, 58, 54, 0.32);
    text-underline-offset: 3px;
}
.has-reason:focus {
    outline: 2px solid rgba(70, 110, 95, 0.45);
    outline-offset: -2px;
    border-radius: 4px;
}

/* Inline divergence pill — sits next to the change figure when HD1 ≠ SD1.
   Compact so it doesn't blow out the column; chamber-tinted so the eye
   picks up "the chambers disagree here" before reading the number. */
.hd-sd-pill {
    display: inline-flex;
    align-items: baseline;
    gap: 3px;
    margin-left: 6px;
    padding: 1px 6px 2px;
    font-size: 0.72rem;
    font-weight: 600;
    line-height: 1.25;
    border-radius: 999px;
    border: 1px solid transparent;
    white-space: nowrap;
    vertical-align: middle;
    /* Default (positive = Senate added vs House) — Senate blue */
    background: rgba(44, 82, 130, 0.10);
    color: #2c5282;
    border-color: rgba(44, 82, 130, 0.28);
}
.hd-sd-pill.neg {
    /* Senate cut vs House — House red so the "House preserved more" reading
       comes through.  Both chamber colors live on this single pill so users
       don't have to learn two separate badges. */
    background: rgba(155, 44, 44, 0.10);
    color: #9b2c2c;
    border-color: rgba(155, 44, 44, 0.28);
}
.hd-sd-pill-meta {
    font-weight: 500;
    font-size: 0.66rem;
    opacity: 0.75;
    letter-spacing: 0.03em;
}

/* ===== Reason popover (the formatted hover card on change cells) ===== */
.reason-popover {
    position: absolute;
    z-index: 1000;
    width: 420px;
    max-width: min(420px, calc(100vw - 24px));
    /* Hard ceiling: never taller than the viewport.  The JS positioner
       sets a tighter max-height inline when the available slot is even
       smaller; this rule is the safety net. */
    max-height: calc(100vh - 24px);
    background: #ffffff;
    border: 1px solid rgba(47, 58, 54, 0.18);
    border-radius: 8px;
    box-shadow: 0 10px 28px rgba(20, 30, 28, 0.18),
                0 2px 6px rgba(20, 30, 28, 0.10);
    padding: 0;
    font-size: 0.88rem;
    line-height: 1.45;
    color: #2f3a36;
    /* Internal scroll when content exceeds max-height.  `overflow-y: auto`
       supersedes the previous `overflow: hidden` (which was clipping the
       bottom of long lists).  The rounded-corner safety for section bars
       is preserved by `overflow-x: hidden`. */
    overflow-y: auto;
    overflow-x: hidden;
    overscroll-behavior: contain;   /* don't bubble scroll to page */
}
/* Slimmer scrollbar so the card doesn't look like a code editor. */
.reason-popover::-webkit-scrollbar { width: 8px; }
.reason-popover::-webkit-scrollbar-thumb {
    background: rgba(47, 58, 54, 0.22);
    border-radius: 4px;
}
.reason-popover::-webkit-scrollbar-thumb:hover {
    background: rgba(47, 58, 54, 0.40);
}
.reason-pop-header {
    padding: 10px 14px 8px;
    border-bottom: 1px solid rgba(47, 58, 54, 0.10);
    background: #f7f8f6;
    font-size: 0.78rem;
    letter-spacing: 0.02em;
    color: #4a5550;
}
.reason-pop-header strong {
    color: #1f2a26;
    margin-right: 6px;
    font-weight: 700;
}
.reason-pop-prog-name {
    font-weight: 500;
}
.reason-section {
    padding: 10px 14px 12px 14px;
    border-left: 4px solid transparent;
    background: #ffffff;
}
.reason-section + .reason-section {
    border-top: 1px solid rgba(47, 58, 54, 0.10);
}
.reason-section.reason-house {
    border-left-color: #9b2c2c;     /* warm "House" red */
}
.reason-section.reason-senate {
    border-left-color: #2c5282;     /* cool "Senate" blue */
}
.reason-chamber-label {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 8px;
    font-size: 0.7rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    margin-bottom: 6px;
}
.reason-house .reason-chamber-label { color: #9b2c2c; }
.reason-senate .reason-chamber-label { color: #2c5282; }
.reason-amt {
    font-size: 0.78rem;
    font-weight: 700;
    letter-spacing: 0;
    text-transform: none;
    padding: 1px 7px 2px;
    border-radius: 999px;
    background: rgba(0, 0, 0, 0.04);
    color: #1f2a26;
}
/* Net delta chip: resolves "Reduce funds; Add funds" contradictions by
   surfacing the signed net vs the other chamber inline in the label row.
   Sits after the amount badge, right-aligned by the flex parent. */
.reason-net {
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0;
    text-transform: none;
    padding: 1px 6px 2px;
    border-radius: 999px;
    margin-left: auto;   /* push to the far right of the label row */
}
.reason-net.pos {
    background: rgba(44, 82, 130, 0.12);
    color: #2c5282;
    border: 1px solid rgba(44, 82, 130, 0.28);
}
.reason-net.neg {
    background: rgba(155, 44, 44, 0.10);
    color: #9b2c2c;
    border: 1px solid rgba(155, 44, 44, 0.24);
}
.reason-list {
    list-style: none;
    margin: 0;
    padding: 0;
}
.reason-list li {
    position: relative;
    padding-left: 14px;
    margin: 2px 0 4px;
    color: #2f3a36;
}
.reason-list li::before {
    content: "•";
    position: absolute;
    left: 0;
    top: 0;
    color: rgba(47, 58, 54, 0.55);
    font-weight: 700;
}
.reason-list li:last-child { margin-bottom: 0; }

/* Export button row below tables */
.table-export-row {
    display: flex;
    justify-content: flex-end;
    margin: 0.5rem 0 1.5rem;
}

/* Stat tags for stats bar and summary line */
.stat-tag {
    display: inline-block;
    padding: 3px 11px;
    border-radius: 12px;
    font-size: 0.94rem;
    margin: 2px 3px;
    border: 1px solid transparent;
}
.stat-tag-neutral  { background: #f0f0f0; color: #444; border-color: #ddd; }
.stat-tag-positive { background: #e8f5e9; color: #2e7d32; border-color: #c8e6c9; }
.stat-tag-negative { background: #fce4ec; color: #c62828; border-color: #f8bbd0; }
.stat-tag-added    { background: #e3f2fd; color: #1565c0; border-color: #bbdefb; }
.stat-tag-removed  { background: #fff3e0; color: #e65100; border-color: #ffe0b2; }

.draft-stats { display: flex; flex-wrap: wrap; gap: 2px; margin: 0.4rem 0 0.6rem; }
.search-summary { display: flex; flex-wrap: wrap; align-items: center; gap: 4px; margin-bottom: 0.75rem; }

.filter-inline {
    display: inline-block;
    height: 31px;
    padding: 2px 9px;
    font-size: 0.90rem;
    border: 1px solid #ddd;
    border-radius: 12px;
    background: #f8f8f8;
    cursor: pointer;
    width: auto;
}
.items-filter-tag {
    position: relative;
    cursor: pointer;
    padding-right: 0.6em;
}
.items-filter-select {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    opacity: 0;
    cursor: pointer;
}
.search-inline {
    display: inline-block;
    height: 31px;
    padding: 2px 11px;
    font-size: 0.90rem;
    border: 1px solid #ddd;
    border-radius: 12px;
    width: 176px;
}

/* ===== Unified search + reading-guide row ===== */
.search-row {
    display: flex;
    align-items: center;
    gap: 1rem;
    flex-wrap: wrap;
    margin-bottom: 0.75rem;
}
.search-row .search-summary {
    margin: 0;
    flex-shrink: 0;
}

/* ===== Highlights section (below Total) ===== */
.highlights-section {
    margin-top: 1.5rem;
    margin-bottom: 0.5rem;
}
.highlights-section .card-section-total {
    margin-bottom: 0.5rem;
}
.highlights-sub {
    font-weight: 400;
    font-size: 0.72rem;
    color: var(--text-muted);
    text-transform: none;
    letter-spacing: 0;
    margin-left: 0.4rem;
}
.highlights-section .highlights-list {
    list-style: none;
    margin: 0;
    padding: 0.5rem 0.9rem;
    background: #fafbfa;
    border: 1px solid #e5e7eb;
    border-radius: 6px;
}
.highlights-section .highlight-item {
    display: flex;
    align-items: baseline;
    gap: 0.6rem;
    padding: 0.4rem 0;
    border-bottom: 1px dotted #e5e7eb;
    font-size: 0.92rem;
    line-height: 1.45;
    color: #333;
}
.highlights-section .highlight-item:last-child { border-bottom: none; }
.highlight-bullet {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 1.1rem;
    height: 1.1rem;
    flex-shrink: 0;
    font-weight: 800;
    font-size: 0.95rem;
    border-radius: 50%;
    color: #fff;
    line-height: 1;
    align-self: center;
}
.highlight-bullet.positive { background: #1e7e34; }
.highlight-bullet.negative { background: #c62828; }
.highlight-text { flex: 1; }
.highlight-amt {
    font-weight: 700;
    white-space: nowrap;
    font-variant-numeric: tabular-nums;
}
.highlight-amt.positive { color: #1e7e34; }
.highlight-amt.negative { color: #c62828; }
.highlight-target {
    font-weight: 600;
    color: #2c3e50;
}
.highlight-section {
    font-weight: 400;
    color: #666;
    font-size: 0.88em;
}
.highlight-empty {
    color: var(--text-muted);
    font-style: italic;
    padding: 0.3rem 0;
    font-size: 0.85rem;
}
.highlight-item.highlight-hidden {
    display: none;
}
.highlight-more-btn {
    background: none;
    border: none;
    padding: 0.3rem 0 0.1rem;
    font-size: 0.82rem;
    font-weight: 600;
    color: var(--primary-color);
    cursor: pointer;
    letter-spacing: 0.01em;
    display: block;
    width: 100%;
    text-align: left;
}
.highlight-more-btn:hover {
    text-decoration: underline;
}

/* ===== About Page ===== */
.about-page {
    max-width: 700px;
}
.about-hero {
    margin-bottom: 2rem;
    padding-bottom: 1.5rem;
    border-bottom: 2px solid var(--primary-color);
}
.about-hero h2 {
    margin-bottom: 0.5rem;
    font-size: var(--fs-2xl);
    color: var(--heading-color);
}
.about-lead {
    font-size: 1.05rem;
    color: #444;
    line-height: 1.7;
}
.about-section {
    margin-bottom: 2rem;
    padding-bottom: 1.5rem;
    border-bottom: 1px solid #e8e8e8;
}
.about-section:last-of-type {
    border-bottom: none;
}
.about-section h3 {
    font-size: var(--fs-xl);
    color: var(--heading-color);
    margin-bottom: 0.6rem;
    margin-top: 0;
}
.about-section-process h4 {
    font-weight: 700;
    color: #333;
    margin: 1.2rem 0 0.3rem;
    text-transform: uppercase;
    letter-spacing: 0.4px;
    font-size: 0.78rem;
}
.about-section p {
    color: #555;
    line-height: 1.7;
    margin: 0 0 0.5rem;
}
.about-summary {
    margin-top: 1.2rem !important;
    padding: 0.75rem 1rem;
    background: #f0faf5;
    border-left: 3px solid var(--primary-color);
    border-radius: 0 6px 6px 0;
    font-size: 0.95rem;
    color: #2e4a30 !important;
}
.about-page ul {
    color: #555;
    line-height: 1.9;
    padding-left: 1.25rem;
    margin: 0;
}
.about-page .button {
    margin-top: 1rem;
    display: inline-block;
}

/* ===========================================================================
   Tax Calculator Page ("Where Do My Taxes Go?")
   =========================================================================== */

.nav-link-calc {
    color: #a8e6cf;
    display: flex;
    flex-direction: column;
    align-items: center;
    line-height: 1.2;
}
.nav-link-calc:hover, .nav-link-calc.active {
    color: #a8e6cf;
    background-color: rgba(168, 230, 207, 0.18);
}

.tax-calc-page {
    max-width: 1100px;
    margin: 0 auto;
}
.tax-calc-page > h2 {
    margin-top: 0;
}
.tax-calc-page .page-desc {
    color: #555;
    margin-bottom: 24px;
}

.tax-input-card {
    background: #fff;
    border: 1px solid #e0e5e8;
    border-radius: 10px;
    padding: 24px;
    box-shadow: 0 2px 6px rgba(0,0,0,0.06);
    max-width: 560px;
    margin: 0 auto 24px;
}
.tax-input-label {
    display: block;
    font-weight: 600;
    color: #2e3e2e;
    font-size: 0.95rem;
    margin-bottom: 10px;
}
.input-with-prefix {
    display: flex;
    align-items: center;
    border: 2px solid #cfd8dc;
    border-radius: 8px;
    padding: 0 12px;
    background: #fafbfc;
    transition: border-color 0.15s;
}
.input-with-prefix:focus-within {
    border-color: #4c78a8;
    background: #fff;
}
.input-with-prefix .prefix {
    font-size: 1.4rem;
    color: #6a6a6a;
    padding-right: 6px;
    font-weight: 500;
}
.input-with-prefix input {
    flex: 1;
    border: none;
    background: transparent;
    font-size: 1.4rem;
    font-weight: 600;
    padding: 10px 0;
    outline: none;
    color: #234;
    font-variant-numeric: tabular-nums;
    width: 100%;
}
.input-with-prefix.small {
    padding: 0 10px;
}
.input-with-prefix.small .prefix { font-size: 1rem; }
.input-with-prefix.small input { font-size: 1rem; padding: 6px 0; }

.tax-input-card .action-link {
    display: inline-block;
    margin-top: 12px;
    font-size: 0.88rem;
    color: #4c78a8;
    cursor: pointer;
    background: none;
    border: none;
    padding: 0;
    text-decoration: underline;
}
.tax-input-card .action-link:hover { color: #2a5580; }

.tax-helper {
    margin-top: 14px;
    padding: 14px;
    background: #f5f8fa;
    border-radius: 6px;
    border: 1px solid #e0e8ec;
}
.tax-helper .helper-row {
    display: flex;
    gap: 12px;
    align-items: flex-end;
    flex-wrap: wrap;
}
.tax-helper label {
    display: flex;
    flex-direction: column;
    gap: 4px;
    font-size: 0.82rem;
    color: #456;
    flex: 1;
    min-width: 140px;
}
.tax-helper select {
    padding: 8px;
    border: 1px solid #cfd8dc;
    border-radius: 6px;
    background: #fff;
    font-size: 0.92rem;
}
.tax-helper button {
    padding: 8px 16px;
    white-space: nowrap;
}
.helper-note {
    font-size: 0.78rem;
    color: #7a7a7a;
    margin: 10px 0 0;
    font-style: italic;
}

.tax-calc-page .fy-toggle {
    margin: 0 auto 16px;
    justify-content: center;
}

.calc-note {
    font-size: 0.82rem;
    color: #6a6a6a;
    font-style: italic;
    margin: 8px 0 20px;
    padding: 10px 14px;
    background: #fffbe6;
    border-left: 3px solid #e0b341;
    border-radius: 0 4px 4px 0;
}

.treemap-breadcrumb {
    font-size: 0.9rem;
    margin-bottom: 8px;
    color: #456;
}
.treemap-breadcrumb .crumb-root,
.treemap-breadcrumb .crumb-root-active {
    font-weight: 500;
}
.treemap-breadcrumb [data-crumb="root"] {
    cursor: pointer;
    color: #4c78a8;
    text-decoration: underline;
}
.treemap-breadcrumb [data-crumb="root"]:hover { color: #2a5580; }
.treemap-breadcrumb .crumb-sep {
    margin: 0 8px;
    color: var(--text-muted);
}
.treemap-breadcrumb .crumb-current {
    color: #234;
    font-weight: 600;
}

.treemap-container {
    position: relative;
    width: 100%;
    max-width: 1000px;
    height: 500px;
    margin: 0 auto 8px;
    background: #f5f8fa;
    border-radius: 6px;
    padding: 4px;
}
.treemap-hint {
    text-align: center;
    font-size: 0.78rem;
    color: #7a7a7a;
    font-style: italic;
    margin: 0 0 24px;
}

#tax-detail-table .tax-dept-row {
    cursor: pointer;
    transition: background-color 0.1s;
}
#tax-detail-table .tax-dept-row:hover { background-color: #f5f8fa; }
#tax-detail-table .tax-dept-row .dept-arrow {
    color: #5a7080;
    font-size: 0.75rem;
    display: inline-block;
    width: 12px;
}
#tax-detail-table .tax-prog-row {
    background-color: #fafbfc;
    font-size: 0.88rem;
}
#tax-detail-table .tax-prog-row td.detail-indent {
    padding-left: 2rem;
    color: #456;
}

@media (max-width: 600px) {
    .treemap-container { height: 380px; }
    .tax-helper .helper-row { flex-direction: column; align-items: stretch; }
    .tax-helper label { min-width: 0; }
}

/* ── Program search bar ───────────────────────────────────── */
.table-search-bar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: wrap;
    gap: 0.75rem;
    margin-bottom: 0.5rem;
}
.table-search-bar h3 { margin: 0; }

.search-input-wrap {
    display: flex;
    align-items: center;
    background: #fff;
    border: 1.5px solid var(--border-color);
    border-radius: 8px;
    padding: 0.385rem 0.825rem;
    gap: 0.5rem;
    min-width: 264px;
    max-width: 396px;
    flex: 1 1 264px;
    transition: border-color 0.15s;
}
.search-input-wrap:focus-within {
    border-color: var(--primary-color);
    box-shadow: 0 0 0 3px rgba(108,142,127,0.15);
}
.search-icon { font-size: 0.99rem; color: var(--text-muted); flex-shrink: 0; }
.search-input-wrap input[type="text"] {
    border: none;
    outline: none;
    background: transparent;
    font-size: 1.05rem;
    color: var(--text-color);
    width: 100%;
    min-width: 0;
}
.search-clear {
    background: none;
    border: none;
    cursor: pointer;
    color: var(--text-muted);
    font-size: 0.88rem;
    padding: 0 2px;
    line-height: 1;
    display: inline-flex;
    align-items: center;
    flex-shrink: 0;
    transition: color 0.1s;
}
.search-clear:hover { color: #333; }

.search-status {
    font-size: 0.935rem;
    color: #555;
    margin-bottom: 0.5rem;
    font-style: italic;
}

mark.search-highlight {
    background: #fff3b0;
    color: inherit;
    border-radius: 2px;
    padding: 0 1px;
}

.empty-search {
    text-align: center;
    padding: 2rem 1rem;
    color: #777;
    font-style: italic;
}

/* Dept header rows in search mode (no expand arrow) */
.tax-dept-row.search-dept-header { cursor: default; }
.tax-dept-row.search-dept-header:hover { background: #f9f9f9; }

/* ── Tax calculator summary cards ─────────────────────────── */
.tax-summary-grid {
    grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
    gap: 0.75rem;
    margin: 1rem 0;
}
.tax-summary-grid .summary-card {
    padding: 0.85rem 1rem;
}
.tax-summary-grid .summary-card .amount {
    font-size: 1.3rem;
    margin-bottom: 0.2rem;
}
.tax-summary-grid .summary-card .label {
    font-size: 0.75rem;
}

.card-sub {
    font-size: 0.75rem;
    color: var(--text-muted);
    margin-top: 0.25rem;
    font-style: italic;
}
.summary-card.empty-state .amount {
    color: var(--text-muted);
}
.summary-card.empty-state .card-sub {
    color: var(--primary-color);
    font-style: normal;
    font-weight: 500;
}

/* ── Dept summary card progress bar ──────────────────────── */
.dept-summary-card {
    display: flex;
    flex-direction: column;
    gap: 0.2rem;
}
.dept-pct-row {
    margin-top: 0.5rem;
    display: flex;
    flex-direction: column;
    gap: 0.25rem;
}
.dept-bar-wrap {
    width: 100%;
    height: 6px;
    background: #e8e8e8;
    border-radius: 3px;
    overflow: hidden;
}
.dept-bar {
    height: 100%;
    background: var(--primary-color);
    border-radius: 3px;
    transition: width 0.4s ease;
    max-width: 100%;
}
.dept-pct-label {
    font-size: 0.72rem;
    color: var(--text-muted);
    text-align: right;
}

/* ── Tax calc input restructure ───────────────────────────── */
.income-inputs-row {
    display: flex;
    gap: 1rem;
    flex-wrap: wrap;
    margin-bottom: 1.25rem;
}
.income-field {
    flex: 2 1 200px;
    display: flex;
    flex-direction: column;
    gap: 0.3rem;
}
.filing-field {
    flex: 1 1 160px;
    display: flex;
    flex-direction: column;
    gap: 0.3rem;
}
.income-field label,
.filing-field label {
    font-weight: 600;
    font-size: 0.9rem;
    color: var(--text-color);
}
.filing-field select {
    padding: 0.6rem 0.75rem;
    border: 1.5px solid var(--border-color);
    border-radius: 8px;
    font-size: 0.95rem;
    background: #fff;
    color: var(--text-color);
}
.tax-paid-row {
    display: flex;
    flex-direction: column;
    gap: 0.3rem;
    margin-bottom: 0.75rem;
}
.tax-paid-row .tax-input-label {
    font-weight: 600;
    font-size: 0.9rem;
    color: var(--text-color);
}
.auto-label {
    font-weight: 400;
    font-size: 0.8rem;
    color: var(--text-muted);
    margin-left: 0.25rem;
}

/* ── Compare page hero card ──
   Wraps the page title + description in a lifted white card that
   overlaps the header's curved bottom edge for a magazine-cover effect.
   A sage left accent bar ties the card visually to the header band. */
.compare-page-hero {
    background: #ffffff;
    border-radius: 14px;
    padding: 1.4rem 1.6rem 1.3rem 1.85rem;
    margin: -3.2rem 0 1.5rem;            /* negative top → overlap the curve */
    border: 1px solid rgba(16, 24, 40, 0.06);
    box-shadow:
        0 1px 2px rgba(16, 24, 40, 0.04),
        0 8px 24px rgba(16, 24, 40, 0.08);
    position: relative;
    overflow: hidden;
}
/* Sage left accent bar — draws the eye and ties to the header band. */
.compare-page-hero::before {
    content: '';
    position: absolute;
    left: 0; top: 0; bottom: 0;
    width: 4px;
    background: linear-gradient(to bottom, #6c8e7f, #8aa595);
}
/* ── Compare page description ── */
/* (.compare-page-titlerow rules removed — the markup they targeted is no
   longer rendered anywhere in the app.) */
/* Title-area variant — sage palette, gentle gradient + lift so the pill
   reads as an inviting affordance rather than a flat info badge.
   Sized compactly so it slots beside the search input without crowding. */
.compare-info-icon.reading-guide-pill {
    height: 30px;
    padding: 0 13px;
    font-size: 0.92rem;
    font-weight: 600;
    background: linear-gradient(180deg, #eaf2ec 0%, #d6e4dc 100%);
    border: 1px solid #9fc0ad;
    color: #3d5249;
    margin-left: 0;
    cursor: help;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.55),
                0 1px 3px rgba(60, 82, 73, 0.12);
}
.compare-info-icon.reading-guide-pill:hover,
.compare-info-icon.reading-guide-pill:focus-within {
    background: linear-gradient(180deg, #dfeae3 0%, #c8d9d0 100%);
    border-color: #6f9184;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.55),
                0 2px 6px rgba(60, 82, 73, 0.18);
}
.compare-page-desc {
    font-size: 1.09rem;
    line-height: 1.65;
    color: #4a5568;
    max-width: 780px;
    margin: 0 0 1rem;
}

/* ── Unified view-controls bar (single flex row) ── */
/* Controls card — white card on tinted page, soft two-layer shadow */
.compare-controls-bar {
    display: flex;
    flex-direction: column;
    background: #ffffff;
    border: 1px solid rgba(16, 24, 40, 0.06);
    border-radius: 12px;
    padding: 0;
    margin-bottom: 1.25rem;
    box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04),
                0 1px 3px rgba(16, 24, 40, 0.06);
}
/* (The pinned-shadow ::after pseudo-element used to sit at bottom: -1px
   and stack visually below the card's own border + box-shadow, creating
   a visible double-line on the bottom edge.  The card's existing box-shadow
   already provides enough depth, so the extra gradient was removed.)     */
/* --compare-bar-h is set by JS (ResizeObserver) so the table header and
   sticky dept/fund rows can account for the pinned controls bar height. */
.compare-page {
    --compare-bar-h: 0px;
    --compare-search-h: 0px;
    --compare-thead-h: 39px;
}
.compare-page .data-table th {
    top: calc(var(--compare-bar-h, 0px) + var(--compare-search-h, 0px));
}
/* Tighter column padding so the default 2-stage table (Program · Section ·
   Fund · two amounts · Change) fits the card without a horizontal scroll at
   common laptop widths. The amount columns are sized by the perm/temp
   sub-line, which we keep readable — so the gutter is the lever. The first
   column (Program, widest) keeps a roomier left inset for breathing room. */
.compare-page .data-table th,
.compare-page .data-table td {
    padding-left: 7px;
    padding-right: 7px;
}
.compare-page .data-table th:first-child,
.compare-page .data-table td:first-child {
    padding-left: 13px;
}
.compare-page .dept-group-row.open td,
.compare-page .fund-group-row.open td {
    /* Subtract 1px so the open row's sticky top sits 1px BEHIND the thead's
       bottom edge. Sub-pixel rounding can otherwise leave a hairline gap
       through which scrolling content shows. The thead's z-index (2) is
       higher than the open row (1), so the thead's last pixel stays on top
       — the 1px overlap is invisible but plugs the hairline reliably. */
    top: calc(var(--compare-bar-h, 0px) + var(--compare-search-h, 0px) + var(--compare-thead-h, 39px) - 1px);
}
/* Scroll pane for the comparison table — TWO MODES, toggled by JS
   (syncTableScrollMode) per render:

   Default (table fits the card): the pane is a plain in-flow wrapper with no
   overflow of its own. The page is the only vertical scroller — no
   nested-scroll trap capturing the wheel mid-page — and the thead/open rows
   pin below the sticky search row via the page-level rules above.

   .is-wide (3–4 stages on; position columns push the table wider than the
   card): the pane becomes its own scroll context containing both axes, with
   thead/open rows pinning to the pane's top instead. ANY overflow value other
   than visible would create a sticky containment that silently breaks the
   page-level pinning, which is why this is a JS-measured class and not a
   blanket overflow-x rule. */
.compare-page .table-scroll.is-wide {
    overflow: auto;
    max-height: calc(100vh - var(--compare-search-h, 56px) - 16px);
}
.compare-page .table-scroll.is-wide .data-table th {
    top: 0;
}
.compare-page .table-scroll.is-wide .dept-group-row.open td,
.compare-page .table-scroll.is-wide .fund-group-row.open td {
    top: calc(var(--compare-thead-h, 39px) - 1px);
}
/* Slim, unobtrusive scrollbars for the pane */
.compare-page .table-scroll.is-wide::-webkit-scrollbar { height: 10px; width: 10px; }
.compare-page .table-scroll.is-wide::-webkit-scrollbar-thumb {
    background: rgba(16, 24, 40, 0.22);
    border-radius: 6px;
}
.compare-page .table-scroll.is-wide::-webkit-scrollbar-track { background: transparent; }
/* Jump targets (dept links, FY-swap anchor restore, project rows) land below
   the sticky chrome instead of underneath it — applies to every
   scrollIntoView call site at once. */
.compare-page .dept-group-row,
.compare-page .dept-detail-row,
.compare-page .fund-group-row,
.compare-page .project-dept-row {
    scroll-margin-top: calc(var(--compare-search-h, 56px) + var(--compare-thead-h, 39px) + 10px);
}
/* Sticky search/filter row pinned immediately below the controls card */
.compare-page > .search-row {
    position: sticky;
    top: var(--compare-bar-h, 0px);
    z-index: 9;
    background: #fafbfc;
    margin: 0 -2rem;
    padding: 0.5rem 2rem 0.6rem;
    box-shadow: 0 1px 0 rgba(16, 24, 40, 0.04);
}
.compare-page > .search-row .search-summary {
    margin-bottom: 0;
}
/* Scope strip — floats above the sticky timeline card and scrolls away with the page */
.compare-scope-row {
    display: flex;
    justify-content: flex-start;
    align-items: center;
    gap: 0.55rem;
    padding: 4px 4px 10px;
}
.compare-scope-label {
    font-size: 0.78rem;
    font-weight: 500;
    color: #8a9199;
    letter-spacing: 0.02em;
    text-transform: uppercase;
}
/* Timeline sits inside the sticky card with its own internal padding */
.compare-controls-bar > .compare-timeline {
    padding: 14px 18px 16px;
}
/* Page tint only on the compare page — makes the white card pop.
   Extends edge-to-edge by consuming #app's 2rem padding with negative margin,
   then re-applying its own padding so content stays in place. */
.compare-page {
    background: #fafbfc;
    margin: -2rem -2rem 0;
    padding: 1.5rem 2rem 2rem;
    min-height: calc(100vh - 180px);
}

/* Shared white-card treatment — table sections echo the controls card so
   the whole page reads as one lifted-card system on the tinted page. */
.compare-page #draft-results,
.compare-page .projects-section,
.compare-page #fund-detail-section {
    background: #ffffff;
    border: 1px solid rgba(16, 24, 40, 0.06);
    border-radius: 12px;
    box-shadow: 0 1px 2px rgba(16, 24, 40, 0.04),
                0 1px 3px rgba(16, 24, 40, 0.06);
    padding: 20px 22px;
    margin-bottom: 1.25rem;
}
/* Hide empty fund-detail wrapper so it doesn't render as an empty card */
.compare-page #fund-detail-section:empty {
    display: none;
}
/* ── FY segmented control: pill with sliding sage thumb ── */
.fy-seg-ctrl {
    display: inline-flex;
    position: relative;
    background: #f1f3f5;
    border-radius: 999px;
    padding: 3px;
    font-size: 0.86rem;
    line-height: 1;
    align-self: center;
    isolation: isolate;
}
.fy-seg-ctrl::before {
    content: '';
    position: absolute;
    top: 2px;
    bottom: 2px;
    left: 2px;
    width: calc(50% - 2px);
    background: rgba(30, 126, 52, 0.10);
    border-radius: 999px;
    transition: transform 220ms cubic-bezier(0.4, 0, 0.2, 1);
    z-index: 0;
}
.fy-seg-ctrl[data-active="27"]::before {
    transform: translateX(100%);
}
.fy-seg-ctrl button {
    position: relative;
    z-index: 1;
    border: 0;
    background: transparent;
    padding: 7px 16px;
    font-size: inherit;
    font-weight: 500;
    color: #6b7280;
    cursor: pointer;
    transition: color 180ms ease;
    line-height: 1;
    border-radius: 999px;
}
.fy-seg-ctrl button.active {
    color: #1e7e34;
    font-weight: 600;
}
.fy-seg-ctrl button:hover:not(.active) {
    color: #374151;
}
/* Single-button variant (FY27-only): no thumb animation needed */
.fy-seg-ctrl:has(button:only-child)::before {
    display: none;
}

/* ── Compare timeline (Gov's Request → HD1 → SD1 → Net Change) ──
   Five-column CSS grid. Col 1 is a left rail for the expand caret and
   the Operating/Capital row labels; cols 2–5 are Gov/HD1/SD1/Net. Rows
   are: labels → dots → totals → operating breakdown → capital breakdown.
   Breakdown rows collapse via [hidden] when the caret is closed. */
.compare-timeline {
    display: grid;
    /* 9 columns: [flex-spacer] [left-rail] [gov] [hd1] [sd1] [cd1] [enacted] [net] [flex-spacer]
       Flex spacers absorb the slack on both edges so the dot+totals group
       stays centered. The tl-band uses grid-column: 1 / -1 to span all 8
       so the zebra tint extends edge-to-edge.
       Column 2 is fixed-width so the "Operating"/"Capital" labels (visible
       when the breakdown is open) don't widen it and shift the row sideways.
       The 158px is sized to fit "Operating" plus its share-of-total chip
       and the 14px+14px horizontal padding without overflowing the band. */
    grid-template-columns: 1fr 158px repeat(5, minmax(118px, 158px)) minmax(130px, max-content) 1fr;
    grid-template-rows: auto auto auto auto auto auto;
    column-gap: 0;
    row-gap: 0;
    padding: 4px 0 0;
    align-items: center;
}
/* Explicit vertical spacing between rows 1–3 (row-gap is 0 so that the
   Op/Cap zebra bands can be contiguous with no transparent stripe). */
.compare-timeline > [data-row="dots"]   { margin-top: 6px; }
.compare-timeline > [data-row="totals"] { margin-top: 6px; }
/* Grid placement driven by data attributes on cell children */
.compare-timeline > [data-col="gov"] { grid-column: 3; }
.compare-timeline > [data-col="hd1"] { grid-column: 4; }
.compare-timeline > [data-col="sd1"] { grid-column: 5; }
.compare-timeline > [data-col="cd1"] { grid-column: 6; }
.compare-timeline > [data-col="enacted"] { grid-column: 7; }
.compare-timeline > [data-col="net"] { grid-column: 8; }
.compare-timeline > [data-row="labels"] { grid-row: 1; }
.compare-timeline > [data-row="dots"]   { grid-row: 2; }
.compare-timeline > [data-row="totals"] { grid-row: 3; }
.compare-timeline > [data-row="subs"]   { grid-row: 4; }
.compare-timeline > [data-row="op"]     { grid-row: 5; }
.compare-timeline > [data-row="cap"]    { grid-row: 6; }
/* Left-rail corner cells — col 2 (col 1 is flex spacer) */
.compare-timeline > .tl-corner { grid-column: 2; }
.compare-timeline > .tl-corner-labels { grid-row: 1; }
.compare-timeline > .tl-corner-dots   { grid-row: 2; }
.compare-timeline > .tl-corner-caret {
    grid-row: 3;
    display: flex;
    align-items: center;
    justify-content: flex-end;
    padding-right: 10px;
}
/* Small left-margin on the Net column to separate it visually from SD1 */
.compare-timeline > [data-col="net"] { margin-left: 4px; }
/* Dots row */
.tl-dot-row {
    display: flex;
    align-items: center;
    width: 100%;
    height: 23px;
    justify-content: center;
}
.tl-seg {
    flex: 1;
    height: 2px;
    background: #c2cdc7;
    position: relative;
    transition: background 0.15s;
}
/* Segment joins two ADJACENT active stages (JS toggles the class) — sage to
   show the hand-off is part of the active comparison. The sage layer is a
   scaleX overlay so it sweeps in/out; each half-segment grows out of the dot
   it's attached to, so a newly-joined pair reads as the two stages reaching
   toward each other and meeting in the middle. */
.tl-seg::after {
    content: '';
    position: absolute;
    inset: 0;
    background: #8fae9f;
    transform: scaleX(0);
    transition: transform 0.3s ease;
}
.tl-seg-after::after  { transform-origin: left; }
.tl-seg-before::after { transform-origin: right; }
.tl-seg.tl-seg-on::after {
    transform: scaleX(1);
}
/* First column hides seg-before; Enacted hides seg-after (no line into Net) */
.compare-timeline > [data-col="gov"] .tl-seg-before { visibility: hidden; }
.compare-timeline > [data-col="enacted"] .tl-seg-after { visibility: hidden; }
.tl-dot {
    position: relative;
    width: 22px;
    height: 22px;
    border-radius: 50%;
    background: #5a7468;
    flex-shrink: 0;
    border: 2px solid #5a7468;
    transition: background 0.15s, border-color 0.15s;
}
/* Pop-in when a stage becomes active: the animation declaration only applies
   while the column is NOT inactive, so re-checking a stage re-attaches the
   animation and replays it (and all active dots pop once on page load). */
@keyframes tl-dot-pop {
    0%   { transform: scale(0.65); }
    60%  { transform: scale(1.14); }
    100% { transform: scale(1); }
}
.compare-timeline:not(.col-gov-inactive) > [data-col="gov"] .tl-dot,
.compare-timeline:not(.col-hd1-inactive) > [data-col="hd1"] .tl-dot,
.compare-timeline:not(.col-sd1-inactive) > [data-col="sd1"] .tl-dot,
.compare-timeline:not(.col-cd1-inactive) > [data-col="cd1"] .tl-dot,
.compare-timeline:not(.col-enacted-inactive) > [data-col="enacted"] .tl-dot {
    animation: tl-dot-pop 0.3s ease-out;
}
/* Checkmark on active dots */
.tl-dot::after {
    content: '✓';
    position: absolute;
    inset: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 13px;
    font-weight: 900;
    color: #fff;
    line-height: 1;
}
.tl-label {
    font-size: 0.98rem;
    font-weight: 600;
    text-align: center;
    color: #2c3e50;
    line-height: 1.25;
    transition: color 0.15s, text-decoration 0.15s;
    white-space: nowrap;
    min-height: 2em;
    display: flex;
    align-items: flex-end;
    justify-content: center;
}
.tl-label.has-tooltip {
    cursor: help;
}
/* Dotted underline on hover — same tooltip affordance as the breakdown
   row labels, so the whole bar signals "hover me" consistently. */
.tl-label.has-tooltip:hover {
    text-decoration: underline;
    text-decoration-style: dotted;
    text-decoration-color: #b0bab7;
    text-underline-offset: 3px;
}
/* Inactive state — col-inactive class on .compare-timeline cascades to
   every cell with the matching data-col attribute. */
.compare-timeline.col-gov-inactive [data-col="gov"] .tl-dot,
.compare-timeline.col-hd1-inactive [data-col="hd1"] .tl-dot,
.compare-timeline.col-sd1-inactive [data-col="sd1"] .tl-dot,
.compare-timeline.col-cd1-inactive [data-col="cd1"] .tl-dot,
.compare-timeline.col-enacted-inactive [data-col="enacted"] .tl-dot {
    background: #fff;
    border-color: #c2cdc7;
}
.compare-timeline.col-gov-inactive [data-col="gov"] .tl-dot::after,
.compare-timeline.col-hd1-inactive [data-col="hd1"] .tl-dot::after,
.compare-timeline.col-sd1-inactive [data-col="sd1"] .tl-dot::after,
.compare-timeline.col-cd1-inactive [data-col="cd1"] .tl-dot::after,
.compare-timeline.col-enacted-inactive [data-col="enacted"] .tl-dot::after {
    display: none;
}
.compare-timeline.col-gov-inactive [data-col="gov"] .tl-seg,
.compare-timeline.col-hd1-inactive [data-col="hd1"] .tl-seg,
.compare-timeline.col-sd1-inactive [data-col="sd1"] .tl-seg,
.compare-timeline.col-cd1-inactive [data-col="cd1"] .tl-seg,
.compare-timeline.col-enacted-inactive [data-col="enacted"] .tl-seg {
    background: #e3e8e5;
}
.compare-timeline.col-gov-inactive [data-col="gov"].tl-label,
.compare-timeline.col-hd1-inactive [data-col="hd1"].tl-label,
.compare-timeline.col-sd1-inactive [data-col="sd1"].tl-label,
.compare-timeline.col-cd1-inactive [data-col="cd1"].tl-label,
.compare-timeline.col-enacted-inactive [data-col="enacted"].tl-label {
    /* Muted color only — no line-through. On a legislative site struck
       text reads as "deleted from the bill"; the hollow dot already
       signals the off state. */
    color: #aab5b1;
}
/* Checkbox is hidden — the dot label is the interactive toggle */
.tl-cb {
    position: absolute;
    opacity: 0;
    width: 0;
    height: 0;
    pointer-events: none;
}
.tl-dot-lbl {
    display: flex;
    align-items: center;
    cursor: pointer;
    border-radius: 50%;
    /* expand click target slightly beyond the dot */
    padding: 3px;
    margin: -3px;
    transition: transform 0.12s;
}
.tl-dot-lbl:hover .tl-dot {
    transform: scale(1.15);
    box-shadow: 0 0 0 5px rgba(60, 82, 73, 0.15);
}
.tl-dot-lbl:active .tl-dot {
    transform: scale(0.9);
}
/* Inactive (unchecked) hover — show a green tint as affordance to re-enable */
.compare-timeline.col-gov-inactive [data-col="gov"] .tl-dot-lbl:hover .tl-dot,
.compare-timeline.col-hd1-inactive [data-col="hd1"] .tl-dot-lbl:hover .tl-dot,
.compare-timeline.col-sd1-inactive [data-col="sd1"] .tl-dot-lbl:hover .tl-dot,
.compare-timeline.col-cd1-inactive [data-col="cd1"] .tl-dot-lbl:hover .tl-dot,
.compare-timeline.col-enacted-inactive [data-col="enacted"] .tl-dot-lbl:hover .tl-dot {
    box-shadow: 0 0 0 4px rgba(30, 126, 52, 0.15);
    border-color: #5aaa75;
}
/* Amount beneath each timeline dot — chip styling (consistent w/ figure-chip in table) */
.tl-amt {
    display: inline-block;
    padding: 6px 16px;
    /* Near-white fill + hairline border — the pill is a frame, not a
       button. The numeral carries the visual weight. */
    background: #fafbfa;
    border: 1px solid #e8ecea;
    border-radius: 999px;
    color: #1a2330;
    text-align: center;
    font-variant-numeric: tabular-nums;
    letter-spacing: -0.01em;
    white-space: nowrap;
    min-height: 1.6em;          /* reserve a consistent row height */
    min-width: 3.6em;
    line-height: 1.2;
    transition: background 0.18s ease, border-color 0.18s ease, color 0.18s ease, box-shadow 0.18s ease;
    justify-self: center;
}
/* Two-tone typography — number is the visual hero, suffix is a quieter
   trailing letter so the eye lands on the magnitude first. */
.tl-amt-num {
    font-size: 1.35rem;
    font-weight: 700;
    letter-spacing: -0.015em;
}
.tl-amt-suffix {
    font-size: 0.84rem;
    font-weight: 500;
    color: #7a8590;
    margin-left: 1px;
    vertical-align: baseline;
}
/* Inactive chip state — muted, no gradient */
.compare-timeline.col-gov-inactive [data-col="gov"].tl-amt,
.compare-timeline.col-hd1-inactive [data-col="hd1"].tl-amt,
.compare-timeline.col-sd1-inactive [data-col="sd1"].tl-amt,
.compare-timeline.col-cd1-inactive [data-col="cd1"].tl-amt,
.compare-timeline.col-enacted-inactive [data-col="enacted"].tl-amt {
    color: #aab5b1;
    background: #f9fafa;
    border-color: #ebeeed;
}
.compare-timeline.col-gov-inactive [data-col="gov"] .tl-amt-suffix,
.compare-timeline.col-hd1-inactive [data-col="hd1"] .tl-amt-suffix,
.compare-timeline.col-sd1-inactive [data-col="sd1"] .tl-amt-suffix,
.compare-timeline.col-cd1-inactive [data-col="cd1"] .tl-amt-suffix,
.compare-timeline.col-enacted-inactive [data-col="enacted"] .tl-amt-suffix {
    color: #c1c8c5;
}

/* Stage-based emphasis — the Enacted budget (Act 175) carries the filled
   sage chip when active; earlier drafts keep the quiet outlined pill so
   the timeline reads as progress toward the enacted number. When Enacted
   is toggled off, the emphasis falls back to CD1 as the rightmost "final". */
.compare-timeline:not(.col-enacted-inactive) [data-col="enacted"].tl-amt,
.compare-timeline.col-enacted-inactive:not(.col-cd1-inactive) [data-col="cd1"].tl-amt {
    background: linear-gradient(135deg, #84a89c 0%, #6f9184 100%);
    border-color: transparent;
    color: #ffffff;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.20),
                0 2px 8px rgba(80, 105, 95, 0.18);
}
.compare-timeline:not(.col-enacted-inactive) [data-col="enacted"] .tl-amt-suffix,
.compare-timeline.col-enacted-inactive:not(.col-cd1-inactive) [data-col="cd1"] .tl-amt-suffix {
    color: rgba(255, 255, 255, 0.80);
}

/* ── Context captions under the pills (row 4) ──────────────────────────
   Gov/CD1 get anchor words ("baseline" / "final budget"); the middle
   drafts get stage-to-stage deltas; Net gets percent + scope. These carry
   the story the rounded totals can't — three of the four pills usually
   render the same $23.1B. One typographic voice: the anchor words use the
   same micro-kicker treatment as the connector-delta and net-scope kickers
   (uppercase, tracked, muted), so the caption row reads as a single system. */
.compare-timeline > [data-row="subs"] { margin-top: 5px; }
.tl-sub {
    font-size: 0.62rem;
    font-weight: 600;
    letter-spacing: 0.07em;
    text-transform: uppercase;
    color: #a7b1ac;
    text-align: center;
    justify-self: center;
    white-space: nowrap;
    line-height: 1.3;
    min-height: 1em;          /* keeps the row height when a caption is empty */
    font-variant-numeric: tabular-nums;
}
.tl-sub-up   { color: #4f8862; }
.tl-sub-down { color: #b3614f; }
.tl-sub-final { color: #5a7468; }
/* Captions mute with their column */
.compare-timeline.col-gov-inactive [data-col="gov"].tl-sub,
.compare-timeline.col-hd1-inactive [data-col="hd1"].tl-sub,
.compare-timeline.col-sd1-inactive [data-col="sd1"].tl-sub,
.compare-timeline.col-cd1-inactive [data-col="cd1"].tl-sub,
.compare-timeline.col-enacted-inactive [data-col="enacted"].tl-sub {
    color: #c1c8c5;
}

/* ── Connector deltas (dimension lines between consecutive active pills) ──
   Each stage-to-stage change renders in the subs row as a hairline running
   pill-center to pill-center (--tl-ins insets the line by half a column on
   each side), an arrowhead into the destination stage, and a centered chip —
   colored amount over a tiny "GOV. → HD1" kicker — breaking the line. The
   span's grid-column is set inline by JS from the active-stage chain, so a
   toggled-off stage is simply passed over. */
.compare-timeline > .tl-delta {
    position: relative;
    display: flex;
    justify-content: center;
    align-items: center;
    margin-top: 5px;
    padding: 1px 0;
    min-width: 0;
}
.compare-timeline > .tl-delta::before {
    content: '';
    position: absolute;
    left: var(--tl-ins, 25%);
    right: calc(var(--tl-ins, 25%) + 4px);   /* stop short of the arrowhead */
    top: 50%;
    border-top: 1px solid #c6d2cb;
}
.compare-timeline > .tl-delta::after {
    content: '▸';
    position: absolute;
    right: calc(var(--tl-ins, 25%) - 3px);
    top: 50%;
    transform: translateY(-54%);
    font-size: 0.7rem;
    line-height: 1;
    color: #aabdb2;
}
.tl-delta-chip {
    position: relative;
    z-index: 1;
    display: flex;
    flex-direction: column;
    align-items: center;
    background: #ffffff;
    padding: 0 9px;
    /* Connector chips are rebuilt on every summary update, so this entrance
       fade replays in step with the count-up and sparkline draw. */
    animation: row-enter 0.3s ease-out;
}
.tl-delta-amt {
    font-size: 0.82rem;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    line-height: 1.15;
    color: #6b7672;
    white-space: nowrap;
}
.tl-delta-kicker {
    font-size: 0.6rem;
    font-weight: 600;
    letter-spacing: 0.07em;
    text-transform: uppercase;
    color: #a7b1ac;
    line-height: 1.25;
    white-space: nowrap;
}
/* Net caption reuses the chip but needs no line-breaking background,
   and its percent stays neutral (the Net pill above carries the color). */
.tl-delta-chip-net {
    background: transparent;
    padding: 0;
}

/* ── Card section sub-headers (inside combined Operating & Capital collapse) ── */
.card-section-sub {
    font-size: 0.74rem;
    font-weight: 600;
    color: #4a7a6a;
    padding: 0.6rem 0 0.3rem;
    margin-top: 0.25rem;
    border-top: 1px solid #e8ecf0;
}
.card-section-sub:first-child {
    border-top: none;
    margin-top: 0;
    padding-top: 0.1rem;
}
/* ── Net Change column — 4th slot, derived from SD1 ── */
/* Sparkline: Gov → HD1 → SD1, last dot highlighted */
.tl-net-spark-row {
    display: flex;
    align-items: center;
    justify-content: center;
    height: 23px;
}
.tl-net-spark {
    width: 60px;
    height: 20px;
    overflow: visible;
}
.tl-spark-line {
    stroke: #c9d1cd;
    stroke-width: 1.4;
    fill: none;
    stroke-linecap: round;
    stroke-linejoin: round;
    /* Draw-on: the polyline carries pathLength="100", so a 100-unit dash
       offset hides it and the animation reveals it left-to-right. Replays
       naturally because the SVG is rebuilt on every summary update. */
    stroke-dasharray: 100;
    stroke-dashoffset: 100;
    animation: tl-spark-draw 0.55s ease-out 0.05s forwards;
}
@keyframes tl-spark-draw {
    to { stroke-dashoffset: 0; }
}
/* Dots fade in as the line's drawing edge reaches them — per-dot
   animation-delay is set inline at render time. */
.tl-spark-dot {
    fill: #c9d1cd;
    opacity: 0;
    animation: tl-spark-dot-in 0.2s ease-out forwards;
}
@keyframes tl-spark-dot-in {
    to { opacity: 1; }
}
.tl-spark-dot-end { fill: #7a8a85; }
/* Net direction drives sparkline + chip hue; class lives on .compare-timeline */
.compare-timeline.net-positive [data-col="net"] .tl-spark-line { stroke: #b5cfc0; }
.compare-timeline.net-positive [data-col="net"] .tl-spark-dot { fill: #b5cfc0; }
.compare-timeline.net-positive [data-col="net"] .tl-spark-dot-end { fill: #4f8862; }
.compare-timeline.net-negative [data-col="net"] .tl-spark-line { stroke: #e2bdb2; }
.compare-timeline.net-negative [data-col="net"] .tl-spark-dot { fill: #e2bdb2; }
.compare-timeline.net-negative [data-col="net"] .tl-spark-dot-end { fill: #b3614f; }

/* Net chip — outlined treatment; distinct visual rank vs. the solid
   draft pills. Direction encoded by hue (sage positive / clay negative). */
.tl-net-chip {
    display: inline-flex;
    align-items: baseline;
    gap: 1px;
    padding: 6px 16px;
    font-weight: 700;
    letter-spacing: -0.015em;
    background: #f1f5f2;
    border: 1.5px solid #c4d2cc;
    border-radius: 999px;
    color: #5a6e66;
    box-shadow: none;
}
.tl-net-arrow {
    font-size: 0.78em;
    line-height: 1;
    transform: translateY(-1px);
    opacity: 0.85;
}
/* Net value scales with the totals numerals; the unit suffix steps down
   the same way the B/M/K does inside the draft pills. */
.tl-net-val {
    font-size: 1.35rem;
    letter-spacing: -0.015em;
}
.tl-net-suffix {
    font-size: 0.84rem;
    font-weight: 600;
    opacity: 0.75;
}
.compare-timeline.net-positive [data-col="net"].tl-net-chip {
    background: #eaf2ec;
    border-color: #9fc0ad;
    color: #2f6b48;
}
.compare-timeline.net-negative [data-col="net"].tl-net-chip {
    background: #f5ece8;
    border-color: #d2b1a8;
    color: #8e3f3a;
}

/* Cross-fade on FY toggle — replay via toggling .net-refresh on .compare-timeline. */
@keyframes tl-net-refresh {
    0%   { opacity: 0.25; transform: translateY(1px); }
    100% { opacity: 1;    transform: translateY(0);   }
}
.compare-timeline.net-refresh [data-col="net"].tl-net-spark-row,
.compare-timeline.net-refresh [data-col="net"].tl-net-chip {
    animation: tl-net-refresh 220ms ease;
}
/* Percentage, shown inline after the dollar amount inside the chip */
.tl-net-pct {
    font-size: 0.83rem;
    font-weight: 700;
    opacity: 0.78;
    letter-spacing: 0;
}

/* ── Operating / Capital breakdown rows ─────────────────────────────
   Shared "Operating" / "Capital" labels sit in col 1 (left rail). Each
   per-column cell carries just the formatted value. Labels+cells all
   toggle [hidden] together when the caret is closed.

   Visual treatment:
   - Category color square before the label (sage = Op, ochre = Cap).
   - Kicker typography on labels (tiny-caps, letter-spaced).
   - Dashed separator above the Operating row — signals "breakdown zone".
   - Faint zebra tint per row (barely perceptible — just groups the numbers).
   - Ghost pill borders on values (1px soft sage) so they read as data chips
     without competing with the solid totals pills above. Net column skips
     the pill so direction color stays punchy. */
.tl-bd-label {
    display: flex;
    align-items: center;
    justify-content: flex-start;
    gap: 7px;
    padding-right: 8px;
    padding-left: 14px;
    font-size: 0.74rem;
    font-weight: 600;
    color: #5f6e68;
    letter-spacing: 0.06em;
    text-transform: uppercase;
    white-space: nowrap;
    cursor: help;
    align-self: stretch;
}
/* Category color dot — replaces the old inset accent bar on the bands.
   Tooltips use ::after, so ::before is free. */
.tl-bd-label::before {
    content: '';
    width: 8px;
    height: 8px;
    border-radius: 50%;
    flex-shrink: 0;
}
.tl-bd-label[data-row="op"]::before  { background: #7d9a8d; }
.tl-bd-label[data-row="cap"]::before { background: #c7b187; }
/* Phone-width swap: full name on desktop, abbreviation under 640px */
.tl-bd-name-abbr { display: none; }
/* Share-of-total beside the row label — answers "how does the budget
   split?" without the reader doing mental division. Plain muted text;
   a capsule here competed with the pills above. */
.tl-bd-share {
    font-size: 0.72rem;
    font-weight: 600;
    color: #9aa5a0;
    letter-spacing: 0;
}
.tl-bd-share:empty { display: none; }
/* Dotted underline appears on hover as tooltip affordance */
.tl-bd-label:hover,
.tl-bd-label:focus {
    text-decoration: underline;
    text-decoration-style: dotted;
    text-decoration-color: #b0bab7;
    text-underline-offset: 3px;
}
/* Note: legacy [hidden] rule for .tl-bd-label is replaced by the
   animated collapsed/expanded states defined under .compare-timeline
   (search "show-breakdown") so the row can transition smoothly. */

/* Values: clean tabular numerals — no pill chip. The band tint already
   groups them into a zone; adding a second outlined chip on top of the
   tint created a noisy double-layer look. Keep the typography crisp
   and let the band do the visual grouping.

   IMPORTANT: justify-self/align-self must be stretch (default) so the
   tinted background fills the full grid track. Center the text itself
   via flexbox/text-align, not via self-alignment shrinking. */
.tl-bd-cell {
    display: flex;
    align-items: baseline;
    justify-content: center;
    text-align: center;
    font-variant-numeric: tabular-nums;
    font-weight: 600;
    font-size: 1rem;
    color: #2e3a36;
    letter-spacing: -0.01em;
    white-space: nowrap;
}
/* Small dim unit letter — same two-tone treatment as the totals pills,
   so the breakdown reads as part of the same component. */
.tl-bd-suffix {
    font-size: 0.72rem;
    font-weight: 500;
    color: #7a8590;
    margin-left: 1px;
}
.tl-bd-cell[hidden] { display: none; }
/* Inactive column mutes its breakdown cells (suffix included) */
.compare-timeline.col-gov-inactive [data-col="gov"].tl-bd-cell,
.compare-timeline.col-hd1-inactive [data-col="hd1"].tl-bd-cell,
.compare-timeline.col-sd1-inactive [data-col="sd1"].tl-bd-cell,
.compare-timeline.col-cd1-inactive [data-col="cd1"].tl-bd-cell,
.compare-timeline.col-enacted-inactive [data-col="enacted"].tl-bd-cell {
    color: #aab5b1;
}
.compare-timeline.col-gov-inactive [data-col="gov"].tl-bd-cell .tl-bd-suffix,
.compare-timeline.col-hd1-inactive [data-col="hd1"].tl-bd-cell .tl-bd-suffix,
.compare-timeline.col-sd1-inactive [data-col="sd1"].tl-bd-cell .tl-bd-suffix,
.compare-timeline.col-cd1-inactive [data-col="cd1"].tl-bd-cell .tl-bd-suffix,
.compare-timeline.col-enacted-inactive [data-col="enacted"].tl-bd-cell .tl-bd-suffix {
    color: #c1c8c5;
}
/* Net breakdown cells color by their own sign (Operating can rise while
   the overall net falls — JS toggles bd-net-pos/neg per cell); heavier
   weight echoes the Net chip above so the column reads as one unit. */
.compare-timeline [data-col="net"].tl-bd-cell { font-weight: 700; }
.compare-timeline [data-col="net"].tl-bd-cell.bd-net-pos { color: #1e7e34; }
.compare-timeline [data-col="net"].tl-bd-cell.bd-net-neg { color: #c62828; }

/* Hairline column dividers between every number cell in the breakdown rows.
   Rule appears between Gov/HD1, HD1/SD1, SD1/CD1, CD1/Net — never between
   the label column and Gov (label reads as a row heading, not a column).

   Editorial hairline: a vertical gradient that fades to transparent at the
   top and bottom edges, centered ~70% of the cell height. The taper keeps
   the divider from clashing with the band's rounded feel and gives the
   numbers a refined, gallery-label quality at small sizes. */
.compare-timeline > [data-row="op"][data-col="hd1"]::before,
.compare-timeline > [data-row="op"][data-col="sd1"]::before,
.compare-timeline > [data-row="op"][data-col="cd1"]::before,
.compare-timeline > [data-row="op"][data-col="enacted"]::before,
.compare-timeline > [data-row="op"][data-col="net"]::before,
.compare-timeline > [data-row="cap"][data-col="hd1"]::before,
.compare-timeline > [data-row="cap"][data-col="sd1"]::before,
.compare-timeline > [data-row="cap"][data-col="cd1"]::before,
.compare-timeline > [data-row="cap"][data-col="enacted"]::before,
.compare-timeline > [data-row="cap"][data-col="net"]::before {
    content: '';
    position: absolute;
    left: 0;
    top: 15%;
    bottom: 15%;
    width: 1px;
    background: linear-gradient(
        to bottom,
        rgba(16, 24, 40, 0) 0%,
        rgba(16, 24, 40, 0.10) 50%,
        rgba(16, 24, 40, 0) 100%
    );
    pointer-events: none;
}
/* Remove the 4px left-margin on Net only in breakdown rows, so the
   divider rule sits cleanly adjacent to SD1 with no gap. Totals row
   keeps the margin (visual separation for the Net chip). */
.compare-timeline > [data-row="op"][data-col="net"],
.compare-timeline > [data-row="cap"][data-col="net"] {
    margin-left: 0;
}

/* Zebra bands — .tl-band is a dedicated grid item spanning the label
   column through the Net column only (grid-column: 2 / -2 excludes
   the 1fr flex spacers on both edges). The tint paints as one
   continuous rectangle behind the label + numbers. Values + labels
   sit ABOVE the band via z-index. */
.compare-timeline > .tl-band {
    grid-column: 2 / -2;
    z-index: 0;
    align-self: stretch;
    justify-self: stretch;
    border-radius: 6px;
}
/* Labels need an explicit grid-column (col 2 — left rail) because
   auto-placement can't find room in row 4/5 once the band occupies
   all columns. */
.compare-timeline > .tl-bd-label[data-row="op"]  { grid-column: 2; }
.compare-timeline > .tl-bd-label[data-row="cap"] { grid-column: 2; }
/* Borderless-ledger treatment: no tinted strips. The op "band" carries
   only the dashed rule that marks the start of the breakdown zone; the
   category hue moved to a small dot beside each label (::before below). */
.compare-timeline > .tl-band[data-row="op"]  {
    grid-row: 5;
    background: none;
    box-shadow: none;
    border-top: 1px dashed #dde3e0;
    border-radius: 0;
}
.compare-timeline > .tl-band[data-row="cap"] {
    grid-row: 6;
    background: none;
    box-shadow: none;
}
/* Note: the .tl-band [hidden] rule is replaced by the animated
   collapsed/expanded states under .compare-timeline (see "show-breakdown"). */

/* Values + labels need position so z-index stacks them above the band. */
.compare-timeline > [data-row="op"],
.compare-timeline > [data-row="cap"] {
    position: relative;
    z-index: 1;
}
/* Labels get a higher z-index so their tooltip pseudo-element paints
   above peer cells/bands that share z-index: 1 (later DOM order wins). */
.compare-timeline > .tl-bd-label {
    z-index: 10;
}
/* Generous vertical padding on each Op/Cap cell gives the bands real
   presence and breathing room around the numerals. Since the band is
   a grid item itself, it takes its height from the row, which in turn
   is sized by its children — so padding on the cells determines the
   band height. */
.compare-timeline > [data-row="op"]  { padding-top: 13px; padding-bottom: 6px; }
.compare-timeline > [data-row="cap"] { padding-top: 5px;  padding-bottom: 8px; }
/* Gap between the caption row and the dashed rule that opens the
   breakdown zone. Margin (not row-gap) so the collapse animation can
   zero it. */
.compare-timeline > [data-row="op"] { margin-top: 10px; }

/* ── Breakdown slide-down animation ──────────────────────────────────────
   The Op/Cap rows animate in/out when the user clicks the expand caret.
   Approach: every grid item in those rows transitions max-height (clipped
   by overflow:hidden), padding, margin, and opacity.  Class-driven so a
   single `.show-breakdown` toggle on the timeline animates all items in
   sync — display:none can't be transitioned, so we use max-height: 0
   instead of the old [hidden] attribute.
   Refs:
     – CSS-Tricks: "How to Animate Box Shadow" / max-height pattern
     – web.dev: "Easing animations with cubic-bezier"
   The cubic-bezier(.2,.8,.2,1) is the Material-style "decelerate" curve
   so the rows ease into place (fast start, soft landing). */
.compare-timeline > [data-row="op"],
.compare-timeline > [data-row="cap"] {
    overflow: hidden;
    transition:
        max-height 0.35s cubic-bezier(0.2, 0.8, 0.2, 1),
        opacity   0.22s ease,
        padding   0.35s cubic-bezier(0.2, 0.8, 0.2, 1),
        margin    0.35s cubic-bezier(0.2, 0.8, 0.2, 1);
}
/* Collapsed (default): zero height, transparent, no padding/margin.
   Stack the .tl-band below — its grid-column 2/-2 still spans the row
   tracks but max-height: 0 keeps the row visually empty.            */
.compare-timeline:not(.show-breakdown) > [data-row="op"],
.compare-timeline:not(.show-breakdown) > [data-row="cap"] {
    max-height: 0;
    opacity: 0;
    padding-top: 0;
    padding-bottom: 0;
    margin-top: 0;
    margin-bottom: 0;
    pointer-events: none;
}
/* Expanded: enough height to fit one line of text + breathing room.
   60px comfortably fits the 14.7px line + 11+9 padding without clipping
   tooltips that sit just above the label. */
.compare-timeline.show-breakdown > [data-row="op"],
.compare-timeline.show-breakdown > [data-row="cap"] {
    max-height: 60px;
    opacity: 1;
}
/* Honor users who set `prefers-reduced-motion: reduce`. */
@media (prefers-reduced-motion: reduce) {
    .compare-timeline > [data-row="op"],
    .compare-timeline > [data-row="cap"] {
        transition: none;
    }
    .tl-seg::after,
    .dept-arrow {
        transition: none;
    }
    .tl-dot,
    .tl-spark-line,
    .tl-spark-dot,
    .tl-delta-chip,
    .compare-page .data-table tbody tr {
        animation: none !important;
    }
    /* With their animations disabled, these must land in their end state. */
    .tl-spark-line { stroke-dashoffset: 0; }
    .tl-spark-dot { opacity: 1; }
}

/* Exempt the label from overflow:hidden so the upward tooltip isn't clipped.
   opacity:0 already handles visibility during collapse, so this is safe. */
.compare-timeline > [data-row="op"].tl-bd-label,
.compare-timeline > [data-row="cap"].tl-bd-label {
    overflow: visible;
}
/* Tooltip override — wider + left-aligned so "each year." isn't orphaned
   and doesn't inherit text-align:right from the kicker styling. */
.tl-bd-label.has-tooltip::after {
    left: 0;
    top: auto;
    bottom: calc(100% + 5px); /* open upward — avoids intersecting Capital */
    width: 290px;
    font-size: 0.8rem;
    line-height: 1.45;
    text-align: left;
}

/* ── draft-cards: empty now, collapse it ── */
#draft-cards:empty {
    display: none;
}
/* Expand control — kicker label + circular caret in the left rail at the
   totals row. The label names what the caret reveals; it fades once the
   breakdown is open (the Operating/Capital row labels take over). The
   chevron is inline SVG so it centers crisply, rotating 180° when open. */
.tl-expand-btn {
    display: inline-flex;
    align-items: center;
    gap: 7px;
    background: none;
    border: 0;
    padding: 0;
    cursor: pointer;
    font-family: inherit;
}
.tl-expand-kicker {
    font-size: 0.7rem;
    font-weight: 600;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: #8a9199;
    transition: opacity 0.18s ease;
}
.tl-expand-btn.open .tl-expand-kicker {
    opacity: 0;
}
.tl-expand-caret {
    width: 22px;
    height: 22px;
    border-radius: 50%;
    background: #eef3f0;
    border: 1px solid transparent;   /* border appears on hover only */
    color: #5a7468;
    flex-shrink: 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    transition: background 0.15s, border-color 0.15s, transform 0.18s ease, color 0.12s;
}
.tl-expand-btn:hover .tl-expand-caret {
    background: #dfeae5;
    border-color: #a8c0b8;
    color: #3d5249;
}
.tl-expand-btn:focus-visible {
    outline: none;
}
.tl-expand-btn:focus-visible .tl-expand-caret {
    box-shadow: 0 0 0 3px rgba(90, 123, 104, 0.25);
}
.tl-expand-btn.open .tl-expand-caret {
    transform: rotate(180deg);
}

/* ── Mobile stage picker ────────────────────────────────────────────────
   Hidden on desktop (the dots are the toggle there). Revealed ≤640px,
   where the dots are frozen and inactive columns are hidden. Each chip
   proxies a hidden #tl-* checkbox via JS. Sticky to the scrollport's left
   edge so it stays usable while the timeline scrolls horizontally beneath
   it; width:100% resolves against the bar's client box (not its scroll
   width), so the picker itself never adds horizontal scroll. */
.tl-stage-picker {
    display: none;
    position: sticky;
    left: 0;
    width: 100%;
    box-sizing: border-box;
    justify-content: center;
    gap: 6px;
    padding: 4px 4px 10px;
    background: #ffffff;
    z-index: 2;
}
.tl-stage-chip {
    flex: 0 0 auto;
    min-width: 56px;
    padding: 6px 0;
    font-family: inherit;
    font-size: 0.84rem;
    font-weight: 600;
    color: #5a6e66;
    background: #ffffff;
    border: 1px solid #d1ddd8;
    border-radius: 999px;
    cursor: pointer;
    transition: background 0.15s, border-color 0.15s, color 0.15s, opacity 0.15s;
}
.tl-stage-chip.active {
    background: linear-gradient(135deg, #84a89c 0%, #6f9184 100%);
    border-color: transparent;
    color: #ffffff;
    box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.20),
                0 1px 4px rgba(80, 105, 95, 0.18);
}
.tl-stage-chip:disabled {
    cursor: default;
    opacity: 0.5;
}
.tl-stage-chip:focus-visible {
    outline: none;
    box-shadow: 0 0 0 3px rgba(90, 123, 104, 0.25);
}

/* ── Small screens: contain the timeline inside the card ────────────────
   Below ~640px the chip row is wider than the viewport. Tracks switch to
   max-content so chips can never overlap, the grid grows to its content
   width, and the card scrolls horizontally instead of pushing the whole
   page wide. column-gap stays 0 so the dot connector line is continuous;
   chips get small side margins for separation instead. */
@media (max-width: 768px) {
    .compare-controls-bar {
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
        scroll-snap-type: x proximity;
    }
    .compare-timeline > [data-row="dots"] { scroll-snap-align: center; }
    /* Edge fades — JS toggles scroll-left/right on the card so the fade
       only shows when there genuinely is clipped content on that side. */
    .compare-controls-bar.scroll-right {
        -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 36px), transparent);
        mask-image: linear-gradient(to right, #000 calc(100% - 36px), transparent);
    }
    .compare-controls-bar.scroll-left {
        -webkit-mask-image: linear-gradient(to left, #000 calc(100% - 36px), transparent);
        mask-image: linear-gradient(to left, #000 calc(100% - 36px), transparent);
    }
    .compare-controls-bar.scroll-left.scroll-right {
        -webkit-mask-image: linear-gradient(to right, transparent, #000 36px, #000 calc(100% - 36px), transparent);
        mask-image: linear-gradient(to right, transparent, #000 36px, #000 calc(100% - 36px), transparent);
    }
    .compare-controls-bar > .compare-timeline {
        width: max-content;
        min-width: 100%;
        padding: 10px 10px 12px;
        grid-template-columns: 1fr max-content repeat(5, max-content) max-content 1fr;
    }
    .tl-expand-kicker { display: none; }
    .tl-label { font-size: 0.92rem; }
    .tl-amt {
        padding: 4px 10px;
        margin: 0 3px;
    }
    .tl-amt-num { font-size: 1.1rem; }
    .tl-net-chip { padding: 4px 10px; }
    .tl-net-val { font-size: 1.1rem; }
    .tl-sub { font-size: 0.68rem; }
    .tl-bd-label {
        padding-left: 10px;
        padding-right: 8px;
    }
    .tl-bd-cell {
        font-size: 0.92rem;
        padding-left: 8px;
        padding-right: 8px;
    }
    /* Touch screens can't hover; the opacity-hidden tooltip boxes are
       280px wide and silently inflate the scroll area, so drop them. */
    .compare-timeline .has-tooltip::after { display: none; }
}

/* Phones: show only the ACTIVE stages — the default Gov → Enacted → Net view
   fits 375px with no sideways scroll, which beats panning for the answer.
   The dots become read-only state indicators here; the labeled stage
   picker above is the toggle (a frozen dot can't be re-enabled by tapping
   the column it just hid). Adding stages falls back to the internal
   scroll + edge fades above. */
@media (max-width: 640px) {
    .tl-stage-picker { display: flex; }
    .compare-timeline.col-gov-inactive [data-col="gov"],
    .compare-timeline.col-hd1-inactive [data-col="hd1"],
    .compare-timeline.col-sd1-inactive [data-col="sd1"],
    .compare-timeline.col-cd1-inactive [data-col="cd1"],
    .compare-timeline.col-enacted-inactive [data-col="enacted"] {
        display: none;
    }
    .tl-dot-lbl { pointer-events: none; }
    /* Connector deltas need the full pill row geometry; on phones (hidden
       inactive columns + horizontal scroll) the Net chip carries the story. */
    .compare-timeline > .tl-delta { display: none; }
    .tl-bd-name-full { display: none; }
    .tl-bd-name-abbr { display: inline; }
    .compare-controls-bar > .compare-timeline {
        padding-left: 4px;
        padding-right: 4px;
    }
    .tl-amt { padding: 4px 8px; margin: 0 1px; }
    .tl-net-chip { padding: 4px 8px; }
    .tl-amt-num, .tl-net-val { font-size: 1rem; }
    .tl-sub { padding: 0 3px; }
    .tl-bd-label { padding-left: 4px; padding-right: 2px; }
    /* The pinned search row eats too much of a small screen; let it
       scroll away with the page. */
    .compare-page > .search-row { position: static; }
}

/* The page tint's edge-to-edge bleed assumes #app's 2rem padding; at
   ≤768px #app drops to 1rem, so match it or the page scrolls sideways. */
@media (max-width: 768px) {
    .compare-page {
        margin: -1rem -1rem 0;
        padding: 1rem 1rem 1.5rem;
    }
    .compare-page > .search-row {
        margin: 0 -1rem;
        padding: 0.5rem 1rem 0.6rem;
    }
    /* Tables without an internal scroll pane (capital projects, fund
       detail) scroll inside their card instead of widening the page. */
    .compare-page .projects-section,
    .compare-page #fund-detail-section {
        overflow-x: auto;
    }
    /* The filter/search cluster is flex-shrink: 0 for desktop layout;
       on narrow screens let it shrink and wrap instead of widening
       the page. */
    .compare-page > .search-row .search-summary {
        flex-shrink: 1;
        min-width: 0;
    }
}

.hb300-ref-bar {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: 0.5rem;
    background: #f0f4f2;
    border: 1px solid #c8d8d0;
    border-radius: 6px;
    padding: 0.5rem 0.75rem;
    margin-bottom: 0.5rem;
    font-size: 0.85rem;
}
.hb300-ref-label {
    font-weight: 600;
    color: #4a7a6a;
    white-space: nowrap;
}
.hb300-ref-chip {
    background: #fff;
    border: 1px solid #b8cec7;
    border-radius: 4px;
    padding: 0.15rem 0.5rem;
    color: #333;
    white-space: nowrap;
}

/* ─────────────────────────────────────────────────────────────────────────
   Historical Trends tab — 10-year biennial budget comparison
   ───────────────────────────────────────────────────────────────────────── */
.historical-page {
    max-width: 1100px;
    margin: 0 auto;
    padding: 0 1rem 3rem;
}

.hist-hero {
    padding: 1.25rem 0 0.75rem;
    border-bottom: 1px solid #e3e7e5;
    margin-bottom: 1.5rem;
}
.hist-hero h2 {
    margin: 0 0 0.4rem;
    color: #2f3a36;
}
.hist-lead {
    font-size: 1.05rem;
    color: #444;
    margin: 0 0 0.75rem;
    line-height: 1.5;
}
.hist-meta {
    display: flex;
    flex-wrap: wrap;
    gap: 1.25rem;
    font-size: 0.9rem;
    color: #5a6260;
}
.hist-meta strong {
    color: #2f3a36;
    font-weight: 600;
}
.hist-meta-note {
    color: #8a6b3a;
    font-style: italic;
}

.hist-acts {
    display: flex;
    flex-wrap: wrap;
    gap: 0.5rem;
    margin-bottom: 1.75rem;
}
.hist-act-card {
    display: inline-flex;
    flex-direction: column;
    align-items: flex-start;
    gap: 0.15rem;
    padding: 0.55rem 0.85rem;
    background: #f5f3ed;
    border: 1px solid #d9d3c1;
    border-radius: 8px;
    text-decoration: none;
    color: #3d4a45;
    transition: background 0.15s, border-color 0.15s, transform 0.15s;
    min-width: 92px;
}
.hist-act-card:hover {
    background: #efeadd;
    border-color: #c2b89c;
    transform: translateY(-1px);
}
.hist-act-year {
    font-size: 0.92rem;
    font-weight: 600;
    color: #5a7b68;
}
.hist-act-bill {
    font-size: 1rem;
    font-weight: 700;
    color: #2f3a36;
    display: inline-flex;
    align-items: baseline;
    gap: 0.35rem;
}
.hist-act-fy {
    font-size: 0.78rem;
    color: #6f7572;
    letter-spacing: 0.02em;
}
/* Small badge for multi-bill sessions (e.g. 2019 HB2 = Operating, HB1259 = CIP) */
.hist-act-scope {
    font-size: 0.66rem;
    font-weight: 600;
    letter-spacing: 0.04em;
    text-transform: uppercase;
    color: #6f7572;
    background: #efeadd;
    border: 1px solid #d9d0b4;
    border-radius: 3px;
    padding: 0.08rem 0.32rem;
    line-height: 1;
}

.hist-controls {
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: wrap;
    gap: 0.75rem;
    margin-bottom: 0.5rem;
}
.hist-toggle {
    display: inline-flex;
    border: 1px solid #c8cdca;
    border-radius: 6px;
    overflow: hidden;
    background: #fff;
}
.hist-toggle-btn {
    padding: 0.45rem 1rem;
    font-size: 0.95rem;
    background: #fff;
    border: none;
    border-right: 1px solid #c8cdca;
    color: #4a5552;
    cursor: pointer;
    transition: background 0.15s, color 0.15s;
}
.hist-toggle-btn:last-child {
    border-right: none;
}
.hist-toggle-btn:hover {
    background: #f1f5f3;
}
.hist-toggle-btn.active {
    background: #5a7b68;
    color: #fff;
    font-weight: 600;
}
.hist-export-btn {
    padding: 0.45rem 1rem;
    font-size: 0.95rem;
    background: #fff;
    border: 1px solid #c8cdca;
    border-radius: 6px;
    color: #4a5552;
    cursor: pointer;
    transition: background 0.15s, border-color 0.15s;
}
.hist-export-btn:hover {
    background: #f1f5f3;
    border-color: #5a7b68;
    color: #2f3a36;
}

.hist-section {
    margin-top: 2rem;
}
.hist-section h3 {
    margin: 0 0 0.25rem;
    font-size: var(--fs-xl);
    color: var(--heading-color);
}
.hist-section h4 {
    margin: 0 0 0.4rem;
    font-size: 1.05rem;
    color: #2f3a36;
}
.hist-section-sub {
    margin: 0 0 0.85rem;
    font-size: 0.92rem;
    color: #6a7370;
}
.hist-chart-wrap {
    position: relative;
    height: 360px;
    background: #fcfdfc;
    border: 1px solid #e6ebe8;
    border-radius: 8px;
    padding: 0.75rem;
}
.hist-dept-controls {
    display: flex;
    align-items: center;
    gap: 0.6rem;
    margin-bottom: 0.6rem;
    font-size: 0.95rem;
}
#hist-dept-select {
    padding: 0.35rem 0.6rem;
    font-size: 0.95rem;
    border: 1px solid #c8cdca;
    border-radius: 5px;
    background: #fff;
    color: #2f3a36;
    min-width: 320px;
    max-width: 100%;
}

.hist-table-wrap {
    overflow-x: auto;
    border: 1px solid #e6ebe8;
    border-radius: 8px;
}
.hist-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.95rem;
}
.hist-table thead {
    background: #f5f7f5;
}
.hist-table th {
    padding: 0.55rem 0.75rem;
    text-align: left;
    font-weight: 600;
    color: #3d4a45;
    border-bottom: 1px solid #d9e1dd;
    white-space: nowrap;
}
.hist-table th.num,
.hist-table td.num {
    text-align: right;
    font-variant-numeric: tabular-nums;
}
.hist-table tbody tr:nth-child(even) {
    background: #fafbfa;
}
.hist-table td {
    padding: 0.45rem 0.75rem;
    border-bottom: 1px solid #eef1ef;
    color: #2f3a36;
}
.hist-table tbody tr:last-child td {
    border-bottom: none;
}
.hist-table .positive { color: #2f7a5a; }
.hist-table .negative { color: #a04545; }

.hist-notes {
    background: #f9f7f1;
    border: 1px solid #e2dcc8;
    border-radius: 8px;
    padding: 0.85rem 1.1rem;
    font-size: 0.92rem;
    color: #4a4232;
}
.hist-notes ul {
    margin: 0.4rem 0 0.6rem;
    padding-left: 1.25rem;
}
.hist-footnote {
    font-size: 0.85rem;
    color: #6a7370;
    margin: 0.5rem 0 0;
    font-style: italic;
}

@media (max-width: 720px) {
    .hist-chart-wrap { height: 280px; }
    .hist-meta { gap: 0.5rem; flex-direction: column; }
    .hist-controls { flex-direction: column; align-items: stretch; }
    .hist-export-btn { width: 100%; }
    #hist-dept-select { min-width: 0; width: 100%; }
}

/* ── HB300 year selector + history chart + dept-card sparkline ─────────────
   The HB300 tab now spans FY2016–FY2027.  The year selector picks which
   FY's totals appear in the summary cards and on each department card.
   The state-wide chart at the top shows 12 years of operating + capital
   appropriations (carry-over from the old History tab).  The mini SVG
   sparkline on each department card mirrors the same 12-year arc, scoped
   to that department.
   ────────────────────────────────────────────────────────────────────────── */
/* ── Year picker ───────────────────────────────────────────────────────────
   Reusable component used on the home page (HB300 grid) and the dept
   detail page.  Three controls in a single rounded shell: "previous",
   a styled select with a chevron, and "next".  Disabled state on the
   stepper buttons reflects whether you can actually move further.
   ────────────────────────────────────────────────────────────────────────── */
.year-picker-bar {
    display: flex;
    align-items: center;
    gap: 0.85rem;
    flex-wrap: wrap;
    background: linear-gradient(180deg, #fbfcfa 0%, #f3f6f1 100%);
    border: 1px solid rgba(70, 110, 95, 0.18);
    border-radius: 12px;
    padding: 0.85rem 1rem;
    margin: 1rem 0;
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.03);
}
.year-picker-label {
    font-size: 0.7rem;
    text-transform: uppercase;
    letter-spacing: 0.1em;
    color: #6a7370;
    font-weight: 600;
}
.year-picker {
    display: inline-flex;
    align-items: stretch;
    background: #fff;
    border: 1px solid rgba(70, 110, 95, 0.32);
    border-radius: 999px;
    overflow: hidden;
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04);
    transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.year-picker:focus-within {
    border-color: rgba(70, 110, 95, 0.6);
    box-shadow: 0 0 0 3px rgba(90, 123, 104, 0.18);
}
.year-picker-step {
    background: transparent;
    border: 0;
    padding: 0 0.7rem;
    color: #466e5f;
    cursor: pointer;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    transition: background 0.12s ease, color 0.12s ease;
}
.year-picker-step:hover:not(:disabled) {
    background: #eef4ee;
}
.year-picker-step:active:not(:disabled) {
    background: #e1ebe1;
}
.year-picker-step:disabled {
    color: #c4cdc8;
    cursor: not-allowed;
    opacity: 0.7;
}
.year-picker-select-wrap {
    position: relative;
    display: inline-flex;
    align-items: center;
    border-left: 1px solid rgba(70, 110, 95, 0.18);
    border-right: 1px solid rgba(70, 110, 95, 0.18);
}
.year-picker-select {
    /* Drop the native select chrome and re-style with our own chevron */
    -webkit-appearance: none;
    -moz-appearance: none;
    appearance: none;
    border: 0;
    background: transparent;
    color: #2f3a36;
    font-size: 0.95rem;
    font-weight: 600;
    padding: 0.55rem 2rem 0.55rem 1rem;
    cursor: pointer;
    min-width: 220px;
    line-height: 1.2;
    font-family: inherit;
}
.year-picker-select:focus {
    outline: none;
}
.year-picker-chev {
    position: absolute;
    right: 0.7rem;
    color: #6a7370;
    pointer-events: none;
}
.year-picker-help {
    font-size: 0.85rem;
    color: #6a7370;
    flex-basis: 100%;
    margin-top: 0.15rem;
    line-height: 1.45;
}

/* On the dept detail page the picker sits between the dept name and the
   summary cards.  Slightly tighter top margin so it visually attaches to
   the header. */
.dept-year-bar {
    margin-top: 0.5rem;
}

@media (max-width: 540px) {
    .year-picker-select { min-width: 160px; padding-right: 1.8rem; font-size: 0.9rem; }
    .year-picker-step { padding: 0 0.55rem; }
}

.hb300-history-section {
    background: #fff;
    border-radius: 8px;
    border: 1px solid rgba(0, 0, 0, 0.06);
    padding: 1.1rem 1.2rem 0.9rem;
    margin: 1.1rem 0 1.5rem;
    box-shadow: 0 1px 3px rgba(0, 0, 0, 0.04);
}
.hb300-history-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: wrap;
    gap: 0.6rem;
}
.hb300-history-head h3 {
    margin: 0;
    font-size: var(--fs-lg);
    color: var(--heading-color);
}
.hb300-history-sub {
    margin: 0.1rem 0 0.7rem;
    font-size: 0.85rem;
    color: #6a7370;
}
.hb300-history-chart-wrap {
    height: 280px;
    margin-top: 0.4rem;
}

/* Per-department mini sparkline on each card */
.dept-card-spark-wrap {
    margin: 0.4rem 0 0.55rem;
    padding: 0.35rem 0.5rem 0.2rem;
    background: rgba(247, 248, 246, 0.55);
    border: 1px solid rgba(0, 0, 0, 0.04);
    border-radius: 6px;
}
.dept-card-sparkline {
    display: block;
    width: 100%;
    height: auto;
    max-width: 100%;
}
.dept-card-sparkline-legend {
    display: flex;
    justify-content: space-between;
    font-size: 0.68rem;
    color: #8a918e;
    letter-spacing: 0.04em;
    margin-top: -0.1rem;
}

/* Department detail page — per-dept funding history chart */
.dept-history-section {
    background: #fff;
    border-radius: 8px;
    border: 1px solid rgba(0, 0, 0, 0.06);
    padding: 1.1rem 1.2rem 0.9rem;
    margin: 1rem 0 1.4rem;
    box-shadow: 0 1px 3px rgba(0, 0, 0, 0.04);
}
.dept-history-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: wrap;
    gap: 0.6rem;
}
.dept-history-head h3 {
    margin: 0;
    font-size: var(--fs-lg);
    color: var(--heading-color);
}
.dept-history-sub {
    margin: 0.1rem 0 0.7rem;
    font-size: 0.85rem;
    color: #6a7370;
}
.dept-history-chart-wrap {
    height: 300px;
    margin-top: 0.4rem;
}

/* Narrow viewports — keep the year-bar and chart breathable */
@media (max-width: 720px) {
    .hb300-fy-select { min-width: 0; flex: 1 1 auto; }
    .hb300-history-chart-wrap { height: 240px; }
    .dept-history-chart-wrap { height: 240px; }
}

/* ── Department detail · Fund Type doughnut + legend ───────────────────────
   Replaces the plain three-column table.  Doughnut is fixed at 240×240
   on the left; the legend list flows on the right with a colour swatch
   matched to each chart slice.  Hovering a legend row highlights the
   slice (and vice versa) via JS.
   ────────────────────────────────────────────────────────────────────────── */
.fund-breakdown-section {
    background: #fff;
    border-radius: 8px;
    border: 1px solid rgba(0, 0, 0, 0.06);
    padding: 1.1rem 1.2rem 1rem;
    margin: 1rem 0 1.4rem;
    box-shadow: 0 1px 3px rgba(0, 0, 0, 0.04);
}
.fund-breakdown-head h3 {
    margin: 0;
    font-size: var(--fs-lg);
    color: var(--heading-color);
}
.fund-breakdown-sub {
    margin: 0.15rem 0 0.9rem;
    font-size: 0.85rem;
    color: #6a7370;
}
.fund-breakdown-body {
    display: flex;
    align-items: flex-start;
    gap: 1.6rem;
    flex-wrap: wrap;
}
.fund-doughnut-wrap {
    position: relative;
    width: 240px;
    height: 240px;
    flex-shrink: 0;
}
.fund-doughnut-wrap canvas {
    display: block;
}
.fund-doughnut-center {
    position: absolute;
    inset: 0;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    pointer-events: none;
    text-align: center;
    line-height: 1.2;
}
.fund-doughnut-total {
    font-family: 'Newsreader', Georgia, serif;
    font-size: 1.45rem;
    font-weight: 600;
    color: var(--primary-dark);
}
.fund-doughnut-total-lbl {
    margin-top: 0.15rem;
    font-size: 0.7rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: #8a918e;
}
.fund-legend-list {
    flex: 1 1 320px;
    display: flex;
    flex-direction: column;
    gap: 0.15rem;
    min-width: 280px;
}
.fund-legend-row {
    display: grid;
    grid-template-columns: 14px 1fr auto auto;
    align-items: center;
    gap: 0.6rem;
    padding: 0.5rem 0.55rem;
    border-radius: 6px;
    font-size: 0.92rem;
    color: #2f3a36;
    transition: background 0.12s ease, transform 0.12s ease;
    cursor: default;
}
.fund-legend-row:hover,
.fund-legend-row.active {
    background: #f4f6f3;
    transform: translateX(2px);
}
.fund-legend-swatch {
    width: 12px;
    height: 12px;
    border-radius: 3px;
    display: inline-block;
}
.fund-legend-name { color: #2f3a36; }
.fund-legend-amt {
    font-variant-numeric: tabular-nums;
    color: #4a5550;
    font-size: 0.9rem;
}
.fund-legend-pct {
    font-variant-numeric: tabular-nums;
    font-weight: 600;
    color: var(--primary-dark);
    min-width: 48px;
    text-align: right;
}

/* ── Department detail · Program cards ─────────────────────────────────────
   Card list replacing the wide table.  Each card layers three rows of
   information vertically: header (id / name / total), share bar, stats.
   Operating vs capital are colour-encoded everywhere in the card via
   the shared .prog-stat-* dot/swatch tokens.
   ────────────────────────────────────────────────────────────────────────── */
.programs-section {
    margin-top: 1.6rem;
}
.programs-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: wrap;
    gap: 0.6rem;
    margin-bottom: 0.4rem;
}
.programs-head h3 {
    margin: 0;
    font-size: var(--fs-lg);
    color: var(--heading-color);
    display: inline-flex;
    align-items: baseline;
    gap: 0.5rem;
}
.programs-count {
    display: inline-block;
    background: #eef2ec;
    color: #466e5f;
    font-size: 0.78rem;
    font-weight: 600;
    padding: 0.18rem 0.55rem;
    border-radius: 999px;
    letter-spacing: 0.02em;
}
.programs-legend {
    display: flex;
    gap: 1.1rem;
    flex-wrap: wrap;
    font-size: 0.78rem;
    color: #6a7370;
    margin-bottom: 0.65rem;
}
.prog-legend-item {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
}
.programs-note {
    font-size: 0.82rem;
    line-height: 1.55;
    color: #586A6D;
    background: #f8f9fa;
    border-left: 3px solid #b9c4c2;
    border-radius: 4px;
    padding: 0.6rem 0.85rem;
    margin: 0 0 0.85rem;
}
.prog-stat-dot {
    width: 9px;
    height: 9px;
    border-radius: 50%;
    display: inline-block;
    flex-shrink: 0;
}
.prog-stat-dot.prog-stat-op  { background: #5a7b68; }
.prog-stat-dot.prog-stat-cap { background: #a08e58; }
.prog-stat-dot.prog-stat-pos { background: #7d97a3; }

.programs-card-list {
    display: flex;
    flex-direction: column;
    gap: 0.55rem;
}
.program-card {
    background: #fff;
    border-radius: 8px;
    border: 1px solid rgba(0, 0, 0, 0.06);
    padding: 0.8rem 1rem 0.85rem;
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.03);
    transition: box-shadow 0.15s ease, transform 0.15s ease, border-color 0.15s ease;
}
.program-card:hover {
    box-shadow: 0 3px 8px rgba(0, 0, 0, 0.07);
    border-color: rgba(70, 110, 95, 0.2);
    transform: translateY(-1px);
}
.program-card-head {
    display: grid;
    grid-template-columns: auto 1fr auto;
    align-items: baseline;
    gap: 0.7rem;
    margin-bottom: 0.4rem;
}
.program-card-id {
    background: #eef2ec;
    color: #466e5f;
    font-family: 'SF Mono', 'Monaco', 'Consolas', monospace;
    font-size: 0.78rem;
    font-weight: 600;
    padding: 0.22rem 0.5rem;
    border-radius: 4px;
    letter-spacing: 0.02em;
    align-self: center;
}
.program-card-name {
    color: #2f3a36;
    font-size: 0.98rem;
    font-weight: 500;
    line-height: 1.3;
}
.program-card-total {
    font-family: 'Newsreader', Georgia, serif;
    font-size: 1.05rem;
    font-weight: 600;
    color: var(--primary-dark);
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
}
.program-card-bar {
    display: grid;
    grid-template-columns: 1fr auto;
    align-items: center;
    gap: 0.6rem;
    margin-bottom: 0.4rem;
}
.program-card-bar-track {
    position: relative;
    height: 6px;
    background: #f1f3ee;
    border-radius: 999px;
    overflow: hidden;
    display: flex;
}
.program-card-bar-op,
.program-card-bar-cap {
    height: 100%;
    transition: width 0.2s ease;
}
.program-card-bar-op  { background: #5a7b68; }
.program-card-bar-cap { background: #a08e58; }
.program-card-bar-label {
    font-size: 0.72rem;
    color: #8a918e;
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
}
.program-card-stats {
    display: flex;
    flex-wrap: wrap;
    gap: 0.55rem 1rem;
    font-size: 0.84rem;
    color: #6a7370;
}
.prog-stat {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
}
.prog-stat strong {
    color: #2f3a36;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    margin: 0 0.1rem;
}

/* Narrow viewport adjustments */
@media (max-width: 640px) {
    .fund-doughnut-wrap { width: 200px; height: 200px; margin: 0 auto; }
    .fund-doughnut-total { font-size: 1.2rem; }
    .program-card-head {
        grid-template-columns: auto 1fr;
    }
    .program-card-total {
        grid-column: 1 / -1;
        text-align: right;
    }
}

/* ── Dev-mode nav tabs ─────────────────────────────────────────────────────
   [data-dev-only] links are hidden by default — the explicit `display:none`
   is required because `.nav-link { display: flex }` would otherwise win
   over the HTML `hidden` attribute's UA stylesheet.  When the page is
   loaded with ?dev the <html> element gets data-dev="", which unhides
   them and adds a subtle DEV badge so they're visually distinguishable
   from production tabs.
   ────────────────────────────────────────────────────────────────────────── */
[data-dev-only] {
    display: none !important;
}
[data-dev] [data-dev-only] {
    display: inline-flex !important;
}
/* Small DEV badge appended after the tab label */
[data-dev] [data-dev-only]::after {
    content: 'DEV';
    display: inline-block;
    margin-left: 0.45rem;
    padding: 0.1em 0.4em;
    font-size: 0.62rem;
    font-weight: 700;
    letter-spacing: 0.06em;
    line-height: 1.4;
    vertical-align: middle;
    background: rgba(155, 44, 44, 0.15);
    color: #9b2c2c;
    border: 1px solid rgba(155, 44, 44, 0.35);
    border-radius: 3px;
    text-transform: uppercase;
    pointer-events: none;
}

/* ── Department breakdown hover card ──────────────────────────────────── */
/* Refined card: scrollable body, sticky header + net footer, grid-based rows
   with right-aligned tabular amounts, per-section subtotals. */
#dept-breakdown-card {
    position: absolute;
    z-index: 200;
    background: #ffffff;
    border: 1px solid rgba(0, 0, 0, 0.06);
    border-radius: 12px;
    box-shadow:
        0 1px 3px rgba(0, 0, 0, 0.04),
        0 12px 32px rgba(20, 30, 25, 0.18);
    overflow-y: auto;
    overscroll-behavior: contain;
    min-width: 380px;
    max-width: 480px;
    max-height: min(460px, 75vh);
    font-size: 0.82rem;
    line-height: 1.45;
    color: #2c3e35;
    display: none;
    font-family: inherit;
    padding: 0;
}
#dept-breakdown-card::-webkit-scrollbar {
    width: 8px;
}
#dept-breakdown-card::-webkit-scrollbar-track {
    background: transparent;
}
#dept-breakdown-card::-webkit-scrollbar-thumb {
    background: rgba(0, 0, 0, 0.16);
    border-radius: 4px;
    border: 2px solid #fff;
}
#dept-breakdown-card::-webkit-scrollbar-thumb:hover {
    background: rgba(0, 0, 0, 0.28);
}

/* Sticky header — stays anchored while body scrolls */
.dept-bd-header {
    position: sticky;
    top: 0;
    z-index: 3;
    display: flex;
    align-items: flex-start;
    gap: 9px;
    padding: 12px 16px 11px;
    background: linear-gradient(180deg, #fafcfb 0%, #f4f7f5 100%);
    border-bottom: 1px solid rgba(0, 0, 0, 0.06);
    border-radius: 12px 12px 0 0;
}
.dept-bd-dept-chip {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-weight: 700;
    font-size: 0.74rem;
    letter-spacing: 0.04em;
    padding: 3px 8px;
    border-radius: 5px;
    background: #e0eae5;
    color: #2c3e35;
    flex-shrink: 0;
    margin-top: 2px;
}
.dept-bd-dept-name {
    font-size: 0.93rem;
    font-weight: 600;
    color: #2c3e35;
    overflow: hidden;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
    letter-spacing: -0.005em;
    line-height: 1.35;
}

/* Department description under the header — the same copy the detail page shows.
   Scrolls with the body (the header above is sticky); clamps tall paragraphs. */
.dept-bd-desc {
    margin: 0;
    padding: 10px 16px 0;
    font-size: 0.78rem;
    line-height: 1.5;
    color: #5b6b62;
}

/* Body wrapper just provides padding inside the scrollable card */
.dept-bd-body {
    padding: 4px 14px 6px;
}

.dept-bd-section {
    margin-top: 8px;
}
.dept-bd-section:first-child {
    margin-top: 4px;
}
.dept-bd-section-head {
    display: grid;
    grid-template-columns: 14px minmax(0, 1fr) auto;
    align-items: baseline;
    gap: 7px;
    padding: 5px 0 4px;
    border-bottom: 1px solid rgba(0, 0, 0, 0.05);
    margin-bottom: 2px;
}
.dept-bd-section-icon {
    font-size: 0.62rem;
    text-align: center;
    line-height: 1;
}
.dept-bd-icon-up    { color: #1a8050; }
.dept-bd-icon-down  { color: #b32a2a; }
.dept-bd-icon-xfer  { color: #b88a14; }
.dept-bd-section-label {
    font-size: 0.69rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: #6f7d77;
}
.dept-bd-section-total {
    font-size: 0.78rem;
    font-weight: 700;
    font-variant-numeric: tabular-nums;
    letter-spacing: -0.01em;
}
.dept-bd-section-total.positive    { color: #1a8050; }
.dept-bd-section-total.negative    { color: #b32a2a; }
.dept-bd-section-total.transferred { color: #b88a14; }

/* Grid row keeps amount column on a fixed rail so digits align vertically.
   Transparent 3px left border by default; transfer rows color it to indicate
   direction (red-amber for outflow, green-teal for inflow). Border is INSIDE
   the existing horizontal padding so non-transfer rows don't shift. */
.dept-bd-row {
    display: grid;
    grid-template-columns: auto minmax(0, 1fr) 96px minmax(0, auto);
    align-items: center;
    column-gap: 9px;
    padding: 4px 6px 4px 3px;
    margin: 0 -6px;
    border-left: 3px solid transparent;
    border-radius: 5px;
    transition: background 0.1s ease;
}
.dept-bd-row:hover {
    background: rgba(0, 0, 0, 0.025);
}
/* Outflow: money leaving this dept — red-amber edge matches the negative palette. */
.dept-bd-row-xfer-out {
    border-left-color: #c2410c;
    background: linear-gradient(to right, rgba(194, 65, 12, 0.04) 0%, transparent 40%);
}
/* Inflow: money arriving from another dept — teal edge matches the positive palette. */
.dept-bd-row-xfer-in {
    border-left-color: #0f7a5c;
    background: linear-gradient(to right, rgba(15, 122, 92, 0.05) 0%, transparent 40%);
}
.dept-bd-row-xfer-out:hover,
.dept-bd-row-xfer-in:hover {
    /* Preserve the directional tint on hover; just deepen it a touch. */
    filter: brightness(0.985);
}
/* Increase rows — green trim. */
.dept-bd-row-pos {
    border-left-color: #1a6b3a;
    background: linear-gradient(to right, rgba(26, 107, 58, 0.04) 0%, transparent 40%);
}
/* Reduction rows — red trim. */
.dept-bd-row-neg {
    border-left-color: #8b1a1a;
    background: linear-gradient(to right, rgba(139, 26, 26, 0.04) 0%, transparent 40%);
}
.dept-bd-row-pos:hover,
.dept-bd-row-neg:hover {
    filter: brightness(0.985);
}
/* Click-to-jump affordance: rows that wire up to the main table get a
   pointer cursor + a slightly stronger hover. Keyboard focus is ringed. */
.dept-bd-row-clickable {
    cursor: pointer;
}
.dept-bd-row-clickable:focus-visible {
    outline: 2px solid #0f7a5c;
    outline-offset: 1px;
}
/* Sub-group within a transfer section: a "to AGS · $30M · 2 programs" header
   followed by the rows that move to/from that counterpart dept. Indented
   slightly so the visual hierarchy reads section → group → row. */
.dept-bd-subgroup {
    margin: 4px 0 6px 0;
}
.dept-bd-subgroup-head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    padding: 3px 4px 3px 8px;
    margin: 2px 0 1px 0;
    font-size: 0.74rem;
    color: #6f7d77;
    border-bottom: 1px dashed rgba(0, 0, 0, 0.07);
}
.dept-bd-subgroup-label {
    font-weight: 500;
    letter-spacing: 0.01em;
    color: #5a6964;
}
.dept-bd-subgroup-dept {
    display: inline-block;
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 0.72rem;
    font-weight: 700;
    padding: 1px 6px;
    margin-left: 2px;
    border-radius: 3px;
    background: rgba(40, 60, 50, 0.06);
    color: #2c3e35;
    letter-spacing: 0.01em;
}
.dept-bd-subgroup-meta {
    font-variant-numeric: tabular-nums;
    font-weight: 600;
    color: #7a5c0a;
    white-space: nowrap;
}

/* Section icons: directional colors for the OUT/IN sub-section icons. */
.dept-bd-icon-xferOut { color: #c2410c; }
.dept-bd-icon-xferIn  { color: #0f7a5c; }

/* Row-flash: brief highlight on the main-table row after a tooltip jump,
   so the user's eye can lock onto where they landed. */
@keyframes row-flash-anim {
    0%   { background-color: rgba(247, 217, 100, 0.45); }
    100% { background-color: transparent; }
}
.row-flash {
    animation: row-flash-anim 1.4s ease-out;
}
.row-flash > td {
    animation: row-flash-anim 1.4s ease-out;
}
.dept-bd-pid {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 0.69rem;
    font-weight: 700;
    padding: 1px 6px;
    border-radius: 3px;
    background: rgba(40, 60, 50, 0.06);
    color: #2c3e35;
    white-space: nowrap;
    letter-spacing: 0.01em;
}
.dept-bd-name {
    color: #4a5e57;
    font-size: 0.80rem;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    min-width: 0;
}
.dept-bd-amt {
    text-align: right;
    font-size: 0.79rem;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
    letter-spacing: -0.01em;
    padding: 2px 8px;
    border-radius: 5px;
    border: 1px solid transparent;
    white-space: nowrap;
    justify-self: end;
}
.dept-bd-amt.positive {
    color: #1a6b3a;
    background: #eaf7ee;
    border-color: #c5e6d2;
}
.dept-bd-amt.negative {
    color: #8b1a1a;
    background: #fdf0f0;
    border-color: #efcacb;
}
.dept-bd-amt.transferred {
    color: #7a5c0a;
    background: #fdf6e3;
    border-color: #ecd998;
}
.dept-bd-dest {
    font-size: 0.7rem;
    font-weight: 500;
    color: #8b6914;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    min-width: 0;
}

.dept-bd-empty {
    color: #6f7d77;
    font-size: 0.82rem;
    padding: 18px 0;
    text-align: center;
}

/* Sticky net footer */
.dept-bd-net {
    position: sticky;
    bottom: 0;
    z-index: 3;
    background: linear-gradient(180deg, #f4f7f5 0%, #fafcfb 100%);
    border-top: 1px solid rgba(0, 0, 0, 0.07);
    border-radius: 0 0 12px 12px;
    padding: 10px 16px 11px;
    display: grid;
    grid-template-columns: 1fr auto;
    align-items: baseline;
    column-gap: 12px;
    row-gap: 4px;
    margin-top: 4px;
}
.dept-bd-net-label {
    font-size: 0.78rem;
    font-weight: 600;
    color: #2c3e35;
    letter-spacing: -0.005em;
}
.dept-bd-net-value {
    font-size: 1.0rem;
    font-weight: 700;
    font-variant-numeric: tabular-nums;
    letter-spacing: -0.015em;
    text-align: right;
}
.dept-bd-net-value.positive { color: #1a8050; }
.dept-bd-net-value.negative { color: #b32a2a; }
.dept-bd-net-xfer-line {
    grid-column: 1 / -1;
    font-size: 0.72rem;
    color: #8b6914;
    font-weight: 500;
    padding-top: 2px;
    border-top: 1px dashed rgba(184, 138, 20, 0.25);
}

/* Cursor hint on the change cell so users know it's hoverable */
[data-dept-bd] {
    cursor: help;
}
/* Small amber badge below the dept change chip when transfers exist.
   Shows "→ $49.75M reshuffled" so the user knows the real-net chip
   above excludes reshuffled money. */
.dept-xfer-note {
    display: inline-block;
    margin-top: 4px;
    padding: 1px 6px;
    border-radius: 4px;
    font-size: 0.7rem;
    font-weight: 600;
    color: #7a5c0a;
    background: #fef8e7;
    border: 1px solid #f0d580;
    white-space: nowrap;
    line-height: 1.5;
}
/* Transfer footnote inside the breakdown tooltip net line */
.dept-bd-net-xfer {
    font-size: 0.75rem;
    font-weight: 400;
    color: #8b6914;
    margin-left: 4px;
}


/* ── Floating back-to-top ────────────────────────────────────────────────
   Appears after ~1.25 viewports of scroll (JS toggles .show). Sage circle in
   the same family as the timeline chips; sits clear of the table export row. */
.back-to-top {
    position: fixed;
    right: 22px;
    bottom: 22px;
    width: 42px;
    height: 42px;
    border-radius: 50%;
    border: 1px solid rgba(255, 255, 255, 0.35);
    background: linear-gradient(135deg, #84a89c 0%, #6f9184 100%);
    color: #ffffff;
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    box-shadow: 0 3px 10px rgba(60, 82, 73, 0.30);
    opacity: 0;
    visibility: hidden;
    transform: translateY(8px);
    transition: opacity 0.2s ease, transform 0.2s ease, visibility 0.2s;
    z-index: 50;
}
.back-to-top.show {
    opacity: 1;
    visibility: visible;
    transform: translateY(0);
}
.back-to-top:hover {
    background: linear-gradient(135deg, #79a092 0%, #62867a 100%);
    box-shadow: 0 4px 14px rgba(60, 82, 73, 0.38);
}

/* ---------------------------------------------------------------------------
   County budgets — State|Counties scope pill, county selector tabs, and the
   counties page (summary cards reuse existing .summary-card styles).
   --------------------------------------------------------------------------- */

/* Scope pill: sits between the subtitle and the main nav. Smaller-scale echo
   of the .main-nav segmented control so it reads as chrome, not a sibling. */
/* Scope switch (State ↔ Counties) — a top-level mode toggle, pinned to the
   header's top-right corner as a frosted-glass control so it's clearly its own
   thing rather than competing with the centered bill tabs. */
.scope-toggle {
    position: absolute;
    top: 1rem;
    right: 1.15rem;
    z-index: 3;
    display: inline-flex;
    align-items: center;
    gap: 0.1rem;
    padding: 4px;
    border-radius: 999px;
    background: rgba(255, 255, 255, 0.16);
    border: 1px solid rgba(255, 255, 255, 0.5);
    box-shadow: 0 3px 12px rgba(0, 0, 0, 0.20);
    -webkit-backdrop-filter: blur(5px);
    backdrop-filter: blur(5px);
}
.scope-btn {
    color: #fff;
    text-decoration: none;
    padding: 0.34rem 0.85rem;
    border-radius: 999px;
    font-size: 0.78rem;
    font-weight: 700;
    letter-spacing: 0.05em;
    white-space: nowrap;
    transition: background 0.22s ease, color 0.22s ease;
}
.scope-btn:hover { background: rgba(255, 255, 255, 0.14); }
.scope-btn.active {
    background: #fff;
    color: #3d5249;
    box-shadow: 0 1px 4px rgba(0, 0, 0, 0.20);
}

/* County mode keeps the state bill tabs visible: the prominent scope toggle is
   gone (the county view is reached by a quiet footer link now), so the bill
   tabs are the way back to the state view. */

/* Quiet entry to the county view — a small, faint footer link, intentionally
   easy to miss. */
.app-footer-counties {
    margin: 0.4rem 0 0;
}
.app-footer-counties a {
    color: #d2d7d3;
    font-size: 0.7rem;
    letter-spacing: 0.03em;
    text-decoration: none;
    transition: color 0.2s ease;
}
.app-footer-counties a:hover {
    color: #8aa595;
    text-decoration: underline;
}

/* County selector tabs on the counties page */
.county-tabs {
    display: flex;
    flex-wrap: wrap;
    gap: 0.5rem;
    margin: 0 0 1.2rem;
}
.county-tab {
    padding: 0.45rem 1.1rem;
    border-radius: 999px;
    border: 1px solid #d4ddd6;
    background: #fff;
    color: #3d5249;
    text-decoration: none;
    font-weight: 600;
    font-size: 0.95rem;
    transition: background 0.2s ease, color 0.2s ease;
}
.county-tab:hover { background: #eef3ef; }
.county-tab.active {
    background: #3d5249;
    border-color: #3d5249;
    color: #fff;
}
.county-tab-disabled {
    color: #9aa6a0;
    background: #f4f6f5;
    cursor: default;
}
.county-tab-soon {
    margin-left: 0.45em;
    font-size: 0.7rem;
    font-weight: 700;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    color: #b3beb8;
}
.county-title { margin: 0 0 1rem; }

/* Coverage caveat + source line */
.county-caveat {
    font-size: 0.92rem;
    color: #5c6b63;
    background: #f4f6f1;
    border-left: 3px solid #c8cfa8;
    padding: 0.7rem 1rem;
    border-radius: 0 6px 6px 0;
    margin: 1rem 0;
}
.county-source {
    font-size: 0.88rem;
    color: #6b7a72;
    margin-top: 1.2rem;
}

/* Fund-category stacked bar */
.fund-cat-bar-wrap { margin: 1.2rem 0 1.6rem; }
.fund-cat-bar {
    display: flex;
    height: 16px;
    border-radius: 8px;
    overflow: hidden;
    border: 1px solid #d4ddd6;
}
.fund-cat-seg { display: block; height: 100%; }
.fund-cat-legend {
    display: flex;
    flex-wrap: wrap;
    gap: 0.4rem 1.2rem;
    margin-top: 0.55rem;
    font-size: 0.88rem;
    color: #4a5a52;
}
.fund-cat-legend-item { display: inline-flex; align-items: center; gap: 0.4em; }
.fund-cat-legend-amt { color: #7c8a83; }

/* Department table: expandable rows + share bars */
.county-table .county-dept-row { cursor: pointer; }
.county-table .county-dept-row:hover td { background: #f5f8f6; }
/* Flat rows have no program detail to expand (e.g. Hawaiʻi fund-level). */
.county-table .county-dept-flat { cursor: default; }
.county-table .county-dept-flat:hover td { background: transparent; }
.county-row-chevron {
    display: inline-block;
    width: 1.1em;
    color: #8aa595;
    font-size: 0.85em;
}
.county-share-cell { min-width: 130px; }
.county-share-bar {
    display: inline-block;
    vertical-align: middle;
    width: 80px;
    height: 9px;
    border-radius: 5px;
    background: #edf1ee;
    overflow: hidden;
    margin-right: 0.5em;
}
.county-share-fill {
    display: block;
    height: 100%;
    border-radius: 5px;
    background: linear-gradient(90deg, #5a7b68, #7da48d);
}
.county-share-pct { font-size: 0.85rem; color: #6b7a72; }
.county-prog-row td {
    background: #fafbfa;
    font-size: 0.92rem;
    border-top: none;
}
.county-prog-name { padding-left: 2.1em !important; color: #4a5a52; }
.county-prog-fund {
    margin-left: 0.7em;
    font-size: 0.8rem;
    color: #8a978f;
    font-variant: small-caps;
    letter-spacing: 0.04em;
}

@media (max-width: 768px) {
    .scope-toggle { top: 0.7rem; right: 0.7rem; }
    .scope-btn { padding: 0.26rem 0.7rem; font-size: 0.74rem; letter-spacing: 0.03em; }
    .county-tab { padding: 0.4rem 0.85rem; font-size: 0.88rem; }
    .county-share-cell { display: none; }
    .county-table th:nth-child(3) { display: none; }
}
/* Narrow phones: shrink the four bill tabs so the no-wrap row fits without
   being clipped (the page can't scroll sideways — see body overflow-x). */
@media (max-width: 430px) {
    .main-nav { gap: 0.1rem; }
    .nav-link { padding: 0.45rem 0.7rem; font-size: 1rem; }
}

/* Program-level detail inside expanded department rows */
.county-prog-count {
    margin-left: 0.7em;
    font-size: 0.8rem;
    color: #9aa6a0;
    white-space: nowrap;
}
.county-prog-funds {
    display: flex;
    flex-wrap: wrap;
    gap: 0.3rem 0.4rem;
    margin-top: 0.35rem;
}
.county-fund-chip {
    display: inline-flex;
    align-items: baseline;
    gap: 0.35em;
    padding: 0.12rem 0.55rem;
    border-radius: 999px;
    background: #eef3ef;
    border: 1px solid #dde6df;
    font-size: 0.78rem;
    color: #4a5a52;
    font-variant: normal;
    letter-spacing: 0;
}
.county-fund-chip .fmt-num { font-weight: 600; }
.county-fund-chip .fmt-unit { color: #8a978f; }

/* Toolbar: county tabs on the left, fiscal-year toggle on the right */
.county-toolbar {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    gap: 0.8rem 1.2rem;
    margin-bottom: 1.1rem;
}
.county-toolbar .county-tabs { margin: 0; }
.county-year-toggle {
    display: inline-flex;
    align-items: center;
    gap: 0.4rem;
}
.county-year-label {
    font-size: 0.95rem;
    color: #6b7a72;
    margin-right: 0.2rem;
}
.county-year-btn {
    padding: 0.42rem 0.95rem;
    border-radius: 999px;
    border: 1px solid #d4ddd6;
    background: #fff;
    color: #3d5249;
    font-weight: 600;
    font-size: 1rem;
    cursor: pointer;
    transition: background 0.18s ease, color 0.18s ease;
}
.county-year-btn:hover { background: #eef3ef; }
.county-year-btn.active {
    background: #3d5249;
    border-color: #3d5249;
    color: #fff;
}

/* Operating / CIP sections */
.county-section { margin: 1.8rem 0; }
.county-section-head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 1rem;
    padding-bottom: 0.5rem;
    border-bottom: 2px solid #e3eae5;
    margin-bottom: 0.3rem;
}
.county-section-title {
    margin: 0;
    font-size: 1.25rem;
    color: #2f3f37;
}
.county-section-tag {
    margin-left: 0.5em;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.09em;
    color: #fff;
    background: #a68c68;
    padding: 0.1em 0.5em;
    border-radius: 4px;
    vertical-align: middle;
}
.county-section-total {
    font-size: 1.2rem;
    font-weight: 700;
    color: #3d5249;
    white-space: nowrap;
}
.fund-cat-bar-title {
    font-size: 0.95rem;
    color: #5c6b63;
    margin-bottom: 0.5rem;
}
.county-total-card .amount { color: #2f3f37; }

/* CIP project list */
.cip-toolbar {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    gap: 0.6rem 1rem;
    margin: 0.4rem 0 0.8rem;
}
.cip-search {
    flex: 1 1 240px;
    max-width: 360px;
    padding: 0.55rem 0.9rem;
    border-radius: 8px;
    border: 1px solid #d4ddd6;
    background: #fff;
    font-size: 1rem;
    color: #2f3f37;
}
.cip-search:focus {
    outline: none;
    border-color: #7da48d;
    box-shadow: 0 0 0 3px rgba(125, 164, 141, 0.18);
}
.cip-sort { display: inline-flex; gap: 0.35rem; }
.cip-sort-btn {
    padding: 0.4rem 0.85rem;
    border-radius: 999px;
    border: 1px solid #d4ddd6;
    background: #fff;
    color: #4a5a52;
    font-size: 0.95rem;
    font-weight: 600;
    cursor: pointer;
}
.cip-sort-btn.active { background: #3d5249; border-color: #3d5249; color: #fff; }
.cip-table .cip-proj-name { color: #2f3f37; }
.cip-proj-func {
    display: block;
    font-size: 0.8rem;
    color: #8a978f;
    margin-top: 0.15rem;
}
.cip-proj-fund {
    font-size: 0.92rem;
    color: #5c6b63;
    white-space: nowrap;
}
.cip-fund-more {
    font-size: 0.78rem;
    color: #8a978f;
    background: #eef3ef;
    border-radius: 999px;
    padding: 0.05rem 0.45rem;
}
.cip-note {
    font-size: 0.9rem;
    color: #6b7a72;
    margin-top: 0.7rem;
}
.cip-empty { text-align: center; color: #8a978f; padding: 1.4rem 0; }

@media (max-width: 768px) {
    .county-toolbar { gap: 0.6rem; }
    .cip-table th:nth-child(2), .cip-table td.cip-proj-fund { display: none; }
}

/* ── County data-viz: hero, fund donut, treemap, function bars ─────────────── */

/* "Budget at a glance" hero — total + an Operating/Capital proportion bar. */
.county-hero {
    display: grid;
    grid-template-columns: minmax(150px, 0.8fr) 2fr;
    gap: 1.4rem 2.2rem;
    align-items: center;
    background: #fff;
    border: 1px solid var(--border-color);
    border-radius: 12px;
    box-shadow: var(--shadow);
    padding: 1.5rem 1.7rem;
    margin: 1.5rem 0;
}
.chero-total-amt { font-size: 2.4rem; font-weight: 700; color: #2f3f37; line-height: 1; }
.chero-total-amt .fmt-unit { font-size: 0.5em; color: #7a8fa6; margin-left: 0.12em; }
.chero-total-lbl { margin-top: 0.45rem; font-size: 0.92rem; color: #6b7a72; letter-spacing: 0.02em; }
.chero-fy {
    display: inline-block; margin-left: 0.3em; padding: 0.05em 0.5em;
    border-radius: 999px; background: #eef3ef; color: #3d5249;
    font-weight: 700; font-size: 0.82em;
}
.chero-bar { display: flex; height: 16px; border-radius: 999px; overflow: hidden; background: #edf1ee; }
.chero-seg { height: 100%; transition: width 0.5s cubic-bezier(0.2, 0, 0.2, 1); }
.chero-seg-op  { background: linear-gradient(90deg, #5a7b68, #6f9580); }
.chero-seg-cap { background: linear-gradient(90deg, #b89a6f, #c9a87b); }
.chero-figs { display: flex; flex-wrap: wrap; gap: 1.1rem 2rem; margin-top: 0.9rem; }
.chero-fig { display: flex; align-items: flex-start; gap: 0.5rem; }
.chero-fig-dot { width: 11px; height: 11px; border-radius: 3px; margin-top: 0.32rem; flex: none; }
.chero-fig.is-op  .chero-fig-dot { background: #6f9580; }
.chero-fig.is-cap .chero-fig-dot { background: #c9a87b; }
.chero-fig-amt { font-size: 1.35rem; font-weight: 700; color: #2f3f37; line-height: 1.05; }
.chero-fig-amt .fmt-unit { font-size: 0.55em; color: #7a8fa6; margin-left: 0.1em; }
.chero-dash { color: #b6c0ba; }
.chero-fig-lbl { font-size: 0.85rem; color: #6b7a72; margin-top: 0.12rem; }

/* Two-up overview row: fund donut + treemap (operating) / function bars (CIP). */
.county-overview {
    display: grid;
    grid-template-columns: minmax(260px, 1fr) minmax(280px, 1.35fr);
    gap: 1.4rem;
    margin: 0.9rem 0 1.2rem;
}
.county-viz {
    background: #fff; border: 1px solid var(--border-color);
    border-radius: 10px; padding: 1rem 1.1rem 1.1rem;
}
.county-viz-title {
    font-size: 0.82rem; font-weight: 600; letter-spacing: 0.04em;
    text-transform: uppercase; color: #7a8a80; margin-bottom: 0.7rem;
}

/* Fund doughnut + legend */
.cdonut { display: flex; align-items: center; gap: 1.1rem; flex-wrap: wrap; }
.cdonut-chart { position: relative; width: 150px; height: 150px; flex: none; }
.cdonut-center {
    position: absolute; inset: 0; pointer-events: none;
    display: flex; flex-direction: column; align-items: center; justify-content: center;
}
.cdonut-center-amt { font-size: 1.15rem; font-weight: 700; color: #2f3f37; }
.cdonut-center-lbl { font-size: 0.66rem; color: #8a978f; text-transform: uppercase; letter-spacing: 0.06em; }
.cdonut-legend { list-style: none; margin: 0; padding: 0; flex: 1 1 150px; min-width: 0; }
.cdonut-legend-row { display: flex; align-items: center; gap: 0.5rem; padding: 0.22rem 0; font-size: 0.9rem; color: #3f4f47; }
.cdonut-swatch { width: 10px; height: 10px; border-radius: 3px; flex: none; }
.cdonut-legend-name { flex: 1 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cdonut-legend-amt { font-variant-numeric: tabular-nums; color: #2f3f37; font-weight: 600; white-space: nowrap; }
.cdonut-legend-amt em { font-style: normal; color: #93a199; font-weight: 500; margin-left: 0.4em; }

/* Treemap canvas */
.ctreemap { width: 100%; height: 230px; }
.county-viz-treemap { display: flex; flex-direction: column; }

/* CIP "by function" bars */
.cfn-list { list-style: none; margin: 0; padding: 0; }
.cfn-row {
    display: grid; grid-template-columns: minmax(84px, 1.1fr) 2fr auto;
    align-items: center; gap: 0.6rem; padding: 0.3rem 0; font-size: 0.9rem;
}
.cfn-name { color: #3f4f47; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cfn-bar { height: 9px; border-radius: 5px; background: #edf1ee; overflow: hidden; }
.cfn-fill { display: block; height: 100%; border-radius: 5px; }
.cfn-amt { font-variant-numeric: tabular-nums; font-weight: 600; color: #2f3f37; white-space: nowrap; }

/* Fund-color dot before each CIP project name (keeps fund visible when the
   funding-source column is hidden on phones). */
.cip-fund-dot { display: inline-block; width: 8px; height: 8px; border-radius: 2px; margin-right: 0.5em; vertical-align: middle; }

@media (max-width: 760px) {
    .county-hero { grid-template-columns: 1fr; gap: 1rem; }
    .county-overview { grid-template-columns: 1fr; }
    .cdonut-chart { margin: 0 auto; }
}
