/* State Ledger - shared stylesheet. No build step: plain hand-written CSS. */

:root {
  --bg: #F3F0E7;
  --surface: #FFFEFA;
  --surface-2: #EAE4D5;
  --ink: #1C2226;
  --ink-muted: #5B6670;
  --border: rgba(28, 34, 38, 0.2);
  --gold: #B8863A;
  --teal: #178F73;
  --brick: #B14B3B;
  --gold-soft: #B8863A22;
  --teal-soft: #178F7320;
  --brick-soft: #B14B3B1E;
  color-scheme: light dark;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --bg: #14191D;
    --surface: #1B2126;
    --surface-2: #212830;
    --ink: #ECE9E1;
    --ink-muted: #9BA3A8;
    --border: rgba(236, 233, 225, 0.2);
    --gold: #B07E3E;
    --teal: #219478;
    --brick: #C05545;
    --gold-soft: #B07E3E26;
    --teal-soft: #21947824;
    --brick-soft: #C0554522;
  }
}

:root[data-theme="dark"] {
  --bg: #14191D;
  --surface: #1B2126;
  --surface-2: #212830;
  --ink: #ECE9E1;
  --ink-muted: #9BA3A8;
  --border: rgba(236, 233, 225, 0.2);
  --gold: #B07E3E;
  --teal: #219478;
  --brick: #C05545;
  --gold-soft: #B07E3E26;
  --teal-soft: #21947824;
  --brick-soft: #C0554522;
}

* { box-sizing: border-box; }

html, body {
  background: var(--bg);
}

body {
  margin: 0;
  color: var(--ink);
  font-family: "IBM Plex Sans", -apple-system, "Segoe UI", sans-serif;
  padding-inline: 20px;
  line-height: 1.5;
}

img { max-width: 100%; }
[hidden] { display: none !important; }

.wrap { max-width: 1080px; margin: 0 auto; }

h1, h2, h3 { font-family: "Newsreader", Georgia, serif; font-weight: 600; text-wrap: balance; margin: 0; }

.num, .kpi-value, .tabular {
  font-family: "IBM Plex Mono", ui-monospace, monospace;
  font-variant-numeric: tabular-nums;
}

.eyebrow {
  font-family: "IBM Plex Mono", monospace;
  font-size: 11px;
  letter-spacing: .09em;
  text-transform: uppercase;
  color: var(--ink-muted);
}

a { color: var(--teal); text-decoration: none; }
a:hover, a:focus-visible { text-decoration: underline; }
a:focus-visible, input:focus-visible, select:focus-visible, button:focus-visible {
  outline: 2px solid var(--teal);
  outline-offset: 2px;
}

.hairline { border-top: 1px solid var(--border); margin: 0; }

/* ---------- top bar ---------- */
.topbar {
  position: sticky;
  top: env(safe-area-inset-top, 0px);
  z-index: 5;
  background: var(--bg);
  border-bottom: 1px solid var(--border);
}
.topbar-inner {
  display: flex; align-items: center; justify-content: space-between;
  padding: 14px 0; gap: 12px; flex-wrap: wrap;
}
.brand { display: flex; align-items: baseline; gap: 8px; color: var(--ink); }
.brand .mark { width: 20px; height: 20px; border-radius: 3px; background: var(--gold); display: inline-block; flex: none; }
.brand-name { font-family: "Newsreader", serif; font-weight: 600; font-size: 19px; }
nav.toplinks { display: flex; gap: 22px; font-size: 14px; }
nav.toplinks a { color: var(--ink); font-weight: 500; }
nav.toplinks a.active { color: var(--teal); }

/* ---------- hero ---------- */
.hero { padding: 40px 0 28px; display: grid; gap: 18px; }
.hero h1 { font-size: clamp(28px, 4.2vw, 44px); line-height: 1.1; max-width: 17ch; }
.hero p.lede { font-size: 16.5px; color: var(--ink-muted); max-width: 60ch; line-height: 1.55; margin: 0; }

/* Homepage-only: a shorter hero so the state explorer/map sits higher
   on the page. Scoped to .hero-home (index.php only) rather than
   changing .hero itself, which markets.php and status.php also use
   for their own page headers. */
.hero-home { padding: 26px 0 18px; gap: 10px; }
.hero-home p.lede { max-width: 62ch; }

/* Homepage-only: the "Explore a State" divider sits directly under a
   hero that already provides its own spacing, so it skips the
   .section-label top rule/margin used for mid-page dividers elsewhere
   (state.php, and "National Snapshot" below). ID selector keeps this
   off the shared class. */
#states { margin-top: 4px; padding-top: 0; border-top: none; }

.status-strip { display: flex; gap: 10px; flex-wrap: wrap; margin-top: 6px; }
.status-pill {
  display: flex; align-items: center; gap: 7px; padding: 6px 11px;
  border: 1px solid var(--border); border-radius: 999px; font-size: 12.5px;
  background: var(--surface);
}
.status-dot { width: 7px; height: 7px; border-radius: 50%; background: var(--teal); flex: none; }
.status-dot.failed { background: var(--brick); }
.status-pill .lbl { color: var(--ink-muted); }
.status-pill .val { font-family: "IBM Plex Mono", monospace; font-size: 11.5px; }

