/* Dashboard shell — header, tabs, stat tiles, and bucket/debt rows.
 * Ported from Finances_Dashboard_v5.html (the visual ground truth in
 * brief v12 §0). Component-level CSS (.btn, .banner, .kpi) lives in
 * components.css. */

/* The HTML `hidden` attribute is the canonical "hide this" mechanism
 * we use throughout index.html. Browser defaults set `display: none`
 * for it but at low specificity, so ANY `display:` rule (.btn, .tabs,
 * .signin-hero, etc.) overrides it. Force it. */
[hidden] { display: none !important; }

/* --- Signed-out privacy gate --------------------------------------- *
 * When body.is-signed-out is set, hide every chrome element so a
 * public visitor sees nothing but the centred sign-in card. The
 * dashboard JS flips body.is-signed-in once a Supabase session is
 * confirmed. Server-side privacy still relies on RLS (every Supabase
 * row is gated on auth.jwt() ->> 'email' = ALLOWED_EMAIL); this is
 * the UI-level second ring.
 */
body.is-signed-out .dash-header,
body.is-signed-out .sync-bar,
body.is-signed-out #tabstrip,
body.is-signed-out .tab-panel,
body.is-signed-out details {
  display: none !important;
}
/* Signed-out layout matches goals-dashboard's sign-in: a top-anchored
 * centred column, no card chrome, banners stack above the heading
 * naturally because they're earlier siblings inside the same .wrap. */
body.is-signed-out .wrap {
  max-width: 480px;
  margin: 0 auto;
  padding: 0 16px;
}

/* Once signed-in, the hero card itself is hidden (chrome takes over). */
body.is-signed-in #signin-hero-mount { display: none !important; }

.wrap {
  max-width: 1400px;
  margin: 0 auto;
  padding: var(--space-5);
}

/* --- Header --------------------------------------------------------- */

