/* ========================================================================
   DEPLOY PATH: /css/offset-polish.2ca1725e.css
   Tepuy Solutions — Offset vs Shares Calculator sidebar polish
   Version: 2026-03-31 (refactored)
   
   Load AFTER tepuy.css.
   Token overrides are scoped to .calc-aside — they do NOT bleed globally.
   ======================================================================== */

/* ── Design tokens — base sidebar-surface/accordion/footer tokens now live
   in css/simulators.css (body.calc .calc-aside). --inp-focus stays here
   since it's used by this page's own form-row rules below (out of scope
   for the sidebar-chrome consolidation). ── */
.calc-aside {
  --inp-focus:  #1a6b4a;
}


/* ══════════════════════════════════════════════════════════════════════════
   1.  SIDEBAR SURFACE — base surface/background/scrollbar moved to
       css/simulators.css. Only the wide-tier flush-border block stays here.
       Used to be the odd one out on VALUES (border shorthand + --sb-border
       token vs. mortgage/lmi's four longhands + hardcoded #dce8e1 — same
       resolved color, different bytes) while lmi-polish.css was also the
       odd one out on MECHANISM (@media (min-width:1025px) instead of this
       @container calc-layout (min-width:800px)). The mechanism mismatch is
       fixed; the value-shorthand difference is left as-is (see
       mortgage-polish.css's own note).
   ══════════════════════════════════════════════════════════════════════════ */

/* Wide tier (>=800px) — same threshold as tepuy.css's shared calc-layout
   density tiers; measures .main-layout's own rendered width (the iframe's
   width when embedded) instead of the raw viewport. */
@container calc-layout (min-width: 800px) {
  body.calc .calc-aside .sidebar-panel {
    border-radius: 0 !important;
    border: none !important;
    border-right: 1px solid var(--sb-border) !important;
    padding: 0 !important;
  }
  body.calc .calc-aside .sidebar-scroll { padding: 0.5rem 0.6rem 0 !important; }
}


/* Tooltip escape from aside overflow */
aside .i::after { position: fixed !important; left: var(--tip-x, 50%) !important; top: var(--tip-y, -9999px) !important; bottom: auto !important; transform: none !important; z-index: 99999 !important; }
aside .i::before { position: fixed !important; left: var(--tip-arrow-x, 50%) !important; top: var(--tip-arrow-y, -9999px) !important; bottom: auto !important; transform: rotate(45deg) !important; z-index: 99998 !important; }

/* ══════════════════════════════════════════════════════════════════════════
   ACCORDION CARDS — this file deliberately declares NO padding for them.
   ══════════════════════════════════════════════════════════════════════════
   Recorded 2026-09-06 (R4) because "offset-polish has no accordion rule while
   the other two do" reads as an oversight and is not one. The absence IS the
   correct state, and adding an explicit rule here would break the thing it
   looks like it would fix.

   Where the values come from, in cascade order:

     css/simulators.css   the shared open padding, 0.65rem 0.9rem 0.85rem
     css/tepuy.css        the narrow tier, 0.45rem 0.9rem

   Measured in Chromium with the 0.3s transition allowed to settle, this page
   renders 10.4/14.4/13.6 at 1366 and 900 wide and 7.2/14.4/7.2 at 700 — the
   same as LMI and Property vs Shares at every width. It is already converged.

   An explicit `aside .card-content.open { … !important }` here would sit at
   DESKTOP level and therefore win at narrow widths too, pinning this page to
   desktop spacing exactly the way mortgage-polish.css's
   `:not([hidden]).open` selector used to pin Mortgage — the divergence R4
   deleted. So the rule that would make this file look consistent with its two
   siblings is the rule that would make the RENDERED page inconsistent with
   them.

   If a genuine offset-only accordion value is ever needed, put it inside the
   `@container calc-sidebar` block below rather than at desktop level.
   ══════════════════════════════════════════════════════════════════════════ */

/* Form rows */
aside .form-row { margin-bottom: 0.5rem !important; }
/* aside .form-row label now comes from css/tepuy.css, once, at 0.8125rem.
   This file's byte-identical override was one of four. */
aside .form-row input[type="text"],
aside .form-row input[type="number"],
aside .form-row select {
  width: 100% !important; padding: 0.3rem 0.55rem !important;
  font-size: 0.845rem !important; border-radius: 5px !important;
  border: 1px solid var(--inp-border) !important; background: #ffffff !important;
  color: #0f1c16 !important; font-family: inherit !important;
  transition: border-color 0.15s, box-shadow 0.15s !important; box-sizing: border-box !important;
}
aside .form-row input:focus, aside .form-row select:focus {
  outline: none !important; border-color: var(--inp-focus) !important;
  box-shadow: 0 0 0 3px rgba(26,107,74,0.12) !important;
}
/* Select dropdown arrow.

   The selector carries `.form-row` deliberately. Until 2026-09-05 this rule
   was just `aside select` (specificity 0,1,1 -> 0,0,2), while the input
   styling above uses `aside .form-row select` (0,1,2) and sets a
   `background:` SHORTHAND — which resets background-image to none and, being
   more specific, won. Combined with `appearance: none` here, which the
   shorthand does NOT reset, the result was a select with no native arrow and
   no custom one.

   Measured across the four sidebar calculators: NINE of eleven selects
   rendered with no dropdown indicator at all. That is why the chevron's
   2.36:1 contrast never appeared in an axe scan — the chevron was not being
   painted. */
