/* ============================================================
   Urban Lynx — Shared Styles
   ============================================================ */

/* --- Variables --- */
:root {
    --brand-teal: #2BBCB3;
    --brand-teal-hover: #249E97;
    --brand-teal-light: #E8F8F7;
    --text-primary: #222222;
    --text-secondary: #666666;
    --text-muted: #999999;
    --bg-white: #FFFFFF;
    --bg-light: #F8F9FA;
    --bg-gray: #F0F0F0;
    --border-color: #E0E0E0;
    --border-light: #EEEEEE;
    --danger: #E74C3C;
    --warning: #F39C12;
    --success: #27AE60;

    --sidebar-width: 200px;
    --sidebar-collapsed: 60px;
    --header-height: 96px;
    --mode-bar-height: 56px;
    --font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, Cantarell, sans-serif;

    /* ---- Typography tokens (UX review #1) --------------------------
       Measured from the dominant existing families in this stylesheet.
       Apply to title / section-title / content / button / label.
       Agent F: reuse --color-content, --color-label, --color-readonly-bg
       when adding #35 color coding (red/amber/green profit margin). */
    --font-size-title: 1.5rem;          /* page-title, content-header h1 */
    --font-weight-title: 700;
    --font-size-title-lg: 1.6rem;       /* app-logo, login-card h1 */
    --font-size-section: 1.1rem;        /* form-section-title, collapsible-header, search-section h2 */
    --font-weight-section: 700;
    --font-size-subsection: 1rem;       /* card-title, collapsible inner */
    --font-weight-subsection: 600;
    --font-size-content: 0.9rem;        /* body / inputs / dashboard rows / scout results */
    --font-weight-content: 400;
    --font-size-button: 0.9rem;         /* .btn */
    --font-weight-button: 600;
    --font-size-label: 0.85rem;         /* form-label, widget-title, table th */
    --font-weight-label: 600;
    --font-size-meta: 0.8rem;           /* timestamps, footnotes, table column headers */
    --font-size-metric: 2rem;           /* widget-value, hero numbers */
    --font-weight-metric: 700;

    --color-label: #6b7280;             /* grey-500 — labels / captions */
    --color-content: #111111;           /* near-black — primary content */
    --color-readonly-bg: #f3f4f6;       /* grey-100 — read-only field bg */
    --color-readonly-text: #374151;     /* grey-700 — read-only text (slight dim) */
    --color-editable-bg: #ffffff;       /* white — editable field bg */

    /* ---- Spacing tokens (UX review #6) ---------------------------
       4 / 8 / 12 / 16 / 24 / 32 grid. Apply to form-row, form-group,
       action-bar, and any new layout containers. Agents L/M: reuse
       these tokens in pursuit polish work. */
    --space-1: 4px;
    --space-2: 8px;
    --space-3: 12px;
    --space-4: 16px;
    --space-5: 24px;
    --space-6: 32px;

    /* ---- Landing page tokens (Chunk 14 / G3, 2026-05-09) -----------
       Navy is the dark hero + bottom-CTA background; navy-text is the
       muted body color used on top of it. brand-blue is the accent
       blue used in the Lynx-Way comparison title and "VS" pill. */
    --brand-navy: #0F1B2D;
    --brand-navy-elevated: #1A2740;
    --brand-navy-text: #BCC6D6;
    --brand-blue: #2563EB;
    --brand-blue-hover: #1D4ED8;
    --brand-blue-light: #DBEAFE;
}

/* TODO (polish-pass) — ~45 other `font-size:` declarations still use
   hard-coded rem values (mode-btn, sidebar-nav, timeline, editable-table,
   scenario-bar, filters, cost-table, check-item, etc.). Wave 2 scope only
   binds the 5 dominant families (title / section / content / button /
   label) to tokens. Follow-on pass should sweep the rest onto tokens. */

/* ---- Read-only / editable field utilities (UX review #43) ----
   Use .is-readonly on any field whose value is system-derived or
   locked. Use .is-editable (or omit) for user-editable inputs. */
.is-readonly,
input.is-readonly,
select.is-readonly,
textarea.is-readonly {
    background: var(--color-readonly-bg) !important;
    color: var(--color-readonly-text) !important;
    cursor: default;
}
.is-readonly:focus {
    border-color: var(--border-color) !important;
    outline: none;
}
.is-editable,
input.is-editable,
select.is-editable,
textarea.is-editable {
    background: var(--color-editable-bg);
    color: var(--color-content);
}

/* ---- Profit Margin color-coding utilities (UX review #35) ----
   Red = below target, amber = near target (within 3pts), green = at/above.
   Works on any element — use on <input readonly> for Profit Margin display. */
.margin-below {
    color: var(--danger) !important;
    background: rgba(231, 76, 60, 0.08) !important;
    border-color: var(--danger) !important;
}
.margin-near {
    color: var(--warning) !important;
    background: rgba(243, 156, 18, 0.10) !important;
    border-color: var(--warning) !important;
}
.margin-above {
    color: var(--success) !important;
    background: rgba(39, 174, 96, 0.08) !important;
    border-color: var(--success) !important;
}
/* Apply read-only bg to native readonly/disabled inputs by default */
input[readonly]:not(.editable-teal):not(.is-editable),
select[disabled]:not(.is-editable),
textarea[readonly]:not(.is-editable) {
    background: var(--color-readonly-bg);
    color: var(--color-readonly-text);
    cursor: default;
}

/* --- Reset --- */
*, *::before, *::after {
    box-sizing: border-box;
    margin: 0;
    padding: 0;
}

body {
    font-family: var(--font-family);
    color: var(--text-primary);
    background: var(--bg-light);
    line-height: 1.5;
    overflow-x: hidden;
}

a {
    color: var(--brand-teal);
    text-decoration: none;
}
a:hover {
    color: var(--brand-teal-hover);
}

/* Wave2-A Sub-task 5 (2026-04-25): scoped black default for plain content
   anchors. Underline stripped sitewide per work item #21 (2026-04-27) —
   mouse-pointer cursor is the sole clickability cue. `.link-doc` is the
   one exception (work item #3) and is excluded from this rule.
   Audit pass executed against:
   - urban-lynx/static-content/app/{index,scout-results,deals,settings,
     account,support,resources,contact,pursuit-workspace}.html
   - urban-lynx/static-content/index.html (landing)
   - dynamic anchors created in js/app.js (.address-link, .widget,
     dashboard cards, scenario-count-badge) */
a:not(.btn):not(.btn-icon):not(.widget):not(.sidebar-link):not(.scenario-count-badge):not(.deal-status-select):not(.app-logo):not(.landing-logo):not(.landing-footer-link):not(.landing-workflow-link):not(.mode-btn):not(.hide-mobile):not(.back-link):not(.address-link):not(.pursuit-toc-link):not(.link-yellow):not(.smc-ref):not(.link-doc):not(.comp-header-addr):not(.active):not(.btn-primary):not(.btn-outline):not(.btn-sm),
a:visited:not(.btn):not(.btn-icon):not(.widget):not(.sidebar-link):not(.scenario-count-badge):not(.deal-status-select):not(.app-logo):not(.landing-logo):not(.landing-footer-link):not(.landing-workflow-link):not(.mode-btn):not(.hide-mobile):not(.back-link):not(.address-link):not(.pursuit-toc-link):not(.link-yellow):not(.smc-ref):not(.link-doc):not(.comp-header-addr):not(.active):not(.btn-primary):not(.btn-outline):not(.btn-sm) {
    color: #000;
    font-weight: 400;
    text-decoration: none;
}

/* ============================================================
   Landing Page
   ============================================================ */

/* ============================================================
   Landing Page — Chunk 14 / G3 redesign (2026-05-09)
   Mockup: UI/Urban Lynx_Landing Page.pdf
   Layout = 9 sections: nav / hero / trusted / workflow / 4 features
   / icon grid / comparison / CTA / footer. Navy hero+CTA, white in
   between, alternating gray on feature blocks.
   ============================================================ */

.landing-body {
    background: var(--bg-white);
    color: var(--text-primary);
    font-family: var(--font-family);
    margin: 0;
    line-height: 1.5;
}

/* --- 1. Top nav ----------------------------------------------- */
/* Header lives INSIDE the hero <section> — transparent bg so the
   navy continues from the very top edge through the hero, matching
   the PDF mockup. No separate white nav bar. */
.landing-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    max-width: 1200px;
    margin: 0 auto;
    padding: 24px 40px;
    background: transparent;
    position: relative;
    z-index: 2;
}

.landing-logo {
    display: flex;
    align-items: center;
    gap: 16px;
    text-decoration: none;
    color: var(--bg-white);
}

.landing-logo-icon {
    /* 2026-05-11 (round 1 hotfix) — doubled from 40px → 80px per partner.
       Wordmark text "Urban Lynx" sits to the right at the same visual
       height via .landing-logo-word. */
    height: 80px;
    width: auto;
    display: block;
}

.landing-logo-word {
    /* Sized to visually match the 80px logo height. line-height:1 removes
       extra space so the text block height ≈ logo height. */
    font-size: 3rem;
    font-weight: 700;
    line-height: 1;
    letter-spacing: -0.01em;
    color: var(--bg-white);
    white-space: nowrap;
}

.landing-nav {
    display: flex;
    align-items: center;
    gap: 32px;
}

.landing-nav-link {
    color: rgba(255, 255, 255, 0.7);
    font-size: 1rem;
    font-weight: 500;
    transition: color 0.15s;
    text-decoration: none;
}
.landing-nav-link:hover {
    color: var(--bg-white);
}

.landing-nav-login {
    color: rgba(255, 255, 255, 0.86);
    margin-left: 8px;
}

.landing-nav-cta {
    padding: 12px 24px;
    font-size: 1rem;
    border-radius: 6px;
}

/* Ghost variant for secondary landing CTAs (Log In, Join the Waitlist
   in nav + bottom CTA section). Transparent background with a subtle
   white border; keeps the font format from .btn. Overrides
   .landing-body .btn-primary specificity by re-scoping under
   .landing-body. */
.landing-body .btn-primary.landing-nav-cta-ghost,
.landing-body .btn-primary.landing-cta-ghost {
    background: transparent;
    border: 1px solid rgba(255, 255, 255, 0.45);
    color: var(--bg-white);
}
.landing-body .btn-primary.landing-nav-cta-ghost:hover,
.landing-body .btn-primary.landing-cta-ghost:hover {
    background: rgba(255, 255, 255, 0.08);
    border-color: rgba(255, 255, 255, 0.8);
}

/* Specificity fix — `.btn-primary` rule comes later in the stylesheet
   and would otherwise override the landing CTA color. Scoping under
   `.landing-body` lifts specificity to 0,2,0 > 0,1,0. */
.landing-body .btn-primary {
    background: var(--brand-blue);
    border-color: var(--brand-blue);
}
.landing-body .btn-primary:hover {
    background: var(--brand-blue-hover);
    border-color: var(--brand-blue-hover);
}

.landing-body .btn-secondary {
    display: inline-block;
    background: transparent;
    color: var(--bg-white);
    border: 1px solid rgba(255, 255, 255, 0.45);
    text-decoration: none;
    font-weight: 600;
    transition: background 0.15s, border-color 0.15s, color 0.15s;
}
.landing-body .btn-secondary:hover {
    background: rgba(255, 255, 255, 0.08);
    border-color: rgba(255, 255, 255, 0.8);
    color: var(--bg-white);
}
/* On the white-card bottom CTA section, the secondary button sits on
   navy. Same rule applies — outline-on-navy. */
.landing-cta-bottom .btn-secondary {
    background: transparent;
    color: var(--bg-white);
    border: 1px solid rgba(255, 255, 255, 0.55);
}
.landing-cta-bottom .btn-secondary:hover {
    background: rgba(255, 255, 255, 0.1);
    border-color: var(--bg-white);
}

.landing-hero-cta-group {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
    margin-bottom: 24px;
}
.landing-hero-cta-group .landing-hero-cta {
    margin-bottom: 0;
}

.landing-cta-buttons {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
}

/* --- 2. Hero -------------------------------------------------- */
.landing-hero {
    /* Solid navy + a very faint 32px grid (~4% white) to match the
       subtle texture on the PDF mockup. */
    background:
        linear-gradient(rgba(255, 255, 255, 0.04) 1px, transparent 1px) 0 0/32px 32px,
        linear-gradient(90deg, rgba(255, 255, 255, 0.04) 1px, transparent 1px) 0 0/32px 32px,
        var(--brand-navy);
    color: var(--bg-white);
    padding: 0 0 60px;
}

.landing-hero-inner {
    max-width: 1200px;
    margin: 0 auto;
    padding: 32px 40px 0;
    display: grid;
    /* 2 columns × 2 rows. text-top + visual share row 1 (visual cell
       stretches to text-top height so the image's viewport spans
       tag-top → hero-sub-bottom). text-bottom occupies row 2 column 1;
       column 2 of row 2 is empty (CTAs/checkmarks/coverage flow under
       the text, not under the screenshot). */
    grid-template-columns: 1fr 1.4fr;
    grid-template-areas:
        "text-top    visual"
        "text-bottom .";
    column-gap: 60px;
    row-gap: 24px;
    align-items: stretch;
}

.landing-hero-text-top    { grid-area: text-top; }
.landing-hero-text-bottom { grid-area: text-bottom; }

.landing-tag {
    display: inline-block;
    text-transform: uppercase;
    font-size: 0.85rem;
    font-weight: 700;
    letter-spacing: 1.5px;
    color: var(--brand-blue);
    background: var(--brand-blue-light);
    padding: 8px 18px;
    border-radius: 4px;
    margin-bottom: 24px;
}

.landing-tag-light {
    color: rgba(255, 255, 255, 0.86);
    background: var(--brand-navy-elevated);
}

.landing-h1 {
    /* Halved 2026-05-11 per partner request — was clamp(2rem, 4vw, 4.5rem).
       New ceiling 2.25rem (~36px) lets "From Site to Strategy." sit on a
       single line in the hero column. "In Minutes." breaks to the second
       line via <br> in markup. */
    font-size: clamp(1rem, 2vw, 2.25rem);
    font-weight: 700;
    line-height: 1.15;
    letter-spacing: -0.02em;
    margin: 0 0 20px;
    color: var(--bg-white);
}

.landing-h1-emphasis {
    color: rgba(255, 255, 255, 0.8);
}

.landing-hero-sub {
    font-size: 1.1rem;
    line-height: 1.55;
    color: rgba(255, 255, 255, 0.78);
    margin: 0 0 32px;
    max-width: 600px;
}

.landing-hero-cta {
    display: inline-block;
    padding: 12px 28px;
    font-size: 1rem;
    border-radius: 6px;
    margin-bottom: 24px;
}