/* Homepage footer metadata - the same freshness data the hero's
   .status-pill row used to show, moved here so it reads as
   publication metadata (plain text, no pill/card chrome) rather than
   competing with the hero. Reuses .status-dot and .section-label as-is
   - .status-strip/.status-pill above are untouched and still used by
   markets.php. */
.freshness-strip {
  display: flex; flex-wrap: wrap; align-items: baseline; gap: 8px 22px;
  font-size: 12px; color: var(--ink-muted);
}
.freshness-item { display: flex; align-items: baseline; gap: 6px; }
.freshness-name { color: var(--ink); }
.freshness-time { font-family: "IBM Plex Mono", monospace; font-size: 11px; color: var(--ink-muted); }
.freshness-status-link { font-size: 12px; margin-left: auto; }

@media (max-width: 480px) {
  .freshness-strip { gap: 6px 16px; }
  .freshness-status-link { margin-left: 0; width: 100%; }
}

/* ---------- generic tile grids ---------- */
.tile-grid {
  display: grid; gap: 1px; background: var(--border);
  border: 1px solid var(--border); border-radius: 10px; overflow: hidden;
}
.tile-grid.cols-4 { grid-template-columns: repeat(4, 1fr); }
.tile-grid.cols-6 { grid-template-columns: repeat(6, 1fr); }
.tile-grid.cols-3 { grid-template-columns: repeat(3, 1fr); }
.tile-grid.cols-2 { grid-template-columns: repeat(2, 1fr); }
.tile-grid .tile { background: var(--surface); padding: 16px 16px 15px; }
.tile-grid .tile .kpi-value { font-size: 22px; font-weight: 600; }
.tile-grid .tile .kpi-sub { font-size: 11.5px; color: var(--ink-muted); margin-top: 4px; }
.tile-grid.cols-6 .tile .kpi-value { font-size: 19px; }

.trend { display: inline-flex; align-items: center; gap: 3px; font-size: 11px; margin-top: 3px; }
.trend.up { color: var(--teal); }
.trend.down { color: var(--brick); }

/* ---------- section heading ---------- */
.section-head { display: flex; align-items: baseline; justify-content: space-between; margin: 44px 0 16px; gap: 12px; flex-wrap: wrap; }
.section-head h2 { font-size: 22px; }
.section-head .see-all { font-size: 13px; font-family: "IBM Plex Mono", monospace; }

/* ---------- state picker ---------- */
.picker-bar { display: flex; gap: 10px; align-items: center; margin-bottom: 14px; flex-wrap: wrap; }
.search-input {
  flex: 1; min-width: 200px; padding: 10px 14px; border: 1px solid var(--border);
  border-radius: 8px; background: var(--surface); color: var(--ink); font-size: 14px;
  font-family: inherit;
}
.state-empty-msg {
  text-align: center; padding: 16px; color: var(--ink-muted); font-size: 12.5px; line-height: 1.6;
  font-family: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
}

/* ---------- state map ---------- */
.map-wrap {
  border: 1px solid var(--border); border-radius: 10px; background: var(--surface);
  padding: 10px 14px 14px;
}
.map-status {
  margin: 0 0 4px; font-size: 12.5px; color: var(--ink-muted); min-height: 1.4em;
  font-family: "IBM Plex Mono", monospace;
}
.us-map { display: block; width: 100%; height: auto; }
.state-shape {
  fill: var(--surface-2); stroke: var(--border); stroke-width: 1;
  transition: fill .12s ease, stroke .12s ease;
}
.state-link { cursor: pointer; }
.state-link:hover .state-shape,
.state-link:focus-visible .state-shape {
  fill: var(--teal-soft); stroke: var(--teal); stroke-width: 1.5;
}
.state-link.search-match .state-shape {
  fill: var(--gold-soft); stroke: var(--gold); stroke-width: 1.5;
}
.state-link:focus-visible { outline: none; }
.state-label-text {
  font-family: "IBM Plex Mono", monospace; font-size: 9px; text-anchor: middle;
  fill: var(--ink-muted); pointer-events: none; dominant-baseline: middle;
}
.state-link:hover .state-label-text,
.state-link:focus-visible .state-label-text,
.state-link.search-match .state-label-text {
  fill: var(--ink);
}
.callout-leader { stroke: var(--border); stroke-width: 1; stroke-dasharray: 2 2; fill: none; }
.callout-chip {
  fill: var(--surface-2); stroke: var(--border); stroke-width: 1;
  transition: fill .12s ease, stroke .12s ease;
}
.callout-shape {
  fill: var(--ink-muted); stroke: none; pointer-events: none;
  transition: fill .12s ease;
}
.state-link:hover .callout-chip,
.state-link:focus-visible .callout-chip {
  fill: var(--teal-soft); stroke: var(--teal); stroke-width: 1.5;
}
.state-link.search-match .callout-chip { fill: var(--gold-soft); stroke: var(--gold); stroke-width: 1.5; }
.state-link:hover .callout-shape,
.state-link:focus-visible .callout-shape,
.state-link.search-match .callout-shape { fill: var(--ink); }