aside .form-row select,
aside select {
  appearance: none !important; -webkit-appearance: none !important;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 6'%3E%3Cpath d='M0 0l5 6 5-6z' fill='%2355685F'/%3E%3C/svg%3E") !important;
  background-repeat: no-repeat !important; background-position: right 0.6rem center !important;
  background-size: 8px 5px !important; padding-right: 1.8rem !important; cursor: pointer !important;
}
aside .grid-2 { display: grid !important; grid-template-columns: 1fr 1fr !important; gap: 0.5rem !important; }
/* Sidebar's own cramped width — 300px matches the Narrow-tier threshold
   used elsewhere; the sidebar's rendered width never reaches the old 440px
   viewport value verbatim. */
@container calc-sidebar (max-width: 300px) { aside .grid-2 { grid-template-columns: 1fr !important; } }

.check-row {
  display: flex !important; align-items: flex-start !important;
  gap: 0.45rem !important; font-size: 0.8rem !important; color: #3d5248 !important;
  cursor: pointer !important; margin-top: 0.2rem !important;
}
.check-row input[type="checkbox"] { width: auto !important; margin: 2px 0 0 !important; flex-shrink: 0 !important; accent-color: #1a5236 !important; }

/* Scenario B sub-label */
.ovs-scen-b-label {
  font-size: 0.67rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.08em; color: var(--text-muted); margin-bottom: 0.5rem;
  padding-top: 0.35rem; border-top: 1px solid #e8f0eb; margin-top: 0.35rem;
}

/* Sidebar footer's base surface and Calculate button live in
   css/simulators.css — no local override here. Unlike mortgage/lmi, this
   page's #runBtn/.ovs-calc-hint never set letter-spacing/line-height, and
   simulators.css's shared rule deliberately excludes both properties for
   that reason (referenced from mortgage-polish.css and lmi-polish.css —
   keep this note if removing that exclusion). */

/* Scenario buttons (reuse retirement pattern) */
.ret-scenario-row { display: flex; gap: 0.35rem; }
.ret-scen-btn {
  flex: 1; display: inline-flex; align-items: center; justify-content: center;
  gap: 0.28rem; padding: 0.38rem 0.4rem; font-family: inherit;
  font-size: 0.72rem; font-weight: 600; color: #3d5248;
  background: #f4f8f6; border: 1px solid #c8ddd3; border-radius: 6px;
  cursor: pointer; white-space: nowrap;
  transition: background 0.13s, border-color 0.13s, color 0.13s;
}
.ret-scen-btn:hover { background: #e6f2ec; border-color: #3db07e; color: #1a5236; }
/* Load-button busy state (fix-scenario-save-load-followup-bugs, 2026-08-30)
   — :disabled alone gave no visible cue a fetch was in flight, so a click
   right after Save/page-load (before the list request resolves) looked
   like a no-op; reuses tepuy.css's shared @keyframes spin. */
.ret-scen-btn.is-busy { opacity: 0.75; cursor: wait; }
.ret-scen-btn.is-busy::before {
  content: "";
  width: 0.85em; height: 0.85em;
  border-radius: 50%;
  border: 2px solid rgba(61,82,72,0.25);
  border-top-color: currentColor;
  animation: spin 0.8s linear infinite;
}
.ret-scen-btn--share { color: #1a5236; background: #edf7f2; border-color: #b3d9c4; }
.ret-scen-btn--share:hover { background: #d4ede2; border-color: #1a6b4a; }
.ret-scen-hint { display: none; font-size: 0.7rem; font-weight: 500; padding: 0.15rem 0; text-align: center; }

/* Pro badge hidden */
.pro-badge, #footerBadge, .pro-cta, #unlockPro, .pro-emoji { display: none !important; }


/* ══════════════════════════════════════════════════════════════════════════
   4.  SHARED BANNER + SHARE RESULT BAR
   ══════════════════════════════════════════════════════════════════════════ */
.ret-shared-banner {
  display: flex; align-items: center; gap: 0.65rem;
  padding: 0.7rem 1rem; background: #f0fdf4; border: 1px solid #86efac;
  border-radius: 10px; margin-bottom: 1rem; font-size: 0.85rem; color: #14532d; line-height: 1.45;
}
.ret-shared-banner[hidden] { display: none !important; }
.ret-shared-banner__close { margin-left: auto; background: none; border: none; font-size: 0.85rem; color: #4ade80; cursor: pointer; padding: 0.1rem 0.2rem; }

.ret-share-result-bar { display: flex; justify-content: flex-end; margin: 0.5rem 0 0.75rem; }
.ret-share-result-bar[hidden] { display: none !important; }
/* .ret-share-result-btn used to be declared here too, with different (and
   undocumented — unlike the .ret-sc-badge divergence below, which has a
   reasoned comment) padding/font-size/background/border/border-radius
   values, and NO letter-spacing or hover box-shadow. Since this second
   declaration further down the cascade (same specificity) always won,
   THIS block was dead CSS, and the one that rendered had silently drifted
   from Mortgage's/LMI's identical shared value. Removed; see that
   declaration below for the fix. */


/* ══════════════════════════════════════════════════════════════════════════
   5.  KPI STRIP
   ══════════════════════════════════════════════════════════════════════════ */
.ovs-kpi-strip {
  display: grid; grid-template-columns: repeat(4, 1fr);
  gap: 0.6rem; margin-bottom: 1rem;
}
.ovs-kpi-card {
  background: #ffffff; border: 1px solid #dce8e1; border-radius: 10px;
  padding: 0.75rem 0.9rem; box-shadow: 0 1px 4px rgba(0,0,0,0.04);
  display: flex; flex-direction: column; gap: 0.2rem;
}
.ovs-kpi-label { font-size: 0.62rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.08em; color: var(--text-muted); }
.ovs-kpi-value { font-size: 1.15rem; font-weight: 700; color: #0f1c16; line-height: 1.2; font-variant-numeric: tabular-nums; }
.ovs-kpi-value--good { color: #15803d; }
.ovs-kpi-value--warn { color: #b45309; }
.ovs-kpi-sub  { font-size: 0.68rem; color: var(--text-muted); font-weight: 500; }
/* calc-layout, not calc-main: <main> gets display:contents at every
   stacked width below 800px (tepuy.css's .page-head comment, section 5b),
   which strips it of its own box — a @container calc-main query naming a
   broken container simply never matches, silently, so this never
   collapsed on a phone. Same bug/fix as lmi-polish.css's .lmi-kpi-strip
   and mortgage-polish.css's .mort-insights-strip; see either for the full
   mechanism. Checked every @container calc-main rule in this file for
   the same defect. */
@container calc-layout (max-width: 768px) { .ovs-kpi-strip { grid-template-columns: repeat(2, 1fr); } }


/* ══════════════════════════════════════════════════════════════════════════
   6.  RESULTS TAB SYSTEM
   ══════════════════════════════════════════════════════════════════════════ */
.results-tabs-wrap {
  background: #ffffff; border: 1px solid #dce8e1; border-radius: 14px;
  overflow: hidden; margin-bottom: 1.25rem; box-shadow: 0 2px 8px rgba(0,0,0,0.05);
}
/* .rtab-bar / .rtab-btn / .rtab-btn--active / .rtab-panel / .rtab-panel--hidden
   / .rtab-actions were verbatim copies of css/calculators.css's rules and are
   deleted here. This page did not load calculators.css when they were written;
   it has since #204, so the copies were pure duplication — except that
   .rtab-panel--hidden's copy carried `!important` and the shared rule does
   not, so the copy WON and the shared rule was dead on every page that had
   one. Measured after deletion: every panel still hides — calculators.css
   declares .rtab-panel--hidden AFTER .rtab-panel at equal specificity, so it
   wins without needing !important — and .rtab-btn--active still computes
   `2px solid rgb(26, 82, 54)` with font-weight 800, unchanged.
   (No line numbers quoted on purpose: docs/OPEN-ITEMS.md records a previous
   entry whose cited line had drifted by 41 before anyone checked.)
   One deliberate behaviour change: the copy's hover was `.rtab-btn:hover`,
   the shared rule's is `.rtab-btn:hover:not(:disabled)` — a disabled
   ("coming soon") tab no longer takes hover paint, which is what the shared
   rule always intended. */

.btn-ghost-sm {
  display: inline-flex; align-items: center; gap: 0.35rem; font-family: inherit;
  font-size: 0.775rem; font-weight: 500; color: #4a655a; background: transparent;
  border: 1px solid #c8ddd3; border-radius: 4px; padding: 0.3rem 0.7rem;
  cursor: pointer; transition: color 0.15s, border-color 0.15s, background 0.15s; white-space: nowrap;
}
.btn-ghost-sm:hover { color: #0f1c16; border-color: #3db07e; background: #f8faf9; }
.btn-ghost-sm svg { flex-shrink: 0; }

.btn-action {
  display: inline-flex; align-items: center; gap: 0.4rem; font-family: inherit;
  font-size: 0.8rem; font-weight: 600; color: #ffffff; background: #1a5236;
  border: none; border-radius: 8px; padding: 0.45rem 0.95rem; cursor: pointer;
  transition: background 0.15s, box-shadow 0.15s, transform 0.1s; white-space: nowrap;
  box-shadow: 0 1px 2px rgba(0,0,0,0.12);
}
.btn-action:hover { background: #247857; box-shadow: 0 3px 8px rgba(26,82,54,0.25); transform: translateY(-1px); }
.btn-action--ghost { color: #3d5248; background: #f1f7f4; box-shadow: none; border: 1px solid #e3ede8; }
.btn-action--ghost:hover { background: #e6f0eb; border-color: #c8ddd3; box-shadow: none; color: #0f1c16; }

/* Chart container */
body.calc {
  --chart-height-desktop: 400px;
}
.rtab-chart { position: relative; width: 100%; height: var(--chart-height-desktop); min-height: 220px; overflow: hidden; }
.rtab-chart canvas { display: block !important; width: 100% !important; height: 100% !important; }
.rtab-chart::after {
  content: 'tepuysolutions.com'; position: absolute; bottom: 4px; right: 8px;
  font-size: 9px; font-weight: 600; color: rgba(26,107,74,0.25);
  letter-spacing: 0.04em; pointer-events: none; z-index: 1; font-family: 'Inter', system-ui, sans-serif;
}
/* calc-layout, not calc-main — same defect as .ovs-kpi-strip above (the
   calc-main container this queried is display:contents-broken in the
   exact stacked tier this needs to fire in).

   That said: this specific pair is currently DEAD CODE either way, and
   was before this change too. css/tepuy.css declares its own .rtab-chart
   height at every tier via raw @media queries with !important, which
   always wins over a non-!important rule regardless of specificity or
   source order. Confirmed by deleting this pair entirely and measuring
   getComputedStyle('.rtab-chart').height at 375px before and after:
   identical (260px) either way. So this does NOT explain the separately-
   reported "charts too small on mobile" suspicion — tepuy.css's own rule
   already governs this chart's height, unaffected by the calc-main bug.
   Left as a mechanical swap anyway for consistency with the rest of this
   file and in case tepuy.css's rule is ever weakened or removed — but
   it is inert today (same finding, independently confirmed, as
   mortgage-polish.css's identical .rtab-chart pair). */
@container calc-layout (max-width: 960px) { .rtab-chart { height: 300px; } }
@container calc-layout (max-width: 640px) { .rtab-chart { height: 260px; } }

/* Summary text */
.ovs-summary-text {
  font-size: 0.9rem; color: #3d5248; line-height: 1.6; margin: 0 0 0.75rem;
  padding: 0.65rem 0.85rem; background: #f7faf8; border-radius: 8px;
  border-left: 3px solid #c8ddd3;
}

/* Chart legend */
.ovs-chart-legend {
  display: flex; align-items: center; gap: 1.25rem; flex-wrap: wrap;
  padding: 0.6rem 0 0.25rem; font-size: 0.72rem; font-weight: 600; color: #5a7a6a;
}
.ovs-leg-item { display: flex; align-items: center; gap: 0.35rem; }
.ovs-leg-line { display: block; width: 20px; height: 0; border-top: 2.5px solid; flex-shrink: 0; }
.ovs-leg-line--dash { border-top-style: dashed; }

/* Tab intro text */
.ovs-tab-intro {
  font-size: 0.85rem; color: #4a655a; line-height: 1.55;
  margin: 0 0 1rem; padding: 0.65rem 0.85rem;
  background: #f7faf8; border-radius: 8px; border-left: 3px solid #c8ddd3;
}

/* Table */
.ovs-table-wrap { overflow-x: auto; -webkit-overflow-scrolling: touch; border-radius: 8px; border: 1px solid #e3ede8; }
.ovs-table { width: 100%; border-collapse: collapse; font-size: 0.82rem; }
.ovs-table thead th {
  padding: 0.5rem 0.75rem; background: #f7faf8; color: #4a655a;
  font-size: 0.7rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em;
  border-bottom: 1.5px solid #dce8e1; white-space: nowrap; text-align: right;
}
.ovs-table thead th:first-child { text-align: left; }
.ovs-table tbody td {
  padding: 0.4rem 0.75rem; border-bottom: 1px solid #f0f5f2;
  color: #1a3326; text-align: right; font-variant-numeric: tabular-nums;
}
.ovs-table tbody td:first-child { text-align: left; color: #4a655a; font-weight: 600; }
.ovs-table tbody tr:last-child td { border-bottom: none; }
.ovs-table tbody tr:hover td { background: #f7faf8; }


/* ══════════════════════════════════════════════════════════════════════════
   7.  INSIGHTS TAB
   ══════════════════════════════════════════════════════════════════════════ */
.ovs-insight-headline {
  font-size: 1rem; font-weight: 600; line-height: 1.55; color: #1a3326;
  background: #f0fdf4; border: 1px solid #86efac; border-radius: 10px;
  padding: 0.85rem 1rem; margin-bottom: 1rem;
}
.ovs-insight-headline strong { color: #15803d; }
.ovs-ins-good { background: #f0fdf4; border-color: #86efac; }
.ovs-ins-warn { background: #fffbeb; border-color: #fde68a; }
.ovs-ins-warn strong { color: #92400e !important; }

.ovs-ins-grid {
  display: grid; grid-template-columns: repeat(3, 1fr);
  gap: 0.75rem; margin-bottom: 1rem;
}
/* calc-layout, not calc-main — same defect and fix as .ovs-kpi-strip above. */
@container calc-layout (max-width: 640px) { .ovs-ins-grid { grid-template-columns: 1fr 1fr; } }

.ovs-ins-kpi {
  background: #f7faf8; border: 1px solid #e3ede8; border-radius: 10px;
  padding: 0.75rem 0.85rem; display: flex; flex-direction: column; gap: 0.25rem;
}
.ovs-ins-kpi-label { font-size: 0.62rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.07em; color: var(--text-muted); }
.ovs-ins-kpi-value { font-size: 1.1rem; font-weight: 700; color: #0f1c16; font-variant-numeric: tabular-nums; line-height: 1.2; }
.ovs-ins-kpi-value--green { color: #15803d; }
.ovs-ins-kpi-value--warn  { color: #b45309; }
.ovs-ins-kpi-value--blue  { color: #1d4ed8; }
.ovs-ins-kpi-sub { font-size: 0.67rem; color: var(--text-muted); line-height: 1.3; }

.ovs-ins-explain {
  background: #f7faf8; border: 1px solid #e3ede8; border-radius: 10px; padding: 1rem;
}
.ovs-ins-exp-title {
  font-size: 0.72rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.07em; color: var(--text-muted); margin-bottom: 0.6rem;
}
.ovs-ins-explain p { font-size: 0.9rem; color: #3d5248; line-height: 1.65; margin: 0; }


/* ══════════════════════════════════════════════════════════════════════════
   SCENARIO COLOURS & BADGES
   ══════════════════════════════════════════════════════════════════════════ */
:root {
  --scen-a: #60a5fa;  /* blue   — Cashflow Saver    */
  --scen-b: #f472b6;  /* pink   — All in Offset     */
  --scen-c: #22c55e;  /* green  — All in Shares     */
  --scen-d: #fb923c;  /* orange — Balanced Investor */
}

.scen-pill {
  display: inline-flex; align-items: center; justify-content: center;
  width: 18px; height: 18px; border-radius: 50%;
  font-size: 0.65rem; font-weight: 700; line-height: 1;
  flex-shrink: 0;
}
.scen-a { background: var(--scen-a); color: #0a1e3a; }
.scen-b { background: var(--scen-b); color: #3a001a; }
.scen-c { background: var(--scen-c); color: #052e0f; }
.scen-d { background: var(--scen-d); color: #3a1400; }

.scen-badge { /* inline in table/insights */
  display: inline-flex; align-items: center; justify-content: center;
  width: 20px; height: 20px; border-radius: 50%;
  font-size: 0.7rem; font-weight: 700;
}

/* ── Scenario legend strip ── */
.ovs-scen-legend {
  display: flex; flex-wrap: wrap; gap: 0.6rem;
  padding: 0.7rem 0.9rem;
  background: #f7faf8; border: 1px solid #dce8e1; border-radius: 10px;
  margin-bottom: 1rem;
}
.ovs-scen-badge-row { display: flex; align-items: center; gap: 0.45rem; font-size: 0.82rem; color: #3d5248; }
.scen-pill-text { font-size: 0.82rem; color: #3d5248; }

/* ── KPI strip — 5 cards ── */
.ovs-kpi-strip {
  display: grid; grid-template-columns: repeat(5, 1fr);
  gap: 0.6rem; margin-bottom: 1rem;
}
.ovs-kpi-card--winner { border-color: #dce8e1; background: linear-gradient(135deg,#f7faf8,#ffffff); }
/* calc-layout, not calc-main — same defect and fix as the other .ovs-kpi-strip
   block above. */
@container calc-layout (max-width: 960px) { .ovs-kpi-strip { grid-template-columns: repeat(3,1fr); } }
@container calc-layout (max-width: 640px) { .ovs-kpi-strip { grid-template-columns: 1fr 1fr; } }

/* ── Table — three-scenario headers ── */
.td-yr { width: 30px; text-align: center !important; color: #4a655a !important; font-weight: 600 !important; }
.th-scen { text-align: center !important; font-size: 0.72rem !important; padding: 0.35rem !important; }
.th-scen-a { background: color-mix(in srgb, var(--scen-a) 15%, white) !important; color: #1a3a6a !important; }
.th-scen-b { background: color-mix(in srgb, var(--scen-b) 15%, white) !important; color: #3a001a !important; }
.th-scen-c { background: color-mix(in srgb, var(--scen-c) 20%, white) !important; color: #052e0f !important; }
.th-scen-d { background: color-mix(in srgb, var(--scen-d) 15%, white) !important; color: #3a1400 !important; }
.td-win { font-weight: 700 !important; color: #0f1c16 !important; background: rgba(0,255,174,0.08) !important; }
.td-ldr { font-weight: 700 !important; text-align: center !important; }
.scen-a.td-ldr { color: #1e60c0; } .scen-b.td-ldr { color: #a0185f; } .scen-c.td-ldr { color: #0a7a40; } .scen-d.td-ldr { color: #c2440a; }

/* ── Sensitivity table ── */
.ovs-sens-wrap { overflow-x: auto; -webkit-overflow-scrolling: touch; }
.ovs-sens-table { border-collapse: collapse; font-size: 0.8rem; min-width: 360px; }
.ovs-sens-table th { padding: 0.45rem 0.6rem; background: #f7faf8; color: #4a655a; font-size: 0.72rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em; border-bottom: 1.5px solid #dce8e1; text-align: center; }
.ovs-sens-table td { padding: 0.45rem 0.6rem; border-bottom: 1px solid #f0f5f2; text-align: center; cursor: default; }
.ovs-sens-table td.sens-a { background: color-mix(in srgb,var(--scen-a) 15%,white); }
.ovs-sens-table td.sens-d { background: color-mix(in srgb,var(--scen-d) 15%,white); }
.ovs-sens-table td.sens-d { background: color-mix(in srgb,var(--scen-d) 15%,white); }
.ovs-sens-table td.sens-b { background: color-mix(in srgb,var(--scen-b) 12%,white); }
.ovs-sens-table td.sens-c { background: color-mix(in srgb,var(--scen-c) 12%,white); }
.sens-winner { display: block; font-size: 1rem; font-weight: 800; line-height: 1; }
.sens-delta  { display: block; font-size: 0.62rem; color: #4a655a; margin-top: 1px; }
.ovs-sens-note { font-size: 0.72rem; color: var(--text-muted); margin: 0.5rem 0 0; line-height: 1.45; }

/* ── Insights ── */
.ovs-strat-winner td { font-weight: 600 !important; }
.scen-badge.scen-a { background:var(--scen-a);color:#0a1e3a; }
.scen-badge.scen-b { background:var(--scen-b);color:#3a001a; }
.scen-badge.scen-c { background:#0f1c16;color:var(--scen-c); }
.ovs-mc-summary { font-size: 0.82rem; color: #3d5248; background: #f7faf8; border-radius: 8px; padding: 0.7rem 0.85rem; margin-top: 0.85rem; line-height: 1.55; }
.ovs-hurdle-box { background: #fff8ed; border: 1px solid #fde68a; border-radius: 8px; padding: 0.8rem 0.95rem; margin-top: 0.85rem; font-size: 0.85rem; color: #3d5248; line-height: 1.6; }
.ovs-above { color: #15803d; font-weight: 600; }
.ovs-below { color: #b45309; font-weight: 600; }
.ovs-pro { color: #15803d; font-size: 0.8rem; }
.ovs-con { color: #b45309; font-size: 0.8rem; }

/* ── Summary text notes ── */
.ovs-good-note {
  display: inline-block;
  background: #f0fdf4;
  color: #15803d;
  font-size: 0.78rem;
  font-weight: 600;
  padding: 0.15rem 0.5rem;
  border-radius: 4px;
  border: 1px solid #86efac;
  margin-left: 0.25rem;
}

/* ── Equity framing / wealth definition note ── */
.ovs-equity-note {
  background: #f0f9ff;
  border: 1px solid #bae6fd;
  border-left: 3px solid #38bdf8;
  border-radius: 8px;
  padding: 0.75rem 0.95rem;
  margin-top: 0.85rem;
  font-size: 0.82rem;
  color: #0c4a6e;
  line-height: 1.55;
}
.ovs-equity-note strong { color: #0369a1; }
.ovs-wealth-defs {
  display: block;
  margin-top: 0.4rem;
  font-size: 0.75rem;
  color: #0c4a6e;
  opacity: 0.8;
  font-style: italic;
}

/* ── Explainer framing box ── */
.ovs-explainer-framing {
  background: #f0f9ff;
  border: 1px solid #bae6fd;
  border-left: 3px solid #38bdf8;
  border-radius: 8px;
  padding: 0.75rem 0.95rem;
  margin-bottom: 1rem;
  font-size: 0.85rem;
  color: #0c4a6e;
  line-height: 1.55;
}

/* ── Year-by-year table: post-payoff rows (B's loan cleared, all reinvesting) ── */
.ovs-table tbody .tr-postpayoff {
  background: rgba(26, 82, 54, 0.05);
}
.ovs-table tbody .tr-postpayoff td {
  color: #1a5236;
  font-style: italic;
}
.ovs-table tbody .tr-postpayoff .td-yr::after {
  content: ' ★';
  font-size: 0.6rem;
  color: #3db07e;
  font-style: normal;
}


/* ══════════════════════════════════════════════════════════════════════════
   LOAD SCENARIO DROPDOWN  (ret-load-dropdown / rld-*)
   Mirrors lmi-polish.css exactly so Save/Load/Share work on this page.
   ══════════════════════════════════════════════════════════════════════════ */
.ret-load-dropdown {
  background: #ffffff;
  border: 1px solid #c8ddd3;
  border-radius: 8px;
  box-shadow: 0 4px 18px rgba(0,0,0,0.13);
  overflow: hidden;
  margin: 0 0 0.5rem;
  z-index: 200;
  animation: rld-fadein 0.15s ease;
}
@keyframes rld-fadein { from { opacity:0; transform:translateY(-4px); } to { opacity:1; transform:translateY(0); } }

/* The rest of .rld-* (header/list/item/name/date + most hover states)
   moved to css/simulators.css — confirmed byte-identical across this file,
   mortgage-polish.css and lmi-polish.css, via a direct diff, before the
   move. .rld-close itself stays here: this file (and lmi's) set
   `line-height: 1` on it, mortgage-polish.css doesn't — a real, if tiny,
   difference the move must not erase. */
.rld-close { background: none; border: none; font-size: 0.8rem; color: var(--text-muted); cursor: pointer; padding: 0; line-height: 1; }


/* ══════════════════════════════════════════════════════════════════════════
   SHARE CARD MODAL  (ret-sc-overlay / ret-sc-*)
   Mirrors lmi-polish.css exactly so the share result card works on this page.
   ══════════════════════════════════════════════════════════════════════════ */

/* Most of .ret-sc-* moved to css/simulators.css — confirmed byte-identical
   across this file, mortgage-polish.css and lmi-polish.css, via a direct
   diff, before the move. What's left below is page-local ON PURPOSE, not
   an oversight:

   - .ret-sc-badge / .ret-sc-badge-good / .ret-sc-badge-warn: this file's
     bare .ret-sc-badge defaults background/color/border to the "good"
     look, and the -good/-warn variants only override `border-color`.
     mortgage-polish.css's bare .ret-sc-badge sets none of that, so its
     variants each supply the FULL `border` shorthand instead. Same
     rendered result for -good/-warn either way, but a DIFFERENT result
     for an unmodified .ret-sc-badge — moving this would be a behaviour
     change, not a move.
   - .ret-sc-action-primary: `color: #ffffff` here vs `#fff` in
     mortgage-polish.css — identical rendered color, different bytes; left
     alone rather than picking a winner un-asked.

   The .ret-sc-stats/-headline/-action-btn tweak a little further down has
   the same values in all three files but stays local for a different
   reason: lmi-polish.css gates the identical declarations with
   `@media (max-width: 500px)` where this file (and mortgage's) use
   `@container calc-layout (max-width: 500px)` — the same LMI/mortgage
   container-vs-media divergence already flagged elsewhere in this repo,
   not something to paper over here by picking one mechanism. */
.ret-sc-badge {
  display: inline-block; font-size: 0.68rem; font-weight: 700;
  text-transform: uppercase; letter-spacing: 0.09em;
  padding: 0.28rem 0.75rem; border-radius: 20px;
  background: rgba(26,107,74,0.25); color: #4ade80; border: 1px solid rgba(74,222,128,0.3);
}
.ret-sc-badge.ret-sc-badge-good { background: rgba(26,107,74,0.25); color: #4ade80; border-color: rgba(74,222,128,0.3); }
.ret-sc-badge.ret-sc-badge-warn { background: rgba(251,191,36,0.15); color: #fbbf24; border-color: rgba(251,191,36,0.3); }

.ret-sc-action-primary { background: #1a5236; color: #ffffff; }

/* Share result bar (above the chart tabs) */
.ret-share-result-bar {
  display: flex; justify-content: flex-end;
  margin-bottom: 0.5rem;
}
/* Converged onto Mortgage's/LMI's identical value (2026-09) — see the
   comment where the second, drifted declaration used to sit above this
   one, before it was removed. */
.ret-share-result-btn {
  display: inline-flex; align-items: center; gap: 0.4rem;
  padding: 0.45rem 1rem; font-family: inherit; font-size: 0.82rem; font-weight: 600;
  color: #1a5236; background: #f0fdf4; border: 1.5px solid #86efac;
  border-radius: 8px; cursor: pointer; letter-spacing: 0.01em;
  transition: background 0.14s, border-color 0.14s, box-shadow 0.14s;
}
.ret-share-result-btn:hover {
  background: #dcfce7; border-color: #4ade80;
  box-shadow: 0 2px 8px rgba(26,107,74,0.15);
}

@container calc-layout (max-width: 500px) {
  .ret-sc-stats { grid-template-columns: 1fr; }
  .ret-sc-headline { font-size: 0.95rem; }
  .ret-sc-action-btn { padding: 0.5rem 0.75rem; font-size: 0.76rem; }
}

/* ── IP mode indicator note in summary bar ── */
.ovs-ip-note {
  display: inline-block;
  background: #fef3c7;
  color: #92400e;
  border: 1px solid #fde68a;
  border-radius: 4px;
  font-size: 0.72rem;
  font-weight: 600;
  padding: 0.1rem 0.5rem;
  margin-left: 0.4rem;
  vertical-align: middle;
}

/* ── IP property type toggle pill row ── */
#propertyPurpose {
  font-weight: 600;
}

/* ── Out-of-pocket column ── */
.th-oop { background: rgba(0,0,0,0.04) !important; font-style: italic; }
.td-oop { color: #4a655a; font-size: 0.78rem; font-variant-numeric: tabular-nums; }
.td-oop .td-io {
  display: inline-block; font-size: 0.6rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.06em; background: #fef3c7; color: #92400e;
  border: 1px solid #fde68a; border-radius: 3px; padding: 0.05rem 0.3rem;
  margin-left: 0.25rem; vertical-align: middle;
}

/* ── IO phase row (A is in interest-only period) ── */
.ovs-table tbody .tr-io-phase {
  background: rgba(96, 165, 250, 0.04);
}

/* ── Sensitivity grid: actual-input markers ─────────────────────────────── */
.sens-corner { font-size: 0.72rem; }
.sens-corner-sub { font-size: 0.65rem; opacity: 0.7; }
.sens-col-actual { background: rgba(0,0,0,0.06) !important; font-weight: 700; }
.sens-row-actual th, .sens-row-actual-th { background: rgba(0,0,0,0.06) !important; font-weight: 700; }
.sens-cell-actual { outline: 2px solid #334155; outline-offset: -2px; }
.sens-actual-dot { font-size: 0.55rem; color: #334155; vertical-align: middle; margin-left: 2px; }

/* ══════════════════════════════════════════════════════════════════════════
   Plain-English winner summary
   ══════════════════════════════════════════════════════════════════════════ */
.ovs-plain-english {
  background: #f0f7f3;
  border-left: 4px solid #1a6b4a;
  border-radius: 0 8px 8px 0;
  padding: 1rem 1.25rem;
  margin: 0.5rem 0 1.25rem;
  font-size: 0.93rem;
  line-height: 1.7;
  color: #1c2b28;
}
.ovs-pe-label {
  display: block;
  font-size: 0.72rem;
  font-weight: 700;
  letter-spacing: 0.07em;
  text-transform: uppercase;
  color: #1a6b4a;
  margin-bottom: 0.45rem;
}
.ovs-plain-english p {
  margin: 0;
}
.ovs-plain-english strong {
  color: #12523a;
}

@media (prefers-color-scheme: dark) {
  .ovs-plain-english {
    background: rgba(26, 107, 74, 0.12);
    border-left-color: #2d9e6b;
    color: #d4e9de;
  }
  .ovs-pe-label { color: #2d9e6b; }
  .ovs-plain-english strong { color: #7dd3b0; }
}

/* ══════════════════════════════════════════════════════════════════════════
   Insight notices — tie-band, truncation, IO-zero warnings
   ══════════════════════════════════════════════════════════════════════════ */
.ovs-notice {
  border-radius: 8px;
  padding: 0.75rem 1rem;
  margin-bottom: 0.75rem;
  font-size: 0.88rem;
  line-height: 1.55;
}
.ovs-notice--warn {
  background: #fff8ed;
  border-left: 4px solid #d97706;
  color: #7c4a00;
}
.ovs-notice--info {
  background: #eff6ff;
  border-left: 4px solid #3b82f6;
  color: #1e3a5f;
}
.ovs-notice strong { font-weight: 700; }

/* Inline warn note in summary bar */
.ovs-warn-note {
  display: inline-block;
  background: #fff3cd;
  color: #7c4a00;
  border: 1px solid #fcd34d;
  border-radius: 4px;
  font-size: 0.72rem;
  font-weight: 600;
  padding: 0.1rem 0.5rem;
  margin-left: 0.4rem;
  vertical-align: middle;
}

@media (prefers-color-scheme: dark) {
  .ovs-notice--warn {
    background: rgba(217, 119, 6, 0.12);
    border-left-color: #f59e0b;
    color: #fcd34d;
  }
  .ovs-notice--info {
    background: rgba(59, 130, 246, 0.10);
    border-left-color: #60a5fa;
    color: #bfdbfe;
  }
  .ovs-warn-note {
    background: rgba(217,119,6,0.15);
    color: #fcd34d;
    border-color: #d97706;
  }
}

/* Partial final year row */
.tr-partial-year {
  background: rgba(26, 82, 54, 0.08) !important;
}
.tr-partial-year td {
  font-style: italic;
}
.td-partial-badge {
  display: inline-block;
  font-size: 0.6rem;
  font-weight: 700;
  background: #3db07e;
  color: #fff;
  padding: 1px 4px;
  border-radius: 3px;
  margin-left: 4px;
  vertical-align: middle;
}

/* Reference-only label for Scenario A */
.ovs-ref-only {
  font-size: 0.65rem;
  font-weight: 500;
  color: var(--text-muted);
  background: #f0f7f3;
  padding: 1px 6px;
  border-radius: 9999px;
  margin-left: 6px;
}



/* ── CGT regime disclosure (calculators/offset_vs_shares.html) ──────────────
   This calculator models the 1 July 2027 CGT reform (2026-09) — see the
   banner's own comment in the HTML for the history. Deliberately styled as
   a live notice in clay, above the results tabs, rather than a muted
   footnote: its default 25-year horizon always crosses the reform date, so
   the disclosure has to reach a reader who never opens the methodology
   accordion. */

/* ── "For money you have idle today" direct answer ───────────────────────
   The 4-card KPI grid above answers "which of these 4 strategies builds
   the most wealth" (winnable by a hybrid, A or D) — a related but
   different question from the one a first-time visitor with idle cash
   actually came here asking: offset, or shares, full stop. That's
   literally the B-vs-C comparison (the two pure endpoints). Styled as a
   confident positive-answer callout (green, matching the KPI winner
   value's own #15803d) rather than a caveat box like .ovs-cgt-notice
   above — this is the answer, not a warning. */
.ovs-idle-savings-answer {
  border: 1px solid #86efac;
  border-left: 4px solid #15803d;
  background: #f0fdf4;
  border-radius: 8px;
  padding: 14px 18px;
  margin: 0 0 16px;
}
.ovs-idle-savings-answer__label {
  font-size: 0.72rem;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.05em;
  color: #3d5248;
  margin-bottom: 6px;
}
.ovs-idle-savings-answer__verdict {
  font-size: 1.25rem;
  font-weight: 700;
  color: #15803d;
  margin-bottom: 3px;
}
.ovs-idle-savings-answer__verdict--tie { color: #b45309; }
.ovs-idle-savings-answer__sub {
  font-size: 0.83rem;
  color: #3d5248;
  line-height: 1.5;
}
.ovs-cgt-notice {
  border: 1px solid #C97A3A;
  border-left: 4px solid #C97A3A;
  background: #FBF6F0;
  border-radius: 8px;
  padding: 16px 18px;
  margin: 0 0 20px;
  font-size: 0.86rem;
  line-height: 1.6;
  color: #0E1512;
}
.ovs-cgt-notice p { margin: 0 0 9px; }
.ovs-cgt-notice p:last-child { margin-bottom: 0; }
/* Raw clay as text measured 3.08:1 on this banner's #fbf6f0. --gold-text is
   clay's existing darkened companion on PvS and the dark green elsewhere;
   here it resolves to #1a5236. Clay itself is untouched. */
.ovs-cgt-notice a { color: var(--gold-text); }