.landing-checkmarks {
    list-style: none;
    padding: 0;
    margin: 0 0 16px;
    display: flex;
    flex-wrap: nowrap;
    gap: 24px;
    color: rgba(255, 255, 255, 0.85);
    font-size: 0.9rem;
}
.landing-checkmarks li {
    white-space: nowrap;
}

.landing-check {
    color: var(--brand-blue);
    font-weight: 700;
    margin-right: 8px;
}

.landing-hero-coverage {
    color: var(--bg-white);
    font-weight: 700;
    font-size: 0.95rem;
    margin: 0;
}

.landing-hero-visual {
    /* Right column on hero — viewport that spans only the top row
       (tag → hero-sub). Image anchored at top via absolute positioning;
       overflow clips any natural height beyond the row's text-top. */
    grid-area: visual;
    position: relative;
    overflow: hidden;
    align-self: stretch;
    min-width: 0;
    min-height: 0;
    border-radius: 10px;
}

.landing-screenshot-placeholder {
    background: var(--bg-gray);
    border: 1px solid var(--border-color);
    border-radius: 10px;
    min-height: 280px;
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--text-muted);
    font-size: 0.9rem;
    text-align: center;
    padding: 40px;
}

.landing-hero-placeholder {
    width: 100%;
    height: 100%;
    min-height: 280px;
    border-radius: 10px;
    border: 1px dashed rgba(255, 255, 255, 0.25);
    background: rgba(255, 255, 255, 0.04);
    display: flex;
    align-items: center;
    justify-content: center;
    color: rgba(255, 255, 255, 0.55);
    font-size: 0.95rem;
    letter-spacing: 0.02em;
    text-align: center;
    padding: 32px;
}

.landing-screenshot {
    display: block;
    /* Absolute-positioned inside the viewport cell. Width fills the
       cell, height is the image's natural aspect-driven height — any
       overflow past the cell's bottom is clipped by the cell's
       overflow: hidden. Anchored at top so the visible slice is the
       top of the screenshot. */
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: auto;
    border: 1px solid var(--border-color);
    border-radius: 10px;
    box-shadow: 0 6px 18px rgba(15, 30, 60, 0.08);
    cursor: zoom-in;
    transition: transform 0.15s ease, box-shadow 0.15s ease;
}
.landing-screenshot:hover {
    transform: translateY(-2px);
    box-shadow: 0 10px 24px rgba(15, 30, 60, 0.14);
}

/* Center-crop variant: anchor the image's vertical middle to the cell's
   middle so the visible slice is the center of the screenshot (top and
   bottom equally clipped). Override the base hover transform too so the
   centering survives :hover. */
.landing-screenshot.landing-screenshot-center {
    top: 50%;
    transform: translateY(-50%);
}
.landing-screenshot.landing-screenshot-center:hover {
    transform: translateY(calc(-50% - 2px));
}

/* Hero image — banner aspect on dark background. Border tweak for
   contrast against navy. Hero uses object-fit: cover so the image
   fills the full row 1 height (top of tag → bottom of hero-sub);
   width may be cropped at the sides to preserve aspect. */
.landing-hero-screenshot {
    height: 100%;
    object-fit: cover;
    object-position: center;
    border: 1px solid rgba(255, 255, 255, 0.12);
}

/* --- Lightbox (click-to-enlarge for landing screenshots) ----- */
.landing-lightbox {
    position: fixed;
    inset: 0;
    background: rgba(8, 16, 32, 0.88);
    display: none;
    align-items: center;
    justify-content: center;
    z-index: 1000;
    padding: 24px;
    cursor: zoom-out;
}
.landing-lightbox.is-open {
    display: flex;
}
.landing-lightbox-img {
    max-width: 95vw;
    max-height: 92vh;
    width: auto;
    height: auto;
    border-radius: 8px;
    box-shadow: 0 12px 48px rgba(0, 0, 0, 0.55);
    cursor: default;
}
.landing-lightbox-close {
    position: absolute;
    top: 16px;
    right: 24px;
    background: none;
    border: none;
    color: #fff;
    font-size: 32px;
    line-height: 1;
    cursor: pointer;
    padding: 4px 12px;
    opacity: 0.85;
}
.landing-lightbox-close:hover {
    opacity: 1;
}

/* Hero screenshot frame is cream-tinted to match PDF; height auto
   from aspect-ratio so it pairs with the (now smaller) H1 column. */
.landing-hero .landing-screenshot-placeholder {
    aspect-ratio: 1.85 / 1;
    min-height: 360px;
    background: linear-gradient(135deg, #ecece8 0%, #e5e5e2 100%);
    border: 1px solid rgba(255, 255, 255, 0.12);
    color: rgba(40, 50, 70, 0.5);
    font-size: 0.95rem;
}

/* --- 3. Trusted strip ---------------------------------------- */
.landing-trusted-strip {
    text-align: center;
    height: 60px;
    display: flex;
    align-items: center;
    justify-content: center;
    background: var(--bg-white);
    border-top: 1px solid var(--border-light);
    border-bottom: 1px solid var(--border-light);
    color: var(--text-muted);
    font-size: 0.85rem;
    font-weight: 600;
    letter-spacing: 1.5px;
    text-transform: uppercase;
}

/* --- 4. A Smarter Workflow — 4-step ribbon ------------------- */
.landing-workflow {
    max-width: 1200px;
    margin: 0 auto;
    padding: 80px 40px 60px;
    text-align: center;
}

.landing-workflow-steps {
    list-style: none;
    padding: 0;
    margin: 32px 0 0;
    display: grid;
    grid-template-columns: repeat(4, 1fr);
    gap: 32px;
    position: relative;
}

.landing-workflow-steps::before {
    content: "";
    position: absolute;
    top: 22px;
    left: 12.5%;
    right: 12.5%;
    height: 2px;
    background: var(--border-color);
    z-index: 0;
}

.landing-workflow-step {
    text-align: center;
    position: relative;
    z-index: 1;
}

.landing-workflow-num {
    display: inline-flex;
    width: 44px;
    height: 44px;
    align-items: center;
    justify-content: center;
    background: var(--bg-white);
    border: 2px solid var(--border-color);
    border-radius: 50%;
    font-size: 1.1rem;
    font-weight: 700;
    color: var(--text-secondary);
    margin-bottom: 16px;
}

.landing-workflow-num-active,
.landing-workflow-link:hover .landing-workflow-num,
.landing-workflow-link:focus-visible .landing-workflow-num {
    background: var(--brand-blue);
    border-color: var(--brand-blue);
    color: var(--bg-white);
}

/* Workflow steps become clickable shortcuts to their matching feature
   block. Each <a class="landing-workflow-link"> wraps the number + title
   + description; hovering anywhere on the link turns the circle blue and
   smooth-scrolls to the matching #landing-feature-* section. */
.landing-workflow-link {
    display: block;
    text-decoration: none;
    color: inherit;
    cursor: pointer;
    transition: transform 0.15s ease;
}
.landing-workflow-link:hover {
    transform: translateY(-2px);
}
.landing-workflow-link .landing-workflow-num {
    transition: background 0.15s ease, border-color 0.15s ease, color 0.15s ease;
}
/* Feature sections get a small scroll-margin so the scroll-into-view
   target doesn't land flush against the viewport top edge. */
.landing-feature-block {
    scroll-margin-top: 24px;
}

.landing-workflow-title {
    font-size: 1rem;
    font-weight: 700;
    margin: 0 0 8px;
    color: var(--text-primary);
}

.landing-workflow-desc {
    font-size: 0.85rem;
    color: var(--text-secondary);
    margin: 0;
    line-height: 1.5;
}

/* --- 5. Feature blocks (×4, alternating) -------------------- */
.landing-feature-block {
    padding: 60px 40px;
    background: var(--bg-white);
}

.landing-feature-block-alt {
    /* Same look — alternation can be enabled later if partner wants
       a stripe; for now keep both white per mockup. */
}

.landing-feature-block .landing-feature-text,
.landing-feature-block .landing-feature-visual {
    box-sizing: border-box;
}

.landing-feature-block {
    max-width: 1200px;
    margin: 0 auto;
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 60px;
    align-items: stretch;
}

.landing-feature-block .landing-feature-text {
    display: flex;
    flex-direction: column;
    justify-content: center;
}

.landing-feature-block .landing-feature-visual {
    /* Viewport — height matches the text column (via grid stretch +
       absolute-positioned image so the image doesn't push the row taller).
       Tall screenshots get clipped at the bottom; short ones leave empty
       space below. Original image is still reachable via lightbox. */
    position: relative;
    overflow: hidden;
    align-self: stretch;
    min-width: 0;
    min-height: 0;
    border-radius: 10px;
}

.landing-feature-title {
    font-size: 1.6rem;
    font-weight: 700;
    margin: 0 0 16px;
    color: var(--text-primary);
}

.landing-feature-desc {
    font-size: 0.95rem;
    color: var(--text-secondary);
    margin: 0;
    line-height: 1.6;
    max-width: 480px;
}

/* --- 6. Icon grid — 5-column features ------------------------ */
.landing-icon-grid-section {
    background: var(--bg-light);
    padding: 60px 40px;
    text-align: center;
}

.landing-section-title {
    font-size: 1.6rem;
    font-weight: 700;
    margin: 0 0 36px;
    color: var(--text-primary);
}

.landing-icon-grid {
    list-style: none;
    padding: 0;
    margin: 0 auto;
    max-width: 1200px;
    display: grid;
    grid-template-columns: repeat(5, 1fr);
    gap: 16px;
}

.landing-icon-item {
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
    padding: 24px 16px;
    text-align: center;
}

.landing-icon {
    /* Container for the inline-SVG feature icons. Background tint + radius
       matches the PDF rounded-square chip style. SVG sits centered inside. */
    width: 44px;
    height: 44px;
    background: var(--brand-blue-light);
    border-radius: 8px;
    margin: 0 auto 12px;
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--brand-blue);
}
.landing-icon svg {
    width: 22px;
    height: 22px;
    stroke: currentColor;
}

.landing-icon-title {
    font-size: 0.95rem;
    font-weight: 700;
    margin: 0 0 8px;
    color: var(--text-primary);
}

.landing-icon-desc {
    font-size: 0.8rem;
    color: var(--text-secondary);
    margin: 0;
    line-height: 1.5;
}

/* --- 7. Comparison — Old Way vs Lynx Way -------------------- */
.landing-comparison-section {
    max-width: 1100px;
    margin: 0 auto;
    padding: 80px 40px;
    text-align: center;
}

.landing-comparison-title {
    font-size: 1.8rem;
    font-weight: 700;
    margin: 0 0 16px;
    color: var(--text-primary);
    line-height: 1.3;
}

.landing-comparison-emphasis {
    color: var(--brand-blue);
}

.landing-comparison-sub {
    font-size: 0.95rem;
    color: var(--text-secondary);
    max-width: 640px;
    margin: 0 auto 40px;
}

.landing-comparison-grid {
    display: grid;
    grid-template-columns: 1fr auto 1fr;
    gap: 40px;
    align-items: stretch;
    text-align: left;
}

.landing-comparison-col {
    padding: 24px 0;
}

.landing-comparison-old {
    text-align: right;
}

.landing-comparison-col-title {
    font-size: 1.05rem;
    font-weight: 700;
    margin: 0 0 24px;
}

.landing-comparison-old .landing-comparison-col-title {
    color: var(--text-primary);
}

.landing-comparison-new .landing-comparison-col-title {
    color: var(--brand-blue);
}

.landing-comparison-list {
    margin: 0;
    padding: 0;
}

.landing-comparison-list dt {
    font-size: 0.78rem;
    font-weight: 600;
    color: var(--text-muted);
    text-transform: uppercase;
    letter-spacing: 0.5px;
    margin-top: 16px;
}

.landing-comparison-list dt:first-of-type {
    margin-top: 0;
}

.landing-comparison-list dd {
    font-size: 0.95rem;
    color: var(--text-primary);
    margin: 4px 0 0;
    line-height: 1.4;
}

.landing-comparison-vs {
    align-self: center;
    width: 56px;
    height: 56px;
    background: var(--brand-blue);
    color: var(--bg-white);
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 0.95rem;
    font-weight: 700;
    letter-spacing: 1px;
}

/* --- 8. Bottom CTA — waitlist form -------------------------- */
.landing-cta-bottom {
    background: var(--brand-navy);
    color: var(--bg-white);
    padding: 60px 40px;
}

.landing-cta-inner {
    max-width: 1100px;
    margin: 0 auto;
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 48px;
    align-items: center;
}

.landing-cta-title {
    font-size: 1.6rem;
    font-weight: 700;
    margin: 0 0 12px;
    color: var(--bg-white);
}

.landing-cta-sub {
    font-size: 0.95rem;
    color: var(--brand-navy-text);
    margin: 0;
}

.landing-cta-form {
    display: flex;
    gap: 12px;
    margin-bottom: 12px;
}

.landing-cta-input {
    flex: 1;
    padding: 12px 16px;
    border: 1px solid var(--brand-navy-elevated);
    border-radius: 6px;
    background: var(--bg-white);
    color: var(--text-primary);
    font-size: 0.95rem;
    font-family: inherit;
}

.landing-cta-input:focus {
    outline: 2px solid var(--brand-teal);
    outline-offset: 2px;
}

.landing-cta-submit {
    padding: 12px 24px;
    font-size: 0.95rem;
    white-space: nowrap;
    background: var(--brand-blue);
    border-color: var(--brand-blue);
}
.landing-cta-submit:hover {
    background: var(--brand-blue-hover);
    border-color: var(--brand-blue-hover);
}

/* --- "Get Early Access" CTA — primary call-to-action across the
   landing page. Persistent soft glow + a periodic diagonal sheen
   sweep to draw the eye. ----------------------------------------- */
.landing-cta-shine {
    position: relative;
    overflow: hidden;
    isolation: isolate;
    box-shadow:
        0 0 0 1px rgba(255, 255, 255, 0.18) inset,
        0 4px 14px rgba(74, 108, 247, 0.55),
        0 0 28px rgba(74, 108, 247, 0.40);
    transition: box-shadow 0.2s ease, transform 0.2s ease;
}
.landing-cta-shine:hover {
    transform: translateY(-1px);
    box-shadow:
        0 0 0 1px rgba(255, 255, 255, 0.24) inset,
        0 6px 20px rgba(74, 108, 247, 0.70),
        0 0 36px rgba(74, 108, 247, 0.55);
}
.landing-cta-shine::after {
    content: "";
    position: absolute;
    top: 0;
    left: -150%;
    width: 60%;
    height: 100%;
    background: linear-gradient(
        110deg,
        rgba(255, 255, 255, 0) 0%,
        rgba(255, 255, 255, 0.45) 50%,
        rgba(255, 255, 255, 0) 100%
    );
    transform: skewX(-20deg);
    animation: landing-cta-shine-sweep 3.2s ease-in-out infinite;
    pointer-events: none;
    z-index: 1;
}
.landing-cta-shine > * {
    position: relative;
    z-index: 2;
}
@keyframes landing-cta-shine-sweep {
    0%   { left: -150%; }
    60%  { left: 150%; }
    100% { left: 150%; }
}
@media (prefers-reduced-motion: reduce) {
    .landing-cta-shine::after {
        animation: none;
    }
}