@media (max-width: 480px) {
  .state-label-text:not(.callout-label) { display: none; }
}

/* ---------- state detail ---------- */
.state-header { display: flex; justify-content: space-between; align-items: flex-start; gap: 16px; flex-wrap: wrap; margin-bottom: 6px; }
.state-header h1 { font-size: 30px; }
.state-fips-tag {
  font-family: "IBM Plex Mono", monospace; font-size: 14px; font-weight: 500;
  color: var(--ink-muted); vertical-align: middle; margin-left: 6px;
}

/* Quiet section divider for grouping related metrics (e.g. "Labor & Employment")
   without the visual weight of a full .section-head - used when the page needs
   scalable hierarchy but the group isn't its own top-level section yet. */
.section-label {
  font-family: "IBM Plex Mono", monospace; font-size: 11px; letter-spacing: .08em;
  text-transform: uppercase; color: var(--ink-muted);
  margin: 32px 0 12px; padding-top: 16px; border-top: 1px solid var(--border);
}

.freshness-footer {
  font-size: 11px; color: var(--ink-muted); line-height: 1.7;
  margin-top: 12px; opacity: 0.85;
}
.freshness-footer .dotsep { opacity: .6; }
.freshness-footer .caveat { display: block; font-style: italic; margin-top: 2px; }

/* ================= State profile - editorial layout =================
   Everything below is scoped to state.php only: new classes, not
   redefinitions of .tile-grid/.eyebrow/.section-label, which index.php/
   markets.php/status.php still use unchanged. */

/* A plain, non-uppercase label for the new stat components below -
   deliberately not reusing .eyebrow (uppercase, used site-wide) so
   this redesign doesn't change any other page's typography. */
.metric-label { font-size: 11px; letter-spacing: .02em; color: var(--ink-muted); display: block; }

/* Sub-section headings inside the Overview tab (State Highlights,
   Economy & Labor, Leading Industries, Leading Public Companies,
   Population & People, Housing & Real Estate, Federal Spending) - one
   coherent profile rather than an undifferentiated block. Editorial
   serif, with a quiet hairline divider above every one after the
   first (State Highlights sits right under the tab bar and needs no
   extra separator). */
#overview-business-preview .section-title,
#overview-companies-preview .section-title,
#overview-labor .section-title,
#overview-population .section-title,
#overview-housing .section-title,
#overview-spending .section-title {
  padding-top: 28px; border-top: 1px solid var(--border);
}
.section-title {
  font-family: "Newsreader", serif; font-weight: 600; font-size: 20px; color: var(--ink);
  margin: 32px 0 14px;
}
#overview-highlights .section-title { margin-top: 4px; }

/* Byline-style headline strip under the state name: vertical hairline
   dividers between figures, no per-metric box - a masthead statline,
   not another card grid. */
.headline-stats {
  display: flex; gap: 0; margin-top: 20px; padding-top: 18px;
  border-top: 1px solid var(--border); flex-wrap: wrap;
}
.headline-stat { flex: 1 1 150px; padding: 0 24px; border-left: 1px solid var(--border); }
.headline-stat:first-child { border-left: none; padding-left: 0; }
.headline-stat .metric-label { margin-bottom: 5px; }
.headline-stat .kpi-value { font-size: 22px; font-weight: 600; }

/* A second, smaller masthead row for the Housing & Real Estate summary -
   same byline pattern as .headline-stats directly above it, just
   tighter (smaller value type, less top space) so it reads as a
   secondary line under the state's primary headline figures rather
   than a second row of equal weight. */
.housing-headline-stats { margin-top: 14px; padding-top: 14px; }
.housing-headline-stats .kpi-value { font-size: 17px; }
.housing-fhfa-line { margin: 8px 0 0; }

/* Replaces the old per-state "Sources" tab - a single subtle line
   pointing to the centralized Data Sources & Methodology section on
   Status, not a repeat of the full source list on every state page. */
.state-sources-link { margin: 10px 0 0; }

/* Compact supporting-metric row - lighter than .tile-grid, no per-item
   box, for metrics that belong beside/beneath a chart or panel rather
   than as their own card. */
.stat-row-compact {
  display: flex; gap: 28px; margin-top: 16px; padding-top: 14px;
  border-top: 1px solid var(--border); flex-wrap: wrap;
}
.stat-row-compact .kpi-value { font-size: 17px; font-weight: 600; margin-top: 2px; }