.dash-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-bottom: var(--space-5);
  flex-wrap: wrap;
  gap: var(--space-3);
}
.dash-header__title {
  font-size: var(--font-size-xl);
  font-weight: var(--font-weight-bold);
  color: #fff;
  margin: 0;
}
.dash-header__sub {
  font-size: var(--font-size-sm);
  color: var(--muted);
  margin-top: 2px;
}
.dash-header__right {
  display: flex;
  gap: var(--space-5);
  align-items: flex-end;
}
.dash-header__kpi .lbl {
  font-size: var(--font-size-sm);
  color: var(--muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
}
.dash-header__kpi .val {
  font-size: var(--font-size-md);
  font-weight: var(--font-weight-bold);
  margin-top: 2px;
}

/* --- Critical Number / Freedom Gap header (PR #83, skill §1) ------- */
/* Single headline KPI to the right of the title, with a small
   sparkline next to it and three secondaries on the row below. */
.dash-header__fg {
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
  min-width: 320px;
}
.dash-header__fg-row {
  display: flex;
  align-items: center;
  gap: var(--space-4);
}
.dash-header__fg-headline .lbl {
  font-size: var(--font-size-sm);
  color: var(--muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  display: flex;
  align-items: center;
  gap: var(--space-2);
}
.dash-header__fg-headline .val {
  font-size: var(--font-size-xl);
  font-weight: var(--font-weight-bold);
  margin-top: 2px;
  line-height: 1.1;
}
/* Coverage band pill — drives the headline mood. */
.dash-header__fg-band {
  font-size: 0.7rem;
  font-weight: var(--font-weight-bold);
  letter-spacing: 0.04em;
  padding: 2px 6px;
  border-radius: 999px;
  border: 1px solid currentColor;
  text-transform: uppercase;
}
.dash-header__fg-band[data-band="red"]   { color: var(--err, #cf222e); }
.dash-header__fg-band[data-band="amber"] { color: var(--warn, #d29922); }
.dash-header__fg-band[data-band="green"] { color: var(--ok, #2ea043); }
.dash-header__fg-spark {
  width: 160px;
  height: 32px;
}
.dash-header__fg-spark svg { display: block; }
.dash-header__fg-secondaries {
  display: flex;
  gap: var(--space-4);
  flex-wrap: wrap;
}
/* Coach streak chip (PR #97). Tone-driven background that stays
   readable on the dashboard's dark canvas. */
.dash-header__streak {
  font-size: var(--font-size-sm);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-md);
  background: var(--card);
  border: 1px solid var(--border);
  color: var(--text);
  margin-top: var(--space-2);
  line-height: 1.3;
}
.dash-header__streak[data-tone="celebrate"] {
  background: var(--color-success-bg, rgba(46,160,67,0.15));
  border-color: var(--ok, #2ea043);
  color: var(--ok, #2ea043);
}
.dash-header__streak[data-tone="maintain"] {
  background: var(--color-info-bg, rgba(33,136,255,0.10));
  border-color: var(--accent, #2563eb);
}
.dash-header__streak[data-tone="recover"] {
  background: var(--color-warn-bg, rgba(210,153,34,0.10));
  border-color: var(--warn, #d29922);
  color: var(--warn, #d29922);
}
.dash-header__streak[data-tone="idle"] {
  opacity: 0.6;
}
@media (max-width: 640px) {
  .dash-header__fg { min-width: 0; }
  .dash-header__fg-row { flex-wrap: wrap; }
  .dash-header__fg-spark { width: 120px; }
}

/* --- BHAG horizon tile (PR #95, skill §1 + §10) -------------------- *
 * Compact tile sitting next to the Freedom Gap KPI block. Same vibe
 * as a .dash-header__kpi but with a slim progress bar underneath
 * showing percent elapsed against the 10-year horizon. */
.dash-header__bhag {
  display: flex;
  flex-direction: column;
  gap: 4px;
  min-width: 180px;
  padding-left: var(--space-4);
  border-left: 1px solid var(--border);
}
.dash-header__bhag .lbl {
  font-size: var(--font-size-sm);
  color: var(--muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
}
.dash-header__bhag .val {
  font-size: var(--font-size-md);
  font-weight: var(--font-weight-bold);
}
.dash-header__bhag-sub {
  font-size: var(--font-size-xs);
  color: var(--muted);
}
.dash-header__bhag-bar {
  margin-top: 4px;
  height: 4px;
}
@media (max-width: 1100px) {
  .dash-header__bhag { min-width: 0; padding-left: 0; border-left: none; }
}

/* --- Sync bar ------------------------------------------------------- */

.sync-bar {
  display: flex;
  gap: var(--space-2);
  align-items: center;
  font-size: var(--font-size-sm);
  color: var(--muted);
  padding: var(--space-2) var(--space-4);
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  margin-bottom: var(--space-4);
}
.sync-dot {
  width: 8px; height: 8px;
  border-radius: 50%;
  background: var(--green);
  flex-shrink: 0;
}
.sync-dot--offline { background: var(--orange); }
.sync-dot--error   { background: var(--red); }
.sync-bar__spacer  { flex: 1; }

/* --- Tabs ----------------------------------------------------------- */

.tabs {
  display: flex;
  gap: 4px;
  background: var(--card);
  padding: 4px;
  border-radius: var(--radius-lg);
  margin-bottom: var(--space-5);
  overflow-x: auto;
  border: 1px solid var(--border);
}
.tab {
  padding: 8px 18px;
  border-radius: var(--radius-md);
  font-size: var(--font-size-base);
  font-weight: var(--font-weight-medium);
  cursor: pointer;
  border: none;
  background: transparent;
  color: var(--muted);
  transition: background var(--motion-fast), color var(--motion-fast);
  white-space: nowrap;
  font-family: inherit;
}
.tab:hover:not(.tab--active) { color: var(--text); }
.tab--active {
  background: var(--accent);
  color: #fff;
}

.tab-panel { display: none; }
.tab-panel--active { display: block; }

/* --- Cards & grids -------------------------------------------------- */

.card {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: var(--space-5);
  /* PR #129 — bump from --space-4 (16px) to --space-5 (24px) so
     stacked cards on the Income & Tax / Budget / Investments tabs
     have a clearer visual gap. Reported as "widgets touching each
     other". The grid gap on .grid--g2 etc. is unaffected — those
     use their own gap rule; only the bottom-of-card breathing
     room changes. */
  margin-bottom: var(--space-5);
}
.card__title {
  font-size: var(--font-size-md);
  color: #fff;
  margin: 0 0 2px;
  font-weight: var(--font-weight-semi);
}
.card__sub {
  font-size: var(--font-size-sm);
  color: var(--muted);
  margin: 0 0 var(--space-4);
}

.grid     { display: grid; gap: var(--space-4); }
.grid--g4 { grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); }
.grid--g3 { grid-template-columns: 1fr 1fr 1fr; }
.grid--g2 { grid-template-columns: 1fr 1fr; }
@media (max-width: 800px) {
  .grid--g2, .grid--g3 { grid-template-columns: 1fr; }
}

/* --- Stat tile (KPI in a card) -------------------------------------- */

.stat {
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  padding: var(--space-4);
}
.stat__lbl {
  font-size: var(--font-size-xs);
  text-transform: uppercase;
  letter-spacing: 0.05em;
  color: var(--muted);
  display: flex;
  justify-content: space-between;
}
.stat__val {
  font-size: var(--font-size-lg);
  font-weight: var(--font-weight-bold);
  margin-top: 4px;
  color: #fff;
}
.stat__note {
  font-size: var(--font-size-sm);
  color: var(--muted);
  margin-top: 2px;
}

/* --- Balance Sheet (Rich Dad: Income / Expenses / Assets / Liabilities) -- */

.bs-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--space-4);
}
@media (max-width: 800px) {
  .bs-grid { grid-template-columns: 1fr; }
}
.bs-box {
  background: var(--bg);
  border-radius: var(--radius-md);
  padding: var(--space-4);
}
.bs-title {
  font-size: var(--font-size-sm);
  font-weight: var(--font-weight-semi);
  text-transform: uppercase;
  letter-spacing: 0.05em;
  margin-bottom: var(--space-3);
}
.bs-item {
  display: flex;
  justify-content: space-between;
  padding: 6px 0;
  font-size: var(--font-size-base);
  border-bottom: 1px solid rgba(255, 255, 255, 0.04);
}
.bs-item:last-of-type { border-bottom: none; }
.bs-total {
  display: flex;
  justify-content: space-between;
  padding: var(--space-2) 0 0;
  margin-top: var(--space-2);
  border-top: 1px solid var(--border);
  font-weight: var(--font-weight-bold);
  font-size: var(--font-size-base);
}

/* --- Bucket rows (Barefoot) ----------------------------------------- */

.bucket-row {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  padding: var(--space-3);
  border-radius: var(--radius-md);
  background: var(--bg);
  margin-bottom: var(--space-2);
}
.bucket-row__dot {
  width: 8px; height: 8px;
  border-radius: 50%;
  flex-shrink: 0;
}
.bucket-row__info { flex: 1; }
.bucket-row__name { font-size: var(--font-size-base); color: #fff; }
.bucket-row__pct  { font-size: var(--font-size-sm); }
.bar-bg {
  height: 6px;
  border-radius: 3px;
  background: var(--border);
  margin-top: 4px;
}
.bar-fill {
  height: 6px;
  border-radius: 3px;
  transition: width 0.4s;
}

/* --- Debt rows ------------------------------------------------------ */

.debt-item {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  padding: var(--space-3);
  border-radius: var(--radius-md);
  background: var(--bg);
  margin-bottom: var(--space-2);
}
.debt-item__icon {
  width: 36px; height: 36px;
  border-radius: var(--radius-md);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: var(--font-size-md);
  flex-shrink: 0;
  background: var(--card-2);
}
.debt-item__info { flex: 1; }
.debt-item__name { font-size: var(--font-size-base); font-weight: var(--font-weight-medium); color: #fff; }
.debt-item__due  { font-size: var(--font-size-sm); color: var(--muted); }
.debt-item__amt  { font-size: var(--font-size-md); font-weight: var(--font-weight-bold); color: var(--red); }

/* --- Tables --------------------------------------------------------- */

.dash-table {
  width: 100%;
  border-collapse: collapse;
  font-size: var(--font-size-base);
}
.dash-table th {
  text-align: left;
  padding: 6px 8px;
  font-size: var(--font-size-xs);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--muted);
  font-weight: var(--font-weight-medium);
  border-bottom: 1px solid var(--border);
}
.dash-table td {
  padding: 6px 8px;
  border-top: 1px solid var(--border);
  vertical-align: top;
}
.dash-table tr:hover td { background: rgba(255, 255, 255, 0.02); }
.dash-table .r { text-align: right; }

/* --- FY Budget Grid (Jul–Jun monthly × categories) ------------------- */

.fy-grid-wrap { width: 100%; }
.fy-grid-scroll { overflow-x: auto; }
.fy-grid {
  border-collapse: collapse;
  font-size: var(--font-size-sm);
  min-width: 1100px;
  width: 100%;
}
.fy-grid th, .fy-grid td {
  padding: 6px 8px;
  text-align: right;
  border-top: 1px solid var(--border);
  white-space: nowrap;
}
.fy-grid thead th {
  font-size: var(--font-size-xs);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--muted);
  font-weight: var(--font-weight-medium);
  border-top: none;
  border-bottom: 1px solid var(--border);
  background: var(--card);
}
.fy-grid__corner {
  text-align: left !important;
  position: sticky;
  left: 0;
  z-index: 2;
  background: var(--card);
  color: #fff;
  font-weight: var(--font-weight-bold);
}
.fy-grid__name {
  text-align: left;
  font-weight: var(--font-weight-medium);
  color: #fff;
  position: sticky;
  left: 0;
  z-index: 1;
  background: var(--card);
  min-width: 160px;
}
.fy-grid__month--current,
.fy-grid__cell--current {
  background: rgba(37, 99, 235, 0.12);
  border-left: 2px solid var(--accent);
  border-right: 2px solid var(--accent);
}
.fy-grid thead th.fy-grid__month--current {
  background: rgba(37, 99, 235, 0.35);
  color: #fff;
  font-weight: var(--font-weight-bold);
}
.fy-grid__cell.editable {
  cursor: pointer;
  transition: background var(--motion-fast);
}
.fy-grid__cell.editable:hover {
  background: rgba(96, 165, 250, 0.08);
}
.fy-grid__cell.editing {
  background: var(--bg);
  padding: 2px 4px;
}
.fy-grid__cell.saved {
  background: rgba(16, 185, 129, 0.18);
}
.fy-grid__cell.save-error {
  background: rgba(239, 68, 68, 0.22);
}
.fy-grid__input {
  width: 90%;
  background: transparent;
  border: 1px solid var(--accent-l);
  border-radius: 4px;
  color: #fff;
  font: inherit;
  text-align: right;
  padding: 2px 4px;
  outline: none;
}
.fy-grid__total,
.fy-grid__grand {
  font-weight: var(--font-weight-bold);
  color: var(--text);
  border-left: 1px solid var(--border);
}
.fy-grid__grand { color: #fff; }
.fy-grid__totals-label {
  text-align: left !important;
  font-weight: var(--font-weight-bold);
  color: var(--muted);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  font-size: var(--font-size-xs);
  border-top: 2px solid var(--border) !important;
  position: sticky;
  left: 0;
  background: var(--card);
}
.fy-grid tfoot td { border-top: 2px solid var(--border); }

/* --- Payoff Timeline (Debt Dominos tab) ---------------------------- */

.payoff-timeline {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}
.payoff-timeline__item {
  display: grid;
  grid-template-columns: 200px 1fr 40px;
  gap: var(--space-3);
  align-items: center;
}
.payoff-timeline__info { min-width: 0; }
.payoff-timeline__name {
  font-size: var(--font-size-base);
  color: #fff;
  font-weight: var(--font-weight-medium);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.payoff-timeline__meta {
  font-size: var(--font-size-sm);
  color: var(--muted);
}
.payoff-timeline__bar {
  height: 18px;
  border-radius: var(--radius-pill);
  background: var(--bg);
  overflow: hidden;
}
.payoff-timeline__fill {
  height: 100%;
  border-radius: var(--radius-pill);
  transition: width var(--motion-base);
}
.payoff-timeline__order {
  font-weight: var(--font-weight-bold);
  text-align: right;
  font-size: var(--font-size-sm);
}
.payoff-timeline__summary {
  font-size: var(--font-size-sm);
  color: var(--muted);
  margin-top: var(--space-3);
}

/* --- Chart wrapper (Trends sub-charts + Debt paydown) -------------- */
.chart-wrap {
  width: 100%;
  height: 220px;
  position: relative;
}
.chart-wrap svg { display: block; }

/* --- Sign-in hero (matches goals-dashboard .signin) ----------------- *
 * No card chrome (no background / border / shadow). Top-anchored
 * centred column, plain text + a single accent CTA. The .btn override
 * here mirrors goals-dashboard's `.signin .btn` rule — needed because
 * the platform-level .btn defaults to a near-black neutral background,
 * which reads as a disabled-looking secondary action for the primary
 * sign-in CTA. */
.signin-hero {
  text-align: center;
  padding: 64px 16px;
  max-width: 480px;
  margin: 0 auto;
}
.signin-hero h1 {
  font-size: 32px;
  margin: 0 0 8px;
  color: #fff;
}
.signin-hero p {
  color: var(--muted);
  margin: 0 0 24px;
}
.signin-hero .btn {
  min-height: 44px;
  padding: 0 20px;
  background: var(--accent);
  color: #fff;
  border: 1px solid var(--accent);
  border-radius: 8px;
  font-weight: 600;
}
.signin-hero .btn:hover {
  background: var(--accent-dim);
  border-color: var(--accent-dim);
}

/* --- Add Transaction form ----------------------------------------- */

.add-txn-form {
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
  min-width: 380px;
}
/* PR #170 — drop the .add-txn-form prefix so every form (settings
   modal included) gets the labels / hints / errors styled. Pre-#170
   the settings form rendered the `hint` text but had no CSS rule
   for it, so the explainers were invisible by default. */
.form-row {
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.form-row__label {
  display: block;
  font-size: var(--font-size-xs);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--muted);
}
.form-row__hint {
  font-size: var(--font-size-sm);
  color: var(--muted);
  line-height: var(--line-height-body);
  margin-top: 2px;
}
.form-row__error {
  font-size: var(--font-size-xs);
  color: var(--red);
  min-height: 1em;
}
.form-input {
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  color: var(--text);
  font-family: inherit;
  font-size: var(--font-size-base);
  padding: 8px 10px;
  width: 100%;
}
.form-input:focus {
  outline: none;
  border-color: var(--accent-l);
  box-shadow: 0 0 0 2px rgba(96, 165, 250, 0.25);
}
.add-txn-form__kind {
  display: flex;
  gap: var(--space-3);
}
.add-txn-form__kind-option {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  cursor: pointer;
  padding: 6px 10px;
  border-radius: var(--radius-md);
  border: 1px solid var(--border);
  background: var(--bg);
  font-size: var(--font-size-base);
  color: var(--text);
}
.add-txn-form__kind-option--income { border-left: 3px solid var(--green); }
.add-txn-form__kind-option--expense { border-left: 3px solid var(--red); }
.add-txn-form__summary {
  background: var(--color-danger-bg);
  border: 1px solid var(--color-danger-border);
  color: var(--red);
  border-radius: var(--radius-md);
  padding: 8px 10px;
  font-size: var(--font-size-base);
}

/* --- Empty states (when a tab has no data) -------------------------- */

.empty {
  padding: var(--space-6);
  text-align: center;
  color: var(--muted);
  background: var(--card);
  border: 1px dashed var(--border);
  border-radius: var(--radius-lg);
}
.empty__title {
  font-size: var(--font-size-md);
  color: var(--text);
  margin: 0 0 var(--space-2);
}
.empty__body {
  font-size: var(--font-size-base);
  margin: 0;
}

/* --- Misc helpers --------------------------------------------------- */

.activity-log {
  font-family: var(--font-family-mono);
  font-size: var(--font-size-xs);
  background: var(--bg);
  border: 1px solid var(--border);
  padding: var(--space-3);
  border-radius: var(--radius-md);
  max-height: 200px;
  overflow-y: auto;
  color: var(--muted);
}
.activity-log p { margin: 0 0 4px; }

.pill {
  display: inline-flex;
  align-items: center;
  padding: 2px 8px;
  border-radius: var(--radius-pill);
  font-size: var(--font-size-xs);
  background: var(--card-2);
  color: var(--text);
  border: 1px solid var(--border);
}
.pill--info    { background: var(--color-info-bg);    border-color: var(--color-info-border);    color: var(--accent-l); }
.pill--success { background: var(--color-success-bg); border-color: var(--color-success-border); color: var(--green); }
.pill--warn    { background: var(--color-warn-bg);    border-color: var(--color-warn-border);    color: var(--orange); }
.pill--danger  { background: var(--color-danger-bg);  border-color: var(--color-danger-border);  color: var(--red); }
