/* RegardAlert — public web styles
 * Hand-written CSS, single sheet. Shares the landing page's visual identity
 * (landing.css): a dark "financial terminal" look — navy surfaces, aqua accent,
 * Chakra Petch UI type + Red Hat Mono for numerics. Dark-only, like the landing:
 * there is one identity across the whole public web, no light/dark switch.
 *
 * The semantic tokens below (--bg/--fg/--primary/…) map onto the landing palette
 * (--void/--ink/--aqua/…) so every existing component class and inline
 * `var(--token)` in the templates re-themes from this one block.
 */

:root {
  /* landing palette (see landing.css) */
  --void: #040912;
  --bg: #07101f;             /* page background */
  --panel: #0b1830;          /* raised surface */
  --line: #16263f;           /* hairline */
  --line-2: #21354f;         /* stronger line / control border */
  --ink: #eaf6ff;
  --aqua: #35e0d0;
  --amber: #ffc24d;
  --green: #36e07f;
  --rose: #ff5d6c;

  /* semantic tokens consumed by components + template inline styles */
  --fg: var(--ink);
  /* Meta tier (ages, captions). 7.2 :1 on --panel — the ladder is
     fg 16.1 -> muted-fg 9.5 -> muted 7.2; #7488a3 sat at 4.9, technically
     AA and not actually readable at the 11-13px this token is used at. */
  --muted: #97a7bc;          /* dim meta (ages, captions) */
  --muted-fg: #aebfd6;       /* readable secondary text (body copy) */
  --border: #1c2e49;         /* dividers, card borders */
  --card: var(--panel);
  --secondary: rgba(255, 255, 255, 0.04);       /* subtle fills / secondary buttons */
  --secondary-hover: rgba(255, 255, 255, 0.08);
  --primary: var(--aqua);                        /* fills, washes, control accents */
  --primary-hover: #4fe8da;                      /* brighter aqua on hover */
  --primary-fg: #04231e;                         /* dark ink on aqua fills */
  --primary-ink: var(--aqua);                    /* accent text on the dark surface */
  --emerald: var(--green);
  --red: var(--rose);
  --radius: 12px;

  --font-ui: 'Chakra Petch', -apple-system, BlinkMacSystemFont, "Segoe UI", Inter, Roboto, "Helvetica Neue", sans-serif;
  --font-mono: 'Red Hat Mono', ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
}

* { box-sizing: border-box; }
html, body { margin: 0; padding: 0; }
body {
  background: var(--bg);
  color: var(--fg);
  font-family: var(--font-ui);
  font-size: 16px;
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}
a { color: inherit; text-decoration: none; }
.mono { font-family: var(--font-mono); }
.container { max-width: 1100px; margin: 0 auto; padding: 0 24px; }
.container-md { max-width: 760px; }

/* Header */
.site-header {
  position: sticky; top: 0; z-index: 50;
  border-bottom: 1px solid var(--border);
  background: color-mix(in srgb, var(--bg) 88%, transparent);
  backdrop-filter: blur(8px);
}
.site-header__inner {
  display: flex; align-items: center; justify-content: space-between;
  height: 56px; padding: 0 24px;
  max-width: 1280px; margin: 0 auto;
}
.brand { display: flex; align-items: center; gap: 8px; font-weight: 700; letter-spacing: 0.01em; }
.brand__mark {
  width: 32px; height: 32px; border-radius: 8px;
  display: block; object-fit: cover;
}
.header-actions { display: flex; align-items: center; gap: 8px; }

/* Buttons */
.btn {
  display: inline-flex; align-items: center; gap: 6px;
  padding: 9px 16px; border-radius: 10px; font-size: 14px; font-weight: 600;
  letter-spacing: 0.01em;
  border: 1px solid var(--line-2); background: var(--secondary); color: var(--fg);
  cursor: pointer; text-decoration: none; white-space: nowrap;
  transition: background .15s, border-color .15s, filter .15s, transform .15s;
}
.btn:hover { background: var(--secondary-hover); border-color: var(--aqua); }
.btn:active { transform: translateY(1px); }
.btn:focus-visible { outline: none; border-color: var(--aqua); box-shadow: 0 0 0 1px var(--aqua), 0 0 18px rgba(53, 224, 208, 0.22); }
.btn--primary { background: var(--primary); color: var(--primary-fg); border-color: var(--primary); }
.btn--primary:hover { background: var(--primary-hover); border-color: var(--primary-hover); filter: brightness(1.03); }
.btn--lg { padding: 13px 22px; font-size: 15px; border-radius: 12px; }
.btn--block { width: 100%; justify-content: center; }
.btn--ghost { background: transparent; border-color: transparent; }
.btn--ghost:hover { background: var(--secondary); border-color: var(--line-2); }