/* ---------- primary state tabs ----------
   Four tabs, full content width on desktop (flex:1 each - a real
   4-column bar, not small text links), one continuous baseline under
   the whole row from the container's own border-bottom. The active
   tab's underline is its own border-bottom, 3px, positioned to sit
   exactly on that shared baseline (margin-bottom:-2px makes the two
   lines coincide instead of showing as two parallel rules), so it
   reads as "this segment of the baseline is lit up," not a separate
   tiny mark under the text. */
.tabs {
  display: flex; margin-top: 22px; border-bottom: 1px solid var(--border);
  overflow-x: auto; -webkit-overflow-scrolling: touch; scrollbar-width: none;
}
.tabs::-webkit-scrollbar { display: none; }
.tab-btn {
  appearance: none; background: none; border: none; cursor: pointer;
  flex: 1 1 0; min-width: 130px; text-align: center;
  padding: 14px 18px; font-family: "IBM Plex Sans", sans-serif; font-size: 14px;
  color: var(--ink-muted); white-space: nowrap;
  border-bottom: 3px solid transparent; margin-bottom: -2px;
  transition: color .15s ease, border-color .15s ease, background-color .15s ease;
}
.tab-btn:hover { color: var(--ink); background: var(--surface-2); border-bottom-color: var(--border); }
.tab-btn:focus-visible { outline: 2px solid var(--teal); outline-offset: -2px; }
.tab-btn[aria-selected="true"] { color: var(--ink); font-weight: 600; border-bottom-color: var(--gold); }
.tab-btn[aria-selected="true"]:hover { background: none; }
.tab-panel { margin-top: 26px; }

@media (max-width: 640px) {
  .tabs { justify-content: flex-start; }
  .tab-btn { flex: none; }
}

/* The dominant age cohort - a plain-data highlight (uses the same
   already-computed max value the bar width itself uses), not a new
   calculation. */
.agebar-row.largest .lbl, .agebar-row.largest .val { font-weight: 600; color: var(--ink); }

.panel { border: 1px solid var(--border); border-radius: 10px; background: var(--surface); padding: 18px 20px; }
.panel h3 { font-size: 14.5px; margin-bottom: 2px; }
.panel .panel-sub { font-size: 12px; color: var(--ink-muted); margin-bottom: 14px; }
/* The employment chart is the Labor tab's primary visual, full tab
   width - sized to be immediately readable (380-440px range), not the
   small auxiliary chart it was when it shared width with Population. */
.chart-container { position: relative; height: 400px; }

/* Compact demographic profile, not a widget with room to spare -
   tight row gap and a slim bar, so all 8 age groups still read as one
   glance rather than growing into a tall standalone widget. */
.agebars { display: flex; flex-direction: column; gap: 3px; }
.agebar-row { display: grid; grid-template-columns: 56px 1fr 116px; align-items: center; gap: 8px; padding: 1px 0; }
.agebar-row .lbl { font-size: 12px; color: var(--ink-muted); }
.agebar-track { height: 6px; border-radius: 3px; background: var(--surface-2); overflow: hidden; }
.agebar-fill { height: 100%; border-radius: 3px; background: var(--gold); }
.agebar-row .val {
  font-family: "IBM Plex Mono", monospace; font-size: 12px; text-align: right;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}

/* Sources tab: a plain list, not tiles - each row is one data source. */
.source-detail-list { display: flex; flex-direction: column; gap: 16px; }
.source-detail-row { padding-bottom: 14px; border-bottom: 1px solid var(--border); }
.source-detail-row:last-child { border-bottom: none; padding-bottom: 0; }
.source-detail-name { font-size: 13.5px; font-weight: 600; }
.source-detail-meta { font-size: 12px; color: var(--ink-muted); margin-top: 3px; }

.empty-card {
  border: 1px dashed var(--border); border-radius: 10px; padding: 20px 22px;
  background: var(--surface-2); display: flex; gap: 14px; align-items: flex-start; margin-top: 24px;
}
.empty-card .icon {
  width: 30px; height: 30px; border-radius: 7px; background: var(--surface); border: 1px solid var(--border);
  display: flex; align-items: center; justify-content: center; flex: none;
  font-family: "IBM Plex Mono", monospace; font-size: 14px; color: var(--ink-muted);
}
.empty-card h4 { font-size: 14px; margin: 0 0 4px; font-family: "IBM Plex Sans", sans-serif; font-weight: 600; }
.empty-card p { font-size: 12.5px; color: var(--ink-muted); margin: 0; line-height: 1.5; }

.source-line { display: flex; gap: 8px; align-items: baseline; font-size: 12px; color: var(--ink-muted); margin-top: 22px; flex-wrap: wrap; }
.source-line .dotsep { opacity: .5; }

/* Industry breakdown (Business & Industry section) - a compact,
   editorial ranked list, not a dashboard: one stacked block per
   sector, thin bars, muted secondary figures. */