.landing-cta-footnote {
    font-size: 0.8rem;
    color: var(--brand-navy-text);
    margin: 0;
}

.landing-form-success {
    font-size: 1rem;
    color: var(--brand-teal);
    margin: 0;
    padding: 12px 16px;
    background: var(--brand-navy-elevated);
    border-radius: 6px;
}

.landing-form-error {
    color: var(--danger);
}

/* --- 9. Footer ----------------------------------------------- */
.landing-footer {
    background: var(--brand-navy);
    color: var(--brand-navy-text);
    padding: 32px 40px;
    border-top: 1px solid var(--brand-navy-elevated);
}

.landing-footer-inner {
    max-width: 1200px;
    margin: 0 auto;
    display: flex;
    align-items: center;
    justify-content: space-between;
    flex-wrap: nowrap;
    gap: 16px;
    font-size: 0.85rem;
}

.landing-footer-brand {
    color: var(--bg-white);
    font-weight: 600;
    white-space: nowrap;
}

.landing-footer-copy {
    color: var(--bg-white);
    white-space: nowrap;
}

.landing-footer-nav {
    display: flex;
    flex-wrap: nowrap;
    gap: 24px;
    white-space: nowrap;
}

.landing-footer-nav a {
    color: var(--bg-white);
    text-decoration: none;
    transition: opacity 0.15s;
}

.landing-footer-nav a:hover {
    opacity: 0.75;
}

/* --- Toast (coming-soon notice) ----------------------------- */
.landing-toast {
    position: fixed;
    bottom: 32px;
    left: 50%;
    transform: translate(-50%, 24px);
    background: var(--brand-navy);
    color: var(--bg-white);
    padding: 12px 20px;
    border-radius: 6px;
    font-size: 0.9rem;
    font-weight: 500;
    box-shadow: 0 4px 24px rgba(0, 0, 0, 0.2);
    opacity: 0;
    transition: opacity 0.3s, transform 0.3s;
    z-index: 1000;
    pointer-events: none;
}

.landing-toast-visible {
    opacity: 1;
    transform: translate(-50%, 0);
}

/* --- Mobile (≤768px) — stack everything --------------------- */
@media (max-width: 768px) {
    .landing-header {
        padding: 16px 20px;
    }
    .landing-logo-icon {
        width: 40px;
        height: 40px;
    }
    .landing-logo-word {
        font-size: 1.4rem;
    }
    .landing-nav {
        gap: 14px;
    }
    .landing-nav-link {
        font-size: 0.9rem;
    }
    .landing-nav-cta {
        padding: 10px 18px;
        font-size: 0.95rem;
    }
    .landing-hero {
        padding: 0 0 48px;
    }
    .landing-hero-inner {
        padding: 24px 20px 0;
        grid-template-columns: 1fr;
        grid-template-areas: none;
        gap: 32px;
    }
    .landing-hero-text-top,
    .landing-hero-text-bottom,
    .landing-hero-visual {
        grid-area: auto;
        grid-column: 1;
    }
    .landing-hero-visual {
        padding-top: 0;
    }
    .landing-hero .landing-screenshot-placeholder {
        min-height: 240px;
    }
    .landing-trusted-strip {
        height: auto;
        padding: 16px 20px;
        font-size: 0.78rem;
    }
    .landing-workflow-steps {
        grid-template-columns: 1fr 1fr;
        row-gap: 32px;
    }
    .landing-workflow-steps::before {
        display: none;
    }
    .landing-feature-block {
        grid-template-columns: 1fr;
        gap: 32px;
        padding: 40px 20px;
    }
    .landing-icon-grid {
        grid-template-columns: 1fr 1fr;
    }
    .landing-comparison-section {
        padding: 48px 20px;
    }
    .landing-comparison-grid {
        grid-template-columns: 1fr;
        gap: 24px;
    }
    .landing-comparison-old {
        text-align: left;
    }
    .landing-comparison-vs {
        margin: 8px auto;
    }
    .landing-cta-inner {
        grid-template-columns: 1fr;
        gap: 24px;
    }
    .landing-cta-form {
        flex-direction: column;
        gap: 8px;
    }
    .landing-footer-inner {
        flex-direction: column;
        align-items: flex-start;
    }
}

/* ============================================================
   App Shell — Header
   ============================================================ */

.app-header {
    position: fixed;
    top: 0;
    left: 0;
    right: 0;
    min-height: var(--header-height);
    background: var(--bg-white);
    border-bottom: 1px solid var(--border-color);
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 8px 24px;
    z-index: 200;
}

.app-header-left {
    display: flex;
    align-items: center;
    gap: 16px;
}

.app-logo {
    display: flex;
    align-items: center;
    gap: 8px;
    text-decoration: none;
    color: var(--text-primary);
    padding-right: 16px;
    border-right: 1px solid var(--border-color);
}

.app-logo img {
    /* 2026-05-11 — partner-supplied PNG (logo-teal.png) already includes
       the "Urban Lynx" wordmark beside the icon, so the old 80×80 square
       sizing crushed the asset. Height-only scaling preserves aspect ratio. */
    height: 56px;
    width: auto;
    max-width: 200px;
    display: block;
}

.app-logo svg {
    width: 80px;
    height: 80px;
}

.app-logo span {
    /* Brand wordmark to the right of the icon — bold black, sized to
       visually match the 56px logo height (line-height:1 collapses
       the bounding box to ~font-size). Logo image stays teal. */
    font-size: 2.1rem;
    font-weight: 700;
    line-height: 1;
    letter-spacing: -0.01em;
    color: var(--text-primary);
    white-space: nowrap;
}

.app-company {
    font-size: 1.6rem;
    font-weight: 700;
    letter-spacing: 0.5px;
    text-transform: uppercase;
    color: var(--text-primary);
}

.app-header-right {
    display: flex;
    align-items: center;
    gap: 24px;
}

.app-header-right a {
    color: var(--text-secondary);
    font-size: 0.9rem;
    font-weight: 500;
}
.app-header-right a:hover {
    color: var(--text-primary);
}

/* ============================================================
   App Shell — Sidebar
   ============================================================ */

/* Agent H (Wave 4) — sidebar collapse bundle (findings #12-#15).
   Default: collapsed icon-only rail (--sidebar-collapsed = 60px).
   Expands on hover, or permanently when `.is-expanded` is set via JS
   (persisted in localStorage.sidebarExpanded). Hollow-circle active
   dot replaced with left-border + teal tint. Divider removed. */
.app-sidebar {
    position: fixed;
    top: var(--header-height);
    left: 0;
    bottom: 0;
    width: var(--sidebar-collapsed);
    background: var(--bg-white);
    border-right: 1px solid var(--border-color);
    padding: 16px 0;
    z-index: 150;
    transition: width 180ms ease, transform 0.25s ease;
    overflow-x: hidden;
    overflow-y: auto;
}

.app-sidebar:hover,
.app-sidebar.is-expanded {
    width: var(--sidebar-width);
    box-shadow: 2px 0 8px rgba(0, 0, 0, 0.04);
}

.sidebar-toggle {
    display: none;
    background: none;
    border: none;
    font-size: 1.5rem;
    cursor: pointer;
    padding: 8px 16px;
    color: var(--text-primary);
}

.sidebar-nav {
    list-style: none;
    display: flex;
    flex-direction: column;
    height: 100%;
    padding: 0;
    margin: 0;
}

.sidebar-nav li {
    margin-bottom: 2px;
}

.sidebar-nav li.nav-settings {
    margin-top: auto;
}

.sidebar-nav a {
    display: flex;
    align-items: center;
    gap: 14px;
    padding: 11px 18px;
    color: var(--text-secondary);
    font-size: var(--font-size-content, 0.9rem);
    font-weight: 500;
    transition: background 0.15s, color 0.15s, border-left-color 0.15s;
    border-left: 3px solid transparent;
    white-space: nowrap;
    text-decoration: none;
}

.sidebar-nav a:hover {
    background: var(--bg-light);
    color: var(--text-primary);
}

.sidebar-nav a.active {
    background: rgba(43, 188, 179, 0.08);
    color: var(--brand-teal);
    border-left-color: var(--brand-teal);
    font-weight: var(--font-weight-section, 700);
}

.sidebar-icon {
    width: 20px;
    height: 20px;
    flex-shrink: 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    color: currentColor;
}

.sidebar-icon svg {
    width: 18px;
    height: 18px;
    display: block;
    stroke: currentColor;
    fill: none;
}

.sidebar-nav .nav-label {
    opacity: 0;
    transition: opacity 120ms ease;
    pointer-events: none;
}

.app-sidebar:hover .nav-label,
.app-sidebar.is-expanded .nav-label {
    opacity: 1;
    pointer-events: auto;
}

/* ============================================================
   App Shell — Main Content
   ============================================================ */

.app-main {
    /* Agent H (#12): main content reserves space for the collapsed
       rail only. Hover-expanding the sidebar overlays content instead
       of reflowing it — avoids layout jitter. When pinned via
       `.is-expanded`, `.app-shell-expanded` on <body> reflows content. */
    margin-left: var(--sidebar-collapsed);
    margin-top: var(--header-height);
    transition: margin-left 180ms ease;
    /* No min-height: sidebar is position:fixed bottom:0 so it already
       fills the viewport. A min-height here only creates blank filler
       below short pages like Global Settings (UX review #29). */
    padding-bottom: 48px;
}

body.app-shell-expanded .app-main {
    margin-left: var(--sidebar-width);
}

/* ============================================================
   Mode Bar
   ============================================================ */

.mode-bar {
    display: flex;
    align-items: stretch;
    gap: 16px;
    padding: 16px 32px;
    background: var(--bg-white);
    border-bottom: 1px solid var(--border-color);
}

.mode-item {
    display: flex;
    flex-direction: column;
    align-items: center;
    text-align: center;
    flex: 1;
    max-width: 280px;
}

.mode-btn {
    padding: 10px 32px;
    border: 2px solid var(--border-color);
    border-radius: 24px;
    background: var(--bg-white);
    color: var(--text-secondary);
    font-size: 0.95rem;
    font-weight: 600;
    cursor: pointer;
    transition: all 0.15s;
    text-decoration: none;
    display: inline-block;
    width: 100%;
}

.mode-btn:hover {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
}

.mode-btn.active {
    background: var(--brand-teal);
    border-color: var(--brand-teal);
    color: white;
}

.mode-desc {
    font-size: 0.78rem;
    color: var(--text-muted);
    margin-top: 6px;
    line-height: 1.3;
}

/* ============================================================
   Content Area
   ============================================================ */

.content {
    padding: 32px;
}

.content-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    margin-bottom: 24px;
}

.content-header h1 {
    font-size: var(--font-size-title);
    font-weight: var(--font-weight-title);
}

.page-title {
    font-size: var(--font-size-title);
    font-weight: var(--font-weight-title);
    margin-bottom: 24px;
}

/* ============================================================
   Buttons
   ============================================================ */

.btn {
    display: inline-flex;
    align-items: center;
    gap: 8px;
    padding: 10px 24px;
    border: none;
    border-radius: 6px;
    font-size: var(--font-size-button);
    font-weight: var(--font-weight-button);
    cursor: pointer;
    transition: all 0.15s;
    text-decoration: none;
}

.btn-primary {
    background: var(--brand-teal);
    color: white;
}
.btn-primary:hover {
    background: var(--brand-teal-hover);
    color: white;
}

.btn-outline {
    background: var(--bg-white);
    color: var(--text-secondary);
    border: 1px solid var(--border-color);
}
.btn-outline:hover {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
}

.btn-sm {
    padding: 6px 16px;
    font-size: 0.85rem;
}

.btn-icon {
    width: 40px;
    height: 40px;
    padding: 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 6px;
    background: var(--brand-teal);
    color: white;
    border: none;
    cursor: pointer;
    font-size: 1.1rem;
}

/* ============================================================
   Cards
   ============================================================ */

.card {
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
    padding: 24px;
}

.card-title {
    font-size: var(--font-size-subsection);
    font-weight: var(--font-weight-subsection);
    margin-bottom: 16px;
    color: var(--text-primary);
}

/* ============================================================
   Search Bar
   ============================================================ */

.search-section {
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
    padding: 24px;
    margin-bottom: 24px;
}

.search-section h2 {
    font-size: var(--font-size-section);
    font-weight: var(--font-weight-section);
    margin-bottom: 16px;
}

.search-bar {
    display: flex;
    gap: 8px;
    align-items: center;
}

.search-input {
    flex: 1;
    padding: 10px 16px;
    border: 1px solid var(--border-color);
    border-radius: 6px;
    font-size: 0.95rem;
    font-family: var(--font-family);
    outline: none;
    transition: border-color 0.15s;
}

.search-input:focus {
    border-color: var(--brand-teal);
}

.scout-status {
    margin-top: 8px;
    padding: 8px 12px;
    border-radius: 6px;
    font-size: 0.85rem;
}
.scout-status.info {
    background: #EBF5FB;
    color: #1A5276;
}
.scout-status.error {
    background: #FDEDEC;
    color: #922B21;
}

/* Autocomplete dropdown */
.scout-autocomplete {
    position: absolute;
    top: 100%;
    left: 0;
    right: 0;
    background: #fff;
    border: 1px solid var(--border-color);
    border-top: none;
    border-radius: 0 0 6px 6px;
    box-shadow: 0 4px 12px rgba(0,0,0,0.1);
    z-index: 100;
    max-height: 200px;
    overflow-y: auto;
}
.scout-ac-item {
    padding: 10px 16px;
    cursor: pointer;
    font-size: 0.9rem;
    border-bottom: 1px solid #f0f0f0;
}
.scout-ac-item:hover {
    background: #f0faf9;
}
.scout-ac-item:last-child {
    border-bottom: none;
}