/* Feed rows (alert lists on ticker/entity pages) */
.row {
  display: flex; align-items: center; justify-content: space-between;
  gap: 12px; padding: 12px 16px; border-bottom: 1px solid var(--border);
  color: inherit;
}
.row:last-child { border-bottom: 0; }
.row:hover { background: var(--secondary); }
.row__left { display: flex; align-items: baseline; gap: 8px; min-width: 0; flex: 1; }
.row__ticker { font-family: var(--font-mono); font-weight: 700; font-size: 14px; flex-shrink: 0; }
.pill-macro {
  display: inline-block; padding: 1px 7px; flex-shrink: 0;
  background: color-mix(in srgb, var(--muted) 20%, transparent);
  color: var(--muted-fg); font-size: 11px; font-weight: 600;
  letter-spacing: 0.03em; border-radius: 4px; text-transform: uppercase;
}
.row__title { font-size: 14px; color: var(--muted-fg); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; flex: 1; min-width: 0; }
.row__right { display: flex; align-items: center; gap: 12px; flex-shrink: 0; font-size: 12px; }
.row__pct { font-family: var(--font-mono); font-weight: 600; font-size: 13px; }
.row__age { color: var(--muted); font-size: 12px; }
.row__type { color: var(--primary-ink); font-weight: 600; font-size: 12px; text-transform: uppercase; letter-spacing: 0.04em; }

.pos { color: var(--emerald); }
.neg { color: var(--red); }
.flat { color: var(--muted); }

/* CTA */
.cta-inline {
  border: 1px solid var(--border); border-radius: var(--radius);
  background: var(--panel); padding: 20px; text-align: center;
}
.cta-inline h3 { margin: 0 0 4px; font-size: 16px; font-weight: 600; }
.cta-inline p { margin: 0 0 14px; font-size: 14px; color: var(--muted-fg); }

/* Article (alert page) */
.article { padding: 32px 16px 96px; }
.article header { margin-bottom: 24px; }
.article .meta {
  display: flex; flex-wrap: wrap; align-items: center; gap: 8px;
  font-size: 13px; color: var(--muted); margin-bottom: 8px;
}
.article h1 { font-size: clamp(24px, 3vw, 32px); line-height: 1.2; letter-spacing: -0.01em; margin: 0 0 12px; }
.article .body { color: var(--muted-fg); font-size: 16px; line-height: 1.55; margin: 0 0 8px; }
.article .ctx { color: var(--muted); font-size: 14px; margin-top: 8px; }

/* Legal pages (privacy/terms) — prose additions over .article */
.legal h2 { font-size: 18px; margin: 28px 0 8px; }
.legal ul.body { padding-left: 20px; margin: 0 0 8px; }
.legal ul.body li { margin-bottom: 8px; }
.legal .body a { color: var(--primary-ink); }
.legal .body strong { color: var(--fg); font-weight: 600; }

.chart-card { border: 1px solid var(--border); border-radius: var(--radius); background: var(--card); padding: 16px; margin-bottom: 12px; }
/* Identity tile (ticker/entity page heads): real artwork when the server has
 * the asset, else the shared monogram — same hash/palette as the iOS tiles
 * (stock_screener/lib/monogram.py). Geometry mirrors the app's tile chrome:
 * corner radius ≈ 0.22 × size, glyph ≈ 0.5 × size, white-8% hairline. */
.id-tile {
  width: 48px; height: 48px; border-radius: 11px; flex-shrink: 0; align-self: center;
  display: block; object-fit: contain;
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.08);
}
.id-tile--monogram {
  display: flex; align-items: center; justify-content: center;
  color: #fff; font-size: 24px; font-weight: 700; line-height: 1;
  user-select: none;
}