.industry-list { display: flex; flex-direction: column; gap: 14px; margin-top: 6px; }
.industry-row { padding-bottom: 12px; border-bottom: 1px solid var(--border); }
.industry-row:last-child { border-bottom: none; padding-bottom: 0; }
.industry-head {
  display: flex; justify-content: space-between; align-items: baseline;
  gap: 10px; margin-bottom: 6px; flex-wrap: wrap;
}
.industry-name { font-size: 13.5px; }
.naics-badge {
  font-family: "IBM Plex Mono", monospace; font-size: 10.5px; color: var(--ink-muted);
  border: 1px solid var(--border); border-radius: 4px; padding: 1px 5px; margin-right: 7px;
}
.industry-primary {
  font-family: "IBM Plex Mono", monospace; font-size: 13px; font-weight: 600;
  white-space: nowrap; flex: none;
}
.industry-bar-track { height: 6px; border-radius: 3px; background: var(--surface-2); overflow: hidden; margin-bottom: 6px; }
.industry-bar-fill { height: 100%; border-radius: 3px; background: var(--gold); }
.industry-secondary { font-size: 11.5px; color: var(--ink-muted); }
.industry-suppressed {
  font-size: 11.5px; color: var(--ink-muted); font-style: italic;
  font-family: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
}

/* Public-company line under a sector row - deliberately secondary to
   the employment/payroll figures above it (smaller, muted label,
   plain-until-hover links) so the industry list still reads as a
   Census breakdown first, not a ticker list. Wraps naturally on
   mobile instead of forcing a new column. */
.industry-companies { margin-top: 8px; font-size: 11.5px; }
.industry-companies-label {
  color: var(--ink-muted); text-transform: uppercase; letter-spacing: .03em;
  font-size: 10.5px; display: block; margin-bottom: 3px;
}
.industry-companies-links { color: var(--ink-muted); }
.industry-company-link { color: var(--ink); font-weight: 500; }
.industry-company-link:hover, .industry-company-link:focus-visible { color: var(--teal); }
.industry-company-ticker { font-family: "IBM Plex Mono", monospace; color: var(--ink-muted); font-weight: 400; }
.industry-companies-sep { margin: 0 4px; color: var(--border); }
.industry-companies-more { color: var(--ink-muted); font-style: italic; }

/* Public Companies - deliberately not a brokerage/ticker-app look: no
   green/red price colors, no logos, no big ticker type. Same quiet
   stacked-row rhythm as .industry-row, and the company name set in the
   site's serif (same family as section headings) so it reads as the
   clear headline of the row - everything else (ticker, industry, city,
   FY) stays small and muted. Used as-is (a plain stacked list, no
   per-row card) for the 5-item "Leading Public Companies" Overview
   preview; the full Public Companies tab adds the denser
   .company-list-cards treatment below for scanning 100+ rows. */
.company-list { display: flex; flex-direction: column; gap: 20px; margin-top: 6px; }
.company-row { padding-bottom: 16px; border-bottom: 1px solid var(--border); }
.company-row:last-child { border-bottom: none; padding-bottom: 0; }
.company-head { display: flex; justify-content: space-between; align-items: baseline; gap: 10px; flex-wrap: wrap; }
.company-name { font-family: "Newsreader", serif; font-size: 16px; font-weight: 600; color: var(--ink); }
.company-ticker { font-family: "IBM Plex Mono", monospace; font-size: 12px; font-weight: 400; color: var(--ink-muted); }
.company-meta { font-size: 12.5px; color: var(--ink-muted); margin-top: 4px; }

/* Ticker as a quiet mono pill, not a second headline next to the
   company name - keeps identity hierarchy unambiguous (name first,
   ticker secondary) at a glance across a long list. */
.ticker-badge {
  display: inline-block; font-family: "IBM Plex Mono", monospace; font-size: 10.5px;
  font-weight: 600; letter-spacing: .01em; color: var(--ink-muted); background: var(--surface-2);
  border-radius: 4px; padding: 1px 6px; margin-left: 6px; vertical-align: middle;
}

/* Same quiet pill as .ticker-badge, but in the default sans font - for a
   short word/phrase label (school type, higher-ed control/level) rather
   than a mono ticker symbol. */
.type-badge {
  display: inline-block; font-size: 10.5px; font-weight: 600; letter-spacing: .01em;
  color: var(--ink-muted); background: var(--surface-2);
  border-radius: 4px; padding: 1px 6px; margin-left: 6px; vertical-align: middle;
}

/* Full Public Companies tab: a light per-company card instead of the
   plain stacked-row look above, so 100-300+ companies (e.g. Illinois,
   California) stay scannable as distinct units rather than one long
   run-on list. Kept deliberately subtle - thin border, tiny radius, no
   shadow, tight (not spacious) padding - so it still reads as a dense
   data list, not a grid of feature cards. */
.company-list-cards { gap: 8px; margin-top: 10px; }
.company-list-cards .company-row,
.company-list-cards .company-row:last-child {
  border: 1px solid var(--border); border-radius: 8px; background: var(--surface);
  padding: 12px 14px 13px;
}
.company-list-cards .company-row:hover,
.company-list-cards .company-row:focus-within {
  border-color: var(--teal);
}
.company-primary { min-width: 0; }