/* CSV preview */
.scout-csv-preview {
    margin-top: 12px;
    padding: 12px 16px;
    background: #F8F9FA;
    border: 1px solid var(--border-color);
    border-radius: 6px;
}
.scout-csv-list {
    max-height: 200px;
    overflow-y: auto;
}
.scout-csv-item {
    display: flex;
    justify-content: space-between;
    align-items: center;
    padding: 4px 8px;
    font-size: 0.85rem;
    border-bottom: 1px solid #eee;
}
.scout-csv-item:last-child {
    border-bottom: none;
}
.scout-csv-remove {
    background: none;
    border: none;
    color: #999;
    cursor: pointer;
    font-size: 1.1rem;
    padding: 0 4px;
}
.scout-csv-remove:hover {
    color: #c0392b;
}

/* Fuzzy match confirmation */
.scout-confirm {
    margin-top: 12px;
    padding: 12px 16px;
    background: #FEF9E7;
    border: 1px solid #F9E79F;
    border-radius: 6px;
    font-size: 0.9rem;
}
.scout-confirm-row {
    padding: 6px 0;
    border-bottom: 1px solid #F9E79F;
}
.scout-confirm-row:last-child {
    border-bottom: none;
}
.scout-confirm-row label {
    display: flex;
    align-items: center;
    gap: 8px;
    cursor: pointer;
}
.scout-confirm-query {
    color: #666;
}
.scout-confirm-nomatch {
    color: #c0392b;
    font-size: 0.8rem;
    font-style: italic;
}

.search-input::placeholder {
    color: var(--text-muted);
}

/* ============================================================
   Data Tables
   ============================================================ */

.table-container {
    overflow-x: auto;
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
}

.data-table {
    width: 100%;
    border-collapse: collapse;
    /* UX #25 — Scout Results table + Dashboard cards share content size */
    font-size: var(--font-size-content);
    white-space: nowrap;
}

.data-table thead {
    background: var(--bg-light);
    position: sticky;
    top: 0;
}

.data-table th {
    padding: 12px 16px;
    text-align: left;
    font-weight: var(--font-weight-label);
    color: var(--text-secondary);
    border-bottom: 2px solid var(--border-color);
    font-size: var(--font-size-meta);
    text-transform: uppercase;
    letter-spacing: 0.3px;
}

.data-table td {
    padding: 12px 16px;
    border-bottom: 1px solid var(--border-light);
    color: var(--text-primary);
}

.data-table tbody tr:hover {
    background: var(--brand-teal-light);
}

.data-table .address-link {
    color: var(--brand-teal);
    font-weight: 500;
    cursor: pointer;
}
.data-table .address-link:hover {
    text-decoration: none;
}

.rec-badge {
    display: inline-block;
    padding: 3px 10px;
    border-radius: 12px;
    font-size: 0.75rem;
    font-weight: 600;
    text-transform: uppercase;
}
.rec-high { background: #D5F5E3; color: #1E8449; }
.rec-medium { background: #FEF9E7; color: #B7950B; }
.rec-low { background: #FADBD8; color: #C0392B; }
.rec-na { background: #EAECEE; color: #717D7E; }

/* ============================================================
   Forms
   ============================================================ */

.form-group {
    margin-bottom: var(--space-5); /* 24px — snaps to spacing grid (#6) */
}

.form-label {
    display: block;
    font-size: var(--font-size-label);
    font-weight: var(--font-weight-label);
    color: var(--text-secondary);
    margin-bottom: 6px;
}

.form-input, .form-select {
    width: 100%;
    padding: 10px 12px;
    border: 1px solid var(--border-color);
    border-radius: 6px;
    font-size: var(--font-size-content);
    font-family: var(--font-family);
    outline: none;
    transition: border-color 0.15s;
}

.form-input:focus, .form-select:focus {
    border-color: var(--brand-teal);
}

.form-row {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
    gap: var(--space-4); /* 16px — spacing token (#6) */
    margin-bottom: var(--space-4); /* 16px — consistent vertical rhythm */
}

/* Property Info (Section 2) stacks every field in a single column per
   user request 2026-04-20 — multiple fields per row was visually noisy. */
#section-2 .form-row {
    grid-template-columns: 1fr;
    gap: var(--space-3);
}

.form-section {
    margin-bottom: var(--space-6); /* 32px — spacing token (#6) */
}

.form-section-title {
    font-size: var(--font-size-section);
    font-weight: var(--font-weight-section);
    padding-bottom: var(--space-2); /* 8px */
    border-bottom: 2px solid var(--brand-teal);
    margin-bottom: var(--space-4); /* 16px — snaps to spacing grid (#6) */
}

.toggle-container {
    display: flex;
    align-items: center;
    gap: 12px;
    margin-bottom: 16px;
}

.toggle {
    position: relative;
    width: 48px;
    height: 24px;
    background: var(--border-color);
    border-radius: 12px;
    cursor: pointer;
    transition: background 0.2s;
}

.toggle.active {
    background: var(--brand-teal);
}

.toggle::after {
    content: '';
    position: absolute;
    top: 2px;
    left: 2px;
    width: 20px;
    height: 20px;
    background: white;
    border-radius: 50%;
    transition: transform 0.2s;
}

.toggle.active::after {
    transform: translateX(24px);
}

/* ============================================================
   Collapsible Sections (Pursuit Workspace)
   ============================================================ */

.collapsible {
    /* UX review #4 — decorative hairline removed. Section header +
       spacing are sufficient to separate collapsible sections. */
}

.collapsible-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 16px 0;
    cursor: pointer;
    font-size: var(--font-size-subsection);
    font-weight: var(--font-weight-subsection);
    color: var(--text-primary);
    border-bottom: 2px solid var(--brand-teal);
}

.collapsible-header::after {
    content: '\25BC';
    font-size: 0.7rem;
    color: var(--text-muted);
    transition: transform 0.2s;
}

.collapsible-header.collapsed::after {
    transform: rotate(-90deg);
}

.collapsible-body {
    padding: 16px 0;
}

.collapsible-body.hidden {
    display: none;
}

/* ============================================================
   Dashboard Widgets
   ============================================================ */

.widget-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
    gap: 20px;
    margin-bottom: 32px;
}

.widget {
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
    padding: 20px;
}

.widget-title {
    font-size: var(--font-size-label);
    font-weight: var(--font-weight-label);
    color: var(--text-secondary);
    text-transform: uppercase;
    letter-spacing: 0.3px;
    margin-bottom: 12px;
}

.widget-value {
    font-size: var(--font-size-metric);
    font-weight: var(--font-weight-metric);
    color: var(--text-primary);
}

.widget-list {
    list-style: none;
}

.widget-list li {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 10px 0;
    border-bottom: 1px solid var(--border-light);
    /* UX #25 — match Scout Results data-table content size */
    font-size: var(--font-size-content);
    /* UX #26 — signal clickability on dashboard cards */
    cursor: pointer;
    transition: background 0.15s ease, padding 0.15s ease;
    position: relative;
    padding-right: 20px;
}

.widget-list li:hover {
    background: var(--color-readonly-bg);
    padding-left: 8px;
    padding-right: 28px;
}

.widget-list li::after {
    content: '\203A'; /* › single right-pointing angle */
    position: absolute;
    right: 6px;
    top: 50%;
    transform: translateY(-50%);
    color: var(--color-label);
    font-size: 1.1rem;
    line-height: 1;
    opacity: 0;
    transition: opacity 0.15s ease, right 0.15s ease;
    pointer-events: none;
}

.widget-list li:hover::after {
    opacity: 1;
    right: 10px;
}

.widget-list li:last-child {
    border-bottom: none;
}

/* ============================================================
   Info Tooltip (i) Icon
   ============================================================ */

.info-tip {
    position: relative;
    display: inline-flex;
    align-items: center;
    gap: 4px;
}

.info-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 16px;
    height: 16px;
    border-radius: 50%;
    border: 1.5px solid var(--text-muted);
    font-size: 10px;
    font-weight: 700;
    font-style: italic;
    color: var(--text-muted);
    cursor: help;
    position: relative;
    flex-shrink: 0;
}

.info-icon:hover,
.info-icon:focus,
.info-tip:focus .info-icon,
.info-tip:focus-within .info-icon {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
    outline: none;
}

/* === SS Wave 7 follow-up (2026-04-19): pseudo-element tooltip DISABLED ===
   The former `.info-icon::after` rules that positioned tooltips with
   `position: absolute; bottom: calc(100% + 8px)` caused ancestor-overflow
   clipping (scout-results thead inside `.table-frozen-cols` + `.has-vscroll`).
   Tooltips are now rendered via a body-level portal by `window.__initInfoTips`
   in `js/app.js`. See new `.info-tip-portal` block at the tail of this file.
   The `.info-tip-right` / `.info-tip-left` variants are moot under the portal —
   horizontal clamping is JS-side. Icon hover/focus border coloring above still
   applies. Pseudo-element blocks intentionally removed (not just commented)
   so the cascade is clean. */

.info-tip:focus { outline: none; }
.info-tip:focus-visible {
    outline: 2px solid var(--brand-teal);
    outline-offset: 2px;
    border-radius: 4px;
}

/* Ensure table headers don't clip tooltips */
.data-table thead th {
    overflow: visible;
    position: relative;
}
.data-table thead {
    overflow: visible;
}
.table-container {
    overflow-x: auto;
    overflow-y: visible;
}
.data-table-mobile-cards {
    overflow: visible;
}

/* ============================================================
   Scenario Tabs
   ============================================================ */

.scenario-bar {
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 12px 0;
    margin-bottom: 24px;
    border-bottom: 1px solid var(--border-color);
    overflow-x: auto;
}

.scenario-tab {
    padding: 8px 20px;
    border: 1px solid var(--border-color);
    border-radius: 6px;
    background: var(--bg-white);
    font-size: 0.85rem;
    font-weight: 500;
    cursor: pointer;
    white-space: nowrap;
    transition: all 0.15s;
    color: var(--text-secondary);
    text-decoration: none;
}

.scenario-tab:hover {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
}

.scenario-tab.active {
    background: var(--brand-teal);
    border-color: var(--brand-teal);
    color: white;
}

.scenario-tab-add {
    padding: 8px 12px;
    border: 1px dashed var(--border-color);
    border-radius: 6px;
    background: none;
    font-size: 1rem;
    cursor: pointer;
    color: var(--text-muted);
}

/* ============================================================
   Pursuit Layout (single-column; Map + Site Plan right column
   was removed 2026-04-16. Keep .pursuit-layout / .pursuit-left
   selectors since pursuit-workspace.html still wraps content in
   them — orphan .pursuit-right, .map-placeholder, .plan-placeholder
   rules were removed along with the HTML.)
   ============================================================ */

.pursuit-layout {
    /* HH (Wave 6 E3): flex row so sticky TOC sits as a sibling
       to .pursuit-left. On narrow viewports we hide the TOC and
       this reduces to a single-column flow. Gap is tokenized. */
    display: flex;
    align-items: flex-start;
    gap: var(--space-5);
}

.pursuit-left {
    min-width: 0;
    flex: 1 1 auto;
}

/* ============================================================
   Status Badges
   ============================================================ */

.status-badge {
    display: inline-block;
    padding: 4px 12px;
    border-radius: 12px;
    font-size: 0.75rem;
    font-weight: 600;
    text-transform: capitalize;
}