/* Ticker page */
.ticker-head { display: flex; align-items: baseline; gap: 12px; flex-wrap: wrap; }
.ticker-head h1 { font-size: 36px; margin: 0; letter-spacing: -0.01em; }
.ticker-head .company { font-size: 18px; color: var(--muted); }
.ticker-meta { margin-top: 8px; font-size: 14px; display: flex; gap: 16px; flex-wrap: wrap; }
.ticker-chart { margin: 24px 0; border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; }
.ticker-chart > div { width: 100%; height: 420px; }

/* Category list nav */
.chip-row { display: flex; flex-wrap: wrap; gap: 8px; margin: 0 0 20px; }
.chip {
  display: inline-block; padding: 6px 13px; border-radius: 999px;
  border: 1px solid var(--line-2); background: var(--secondary); color: var(--muted-fg);
  font-size: 12px; font-weight: 500;
  transition: color .15s, background .15s, border-color .15s;
}
.chip:hover { color: var(--fg); background: var(--secondary-hover); border-color: var(--aqua); }

/* Sticky bottom CTA */
.sticky-cta {
  position: fixed; bottom: 0; left: 0; right: 0; z-index: 40;
  padding: 12px 16px; border-top: 1px solid var(--border);
  background: color-mix(in srgb, var(--bg) 90%, transparent); backdrop-filter: blur(8px);
}
@media (min-width: 768px) { .sticky-cta { display: none; } }

/* Footer */
.site-footer {
  border-top: 1px solid var(--border); padding: 32px 0;
  font-size: 13px; color: var(--muted);
}
.site-footer .inner {
  display: flex; flex-wrap: wrap; gap: 24px; justify-content: space-between; align-items: center;
}
.site-footer a:hover { color: var(--fg); }

/* Empty states */
.empty { padding: 32px; text-align: center; color: var(--muted); font-size: 14px; }

/* Responsive tweaks */
/* Mobile header + chrome: below the desktop breakpoint the waitlist CTA is the
   priority — the brand + CTA share one row, and the body is padded so the
   fixed CTA bar never sits over the footer. */
@media (max-width: 767px) {
  .site-header__inner { padding: 0 16px; }
  body { padding-bottom: 76px; }
}
@media (max-width: 640px) {
  /* Feed-list rows: let the headline use two lines instead of collapsing to an
     ellipsis when a category pill + type label share the row. */
  .live-feed .row { align-items: flex-start; }
  .live-feed .row__title {
    white-space: normal; line-height: 1.35;
    display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical;
  }
}

/* Holdings table — 13F structured alerts */
.holdings-table {
  width: 100%; border-collapse: collapse;
  font-size: 14px; margin: 16px 0;
}
.holdings-table th {
  text-align: left; font-weight: 600; font-size: 12px;
  text-transform: uppercase; letter-spacing: 0.04em;
  color: var(--muted); border-bottom: 1px solid var(--border);
  padding: 8px 4px;
}
.holdings-table td {
  border-bottom: 1px solid var(--border);
  padding: 8px 4px; font-variant-numeric: tabular-nums;
}
.holdings-table .t-left { text-align: left; }
.holdings-table .t-right { text-align: right; }
.holdings-table a { color: var(--fg); font-weight: 500; }
.pill {
  display: inline-block; padding: 2px 8px; border-radius: 999px;
  font-size: 11px; font-weight: 700; letter-spacing: 0.02em;
}
.pill--pos { background: color-mix(in srgb, var(--emerald) 18%, transparent); color: var(--emerald); }
.pill--neg { background: color-mix(in srgb, var(--red) 18%, transparent); color: var(--red); }

/* Analyst ratings & price target (ticker page) */
.analyst-head { display: flex; align-items: center; flex-wrap: wrap; gap: 12px; margin-bottom: 18px; }
.analyst-badge {
  display: inline-block; padding: 3px 11px; border-radius: 999px;
  font-size: 12px; font-weight: 700; letter-spacing: 0.03em; text-transform: uppercase;
}
.analyst-badge--pos { color: var(--emerald); background: color-mix(in srgb, var(--emerald) 16%, transparent); }
.analyst-badge--neg { color: var(--red); background: color-mix(in srgb, var(--red) 16%, transparent); }
.analyst-badge--flat { color: var(--muted-fg); background: color-mix(in srgb, var(--muted) 16%, transparent); }
.analyst-count { font-size: 13px; color: var(--muted); }
.analyst-upside {
  font-family: var(--font-mono); font-weight: 700;
  font-size: 15px; font-variant-numeric: tabular-nums;
}
.analyst-upside__lbl { font-family: var(--font-ui); font-weight: 400; font-size: 12px; color: var(--muted); }