/* Wide desktop only: put the financial snapshot beside the company/
   market column instead of below it, using the card's unused right-
   hand space - .company-financials switches from its default 3-column
   row (tablet/mobile, unchanged below) to a narrow vertical stack.
   Only applied to rows that actually have financials (.has-financials,
   set in state.php) - a company with none keeps the plain single-
   column layout at every width, so there's never an empty right rail. */
@media (min-width: 880px) {
  .company-list-cards .company-row.has-financials {
    display: flex; align-items: flex-start; gap: 20px;
  }
  .company-list-cards .company-row.has-financials .company-primary {
    flex: 1 1 auto;
  }
  .company-list-cards .company-row.has-financials .company-financials {
    flex: 0 0 210px; grid-template-columns: 1fr; max-width: none;
    margin-top: 0; gap: 8px; padding-left: 18px; border-left: 1px solid var(--border);
  }
}

/* A real aligned column grid, not just wrapped flex items - so
   Revenue/Net income/Assets line up down the whole list like a ledger. */
.company-financials {
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr));
  max-width: 460px; gap: 8px 24px; margin-top: 10px;
}
.fin-item { display: flex; flex-direction: column; gap: 2px; }
.fin-label { font-size: 10.5px; text-transform: uppercase; letter-spacing: .04em; color: var(--ink-muted); }
.fin-val { font-family: "IBM Plex Mono", monospace; font-size: 13.5px; font-weight: 600; color: var(--ink); }
.fin-unavailable {
  font-size: 12px; color: var(--ink-muted); font-style: italic;
  font-family: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
}

/* Compact per-company market snapshot on the state Public Companies
   tab (close/change/volume/trading date only - no open/high/low/vwap,
   no chart). Deliberately restrained: a dashed rule (lighter than the
   .company-financials section's implicit weight), small mono type, and
   the same muted .change colors used everywhere else on the site - not
   a brokerage-style price ticker. No "Market" label - close price +
   signed change is already unambiguous, and dropping the per-row label
   cuts one more repeated uppercase word from a long list.
   .company-market-meta forces its own line via width:100% inside the
   wrapping flex row (volume + date under the price line), rather than
   a second grid/row markup. Omitted entirely (not rendered) for a
   company with no market data - never filled with placeholder dashes. */
.company-market {
  margin-top: 10px; padding-top: 10px; border-top: 1px dashed var(--border);
  display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 10px; font-size: 12.5px;
}
.company-market-price { font-family: "IBM Plex Mono", monospace; font-size: 13px; font-weight: 600; color: var(--ink); }
.company-market .change { font-family: "IBM Plex Mono", monospace; font-size: 12.5px; font-weight: 600; }
.company-market-meta { width: 100%; font-family: "IBM Plex Mono", monospace; font-size: 11px; color: var(--ink-muted); }

.company-show-all { margin-top: 16px; display: flex; flex-direction: column; gap: 8px; align-items: flex-start; }
.company-show-all-note { font-size: 11.5px; color: var(--ink-muted); }
.show-all-btn {
  padding: 8px 16px; font-size: 12.5px; font-family: "IBM Plex Sans", sans-serif;
  color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: 6px;
  cursor: pointer;
}
.show-all-btn:hover { border-color: var(--teal); color: var(--teal); }

/* ---------- state comparisons (homepage) ---------- */
.compare-grid { display: grid; grid-template-columns: repeat(2, 1fr); gap: 16px; }

/* Business & Employment is the one .compare-grid with three panels
   (establishments/employment/density) rather than two - without this,
   the third card drops to its own near-empty row on desktop. Scoped to
   .compare-grid-3 so the other (two-panel) comparison grids sitewide
   are unaffected. */