.status-contact-broker { background: #E8F8F7; color: #2BBCB3; }
.status-in-underwriting { background: #EBF5FB; color: #2E86C1; }
.status-loi-signed { background: #FEF9E7; color: #B7950B; }
.status-in-due-diligence { background: #F5EEF8; color: #7D3C98; }
.status-closed { background: #D5F5E3; color: #1E8449; }
.status-passed { background: #FADBD8; color: #C0392B; }

/* ============================================================
   Filters Bar
   ============================================================ */

.filters-bar {
    display: flex;
    flex-wrap: wrap;
    gap: 12px;
    align-items: center;
    padding: 16px 24px;
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 8px;
    margin-bottom: 24px;
}

.filter-select {
    padding: 8px 12px;
    border: 1px solid var(--border-color);
    border-radius: 6px;
    font-size: 0.85rem;
    font-family: var(--font-family);
    outline: none;
    color: var(--text-secondary);
    min-width: 140px;
}

.filter-select:focus {
    border-color: var(--brand-teal);
}

/* ============================================================
   Timeline / Activity Feed
   ============================================================ */

.timeline {
    list-style: none;
}

.timeline-item {
    display: flex;
    gap: 16px;
    padding: 12px 0;
    border-bottom: 1px solid var(--border-light);
    font-size: 0.9rem;
}

.timeline-date {
    color: var(--text-muted);
    font-size: 0.8rem;
    flex-shrink: 0;
    width: 80px;
}

.timeline-event {
    color: var(--text-primary);
}

/* ============================================================
   Login Page
   ============================================================ */

.login-container {
    max-width: 460px;
    margin: 80px auto;
    padding: 0 20px;
}

.login-card {
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 12px;
    padding: 48px 40px;
    text-align: center;
}

.login-card h1 {
    font-size: 1.6rem;
    font-weight: 700;
    margin-bottom: 32px;
}

.login-card .form-input {
    text-align: center;
    margin-bottom: 16px;
}

.login-card .btn {
    width: 100%;
    justify-content: center;
    padding: 14px;
    font-size: 1rem;
    margin-top: 8px;
}

.login-checkbox {
    display: flex;
    align-items: flex-start;
    gap: 8px;
    margin-top: 24px;
    text-align: left;
    font-size: 0.85rem;
    color: var(--text-secondary);
}

.login-checkbox input {
    margin-top: 3px;
    flex-shrink: 0;
}

/* ============================================================
   Editable Table (Development Plan)
   ============================================================ */

.editable-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.85rem;
}

.editable-table th {
    padding: 10px 12px;
    text-align: left;
    font-weight: 600;
    color: var(--text-secondary);
    border-bottom: 2px solid var(--border-color);
    font-size: 0.8rem;
}

.editable-table td {
    padding: 8px 12px;
    border-bottom: 1px solid var(--border-light);
}

.editable-table input {
    width: 100%;
    padding: 6px 8px;
    border: 1px solid var(--border-light);
    border-radius: 4px;
    font-size: 0.85rem;
    font-family: var(--font-family);
    background: var(--bg-light);
}

.editable-table input:focus {
    border-color: var(--brand-teal);
    outline: none;
    background: white;
}

/* ============================================================
   Responsive — Tablet (768px)
   ============================================================ */

@media (max-width: 768px) {
    /* Header */
    .app-header {
        padding: 0 16px;
    }
    .app-company {
        font-size: 1rem;
    }
    .app-header-right {
        gap: 16px;
    }
    .app-header-right a {
        font-size: 0.8rem;
    }

    /* Sidebar (mobile) — slide-out drawer, always full-width labels.
       Overrides Agent H hover-collapse behavior on small screens. */
    .app-sidebar {
        transform: translateX(-100%);
        width: 240px;
        box-shadow: 4px 0 12px rgba(0,0,0,0.1);
    }
    .app-sidebar:hover,
    .app-sidebar.is-expanded {
        width: 240px;
    }
    .app-sidebar.open {
        transform: translateX(0);
    }
    .app-sidebar .nav-label {
        opacity: 1;
        pointer-events: auto;
    }
    .sidebar-toggle {
        display: block;
    }

    /* Main */
    .app-main,
    body.app-shell-expanded .app-main {
        margin-left: 0;
    }

    /* Mode bar */
    .mode-bar {
        padding: 10px 16px;
        gap: 8px;
        flex-wrap: wrap;
    }
    .mode-item {
        flex: 0 0 auto;
        max-width: none;
    }
    .mode-btn {
        padding: 8px 20px;
        font-size: 0.85rem;
    }
    .mode-desc {
        display: none;
    }

    /* Scenario bar */
    .scenario-bar {
        flex-wrap: wrap;
    }
    .scenario-bar > span {
        width: 100%;
        margin-left: 0 !important;
        margin-top: 8px;
    }

    /* Filters bar */
    .filters-bar {
        flex-direction: column;
        align-items: stretch;
    }

    /* Editable tables */
    .editable-table {
        font-size: 0.8rem;
    }
    .editable-table th, .editable-table td {
        padding: 6px 8px;
    }

    /* All cards and content: prevent overflow */
    .card, .search-section {
        overflow-x: auto;
    }

    /* Data tables inside cards: allow horizontal scroll */
    .card .data-table {
        min-width: 500px;
    }

    /* Content */
    .content {
        padding: 20px 16px;
    }

    /* Pursuit layout (single-column since right column removed) */
    .pursuit-left {
        overflow-x: hidden;
    }

    /* Landing */
    .landing-header {
        padding: 12px 20px;
    }
    .landing-nav {
        gap: 16px;
    }
    .landing-hero {
        flex-direction: column;
        gap: 32px;
        margin: 40px auto;
        padding: 0 20px;
    }
    .landing-hero-text h1 {
        font-size: 2rem;
    }
    .landing-hero-image {
        width: 100%;
        height: 220px;
    }
    .landing-features {
        grid-template-columns: 1fr;
        padding: 0 20px;
    }

    /* Widget grid */
    .widget-grid {
        grid-template-columns: 1fr;
    }

    /* Filters */
    .filters-bar {
        flex-direction: column;
        align-items: stretch;
    }
}

/* ============================================================
   Responsive — Mobile (480px)
   ============================================================ */

@media (max-width: 480px) {
    .app-header-right a.hide-mobile {
        display: none;
    }

    .app-company {
        font-size: 0.85rem;
    }

    .landing-nav a.hide-mobile {
        display: none;
    }

    .landing-hero-text h1 {
        font-size: 1.6rem;
    }

    .content-header {
        flex-direction: column;
        align-items: flex-start;
        gap: 12px;
    }

    /* Scout results: card view on mobile */
    .data-table-mobile-cards .data-table thead {
        display: none;
    }
    .data-table-mobile-cards .data-table tbody tr {
        display: block;
        border: 1px solid var(--border-color);
        border-radius: 8px;
        padding: 16px;
        margin-bottom: 12px;
        background: var(--bg-white);
    }
    .data-table-mobile-cards .data-table tbody td {
        display: flex;
        justify-content: space-between;
        padding: 6px 0;
        border-bottom: 1px solid var(--border-light);
        white-space: normal;
    }
    .data-table-mobile-cards .data-table tbody td::before {
        content: attr(data-label);
        font-weight: 600;
        color: var(--text-secondary);
        font-size: 0.8rem;
        flex-shrink: 0;
        margin-right: 12px;
    }
    .data-table-mobile-cards .data-table tbody td:last-child {
        border-bottom: none;
    }

    .form-row {
        grid-template-columns: 1fr;
    }

    .scenario-bar {
        flex-wrap: nowrap;
        overflow-x: auto;
    }

    .login-card {
        padding: 32px 24px;
    }
}

/* ============================================================
   Sidebar Overlay (mobile)
   ============================================================ */

.sidebar-overlay {
    display: none;
    position: fixed;
    inset: 0;
    background: rgba(0,0,0,0.3);
    z-index: 140;
}

.sidebar-overlay.visible {
    display: block;
}

/* ============================================================
   Utility Classes
   ============================================================ */

.text-muted { color: var(--text-muted); }
.text-secondary { color: var(--text-secondary); }
.text-right { text-align: right; }
.text-center { text-align: center; }
/* DD (Wave 6 C1, 2026-04-19): retokenize margin utilities so
   inline uses pick up token-driven rhythm. Values unchanged —
   tokens resolve to the same 8/16/24px the rules previously hard-coded. */
.mt-8 { margin-top: var(--space-2); }
.mt-16 { margin-top: var(--space-4); }
.mt-24 { margin-top: var(--space-5); }
.mb-8 { margin-bottom: var(--space-2); }
.mb-16 { margin-bottom: var(--space-4); }
.mb-24 { margin-bottom: var(--space-5); }
.flex { display: flex; }
.gap-8 { gap: 8px; }
.gap-16 { gap: 16px; }
.items-center { align-items: center; }
.justify-between { justify-content: space-between; }

/* ============================================================
   B8: Address column — black, bold, clickable
   ============================================================ */
.address-link {
    color: var(--text-primary) !important;
    font-weight: 700;
    text-decoration: none;
}
.address-link:hover {
    text-decoration: none;
}

/* ============================================================
   .link-doc — exception to sitewide no-underline rule.
   Used on Property Info doc anchors (work item #3, 2026-04-27).
   Applied via DOM by another agent.
   ============================================================ */
.link-doc {
    color: var(--color-content);
    font-weight: 400;
    text-decoration: underline;
}

/* D1 (issuelog_since0504 R6, 2026-05-09): comp grid address links to Redfin.
   Anchor inherits header's bold + color; underlines only on hover so the
   cell still reads like a header by default. */
a.comp-header-addr,
a.comp-header-addr:visited {
    color: inherit;
    font-weight: inherit;
    text-decoration: none;
}
a.comp-header-addr:hover {
    text-decoration: underline;
}

/* ============================================================
   C17: Color coding — yellow = clickable/link, teal = editable
   ============================================================ */
.field-clickable {
    background-color: #FFF9C4;
    cursor: pointer;
}
.field-clickable:hover {
    background-color: #FFF176;
}
.field-editable {
    background-color: #E0F2F1;
    border-color: var(--brand-teal);
}
.field-editable:focus {
    outline: 2px solid var(--brand-teal);
    background-color: #fff;
}

/* ============================================================
   Asking Price inline input (Scout results table)
   ============================================================ */
.asking-price-input {
    width: 90px;
    padding: 4px 6px;
    border: 1px solid var(--border-color);
    border-radius: 4px;
    font-size: 0.85rem;
    text-align: right;
    background: var(--bg-light);
}
.asking-price-input:focus {
    outline: 2px solid var(--brand-teal);
    background: #fff;
}

/* D12 (2026-05-09): inline-editable Asking Price cell in deal-log table.
   Borderless until focus so the column reads like static text but invites
   click-to-edit. */
.asking-price-cell {
    width: 100%;
    padding: 2px 4px;
    border: 1px solid transparent;
    border-radius: 4px;
    font-size: inherit;
    text-align: inherit;
    background: transparent;
    color: inherit;
}
.asking-price-cell:hover {
    border-color: var(--border-color);
    background: var(--bg-light);
}
.asking-price-cell:focus {
    outline: 2px solid var(--brand-teal);
    background: #fff;
}

/* ============================================================
   Pursuit page: Section nav bullets
   ============================================================ */
.section-nav {
    position: sticky;
    top: calc(var(--header-height) + 16px);
    display: flex;
    flex-direction: column;
    gap: 8px;
    padding-right: 16px;
}
.section-nav-dot {
    width: 12px;
    height: 12px;
    border-radius: 50%;
    border: 2px solid var(--border-color);
    background: var(--bg-white);
    cursor: pointer;
    transition: all 0.15s;
}
.section-nav-dot.active,
.section-nav-dot:hover {
    border-color: var(--brand-teal);
    background: var(--brand-teal);
}

/* ============================================================
   Pursuit page: Two-way toggle
   ============================================================ */
.two-way-toggle {
    display: inline-flex;
    border: 1px solid var(--border-color);
    border-radius: 6px;
    overflow: hidden;
    font-size: 0.8rem;
}
.two-way-toggle button {
    padding: 6px 14px;
    border: none;
    background: var(--bg-light);
    cursor: pointer;
    font-size: 0.8rem;
    color: var(--text-secondary);
    transition: all 0.15s;
}
.two-way-toggle button.active {
    background: var(--brand-teal);
    color: #fff;
}

/* ============================================================
   Pursuit page: Collapsible section with expand/collapse arrow
   ============================================================ */
.collapsible-header::after {
    content: '\25BC';
    font-size: 0.65rem;
    color: var(--text-muted);
    margin-left: auto;
    transition: transform 0.2s;
}
.collapsible-header.collapsed::after {
    transform: rotate(-90deg);
}

/* ============================================================
   Confirm Dialog (window.confirmAction)
   ============================================================ */

.confirm-dialog-backdrop {
    position: fixed;
    inset: 0;
    background: rgba(0, 0, 0, 0.45);
    z-index: 10000;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 16px;
}

.confirm-dialog {
    background: #fff;
    border-radius: 10px;
    max-width: 440px;
    width: 100%;
    padding: 24px;
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.25);
    animation: confirm-dialog-pop 120ms ease-out;
}

@keyframes confirm-dialog-pop {
    from { opacity: 0; transform: translateY(-8px) scale(0.98); }
    to   { opacity: 1; transform: translateY(0)    scale(1); }
}

.confirm-dialog-message {
    font-size: 0.95rem;
    line-height: 1.5;
    color: var(--text-primary);
    margin: 0 0 20px 0;
}

.confirm-dialog-actions {
    display: flex;
    justify-content: flex-end;
    gap: 8px;
}

.confirm-dialog-cancel,
.confirm-dialog-ok {
    font-family: inherit;
    font-size: 0.9rem;
    font-weight: 600;
    padding: 8px 16px;
    border-radius: 6px;
    cursor: pointer;
    border: 1px solid transparent;
}

.confirm-dialog-cancel {
    background: #fff;
    color: var(--text-secondary);
    border-color: var(--border-color);
}

.confirm-dialog-cancel:hover {
    background: var(--bg-light);
    color: var(--text-primary);
}

.confirm-dialog-ok {
    background: var(--danger, #c0392b);
    color: #fff;
    border-color: var(--danger, #c0392b);
}

.confirm-dialog-ok:hover {
    filter: brightness(0.95);
}

.confirm-dialog-cancel:focus-visible,
.confirm-dialog-ok:focus-visible {
    outline: 2px solid var(--brand-teal);
    outline-offset: 2px;
}

/* ============================================================
   Agent G (Wave 4) — Table Primitives
   Reusable across Scout Results (#18/#19/#20) and comps grid (#57).
   ============================================================ */

/* --- Scrollable container for frozen-column tables --- */
.table-frozen-cols {
    overflow-x: auto;
    /* Let browsers do their own scrollbar styling; container owns the scroll */
    -webkit-overflow-scrolling: touch;
}

/* --- Sticky freeze for first N columns (default: first 2) ---
   Offset for 2nd column uses --freeze-col1-width; defaults to 56px
   (checkbox cell). Override per-table with inline style or custom
   class if column widths differ. */
.table-frozen-cols table {
    /* Ensure sticky cells paint above hover highlights */
    position: relative;
}
.table-frozen-cols thead th:nth-child(1),
.table-frozen-cols tbody td:nth-child(1) {
    position: sticky;
    left: 0;
    z-index: 3;
    background: #fff;
}
.table-frozen-cols thead th:nth-child(1) {
    background: var(--bg-light);
    z-index: 4;
}
.table-frozen-cols thead th:nth-child(2),
.table-frozen-cols tbody td:nth-child(2) {
    position: sticky;
    left: var(--freeze-col1-width, 56px);
    z-index: 3;
    background: #fff;
    /* subtle shadow to mark freeze boundary */
    box-shadow: 1px 0 0 0 var(--border-light);
}
.table-frozen-cols thead th:nth-child(2) {
    background: var(--bg-light);
    z-index: 4;
}
/* Preserve hover tint for rows that aren't checked — sticky cells
   need to pick up the tr:hover background, not stay white. */
.table-frozen-cols tbody tr:hover td:nth-child(1),
.table-frozen-cols tbody tr:hover td:nth-child(2) {
    background: var(--brand-teal-light);
}

/* --- Sortable headers --- */
.table-sortable thead th[data-sort] {
    cursor: pointer;
    user-select: none;
    white-space: nowrap;
}
.table-sortable thead th[data-sort]::after {
    content: ' \2195'; /* ↕ */
    opacity: 0.35;
    margin-left: 4px;
    font-size: 0.85em;
}
.table-sortable thead th[data-sort].sort-asc::after {
    content: ' \2191'; /* ↑ */
    opacity: 1;
    color: var(--brand-teal);
}
.table-sortable thead th[data-sort].sort-desc::after {
    content: ' \2193'; /* ↓ */
    opacity: 1;
    color: var(--brand-teal);
}

/* --- Row highlight when any cell in the row has a checked checkbox ---
   Uses :has() (evergreen browsers ≥ 2023). JS fallback sets
   .row-selected on the <tr> when unsupported. */
.table-select-highlight tbody tr:has(input[type="checkbox"]:checked),
.table-select-highlight tbody tr.row-selected {
    background: var(--brand-teal-light);
}
.table-select-highlight tbody tr:has(input[type="checkbox"]:checked) td:nth-child(1),
.table-select-highlight tbody tr:has(input[type="checkbox"]:checked) td:nth-child(2),
.table-select-highlight tbody tr.row-selected td:nth-child(1),
.table-select-highlight tbody tr.row-selected td:nth-child(2) {
    background: var(--brand-teal-light);
}

/* --- Home search tabs (#8) — Agent J --- */
/* Split single-address vs multi-address inputs behind tabs; single is default. */
.scout-input-tabs {
    display: flex;
    gap: 4px;
    margin-bottom: 12px;
    border-bottom: 1px solid var(--border-color, #e5e7eb);
}
.scout-tab {
    background: none;
    border: none;
    padding: 8px 16px;
    font-size: var(--font-size-button);
    font-weight: var(--font-weight-button, 600);
    color: var(--color-label);
    cursor: pointer;
    border-bottom: 2px solid transparent;
    margin-bottom: -1px;
    transition: color 0.15s ease, border-color 0.15s ease;
}
.scout-tab:hover {
    color: var(--color-content, var(--text-primary));
}
.scout-tab.is-active {
    color: var(--brand-teal);
    border-bottom-color: var(--brand-teal);
}
.scout-tab:focus-visible {
    outline: 2px solid var(--brand-teal);
    outline-offset: 2px;
    border-radius: 2px;
}
.scout-input-panel.is-hidden {
    display: none;
}
.scout-input-single,
.scout-input-multi {
    font-family: inherit;
    font-size: var(--font-size-content);
}
/* --- end Home search tabs (#8) --- */

/* ============================================================
   Agent I (Wave 4) — Pursuit workspace top-of-page + comps upgrades
   Findings #52 (zoning strip), #57 (freeze cols on comp grid),
   #60 (collapsible adjustment detail).
   ============================================================ */

/* --- #52: Compact zoning strip below address H1 --- */
.zoning-strip {
    display: flex;
    flex-wrap: wrap;
    gap: 24px;
    padding: 12px 16px;
    margin: 12px 0 20px;
    background: var(--color-readonly-bg);
    border-radius: 6px;
}
.zoning-strip-item {
    display: flex;
    flex-direction: column;
    min-width: 80px;
}
.zoning-strip-label {
    font-size: var(--font-size-label);
    font-weight: var(--font-weight-label);
    color: var(--color-label);
    text-transform: uppercase;
    letter-spacing: 0.02em;
}
.zoning-strip-value {
    font-size: var(--font-size-subsection);
    font-weight: var(--font-weight-subsection);
    color: var(--color-content);
    margin-top: 2px;
}

/* --- #57: Freeze primitive tuning for the comp grid ---
   The comp grid has colspan=2 header cells on comp columns and a wider
   first column (Feature, min-width:140px). Inline style on the wrapper
   sets --freeze-col1-width. Below we also make the sticky background
   match the table to avoid a white freeze band when zebra/summary rows
   render. */
.comp-grid-frozen .comp-grid {
    /* ensure sticky cells have a solid paint surface */
    background: #fff;
}
/* Summary rows in comp grid use --bg-light; sticky cells must match. */
.comp-grid-frozen tbody tr[data-row-kind="summary"] td:nth-child(1),
.comp-grid-frozen tbody tr[data-row-kind="summary"] td:nth-child(2) {
    background: var(--bg-light);
}
/* Feature column (col 1) in body rows uses a subtle contrast */
.comp-grid-frozen tbody td:nth-child(1) {
    background: #fff;
    font-weight: 600;
}

/* --- R02-COMP-05 (A.3 — 2026-04-30): dual-view adjustment cells.
   Display span shown by default. Under Manual Override mode, hide the
   formatted display and show a raw-number editable input. Pairs with
   the JS listener in pursuit-workspace.html that mutates
   container._comps and recomputes the comp's summary + the avg-adj-psf
   cascade into Sales PSF. */
td[data-adj-key] .adj-input {
    display: none;
    width: 80px;
    padding: 2px 6px;
    font-size: inherit;
    border: 1px solid var(--color-border, #d1d5db);
    border-radius: 3px;
    background: #fff;
    text-align: right;
    -moz-appearance: textfield;
}
td[data-adj-key] .adj-input::-webkit-outer-spin-button,
td[data-adj-key] .adj-input::-webkit-inner-spin-button {
    -webkit-appearance: none;
    margin: 0;
}
td[data-adj-key] .adj-input:focus {
    outline: 2px solid var(--brand-teal, #2BBCB3);
    outline-offset: -1px;
}
body[data-price-mode="manual"] td[data-adj-key] .adj-display {
    display: none;
}
body[data-price-mode="manual"] td[data-adj-key] .adj-input {
    display: inline-block;
}

/* --- R02-COMP-03 (A.4): per-comp × remove button. Hidden by default; only
   visible when Sales Trio is in Manual mode (matches A.3 dual-view pattern). --- */
.comp-grid .comp-remove-btn {
    display: none;
    position: absolute;
    top: 2px;
    right: 4px;
    background: transparent;
    border: 1px solid var(--color-border, #d1d5db);
    color: var(--color-content);
    cursor: pointer;
    padding: 0 6px;
    font-size: 14px;
    line-height: 1.2;
    border-radius: 3px;
}
.comp-grid .comp-remove-btn:hover {
    background: var(--danger);
    color: #fff;
    border-color: var(--danger);
}
body[data-price-mode="manual"] .comp-grid .comp-remove-btn {
    display: inline-block;
}
body[data-price-mode="manual"] .comp-grid th {
    padding-right: 28px;
}

/* --- #60 / R02-COMP-04 (Chunk B): Collapsible adjustment-detail rows.
   Default state: hide only rows with data-row-kind="detail" (the 8 rows
   that carry adj_* values). Always-visible rows (Sale Price, Price PSF,
   Distance, plus the 3 summary rows) stay visible regardless of toggle.
   Toggle button now lives as an inline <tr> between Distance and Sale Date
   so it visually separates the always-visible block from the detail block. --- */
.adj-grid-wrapper[data-collapsed="true"] tr[data-row-kind="detail"] {
    display: none;
}
.adj-grid-wrapper[data-collapsed="false"] .adj-grid-toggle-icon {
    transform: rotate(180deg);
}
.adj-detail-toggle-row td {
    background: var(--bg-light, #f9fafb);
    border-top: 1px solid var(--border-light, #e5e7eb);
    border-bottom: 1px solid var(--border-light, #e5e7eb);
}
.adj-detail-toggle-row .adj-grid-toggle {
    margin-bottom: 0;
}

/* --- R02-SALES-04 (2026-04-30): Market Comparables right-side add-on.
   Two-column flex grid pairs the Revenue table (left, flexes to fill) with a
   compact reference panel (right, intrinsic width) showing Submarket Avg /
   Adjusted Avg per unit type. Wraps on narrow viewports so the reference
   panel drops below the Revenue table instead of squeezing it. --- */
.sales-revenue-grid {
    display: flex;
    gap: 24px;
    align-items: flex-start;
    flex-wrap: wrap;
}
.sales-revenue-main {
    flex: 1 1 600px;
    min-width: 0;
}
.sales-market-comparables {
    flex: 0 1 auto;
    min-width: 280px;
}
.sales-market-comparables .data-table {
    font-size: 0.88rem;
}
.sales-market-comparables .data-table th,
.sales-market-comparables .data-table td {
    padding: 6px 12px;
}
.sales-market-comparables .data-table thead th {
    background: var(--bg-light, #f9fafb);
    font-weight: 600;
}
.adj-grid-toggle {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    background: none;
    border: 1px solid var(--border-light, #e5e7eb);
    padding: 6px 12px;
    margin-bottom: 8px;
    cursor: pointer;
    border-radius: 4px;
    font-size: var(--font-size-button);
    font-weight: var(--font-weight-button);
    color: var(--color-content);
}
.adj-grid-toggle:hover {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
}
.adj-grid-toggle-icon {
    display: inline-block;
    transition: transform 0.15s ease;
    font-size: 0.9em;
}
/* --- end Agent I (Wave 4) --- */

/* --- N: home + results + deals polish (Wave 5) --- */

/* #23/#24 — Data freshness strip: plain grey text, no border, no bg.
   Placed at the top of index.html above the search section. */
.data-freshness-strip {
    display: flex;
    flex-wrap: wrap;
    gap: 24px;
    padding: 4px 0 8px 0;
    margin: 0 0 4px 0;
    font-size: var(--font-size-meta);
    color: var(--color-label);
    border: none;
    background: none;
}
.data-freshness-strip strong {
    color: var(--color-content);
    font-weight: 600;
}

/* #59 — Divider lines between comp sets in the adjustment grid.
   Comp grid columns are: col 1 = Feature, col 2 = Subject, then
   paired (Comp N, Adj N) starting at col 3. Odd columns from 3
   onward mark the start of each comp set — add a subtle left
   border so Comp 1 / Comp 2 / Comp 3 groups are visually scannable.
   Scoped to .comp-grid-frozen so only the pursuit-workspace adjustment
   grid is affected (Agent I's wrapper). */
/* Header: each <th> from col 3 onward uses colspan=2 and marks a comp-set
   start, so apply a divider to every th from col 3 onward. */
.comp-grid-frozen .comp-grid thead th:nth-child(n+3) {
    border-left: 1px solid var(--border-light, #e5e7eb);
}
/* Body (non-summary) rows: each comp occupies 2 cells (value + adj). Odd
   cells from col 3 onward (3, 5, 7, ...) start a new comp set. */
.comp-grid-frozen .comp-grid tbody td:nth-child(2n+3) {
    border-left: 1px solid var(--border-light, #e5e7eb);
}
/* Summary rows use colspan=2 per comp, so every cell from col 3 onward is
   the start of a comp set. */
.comp-grid-frozen .comp-grid tbody tr[data-row-kind="summary"] td:nth-child(n+3) {
    border-left: 1px solid var(--border-light, #e5e7eb);
}

/* #80 — Deal Log status dropdown: restyle native <select> to match the
   app's input/button family. Option A (CSS only). Row-click skip logic
   (app.js _renderDealLog row handler) already ignores <select> clicks
   so changing the status never opens the detail panel. */
.deal-status-select {
    appearance: none;
    -webkit-appearance: none;
    -moz-appearance: none;
    background-color: #fff;
    background-image: url("data:image/svg+xml;charset=UTF-8,%3Csvg xmlns='http://www.w3.org/2000/svg' width='10' height='6' viewBox='0 0 10 6'%3E%3Cpath fill='none' stroke='%236b7280' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round' d='M1 1l4 4 4-4'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: right 8px center;
    background-size: 10px 6px;
    border: 1px solid var(--border-light, #e5e7eb);
    border-radius: 4px;
    padding: 5px 26px 5px 10px;
    font-size: var(--font-size-button);
    font-weight: var(--font-weight-button);
    color: var(--color-content);
    line-height: 1.2;
    cursor: pointer;
    min-width: 140px;
    transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.deal-status-select:hover {
    border-color: var(--brand-teal);
}
.deal-status-select:focus {
    outline: none;
    border-color: var(--brand-teal);
    box-shadow: 0 0 0 2px rgba(20, 184, 166, 0.2);
}
.deal-status-select:disabled {
    background-color: var(--color-readonly-bg, #f3f4f6);
    color: var(--color-label);
    cursor: not-allowed;
}
/* --- end N (Wave 5) --- */

/* --- O: global polish (Wave 5) --- */

/* #5 — Icon button with hover label.
   Universal actions (Export CSV/PDF, Print, Remove/Delete) use the
   icon-only treatment with a tooltip label on hover. Primary or
   domain-specific actions keep text labels.
   Markup pattern:
     <button class="btn-icon" aria-label="Export CSV" data-tip="Export CSV">
       <span class="btn-icon-glyph">CSV</span>
     </button>
   Tooltip renders via ::after from data-tip attribute. */
.btn-icon {
    position: relative;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 32px;
    height: 32px;
    padding: 0;
    background: var(--bg-white);
    border: 1px solid var(--border-color);
    border-radius: 4px;
    cursor: pointer;
    color: var(--text-secondary);
    font-size: 0.75rem;
    font-weight: 700;
    line-height: 1;
    transition: border-color 0.15s, color 0.15s, background 0.15s;
}
.btn-icon:hover,
.btn-icon:focus {
    border-color: var(--brand-teal);
    color: var(--brand-teal);
    outline: none;
}
.btn-icon-glyph {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    pointer-events: none;
}
.btn-icon[data-tip]::after {
    content: attr(data-tip);
    position: absolute;
    bottom: calc(100% + 6px);
    left: 50%;
    transform: translateX(-50%);
    background: var(--text-primary);
    color: #fff;
    padding: 4px 8px;
    border-radius: 4px;
    font-size: var(--font-size-meta);
    font-weight: 400;
    line-height: 1.2;
    white-space: nowrap;
    opacity: 0;
    visibility: hidden;
    transition: opacity 120ms ease;
    pointer-events: none;
    z-index: 9999;
}
.btn-icon:hover[data-tip]::after,
.btn-icon:focus[data-tip]::after {
    opacity: 1;
    visibility: visible;
}
.btn-icon + .btn-icon {
    margin-left: var(--space-2); /* 8px — consistent group spacing */
}

/* #28 — Settings bottom Save button block: anchor + spacing, no divider */
.settings-actions-bottom {
    padding: var(--space-4) 0;      /* 16px */
    margin-top: var(--space-5);     /* 24px */
    border-top: none;
    display: flex;
    justify-content: flex-start;
    gap: var(--space-2);
}

/* #6 — Spacing-token normalization for common inline layout helpers.
   Pinning hard-coded gap utilities to tokens so L/M pursuit polish picks
   up the same rhythm. Scope kept tight to avoid knock-on regressions. */
.flex.gap-8  { gap: var(--space-2); }
.flex.gap-16 { gap: var(--space-4); }
.flex.gap-24 { gap: var(--space-5); }

/* --- end O (Wave 5) --- */

/* --- L (Wave 5 Stage 2): pursuit workspace body polish --- */

/* #39 — Export button hierarchy. PDF is the primary action (filled teal),
   CSV stays as the default outlined .btn-icon (secondary). Variant modifier
   class, not a replacement — preserves Agent O's tooltip + sizing. */
.btn-icon.btn-icon-primary {
    background: var(--brand-teal);
    border-color: var(--brand-teal);
    color: #fff;
}
.btn-icon.btn-icon-primary:hover,
.btn-icon.btn-icon-primary:focus {
    background: var(--brand-teal-hover);
    border-color: var(--brand-teal-hover);
    color: #fff;
}

/* #40 — Remove horizontal divider under collapsible section headers.
   Global rule #4: section header weight + spacing are sufficient.
   Was: `border-bottom: 2px solid var(--brand-teal);` on .collapsible-header.
   Keeping the disclosure chevron and padding for visual rhythm. */
.collapsible-header {
    border-bottom: none;
}
/* Tighter bottom margin between sections so removed border doesn't
   make them feel glued together. Use spacing token. */
.collapsible + .collapsible {
    margin-top: var(--space-3);
}

/* #44 — Center-align Dev Plan numeric columns. Unit Type (first col)
   stays left. Scoped to section-3 editable-table so other tables unaffected. */
#section-3 .editable-table th,
#section-3 .editable-table td {
    text-align: center;
}
#section-3 .editable-table th:first-child,
#section-3 .editable-table td:first-child {
    text-align: left;
}
/* Restore right-alignment on total cells which already have inline
   `style="text-align:right"` — inline style wins over these rules, so
   no change needed there. */

/* #65 — Cost summary total rows: dollar value must sit in the bulk-budget
   column. cost-table rows have 3 cells (label / rate / amount). The total
   row already spans label across 2 cells via empty second <td>. Force the
   third <td> to match amount-column width and right-align for alignment
   with the row-level amount inputs below it. */
.cost-table .cost-total-row td:first-child {
    font-weight: 600;
}
.cost-table .cost-total-row td:last-child {
    text-align: right;
    font-weight: 600;
    /* Match the width of .cost-amount-input cells so the dollar aligns
       with the per-row amount column. */
    width: 140px;
    min-width: 140px;
}
.cost-table .cost-amount-input {
    width: 100%;
    box-sizing: border-box;
    text-align: right;
}

/* #68 — Construction tier delta note. Small italic label under the tier
   picker. Uses Agent D's meta + label tokens. */
.tier-delta-note {
    margin-top: var(--space-1); /* 4px */
    font-size: var(--font-size-meta);
    color: var(--color-label);
    font-style: italic;
}

/* #69 — User-added cost rows: subtle "Custom" badge + row bg tint so
   custom items read as distinct from system defaults without shouting. */
.custom-row-badge {
    display: inline-block;
    margin-left: var(--space-1); /* 4px */
    padding: 1px 6px;
    font-size: var(--font-size-meta);
    background: var(--color-readonly-bg);
    color: var(--color-label);
    border-radius: 3px;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    font-weight: 600;
    vertical-align: middle;
}
.cost-table tr.is-custom {
    background: rgba(43, 188, 179, 0.04); /* 4% teal wash */
}
/* KK (Wave 6 D2, 2026-04-19): custom cost row — label as plain text,
   × delete button at end of the amount cell. */
.cost-table tr.is-custom .custom-row-label {
    display: inline-block;
    font-weight: 500;
    color: var(--color-content, #111);
    vertical-align: middle;
}
/* R02-COST-04 (2026-04-30): inline editable label input for custom cost rows. */
.cost-table tr.is-custom .custom-row-label-input {
    width: 100%;
    padding: 4px 8px;
    border: 1px solid var(--border-color, #e5e7eb);
    border-radius: 4px;
    font-size: 0.82rem;
    background: #E0F2F1;
    color: var(--color-content, #111);
    box-sizing: border-box;
}

/* R02-SALES-02 (2026-04-30): 3-mode price source selector — three stacked
   toggle rows (Submarket / Adjusted / Manual Override), mutually exclusive
   via radio inputs. Styled to match partner mock on Review 02 page 6. */
.price-mode-group {
    display: flex;
    flex-direction: column;
    gap: 8px;
    margin-bottom: 16px;
    max-width: 320px;
}
.price-mode-row {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 16px;
    cursor: pointer;
    user-select: none;
}
.price-mode-row input[type="radio"] {
    position: absolute;
    opacity: 0;
    pointer-events: none;
}
.price-mode-label {
    font-size: 0.85rem;
    color: var(--color-content, #111);
    flex: 1;
}
.price-mode-switch {
    display: inline-block;
    position: relative;
    width: 36px;
    height: 20px;
    background: #d1d5db;
    border-radius: 10px;
    transition: background 0.2s;
    flex-shrink: 0;
}
.price-mode-knob {
    position: absolute;
    top: 2px;
    left: 2px;
    width: 16px;
    height: 16px;
    background: #fff;
    border-radius: 50%;
    transition: left 0.2s;
}
.price-mode-row input[type="radio"]:checked ~ .price-mode-switch {
    background: var(--brand-teal, #2BBCB3);
}
.price-mode-row input[type="radio"]:checked ~ .price-mode-switch .price-mode-knob {
    left: 18px;
}
.price-mode-row:hover .price-mode-switch {
    box-shadow: 0 0 0 2px rgba(43, 188, 179, 0.15);
}
/* R02-SALES-03 (A.2 — 2026-04-30): editable PSF cells under Manual Override.
   Cells become editable inline when body[data-price-mode="manual"]. Visual
   matches `.is-editable` convention (white bg, thin border, focus outline). */
body[data-price-mode="manual"] #field-sales-pri-psf,
body[data-price-mode="manual"] #field-sales-adu-psf {
    cursor: text;
    background: var(--color-editable-bg, #ffffff);
    border: 1px solid var(--color-border, #d1d5db);
    border-radius: 4px;
    padding: 4px 8px;
    box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.04);
    min-width: 60px;
}
body[data-price-mode="manual"] #field-sales-pri-psf:focus,
body[data-price-mode="manual"] #field-sales-adu-psf:focus {
    outline: 2px solid var(--brand-teal, #2BBCB3);
    outline-offset: -1px;
    background: #fff;
}
.cost-table tr.is-custom .btn-icon-del {
    width: 24px;
    height: 24px;
    margin-left: 6px;
    line-height: 1;
    padding: 0;
    vertical-align: middle;
    border-color: var(--color-border, #e5e7eb);
    color: var(--danger, #c1121f);
}
.cost-table tr.is-custom .btn-icon-del:hover {
    background: rgba(193, 18, 31, 0.08);
    border-color: var(--danger, #c1121f);
}
.cost-table tr.is-custom .btn-icon-del .btn-icon-glyph {
    font-size: 16px;
    font-weight: 700;
}

/* #71 — Inline note for inputs that affect downstream calcs (financing
   months, etc). Italic, muted, small. */
.inline-note {
    display: inline-block;
    margin-left: var(--space-1); /* 4px */
    font-size: var(--font-size-meta);
    color: var(--color-label);
    font-style: italic;
}

/* --- end L (Wave 5 Stage 2) --- */

/* --- FF (Wave 6 C5, 2026-04-19): Deal-Log toggle button on pursuit header ---
   Teal outline = stateful toggle, distinct from Export icon cluster.
   .is-in-deal-log = entry currently tracked (teal tint). .deal-toggle-flash =
   brief "Saved ✓" / "Removed" confirmation state after click. */
.btn-deal-toggle {
    border: 1px solid var(--brand-teal);
    color: var(--brand-teal);
    background: var(--bg-white);
    min-width: 164px;        /* prevents width jitter between "Add..." ↔ "Remove..." */
    justify-content: center;
}
.btn-deal-toggle:hover {
    background: rgba(43, 188, 179, 0.06);
    color: var(--brand-teal);
    border-color: var(--brand-teal-hover, var(--brand-teal));
}
.btn-deal-toggle.is-in-deal-log {
    background: rgba(43, 188, 179, 0.10);
    color: var(--brand-teal);
    border-color: var(--brand-teal);
}
.btn-deal-toggle.is-in-deal-log:hover {
    background: rgba(220, 53, 69, 0.08);
    color: var(--danger, #dc3545);
    border-color: var(--danger, #dc3545);
}
.btn-deal-toggle.deal-toggle-flash {
    background: var(--success, #28a745);
    color: #fff;
    border-color: var(--success, #28a745);
    transition: background 120ms, color 120ms, border-color 120ms;
}
.btn-deal-toggle:disabled {
    opacity: 0.55;
    cursor: not-allowed;
}
/* --- end FF (Wave 6 C5) --- */

/* ============================================================
   DD (Wave 6 C1, 2026-04-19): Pursuit formatting pass.
   Applies `--space-*` tokens consistently across the pursuit
   workspace, caps row widths, and defines a vertical list
   primitive for Scenario Summary. Zoning check-item pattern
   (label left / value right / bordered rows) is the reference
   rhythm every section now echoes.
   ============================================================ */

/* Cap content width inside pursuit workspace so wide form-rows
   don't stretch across 1400px+ monitors. ~920px is the tightest
   partner-approved ceiling that still fits two-column form-row
   pairs comfortably. Applies only to .content inside pursuit —
   other pages keep their own layout. */
.pursuit-left {
    max-width: 920px;
    width: 100%;
}

/* Work item #22 (2026-04-27): section dividers in pursuit-workspace.
   Single consolidated rule — 1px horizontal divider between adjacent
   .collapsible siblings inside .pursuit-left, matched space-4 padding
   above and below. First section gets no top divider (sibling combinator).
   Scoped to .pursuit-left so deals.html / settings.html collapsibles
   are unaffected. Supersedes prior Wave2-A Sub-task 4 + Wave 5 rhythm
   rules (--space-6 / --space-3 split). */
.pursuit-left .collapsible + .collapsible {
    border-top: 1px solid var(--border-color);
    margin-top: var(--space-4);
    padding-top: var(--space-4);
}
.pursuit-left .collapsible-header {
    padding: var(--space-3) 0;
}
.pursuit-left .collapsible-body {
    padding-top: var(--space-3);
    padding-bottom: 0;
}

/* Inside each section body, rows snap to `--space-3` between
   one another — same cadence as Zoning check-item's 6px/row +
   border-bottom. `.form-row` inside a pursuit section gets the
   token-based bottom margin; the last row in a body drops it
   so the body's padding-bottom controls the gap. */
.pursuit-left .collapsible-body > .form-row {
    margin-bottom: var(--space-3);
}
.pursuit-left .collapsible-body > .form-row:last-child {
    margin-bottom: 0;
}

/* Form-groups inside pursuit sections use `--space-2` (8px)
   label-to-input gap via the default `.form-label { margin-bottom: 6px }`
   already in place — just trim the extra 24px bottom margin that
   .form-group carries for standalone page use (it's redundant
   inside a grid .form-row). */
.pursuit-left .collapsible-body .form-row > .form-group {
    margin-bottom: 0;
}

/* Section 2: remove the decorative divider between the top
   property-info fields and the "Coming soon" owner/permit
   placeholders. Use spacing token for the gap. (Agent O's rule:
   no decorative dividers between sub-blocks.) */
.pursuit-left #section-2 .collapsible-body > div[style*="border-top"] {
    border-top: none !important;
    margin-top: var(--space-4) !important;
    padding-top: 0 !important;
}

/* Scenario Summary: vertical one-row-per-field layout. Each
   row = label on the left, value on the right, bordered-bottom
   rhythm echoes the Zoning .check-item pattern. Labels are
   label-token sized + muted; values are metric-token sized +
   strong. */
.scenario-summary-list {
    display: flex;
    flex-direction: column;
}
.scenario-summary-list .ss-row {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-4);
    padding: var(--space-3) 0;
    border-bottom: 1px solid var(--border-light);
}
.scenario-summary-list .ss-row:last-child {
    border-bottom: none;
}
.scenario-summary-list .ss-row-label {
    font-size: var(--font-size-label);
    font-weight: var(--font-weight-label);
    color: var(--text-secondary);
    display: inline-flex;
    align-items: center;
    gap: var(--space-2);
    flex: 0 1 auto;
}
.scenario-summary-list .ss-row-value {
    font-size: var(--font-size-metric, 1rem);
    font-weight: var(--font-weight-subsection, 600);
    color: var(--text-primary);
    text-align: right;
    display: inline-flex;
    align-items: center;
    gap: var(--space-3);
}
/* Value pill for the headline "Max Offer Price" — larger
   typography echoes the old .value-large treatment. */
.scenario-summary-list .ss-row.ss-row-headline .ss-row-value {
    font-size: 1.4rem;
    font-weight: var(--font-weight-metric, 700);
}
/* Agent AAC P0 #4b (2026-04-20): readonly scenario-summary inputs that
   should render like plain text (no border/bg) but keep the metric
   typography rhythm. Replaces inline style="border:none;…font-weight:600"
   on rows 2-7. Use .ss-row-input-strong where a heavier weight is needed
   (e.g., Profit Margin at 700). */
.scenario-summary-list .ss-row-input {
    border: none;
    background: transparent;
    padding: 0;
    text-align: right;
    font-weight: var(--font-weight-subsection, 600);
}
.scenario-summary-list .ss-row-input-strong {
    font-weight: var(--font-weight-metric, 700);
}
/* Proposed-offer toggle sizing — moved from inline transform:scale(0.85). */
.scenario-summary-list .ss-row-toggle {
    transform: scale(0.85);
}
/* Editable row on Proposed Offer Price: input sits inline on
   the right of the row, toggle sits between the label and the
   input. Keeps Agent F's wiring intact — we only changed the
   DOM surrounding the IDs. */
.scenario-summary-list .ss-row-editable .ss-row-value {
    gap: var(--space-3);
}
.scenario-summary-list .ss-row-editable input.form-input {
    max-width: 200px;
    text-align: right;
    font-weight: var(--font-weight-subsection, 600);
}
/* Profit Margin readout — color bands (Agent F #35) applied
   directly to the value span rather than an input. Reuse the
   existing utility classes unchanged. */
.scenario-summary-list .ss-row-value.margin-above,
.scenario-summary-list .ss-row-value.margin-near,
.scenario-summary-list .ss-row-value.margin-below {
    padding: 2px 10px;
    border-radius: 4px;
}

/* Agent AAC P0 #4c (2026-04-20): unified mobile breakpoint at 768px to
   match .scenario-map-row (was 640px — left a 641-768 awkward band where
   outer row stacked but inner rows stayed side-by-side). */
@media (max-width: 768px) {
    .scenario-summary-list .ss-row {
        flex-direction: column;
        align-items: flex-start;
        gap: var(--space-1);
    }
    .scenario-summary-list .ss-row-value {
        text-align: left;
    }
}
/* --- end DD (Wave 6 C1) --- */

/* ==================================================================
   Agent EE — Wave 6 B4 + B6 (2026-04-19)
   Results-table vertical-scroll wrapper + autocomplete full-address
   fragments. Scoped to not interfere with other pages.
   ================================================================== */

/* B4 — when row count exceeds cap, the existing .table-container caps
   its height and scrolls vertically. Horizontal overflow stays via its
   original overflow-x:auto; both axes work in one wrapper. The existing
   .data-table thead { position:sticky; top:0 } keeps headers visible. */
.table-container.has-vscroll {
    max-height: 600px;
    overflow-y: auto;
}

.table-container.has-vscroll .data-table thead th {
    /* Ensure the sticky header sits above content rows (and above the
       frozen column's z-index so it paints on top at corners). */
    z-index: 3;
    background: var(--bg-light);
}

/* --- 2026-04-19 tooltip clipping fix on scout-results header ---
   SUPERSEDED by SS Wave 7 follow-up (body-level portal). The flip-to-below
   override below is moot under the portal (pseudo-element is no longer
   rendered). Intentionally removed; see `.info-tip-portal` block at file tail. */

/* B6 — autocomplete items now render street bold + "City, State ZIP"
   muted; keep them on one row each with comfortable spacing. */
.scout-ac-item {
    display: flex;
    align-items: baseline;
    gap: var(--space-2, 8px);
    flex-wrap: wrap;
}

.scout-ac-item .scout-ac-street {
    font-weight: 600;
    color: var(--text-primary);
}

.scout-ac-item .scout-ac-citystate {
    font-size: 0.85rem;
    color: var(--text-secondary);
}
/* --- end EE (Wave 6 B4 + B6) --- */

/* ============================================================
   Agent PP (Wave 7, 2026-04-19): docked search + history card on
   scout-results.html. Scope by `.scout-results-search` so it can't
   regress home's `.search-section`.
   ============================================================ */
.scout-results-search {
    margin-top: var(--space-4, 16px);
    margin-bottom: var(--space-3, 12px);
    padding: var(--space-3, 12px) var(--space-4, 16px);
    background: var(--bg-light, #f7fafa);
    border-radius: 6px;
}
.scout-results-search .search-bar {
    margin-top: 0;
}
.scout-history-card {
    margin-top: var(--space-5, 24px);
    margin-bottom: var(--space-5, 24px);
}
.scout-history-card #scout-past-searches tr {
    cursor: pointer;
}
.scout-history-card #scout-past-searches tr:hover td {
    background: var(--brand-teal-light, #e8f7f4);
}
/* --- end Agent PP (Wave 7) --- */

/* ============================================================
   JJ (Wave 6 C3, 2026-04-19): Scenario lifecycle controls on pursuit header,
   plus scenario-count badge on deals.html rows.
   ============================================================ */
.scenario-controls {
    display: inline-flex;
    align-items: center;
    gap: var(--space-2);
    padding: 4px 8px;
    border: 1px solid var(--border-color, #d0d5dd);
    border-radius: 6px;
    background: var(--bg-white, #fff);
}
.scenario-controls-label {
    font-size: var(--font-size-label, 0.75rem);
    font-weight: var(--font-weight-label, 600);
    color: var(--color-label, var(--text-secondary, #6b7280));
    letter-spacing: 0.02em;
    text-transform: uppercase;
    margin: 0;
}
.scenario-select {
    min-width: 140px;
    max-width: 200px;
    padding: 4px 8px;
    border: 1px solid var(--border-color, #d0d5dd);
    border-radius: 4px;
    background: var(--bg-white, #fff);
    font-size: 0.875rem;
    color: var(--text-primary, #111);
    cursor: pointer;
}
.scenario-select:focus {
    outline: none;
    border-color: var(--brand-teal, #2bbcb3);
    box-shadow: 0 0 0 2px rgba(43, 188, 179, 0.2);
}
/* Scenario action icon buttons reuse Agent O's .btn-icon sizing + tooltip.
   This modifier matches teal-outline parity with FF; red for delete. */
.scenario-btn:hover:not(:disabled),
.scenario-btn:focus:not(:disabled) {
    border-color: var(--brand-teal, #2bbcb3);
    color: var(--brand-teal, #2bbcb3);
}
.scenario-btn:disabled {
    opacity: 0.45;
    cursor: not-allowed;
}
.scenario-btn-danger:hover:not(:disabled),
.scenario-btn-danger:focus:not(:disabled) {
    border-color: var(--danger, #dc3545);
    color: var(--danger, #dc3545);
}

/* Scenario count badge — rendered next to the address link in the Deal Log
   table. Small pill, teal, clickable. */
.scenario-count-badge {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 18px;
    height: 18px;
    padding: 0 6px;
    margin-left: 8px;
    border-radius: 9px;
    background: var(--brand-teal, #2bbcb3);
    color: #fff;
    font-size: 0.7rem;
    font-weight: 700;
    line-height: 1;
    text-decoration: none;
    vertical-align: middle;
    cursor: pointer;
    transition: background 0.15s;
}
.scenario-count-badge:hover,
.scenario-count-badge:focus {
    background: var(--brand-teal-hover, #249b94);
    color: #fff;
    outline: none;
}
/* --- end JJ (Wave 6 C3) --- */

/* ==================================================================
   HH (Wave 6 E3, 2026-04-19)
   Sticky workspace TOC sidebar. Sibling of .pursuit-left (not a
   subgrid inside it) so DD's 920px width cap on .pursuit-left
   remains untouched. On <=1200px we hide the TOC and rely on the
   content scroll. Active-section highlight is driven by an
   IntersectionObserver wired in pursuit-workspace.html.

   Sticky top = --header-height (96px, from the fixed .app-header)
   + var(--space-4) breathing room. Same formula as .filters-bar at
   css/styles.css:1707 so the two sticky primitives line up.
   ================================================================== */

.pursuit-toc {
    position: sticky;
    top: calc(var(--header-height) + var(--space-4));
    align-self: flex-start;
    flex: 0 0 180px;
    width: 180px;
    max-height: calc(100vh - var(--header-height) - var(--space-5));
    overflow-y: auto;
    padding: var(--space-2) 0;
    border-left: 1px solid transparent;
    /* aria-label lives on the <nav>; visually muted until hover/active */
    font-size: var(--font-size-label, 0.85rem);
    line-height: 1.4;
}

.pursuit-toc-title {
    font-size: var(--font-size-meta, 0.72rem);
    font-weight: var(--font-weight-label, 600);
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: var(--text-muted);
    padding: 0 var(--space-3) var(--space-2);
    margin: 0;
}

.pursuit-toc-list {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
}

.pursuit-toc-link {
    display: block;
    padding: var(--space-2) var(--space-3);
    color: var(--text-secondary);
    text-decoration: none;
    border-left: 2px solid transparent;
    transition: color 120ms ease, background 120ms ease, border-color 120ms ease;
}

.pursuit-toc-link:hover,
.pursuit-toc-link:focus {
    color: var(--brand-teal);
    background: rgba(43, 188, 179, 0.06);
    outline: none;
}

/* Active state — mirrors Agent H's left-sidebar active pattern:
   teal 2px border on the left, teal text, faint teal fill. */
.pursuit-toc-link.toc-active {
    color: var(--brand-teal);
    font-weight: 600;
    border-left-color: var(--brand-teal);
    background: rgba(43, 188, 179, 0.08);
}

/* Smooth scroll so IntersectionObserver also updates mid-scroll
   instead of jumping. Scoped to the root; the pages that don't
   benefit get the same cheap no-op. */
html {
    scroll-behavior: smooth;
}

/* Anchor jumps offset for the fixed app header so clicked sections
   don't land under it. Apply to every #section-N on pursuit so both
   TOC clicks and direct hash loads land cleanly. */
.pursuit-left > .collapsible[id^="section-"] {
    scroll-margin-top: calc(var(--header-height) + var(--space-4));
}

/* Responsive: below 1200px there isn't room for the 180px rail
   without crowding DD's 920px content column. Hide the TOC and
   let the page scroll normally. */
@media (max-width: 1200px) {
    .pursuit-toc {
        display: none;
    }
    .pursuit-layout {
        display: block;
    }
}

/* Respect prefers-reduced-motion — swap smooth scroll for instant. */
@media (prefers-reduced-motion: reduce) {
    html {
        scroll-behavior: auto;
    }
    .pursuit-toc-link {
        transition: none;
    }
}
/* --- end HH (Wave 6 E3) --- */

/* ==================================================================
   === SS Wave 7 follow-up: tooltip portal === (2026-04-19)
   Replaces the pseudo-element `.info-icon::after` tooltip pattern
   (which was clipped by ancestor overflow like .table-frozen-cols +
   .has-vscroll) with a body-level portal element positioned via
   JS using `position: fixed`. Fixed positioning escapes every
   ancestor overflow by browser design. See `window.__initInfoTips`
   in `js/app.js` for positioning logic.

   A single singleton portal `<div class="info-tip-portal">` is
   appended to `document.body` lazily on first hover/focus and
   reused across tooltips (perf + DOM cleanliness).
   ================================================================== */
.info-tip-portal {
    position: fixed;
    z-index: 9999;
    top: 0;
    left: 0;
    background: var(--text-primary);
    color: white;
    padding: 8px 12px;
    border-radius: 6px;
    font-size: 0.8rem;
    font-style: normal;
    font-weight: 400;
    line-height: 1.4;
    max-width: 260px;
    pointer-events: none;
    box-shadow: 0 4px 12px rgba(0,0,0,0.15);
    opacity: 0;
    display: none;
    transition: opacity 120ms ease-out;
    /* Word wrapping so long tooltips break instead of overflowing.
       `pre-line` (vs `normal`) preserves explicit `&#10;` line breaks from
       data-tooltip attributes while still collapsing other whitespace
       and allowing soft wraps — needed for multi-step tooltips like the
       Recorded Documents workflow. Existing tooltips without explicit
       newlines render identically. */
    white-space: pre-line;
    word-wrap: break-word;
    overflow-wrap: break-word;
}

.info-tip-portal.is-visible {
    opacity: 1;
    display: block;
}

@media (prefers-reduced-motion: reduce) {
    .info-tip-portal {
        transition: none;
    }
}
/* --- end SS Wave 7 follow-up: tooltip portal --- */

/* ==================================================================
   === Agent TT Wave 7 follow-up: responsive overflow === (2026-04-19)
   Fixes two horizontal `body.scrollWidth` overflow bugs surfaced by
   `tests/e2e/tests/responsive.spec.ts`:

   R2 — deals.html @ 900px tablet: the deal-log table is
        `<div class="table-container data-table-mobile-cards">` and the
        global rule `.data-table-mobile-cards { overflow: visible; }`
        (styles.css:1158–1160, needed so thead info-tip bubbles don't
        clip at the top edge) disables horizontal scroll containment.
        With 10 columns + nowrap, the table escapes the container at
        tablet width. Mobile-cards styling only activates at ≤480px,
        so the 481–1199 range was unserved.

        Fix: restore horizontal containment on the container at
        viewports WIDER than the mobile-cards breakpoint. We already
        have `.table-container { overflow-x: auto }` baseline; just
        preserve it when `.data-table-mobile-cards` is also on the
        element, and only drop it (back to `visible`) at ≤480 where
        the cards layout is active and there's nothing to scroll.
        This keeps the R1/SS tooltip-portal fix intact because the
        portal is `position: fixed` and doesn't depend on ancestor
        overflow at all.

   R3 — scout-results.html @ 375px mobile: `.content-header` button
        row (`<div class="flex gap-8">` with 5 buttons) doesn't wrap,
        and the `.scout-results-search` docked search bar can crowd
        the input + icon button past the viewport. With 16px content
        padding, 343px is the useful width, and `min-width:0` on the
        flex item is required for `flex: 1` to actually shrink the
        input wrapper around the 40px search button.

        Fix: wrap the action-bar button row at mobile; give the docked
        search `.search-bar` the `min-width: 0` + `max-width: 100%`
        safety so its children contain cleanly; and belt-and-braces
        `max-width: 100%` on `.app-main` so nothing child-level can
        force it past viewport.
   ================================================================== */

/* R2 — keep horizontal scroll on .table-container even when it also
   carries `.data-table-mobile-cards`, at tablet+desktop widths. */
.table-container.data-table-mobile-cards {
    overflow-x: auto;
}

/* At ≤480px the mobile-cards layout is active (thead hidden, tbody
   rows render as stacked cards) so no horizontal scroll is needed
   or wanted — restore the visible overflow so no phantom scrollbar
   appears under the card stack. */
@media (max-width: 480px) {
    .table-container.data-table-mobile-cards {
        overflow-x: visible;
    }
}

/* R3 — mobile action-bar wrap + search-bar containment. */
@media (max-width: 480px) {
    /* Action-bar button row inside .content-header. `flex-direction:
       column` on the parent is already set at ≤480 (styles.css:1535);
       inner row needs to wrap so 5 buttons don't overflow the 343px
       content width. */
    .content-header .flex {
        flex-wrap: wrap;
    }

    /* Docked search bar containment. The `<div style="flex:1">`
       wrapping the input needs min-width:0 for the input's
       `width:100%` not to push the 40px search button out of row. */
    .search-bar {
        min-width: 0;
        max-width: 100%;
    }
    .search-bar > div {
        min-width: 0;
    }

    /* Belt-and-braces: cap `.app-main` at viewport so no descendant
       can force the document past it. `.app-main` has `margin-left:0`
       on mobile (styles.css:1411), so 100% is 100vw. */
    .app-main {
        max-width: 100vw;
        overflow-x: hidden;
    }
}
/* --- end Agent TT Wave 7 follow-up: responsive overflow --- */

/* ============================================================
   Agent GG (2026-04-20) — Google Maps integration (Track 5)
   B3 home-results map (scout-results.html) + C4 pursuit map.
   Tokens: reuse --space-*, --color-*; no new root tokens.
   ============================================================ */
.map-section {
    margin: var(--space-5) 0 var(--space-4);
    padding: 0;
    /* User request 2026-04-20: scout-results map half the previous width. */
    max-width: 50%;
}
.map-section .map-heading {
    font-size: var(--font-size-subsection);
    font-weight: var(--font-weight-subsection);
    color: var(--color-content);
    margin: 0 0 var(--space-2) 0;
}
.map-container {
    position: relative;
    width: 100%;
    height: 420px;
    background: var(--color-readonly-bg);
    border: 1px solid #e5e7eb;
    border-radius: 6px;
    overflow: hidden;
}
.map-container.map-pursuit {
    height: 280px;
}
/* Pursuit map sidebar — sibling of .pursuit-left inside .pursuit-layout
   (user request 2026-04-20). Fixed 25vw width, sticky so it tracks scroll,
   and completely outside the .pursuit-left content flow so it can never
   overlap or squeeze any pursuit result. Hidden below 960px to avoid
   fighting for space on phones/tablets — user scrolls past sections
   without the map distraction. Scout-results map reverts to full width
   on mobile as before. */
.pursuit-map-side {
    flex: 0 0 25vw;
    max-width: 400px;
    min-width: 260px;
    align-self: flex-start;
}
.pursuit-map-side .map-container.map-pursuit-side {
    width: 100%;
    height: 100%;
    min-height: 500px;
}
@media (max-width: 960px) {
    .pursuit-map-side {
        display: none;
    }
    .map-section {
        max-width: 100%;
    }
}
.map-loading,
.map-fallback {
    position: absolute;
    inset: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: var(--font-size-content);
    color: var(--color-label);
    background: var(--color-readonly-bg);
    text-align: center;
    padding: var(--space-3);
}
.map-fallback {
    color: var(--color-readonly-text);
}
/* Row-highlight driven by map marker clicks. Uses existing brand-teal tint
   (same family as .row-selected) so visual language stays consistent. */
#scout-results-body tr.map-highlight {
    background: var(--brand-teal-light, #e6f7f5) !important;
    outline: 2px solid var(--brand-teal, #2BBCB3);
    outline-offset: -2px;
}
@media (max-width: 768px) {
    .map-container {
        height: 400px;
    }
    .map-container.map-pursuit {
        height: 260px;
    }
}