/* Price-target range bar (low — mean — high + current marker) */
.pt-range { margin: 4px 0 22px; }
.pt-range__bar { position: relative; height: 8px; margin: 16px 0 8px; }
.pt-range__track {
  position: absolute; inset: 0; border-radius: 999px;
  background: linear-gradient(to right,
    color-mix(in srgb, var(--red) 35%, transparent),
    color-mix(in srgb, var(--muted) 28%, transparent),
    color-mix(in srgb, var(--emerald) 42%, transparent));
}
.pt-range__mean, .pt-range__cur { position: absolute; top: 50%; transform: translate(-50%, -50%); }
.pt-range__mean { width: 13px; height: 13px; border-radius: 50%; background: var(--fg); border: 2px solid var(--card); box-shadow: 0 0 0 1px var(--border); }
.pt-range__cur { width: 3px; height: 18px; border-radius: 2px; background: var(--primary-ink); }
.pt-range__labels { display: flex; justify-content: space-between; font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.pt-range__labels-mean { color: var(--fg); font-weight: 600; }
.pt-range__cur-note { margin: 6px 0 0; font-size: 12px; color: var(--primary-ink); font-variant-numeric: tabular-nums; }

/* Buy / Hold / Sell distribution bar */
.rating-dist { margin: 16px 0 20px; }
.rating-dist__bar { display: flex; height: 10px; border-radius: 999px; overflow: hidden; background: var(--secondary); }
.rating-dist__seg { height: 100%; }
.rating-dist__seg--buy { background: var(--emerald); }
.rating-dist__seg--hold { background: color-mix(in srgb, var(--muted) 55%, transparent); }
.rating-dist__seg--sell { background: var(--red); }
.rating-dist__legend { display: flex; flex-wrap: wrap; gap: 16px; margin-top: 9px; font-size: 12px; font-weight: 600; }
.rating-dist__key { display: inline-flex; align-items: center; gap: 6px; color: var(--muted-fg); }
.rating-dist__key::before { content: ""; width: 9px; height: 9px; border-radius: 2px; display: inline-block; }
.rating-dist__key--buy::before { background: var(--emerald); }
.rating-dist__key--hold::before { background: color-mix(in srgb, var(--muted) 55%, transparent); }
.rating-dist__key--sell::before { background: var(--red); }

/* Monthly target-trend sparkline */
.analyst-trend { margin: 16px 0 8px; border: 1px solid var(--border); border-radius: var(--radius); background: var(--card); padding: 12px 14px; }
.analyst-trend__cap { font-size: 12px; color: var(--muted); margin-bottom: 6px; }
.analyst-asof { font-size: 12px; color: var(--muted); margin: 10px 0 0; }

/* Plot + its high/low gutter (#391). `stretch` is what makes this work: the
   labels are out of flow and the svg is the only item with an intrinsic
   height, so the gutter ends up exactly as tall as the plot and the labels'
   percentage offsets resolve against the plot's own height. The offsets come
   from the macro (the viewBox pad), not from here — top/bottom would be wrong,
   the line's extremes sit inset from the box edge. */
.trend-chart { display: flex; align-items: stretch; gap: 8px; }
.trend-chart__plot { flex: 1 1 auto; min-width: 0; }
/* Load-bearing, not tidiness: an inline svg sits on a text baseline, so the
   wrapper would be ~7px taller than the plot, the gutter would stretch to
   THAT, and every percentage offset would resolve against the wrong height
   (measured: the low label landed 6.3px under the trough). */
.trend-chart__plot svg { display: block; }
.trend-chart__axis {
  position: relative; flex: 0 0 auto;
  font-size: 12px; line-height: 1; color: var(--muted);
}
/* Width source, not a visible element: height 0 so a very narrow viewport
   can't let two stacked lines outgrow the plot and drive the row height. */
.trend-chart__axis-sizer { display: block; height: 0; overflow: hidden; visibility: hidden; }
.trend-chart__axis-val { position: absolute; right: 0; transform: translateY(-50%); white-space: nowrap; }