.compare-grid.compare-grid-3 { grid-template-columns: repeat(3, 1fr); }
@media (max-width: 900px) {
  .compare-grid.compare-grid-3 { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 760px) {
  .compare-grid.compare-grid-3 { grid-template-columns: 1fr; }
}

.compare-panel { border: 1px solid var(--border); border-radius: 10px; background: var(--surface); padding: 18px 20px; }
.compare-panel h3 { font-size: 14.5px; margin-bottom: 12px; }
.rank-list { display: flex; flex-direction: column; gap: 10px; }
.rank-row {
  display: grid; grid-template-columns: 18px 1fr 70px auto; align-items: center; gap: 8px;
  color: var(--ink); text-decoration: none;
}
.rank-row:hover .rank-name, .rank-row:focus-visible .rank-name { color: var(--teal); text-decoration: underline; }
.rank-num { font-family: "IBM Plex Mono", monospace; font-size: 11px; color: var(--ink-muted); }
.rank-name { font-size: 13px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.rank-bar-track { height: 5px; border-radius: 3px; background: var(--surface-2); overflow: hidden; }
.rank-bar-fill { display: block; height: 100%; border-radius: 3px; background: var(--gold); }
.rank-val { font-family: "IBM Plex Mono", monospace; font-size: 12px; text-align: right; white-space: nowrap; }

/* ---------- markets ---------- */
.markets-list { border: 1px solid var(--border); border-radius: 10px; overflow: hidden; background: var(--surface); margin-bottom: 32px; }
.market-row { display: grid; grid-template-columns: 1.6fr 1fr 1fr 1fr; align-items: center; padding: 13px 18px; gap: 10px; }
.market-row.head { background: var(--surface-2); font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--ink-muted); font-family: "IBM Plex Mono", monospace; }
.market-row + .market-row { border-top: 1px solid var(--border); }
.market-row .sym { font-family: "IBM Plex Mono", monospace; font-size: 11px; color: var(--ink-muted); }
.market-row .name { font-size: 13.5px; }
.market-row .value { font-family: "IBM Plex Mono", monospace; font-size: 13.5px; text-align: right; }
.market-row .change { font-family: "IBM Plex Mono", monospace; font-size: 12.5px; text-align: right; font-weight: 600; }
.change.pos { color: var(--teal); }
.change.neg { color: var(--brick); }
.change.flat { color: var(--ink-muted); }
.cat-badge {
  font-family: "IBM Plex Mono", monospace; font-size: 10px; text-transform: uppercase;
  letter-spacing: .05em; color: var(--ink-muted); border: 1px solid var(--border);
  border-radius: 5px; padding: 2px 6px; justify-self: start;
}

/* A row's company name is a link (to that company's profile) but reads
   as plain text until hover/focus - same convention as .rank-name and
   .company-name elsewhere, not an always-teal link inside a dense
   table/list. */
.market-row .name a, .markets-row .company-cell a { color: var(--ink); text-decoration: none; }
.market-row .name a:hover, .market-row .name a:focus-visible,
.markets-row .company-cell a:hover, .markets-row .company-cell a:focus-visible { color: var(--teal); text-decoration: underline; }

/* ---------- Public Markets: highlights ----------
   Three .markets-list blocks (Largest Gains / Largest Declines / Most
   Active) side by side on desktop, stacked on mobile - the exact same
   .markets-list/.market-row component Commodities and Economic
   Indicators use below on this page, just repurposed, so this adds
   only the outer grid + a small block title, no new row component. */
.highlight-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; }
.highlight-grid .markets-list { margin-bottom: 0; }
.highlight-title { font-size: 13px; font-weight: 600; color: var(--ink-muted); margin: 0 0 8px; font-family: "IBM Plex Sans", sans-serif; }

/* ---------- Public Markets: company table ----------
   Same horizontal-scroll-on-mobile technique as .fh-table/.fh-row
   (company.php's Financial History table) rather than a new
   responsive pattern: a fixed min-width on the row plus overflow-x on
   the wrapper, so narrow screens scroll the table sideways instead of
   silently dropping columns or overflowing the page. */
.markets-table { border: 1px solid var(--border); border-radius: 10px; background: var(--surface); margin-top: 6px; overflow-x: auto; }
.markets-row {
  display: grid; grid-template-columns: 1.8fr 64px 84px 96px 96px 100px 96px 116px;
  gap: 10px; padding: 12px 16px; align-items: center; font-size: 13px; min-width: 860px;
}
.markets-row.head { background: var(--surface-2); font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--ink-muted); font-family: "IBM Plex Mono", monospace; }
.markets-row.head a { color: inherit; text-decoration: none; }
.markets-row.head a:hover, .markets-row.head a:focus-visible { color: var(--teal); }
.markets-row + .markets-row { border-top: 1px solid var(--border); }
.markets-row .val { text-align: right; }
.markets-row .change { font-weight: 600; }

.markets-pagination {
  display: flex; justify-content: space-between; align-items: center; flex-wrap: wrap;
  gap: 10px; margin-top: 14px; font-size: 12.5px; color: var(--ink-muted);
}

/* ---------- status page ---------- */
.status-table { border: 1px solid var(--border); border-radius: 10px; overflow: hidden; background: var(--surface); }
.status-row { display: grid; grid-template-columns: 1fr 100px 1fr 1fr 90px 90px; gap: 10px; padding: 13px 18px; align-items: center; font-size: 13px; }
.status-row.head { background: var(--surface-2); font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--ink-muted); font-family: "IBM Plex Mono", monospace; }
.status-row + .status-row { border-top: 1px solid var(--border); }
.status-badge { display: inline-flex; align-items: center; gap: 5px; font-size: 12px; font-weight: 600; }
.status-badge.success { color: var(--teal); }
.status-badge.failed { color: var(--brick); }
.status-row .tabular { font-size: 12.5px; }

/* ---------- breadcrumb (company detail page) ---------- */
.breadcrumb { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; font-size: 12.5px; color: var(--ink-muted); margin: 18px 0 4px; }
.breadcrumb a { color: var(--ink-muted); }
.breadcrumb a:hover, .breadcrumb a:focus-visible { color: var(--teal); }
.breadcrumb-sep { opacity: .5; }
.breadcrumb-current { color: var(--ink); }

/* ---------- financial history table (company detail page) ----------
   Same CSS-grid pseudo-table technique as .status-row/.market-row, not
   a new pattern. Today's API only ever returns one row (see
   CompanyFinancialsHistoryEntry's own doc comment) - this renders any
   number of rows without changes, so a future multi-year backfill
   needs no template work here, only a chart added alongside it. */
.fh-table { border: 1px solid var(--border); border-radius: 10px; background: var(--surface); margin-top: 6px; overflow-x: auto; }
.fh-row { display: grid; grid-template-columns: 90px repeat(5, minmax(100px, 1fr)); gap: 10px; padding: 12px 16px; align-items: center; font-size: 13px; min-width: 640px; }
.fh-row.head { background: var(--surface-2); font-size: 11px; text-transform: uppercase; letter-spacing: .05em; color: var(--ink-muted); font-family: "IBM Plex Mono", monospace; }
.fh-row + .fh-row { border-top: 1px solid var(--border); }
.fh-row .val { text-align: right; }

/* ---------- documentation-style annotations ----------
   Shared treatment for methodology notes, data-source caveats, guide/
   help callouts, and other explanatory text that's clearly secondary
   to the actual data - a quiet "inline code comment" look (small
   monospace, muted color, a soft panel with a left accent), not a
   full black terminal. One shared rule so every page picks up the
   same look automatically through whichever class it already uses for
   this kind of text, rather than a new class threaded through every
   template.

   .kpi-sub here is the bare/paragraph use (methodology captions,
   guide text like the map's search hint) - NOT the more specific
   ".tile-grid .tile .kpi-sub" rule above, which wins by specificity
   and stays a plain short inline tag (a source label, a state-name
   link, a contributor count) bolted onto one metric inside a tile;
   that's primary content, not a note, and is deliberately untouched. */
.kpi-sub,
.panel-sub,
.source-detail-meta,
.company-show-all-note,
.source-line {
  font-family: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
  font-size: 12px;
  line-height: 1.6;
  color: var(--ink-muted);
  background: var(--surface-2);
  border-left: 2px solid var(--border);
  border-radius: 0 6px 6px 0;
  padding: 10px 14px;
  margin: 10px 0;
}

/* ---------- generic empty/error banners ---------- */
.notice {
  border: 1px solid var(--border); border-radius: 10px; padding: 16px 18px;
  background: var(--surface-2); font-size: 12.5px; line-height: 1.6; color: var(--ink-muted); margin: 16px 0;
  font-family: SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", monospace;
}
.notice.error { border-color: var(--brick-soft); background: var(--brick-soft); color: var(--ink); }

/* ---------- footer ---------- */
footer { margin: 56px 0 40px; padding-top: 22px; padding-bottom: env(safe-area-inset-bottom, 0px); border-top: 1px solid var(--border); }
.footer-grid { display: grid; grid-template-columns: 2fr 1fr 1fr; gap: 24px; font-size: 12.5px; color: var(--ink-muted); line-height: 1.7; }
.footer-grid h5 { font-size: 12px; text-transform: uppercase; letter-spacing: .06em; color: var(--ink); margin: 0 0 8px; font-family: "IBM Plex Sans", sans-serif; }

@media (prefers-reduced-motion: reduce) {
  * { transition: none !important; animation: none !important; }
}

@media (max-width: 760px) {
  nav.toplinks { gap: 14px; font-size: 13px; }
  .tile-grid.cols-4, .tile-grid.cols-6, .tile-grid.cols-3 { grid-template-columns: repeat(2, 1fr); }
  .chart-row { grid-template-columns: 1fr; }
  .footer-grid { grid-template-columns: 1fr; }
  .market-row { grid-template-columns: 1.4fr 1fr 1fr; }
  .market-row .cat-badge { display: none; }
  .highlight-grid { grid-template-columns: 1fr; }
  .status-row { grid-template-columns: 1fr 1fr; font-size: 12px; }
  .status-row > :nth-child(n+5) { display: none; }
  .compare-grid { grid-template-columns: 1fr; }
  .rank-row { grid-template-columns: 16px 1fr 56px auto; }
  .headline-stats { display: grid; grid-template-columns: 1fr 1fr; gap: 16px 20px; }
  .headline-stat { border-left: none; padding: 0; border-top: 1px solid var(--border); padding-top: 12px; }
  .headline-stat:nth-child(-n+2) { border-top: none; padding-top: 0; }
}

@media (max-width: 420px) {
  .tile-grid.cols-4, .tile-grid.cols-6, .tile-grid.cols-3, .tile-grid.cols-2 { grid-template-columns: 1fr; }
  .agebar-row { grid-template-columns: 48px 1fr 96px; gap: 6px; }
  .agebar-row .lbl, .agebar-row .val { font-size: 11px; }
  .rank-row { grid-template-columns: 14px 1fr auto; }
  .rank-bar-track { display: none; }
  .company-financials { gap: 8px 14px; }
  .fin-val { font-size: 12.5px; }
}
