/**
 * SAM Dashboard Styles
 * NCAR-themed custom styles for user and project dashboards
 *
 * Design tokens (CSS custom properties) are defined in variables.css,
 * which must be loaded before this file.
 */

/* ============================================================================
   GLOBAL STYLES
   ========================================================================= */

body {
    background-color: var(--surface-page);
    background-image: url('../img/UCAR-Waves-Lines-Only-66.png');
    background-position: 150% 0%;
    background-repeat: repeat-y;
    background-size: 53%;
    min-height: 100vh;
    font-family: var(--font-family-default);
    color: var(--text-primary);
}

/* ============================================================================
   NAVIGATION BAR
   ========================================================================= */

.navbar {
    background-color: var(--surface-navbar);
    padding-top: 0;
    padding-bottom: 0;
}

.navbar-light {
    background-color: var(--surface-navbar);
}

.navbar button {
    border: 0;
    padding: 0 0.5rem;
}

/* Override Bootstrap's stepped container-lg inside the navbar.
   Unity's container-lg is fluid until 86.25rem, then caps at 88.25rem.
   Bootstrap 5's default caps at 960px at 992px — far too narrow. */
.navbar .container-lg {
    max-width: 100%;
    padding-left: 0.75rem;
    padding-right: 0.75rem;
}

@media (min-width: 86.25rem) {
    .navbar .container-lg {
        max-width: 88.25rem;
    }
}

/* Logo */
.logo-ncar {
    width: 13rem;
}

.logo-ncar img {
    width: 100%;
}

@media (min-width: 768px) {
    .logo-ncar {
        width: 18.5rem;
    }
}

/* Site name */
.navbar .site-name {
    align-self: center;
    font-size: 0.875rem;
    font-weight: var(--font-weight-semi-bold);
    line-height: 1rem;
    padding-right: 1.875rem;
}

.navbar .site-name a {
    color: var(--text-link);
    text-decoration: none;
}

.navbar .site-name a:hover,
.navbar .site-name a:active {
    color: var(--text-link);
}

.site-name h1 {
    font-size: var(--font-size-xlg);
    font-weight: var(--font-weight-regular);
    line-height: 3rem;
    text-transform: uppercase;
    margin: 0;
}

.site-name h1 a {
    color: var(--text-heading);
    text-decoration: none;
}

.site-name h1 a:hover {
    color: var(--text-link);
}

/* Nav links (desktop-only row — mobile navigation is the offcanvas drawer) */
.navbar .nav-link {
    color: var(--text-heading);
    font-size: 1rem;
    line-height: 1.5rem;
}

.navbar .nav-link:hover,
.navbar .nav-link:focus {
    color: var(--text-link);
}

.navbar .nav-item {
    list-style: none;
}

/* Mobile toggler */
.mobile-toggler {
    max-width: 4rem;
}

.mobile-toggler button {
    padding: 1.6rem;
}

/* Utility menu (desktop) */
.utility-menu {
    font-size: 0.875rem;
    line-height: 1.35;
}

.utility-menu .nav-link {
    color: var(--text-heading);
    font-weight: var(--font-weight-semi-bold);
    padding: 0;
}

.utility-menu .nav-link:hover {
    color: var(--text-link);
}

/* Theme toggle — the light/dark switch in the utility menu, the mobile
   drawer and the login footer. A .btn-link that must not look like a link:
   no underline, no focus ring inherited from .btn, and it sits beside the
   user dropdown so it takes the same colour treatment. */
.theme-toggle {
    text-decoration: none;
    padding: 0;
    margin-right: 1rem;
    border: 0;
    line-height: inherit;
}

.theme-toggle:focus-visible {
    outline: 2px solid var(--ncar-blue);
    outline-offset: 2px;
}

.theme-toggle [data-theme-label] {
    margin-left: 0.375rem;
}

/* In the drawer and the login footer the control is a standalone row, not a
   navbar item, so it should not inherit .utility-menu's zero padding. */
.mobile-nav-footer .theme-toggle,
.login-footer .theme-toggle {
    font-weight: var(--font-weight-semi-bold);
}

/* Nav row border */
.navbar-wrapper.border-top {
    border-top-color: var(--border-default) !important;
}

/* The dropdown panels hanging off the navbar are already a navy brand surface
   with white text, so they are correct in both themes and must NOT inherit
   the dark theme's card surface. */
:root[data-bs-theme="dark"] .navbar .nav-item.dropdown .dropdown-menu {
    background-color: var(--ncar-navy);
}

.navbar .navbar-wrapper .container-lg {
    padding-top: 0.375rem;
    padding-bottom: 0.375rem;
}

/* Desktop — md breakpoint matches navbar-expand-md */
@media (min-width: 768px) {
    .navbar {
        box-shadow: 0 0.125rem 0.25rem rgba(0, 0, 0, 0.175);
    }

    .navbar .nav-item {
        border-bottom: 0;
        justify-content: center;
        width: auto;
        padding-right: 1.875rem;
    }

    .navbar .nav-item.dropdown {
        padding-right: 1.125rem;
    }

    /* Unity dropdown styling (ported from Kyle Davis's
       refactor/app-route-structure prototype): navy panel, white items,
       sky-blue hover, Font Awesome caret. Applies to both the section
       dropdowns (row 2) and the user-account dropdown (row 1). */
    .dropdown-header {
        border-bottom: 1px solid #000;
        font-size: 0.875rem;
        line-height: 1rem;
        text-transform: uppercase;
    }

    .navbar .nav-item.dropdown .dropdown-menu {
        --bs-dropdown-zindex: 1000;
        --bs-dropdown-min-width: 18.75rem;
        --bs-dropdown-padding-x: 0;
        --bs-dropdown-padding-y: 0.5rem;
        --bs-dropdown-spacer: 0.125rem;
        --bs-dropdown-font-size: 1rem;
        --bs-dropdown-color: #011837;
        --bs-dropdown-bg: #00357a;
        --bs-dropdown-border-color: var(--bs-border-color-translucent);
        --bs-dropdown-border-radius: 0;
        --bs-dropdown-border-width: 0;

        background-color: var(--ncar-navy);
        border: 1px solid rgba(255, 255, 255, 0.1);
        min-width: 18.75rem;
        margin: 0;
        box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15);
        border-radius: 0;
    }

    .navbar .dropdown-toggle::after {
        content: '\f107';
        font-family: 'Font Awesome 6 Free';
        font-weight: 900;
        border: 0;
        font-size: 0.75rem;
        margin-left: 0.5rem;
        vertical-align: middle;
    }

    .navbar .dropdown-toggle[aria-expanded="true"]::after {
        transform: rotate(180deg);
    }

    .navbar .nav-item.dropdown .dropdown-item {
        color: var(--text-on-brand);
        padding: 0.5rem 1rem;
        font-weight: 400;
        line-height: 1.313rem;
        white-space: normal;
    }

    .navbar .nav-item.dropdown .dropdown-item:hover,
    .navbar .nav-item.dropdown .dropdown-item:focus {
        background-color: transparent;
        color: var(--ncar-sky);
    }

    .navbar .nav-item.dropdown .dropdown-item.active {
        background-color: transparent;
        color: var(--text-on-brand);
        font-weight: var(--font-weight-semi-bold);
    }

    .navbar .nav-item.dropdown .dropdown-item.active:hover,
    .navbar .nav-item.dropdown .dropdown-item.active:focus {
        background-color: transparent;
        color: var(--ncar-sky);
    }

    /* Split caret button next to each section label. It's a .nav-link for
       color inheritance but must not pick up the label's active underline. */
    .navbar .nav-link.nav-caret {
        border: 0;
        background: none;
        padding: 0 0.25rem;
        cursor: pointer;
    }

    .navbar .nav-link.nav-caret::after {
        margin-left: 0;
    }

    .navbar .nav-link.nav-caret.active {
        border-bottom: 0;
        margin-bottom: 0;
    }

    .navbar .nav-link {
        padding: 0;
    }

    .navbar .nav-link.active {
        border-bottom: 0.1875rem solid var(--ncar-blue);
        margin-bottom: -0.1875rem;
        color: var(--text-heading);
    }

    .navbar .site-name {
        font-size: 1rem;
        line-height: 1.2rem;
    }

    .site-name h1 {
        font-size: var(--font-size-xsm);
        line-height: 1.2rem;
    }
}

/* ============================================================================
   MOBILE NAVIGATION DRAWER (offcanvas, < md)
   ========================================================================= */

.mobile-nav {
    width: 85vw;
    max-width: 20rem;
}

.mobile-nav .offcanvas-header {
    background-color: var(--ncar-navy);
}

.mobile-nav .offcanvas-title {
    color: var(--text-on-brand);
    font-size: 1rem;
}

.mobile-nav .btn-close {
    filter: invert(1) grayscale(100%) brightness(200%);
}

.mobile-nav .accordion-button {
    color: var(--text-heading);
    font-weight: var(--font-weight-semi-bold);
    padding: 0.875rem 1rem;
}

.mobile-nav .accordion-button:not(.collapsed) {
    background: none;
    color: var(--text-link);
    box-shadow: none;
}

.mobile-nav .accordion-button:focus {
    box-shadow: 0 0 0 0.2rem rgba(var(--ncar-blue-rgb), 0.2);
}

.mobile-nav .mobile-nav-link {
    display: block;
    padding: 0.625rem 1rem 0.625rem 1.75rem;
    color: var(--text-heading);
    text-decoration: none;
}

.mobile-nav .mobile-nav-link:hover,
.mobile-nav .mobile-nav-link:focus {
    color: var(--text-link);
}

.mobile-nav .mobile-nav-link.active {
    color: var(--text-link);
    font-weight: var(--font-weight-semi-bold);
    border-left: 3px solid var(--ncar-blue);
    background-color: rgba(var(--ncar-blue-rgb), 0.06);
}

.mobile-nav-footer a {
    color: var(--text-link);
}

/* ============================================================================
   BREADCRUMBS (dashboards/fragments/breadcrumbs.html) — compact, muted trail
   above the page header. Replaces the old .back-link buttons.
   ========================================================================= */

.sam-breadcrumbs {
    margin-bottom: 0.75rem;
}

.sam-breadcrumbs .breadcrumb {
    font-size: 0.875rem;
}

.sam-breadcrumbs .breadcrumb-item a {
    color: var(--text-link);
    text-decoration: none;
}

.sam-breadcrumbs .breadcrumb-item a:hover {
    text-decoration: underline;
}

.sam-breadcrumbs .breadcrumb-item.active {
    color: var(--bs-secondary-color);
}

/* ============================================================================
   MOBILE COMPACTION (< md) — this is a data-heavy site; the goal is
   "better", not mobile perfection. Unity's CTA-scale buttons and desktop
   heading sizes read comically large on phones; page-header flex rows must
   be allowed to wrap so action buttons stack under the title.
   ========================================================================= */

@media (max-width: 767.98px) {
    .btn {
        font-size: 1rem;
        line-height: 1.25rem;
        padding: 0.5rem 1rem;
    }

    /* Brand row must actually fit a phone: at the desktop sizes
       (13rem logo + site name + 1.6rem-padded hamburger) the header row
       exceeded the viewport and forced document-level horizontal scroll —
       the root cause of the old "menu opens and the page shifts" bug. */
    .logo-ncar {
        width: 9.5rem;
        flex-shrink: 0;
    }

    .navbar .site-name {
        font-size: 0.875rem;
        line-height: 1.1rem;
        min-width: 0;
    }

    .mobile-toggler button {
        padding: 0.875rem 0.75rem;
    }

    .main-content h1,
    .main-content .h1 {
        font-size: 1.5rem;
        line-height: 2rem;
    }

    /* Page headers (h1 + action buttons) wrap instead of squeezing. */
    .main-content > .d-flex,
    .main-content .container-fluid > .d-flex {
        flex-wrap: wrap;
        gap: 0.5rem;
    }

    /* Preset button strips (time-range pickers etc.) wrap instead of
       forcing document-level horizontal scroll. */
    .main-content .btn-group {
        flex-wrap: wrap;
    }

    /* Any utility flex row wraps rather than squeezing or overflowing the
       viewport: card headers with action buttons ("Search Projects" +
       "Create Project"), tab-pane toolbars (date picker + Extend/Renew/Add
       on Manage Project), etc. flex-wrap only engages when the row would
       otherwise overflow, so fitting rows are untouched. Deliberately broad
       — the precise per-container list kept growing (see #359's page-header
       rule above, now one instance of this). Vertical stacks are excluded:
       wrapping a flex-column makes align-items:stretch size children to
       fit-content, which lets an inner table blow the card out to its
       intrinsic width. */
    .main-content .d-flex:not(.flex-column) {
        flex-wrap: wrap;
    }

    .card-header.d-flex {
        flex-wrap: wrap;
        gap: 0.5rem;
    }

    /* Tab strips scroll horizontally by design; fade the right edge as a
       "more tabs off-screen" affordance. Purely cosmetic — 2.5rem is narrow
       enough not to obscure a strip that happens to fit exactly. */
    .nav-tabs {
        mask-image: linear-gradient(to right, #000 calc(100% - 2.5rem), transparent);
        -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 2.5rem), transparent);
    }

    /* Tap targets: expandable drill-down rows and sortable column headers
       are finger-hostile at desktop padding. */
    .expandable-row td {
        padding-top: 0.625rem;
        padding-bottom: 0.625rem;
    }

    .main-content table.table th a {
        display: inline-block;
        padding: 0.25rem 0;
    }

    /* Slightly smaller table type on phones: trades a notch of size for a
       lot less horizontal scrolling on data-heavy tables. */
    .main-content .table {
        font-size: 0.8125rem;
    }
}

/* Below lg (phones AND portrait tablets — the widest data tables exceed even
   an iPad's 820px): any table not already inside a .table-responsive scroller
   gets its own horizontal scrollbox instead of widening the document. The
   child-combinator guard leaves deliberately-wrapped tables (allocations
   summary, admin access-grid with its sticky column) untouched. Known
   tradeoff of display:block — a table narrower than the screen no longer
   stretches to full width. */
@media (max-width: 991.98px) {
    .main-content :not(.table-responsive) > table.table {
        display: block;
        overflow-x: auto;
    }
}

/* ============================================================================
   MAIN CONTENT
   ========================================================================= */

.main-content {
    padding: 0.5rem 0;
    /* Reserve viewport space for header (136px) + footer margin (50px) + footer
       (~99px) = 285px. Previously 200px, which left ~85px of always-on overflow
       and a noisy scrollbar on otherwise-fitting pages like /admin/. */
    min-height: calc(100vh - 285px);
}

@media (min-width: 64rem) {
    .main-content {
        padding-top: 1.875rem;
    }
}

/* ============================================================================
   HEADINGS — Unity NCAR typography. Sizes/weights/line-heights match Unity's
   responsive scale. h1/h2 use ncar-navy in main content; h3-h6 inherit body.
   ========================================================================= */

h1, .h1 { font-size: 1.875rem; line-height: 2.625rem; font-weight: var(--font-weight-semi-bold); }
h2, .h2 { font-size: 1.25rem;  line-height: 1.875rem; font-weight: var(--font-weight-semi-bold); }
h3, .h3 { font-size: 1.125rem; line-height: 1.875rem; font-weight: var(--font-weight-semi-bold); }
h4, .h4 { font-size: 1rem;     line-height: 1.5rem;   font-weight: var(--font-weight-semi-bold); }
h5, .h5 { font-size: 0.875rem; line-height: 1.35;     font-weight: var(--font-weight-semi-bold); }
h6, .h6 { font-size: 0.875rem; line-height: 1.35;     font-weight: var(--font-weight-semi-bold); }

@media (min-width: 64rem) {
    h1, .h1 { font-size: 3rem;     line-height: 3.75rem;  font-weight: var(--font-weight-bold); }
    h2, .h2 { font-size: 2.25rem;  line-height: 3rem;     font-weight: var(--font-weight-bold); }
    h3, .h3 { font-size: 1.875rem; line-height: 2.625rem; }
    h4, .h4 { font-size: 1.5rem;   line-height: 2.25rem; }
    h5, .h5 { font-size: 1.25rem;  line-height: 1.875rem; }
    h6, .h6 { font-size: 1.125rem; line-height: 1.875rem; }
}

.main-content h1,
.main-content h2 {
    color: var(--text-title);
}

.page-header {
    margin-bottom: 1.875rem;
    padding-bottom: 1.25rem;
    border-bottom: 3px solid var(--ncar-blue);
}

.page-header p {
    color: var(--text-tertiary);
    font-size: 1rem;
}

/* ============================================================================
   ACCORDION — Bootstrap CSS variable overrides to match Unity NCAR tokens
   ========================================================================= */

.accordion {
    --bs-accordion-color: var(--text-heading);
    --bs-accordion-btn-color: var(--text-heading);
    --bs-accordion-active-color: var(--text-on-brand);
    --bs-accordion-active-bg: rgba(var(--ncar-blue-rgb), 0.1);
    --bs-accordion-btn-focus-border-color: var(--ncar-blue);
    --bs-accordion-btn-focus-box-shadow: 0 0 0 0.25rem rgba(var(--ncar-blue-rgb), 0.25);
    /* Chevron icon filled with space-blue for collapsed state */
    --bs-accordion-btn-icon: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23011837'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e");
    /* Chevron icon filled with white for expanded state */
    --bs-accordion-btn-active-icon: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23fff'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e");
}

/* The collapsed-state chevron is a data-URI SVG with `fill='%23011837'`
   baked in — space blue, invisible on a dark card. A data URI cannot
   reference a CSS variable, so the only options are a second URI or an SVG
   filter; a second URI is the honest one. (The *expanded* chevron is already
   white and sits on an --ncar-blue fill, so it is correct in both themes.) */
:root[data-bs-theme="dark"] .accordion {
    --bs-accordion-btn-icon: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%23e8eef7'%3e%3cpath fill-rule='evenodd' d='M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z'/%3e%3c/svg%3e");
}

.accordion-button:not(.collapsed) {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
}

/* ============================================================================
   CARDS
   ========================================================================= */

.card {
    /* Override Bootstrap card vars to match Unity's flat editorial style.
       No border, no shadow — cards are just padded content blocks. */
    --bs-card-spacer-y: 1.875rem;
    --bs-card-spacer-x: 1.875rem;
    --bs-card-border-radius: 0;
    --bs-card-inner-border-radius: 0;
    --bs-card-border-width: 0;
    --bs-card-color: var(--text-heading);
    --bs-card-bg: var(--surface-card);
    --bs-card-cap-padding-y: 0.9375rem;
    --bs-card-cap-padding-x: 1.875rem;
    --bs-card-cap-bg: var(--surface-card);
    margin-bottom: 1.5rem;
}

.inner-card {
    padding: 1.875rem;
}

.inner-card > .card-header {
    padding: 0 !important;
    font-weight: var(--font-weight-semi-bold);
    color: var(--text-heading);
}

.inner-card > .card-header h5 {
    font-size: 1rem;
    font-weight: 600;
    line-height: 1;
    text-transform: uppercase;
    color: var(--text-title);
}

.inner-card > .card-body {
    padding: 0;
}

.inner-card p {
    font-size: 1.125rem;
    line-height: 1.875rem;
}

/* Opt-in modifier: a card with a visible 1px hairline border. Use when a
   card needs to read as a self-contained panel (e.g. wrapping a chart or
   a contacts list). Matches Unity's bordered editorial card look. */
.card-bordered {
    --bs-card-border-width: 1px;
    border-color: var(--ncar-gray-light);
}

.card-header h5 {
    color: var(--text-heading);
    font-weight: var(--font-weight-semi-bold);
    margin: 0;
}

.inner-card {
    border: 1px solid var(--ncar-blue);
    box-shadow: none !important;
}

/* ============================================================================
   BUTTONS — Unity NCAR style: flat (0 radius), bold (700), 3px border,
   inverting hover (filled ↔ outlined). Uses Bootstrap btn CSS variables.
   ========================================================================= */

.btn {
    --bs-btn-font-weight: var(--font-weight-bold);
    --bs-btn-border-width: 3px;
    --bs-btn-border-radius: 0;
    --bs-btn-box-shadow: none;
    text-transform: uppercase;
    letter-spacing: 0.05rem;
    line-height: 24px;
    font-size: 1.25rem;
    padding: .75rem 1.5rem;
}

/* Identifiers inside a button render in the case they're stored in: the
   uppercase treatment above is right for button *labels* but wrong for a
   name the user has to match against a shell prompt or a ticket. It also
   erases the convention that tells the two apart at a glance — projcodes
   are uppercase (SCSG0001), usernames lowercase (benkirk) — which the
   entity quick-view links on the job-history tables and histogram
   drill-downs lean on. Covers both spellings in use: <code> and
   .font-monospace. */
.btn code,
.btn .font-monospace {
    text-transform: none;
}

.btn-primary {
    --bs-btn-bg: var(--ncar-blue);
    --bs-btn-border-color: var(--ncar-blue);
    --bs-btn-color: var(--text-on-brand);
    --bs-btn-hover-bg: transparent;
    --bs-btn-hover-border-color: var(--ncar-blue);
    --bs-btn-hover-color: var(--text-link);
    --bs-btn-active-bg: var(--ncar-blue);
    --bs-btn-active-border-color: var(--ncar-blue);
    --bs-btn-active-color: var(--text-on-brand);
}

.btn-outline-primary {
    --bs-btn-color: var(--text-link);
    --bs-btn-border-color: var(--ncar-blue);
    --bs-btn-hover-bg: var(--ncar-blue);
    --bs-btn-hover-border-color: var(--ncar-blue);
    --bs-btn-hover-color: var(--text-on-brand);
    --bs-btn-active-bg: var(--ncar-blue);
    --bs-btn-active-border-color: var(--ncar-blue);
    --bs-btn-active-color: var(--text-on-brand);
}

.btn-outline-secondary {
    --bs-btn-color: var(--text-title);
    --bs-btn-border-color: var(--ncar-navy);
    --bs-btn-hover-bg: var(--ncar-navy);
    --bs-btn-hover-border-color: var(--ncar-navy);
    --bs-btn-hover-color: var(--text-on-brand);
}

/* Unity .btn-outline-white — for buttons on dark/navy backgrounds (e.g.
   inside .filter-sidebar). White outline, transparent fill; hover dims to
   a translucent white wash matching Unity's exact spec (not a full invert). */
.btn-outline-white {
    --bs-btn-color: var(--text-on-brand);
    --bs-btn-border-color: #fff;
    --bs-btn-bg: transparent;
    --bs-btn-hover-bg: rgba(255, 255, 255, 0.1);
    --bs-btn-hover-border-color: #fff;
    --bs-btn-hover-color: var(--text-on-brand);
    --bs-btn-active-bg: rgba(255, 255, 255, 0.1);
    --bs-btn-active-border-color: #fff;
    --bs-btn-active-color: var(--text-on-brand);
}

/* Unity-style :disabled — transparent fill, transparent 3px border (keeps
   the button's footprint so layout doesn't shift / nothing visually
   disappears), gray text. opacity:1 overrides Bootstrap's default .65 fade.
   Mirrors source/scss/_theme-colors.scss .ncar .btn-primary:disabled but
   keeps the border slot so it reads as "available shape, just inert". */
.btn-primary:disabled,
.btn-primary[disabled],
.btn-outline-primary:disabled,
.btn-outline-primary[disabled],
.btn-outline-secondary:disabled,
.btn-outline-secondary[disabled] {
    background-color: transparent !important;
    border-color: transparent !important;
    color: var(--text-tertiary) !important;
    opacity: 1;
}

.btn-link {
    --bs-btn-color: var(--text-link);
    --bs-btn-hover-color: var(--ncar-sky);
    text-decoration: none;
}

.btn-link:hover {
    text-decoration: underline;
}

.btn.btn-sm,
.btn-group-sm > .btn {
    line-height: 18px;
    font-size: 0.95rem;
    padding: 0.45rem 0.9rem;
}

.btn-group-sm > .btn {
    --bs-btn-border-width: 2px;
    line-height: 18px;
    font-size: 0.95rem;
    padding: 0.45rem 0.9rem;
}

.btn-group-sm > .btn:not(:first-child) {
    margin-left: calc(-1 * var(--bs-btn-border-width));
}

/* Unity NCAR defines only .btn-primary and .btn-outline-primary. Other
   semantic variants (.btn-success/.btn-danger/.btn-warning/.btn-info) are
   intentionally NOT styled here — templates should use btn-primary for
   positive actions and btn-outline-primary for destructive/informational
   actions instead. */

/* Toggle button groups (.btn-group with .btn-secondary / .btn-outline-secondary
   pair, used by time_range_picker, date_range_picker, system_user_proj_chart_card,
   and other quick-select preset rows). Match the Unity .nav-tabs invert pattern:
   inactive = solid NCAR-blue, active = white with blue text. Scoped to .btn-group
   so non-group .btn-secondary uses (modal Cancel, queue_history Back) keep their
   existing treatments. The active vars also cover .btn-check radio toggles
   (create-project projcode mode), which Bootstrap styles via
   .btn-check:checked + .btn → --bs-btn-active-*. */
.btn-group .btn-outline-secondary {
    --bs-btn-bg: var(--ncar-blue);
    --bs-btn-border-color: var(--ncar-blue);
    --bs-btn-color: var(--text-on-brand);
    --bs-btn-hover-bg: var(--ncar-navy);
    --bs-btn-hover-border-color: var(--ncar-navy);
    --bs-btn-hover-color: var(--text-on-brand);
    --bs-btn-active-bg: var(--surface-card);
    --bs-btn-active-border-color: var(--ncar-blue);
    --bs-btn-active-color: var(--text-link);
}

.btn-group .btn-secondary,
.btn-group .btn-secondary.active,
.btn-group .btn-secondary:active {
    --bs-btn-bg: var(--surface-card);
    --bs-btn-border-color: var(--ncar-blue);
    --bs-btn-color: var(--text-link);
    --bs-btn-hover-bg: rgba(var(--ncar-teal-rgb), 0.08);
    --bs-btn-hover-border-color: var(--ncar-blue);
    --bs-btn-hover-color: var(--text-link);
    --bs-btn-active-bg: var(--surface-card);
    --bs-btn-active-border-color: var(--ncar-blue);
    --bs-btn-active-color: var(--text-link);
}

/* Unity-style focus ring on interactive button-like elements — upstream
   uses box-shadow 0 0 0 .2rem rgba(ncar-blue, .2) across .btn and .nav-link.
   Replaces Bootstrap's default outline so the ring matches palette. */
.btn:focus,
.btn:focus-visible,
.nav-tabs .nav-link:focus-visible {
    box-shadow: 0 0 0 0.2rem rgba(var(--ncar-blue-rgb), 0.2);
    outline: none;
}

/* ============================================================================
   FOOTER
   ========================================================================= */

.footer {
    background: linear-gradient(135deg, var(--surface-tertiary) 0%, var(--surface-secondary) 100%);
    padding: 24px 0;
    margin-top: 50px;
    border-top: 3px solid var(--ncar-blue);
}

.footer small {
    color: var(--text-tertiary);
    font-weight: var(--font-weight-semi-bold);
}

/* ============================================================================
   PROGRESS BARS
   ========================================================================= */

.progress {
    height: 28px;
    border-radius: var(--radius-md);
    background-color: var(--surface-secondary);
    box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
}

.progress-bar {
    font-size: 14px;
    font-weight: 700;
    line-height: 28px;
    border-radius: var(--radius-md);
    transition: width var(--transition-base);
}

/* The percentage label sits ON the fill, and two of the four fills are light:
 * white on --success-color measured 2.54:1 and on --warning-color 2.15:1.
 * Theme-invariant (the fills are), so this was equally unreadable in light and
 * is a declared legibility fix in both rather than a dark-mode repair — the
 * browser sweep does not distinguish, and neither does a reader. Scoped to
 * `.progress-bar` so the same utility classes keep white ink on badges. */
.progress-bar.bg-success,
.progress-bar.bg-warning {
    color: var(--text-on-brand-dark);
}

/* Progress bar color variants */
.bg-success {
    background-color: var(--success-color) !important;
}

.bg-info {
    background-color: var(--info-color) !important;
}

.bg-warning {
    background-color: var(--warning-color) !important;
}

.bg-danger {
    background-color: var(--danger-color) !important;
}

/* ============================================================================
   STATUS BADGES
   ========================================================================= */

.badge {
    padding: 6px 12px;
    font-size: 0.75rem;
    font-weight: 700;
    border-radius: var(--radius-sm);
    letter-spacing: 0.3px;
}

/* Note: the hyphenated `.badge-success` / `.badge-primary` / etc. variants
   were intentionally removed — no template uses them (every callsite uses
   the Bootstrap `.badge.bg-X` utility form). The live badge palette is the
   subtle Bootstrap 5.3 .bg-X-bg-subtle override applied lower in this file. */

/* ============================================================================
   LOADING SPINNER
   ========================================================================= */

.loading-spinner {
    display: flex;
    justify-content: center;
    align-items: center;
    min-height: 200px;
}

.spinner-border-primary {
    color: var(--text-link) !important;
}

.htmx-indicator {
    display: none;
}

.htmx-request .htmx-indicator {
    display: inline-block;
}

.htmx-request.htmx-indicator {
    display: inline-block;
}

/* ============================================================================
   TABLES
   ========================================================================= */

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

.table thead th {
    border-bottom: 2px solid var(--ncar-blue);
    color: var(--text-title);
    font-weight: 700;
    text-transform: uppercase;
    font-size: 0.85rem;
    letter-spacing: 0.5px;
}

/* Theme-aware replacement for Bootstrap's .table-light.
 *
 * `.table-light` hardcodes `--bs-table-bg:#f8f9fa` and `--bs-table-color:#000`,
 * and Bootstrap's `[data-bs-theme=dark]` block does NOT redefine
 * `--bs-light-rgb` or any of the `.table-*` variants — so every one of them
 * stays light on a dark page. There is no stock class that flips; a SAM class
 * driven by tier-2 tokens is the only option that does.
 *
 * Values chosen to match `.table-light` exactly in light mode:
 * `--surface-tertiary` IS #f8f9fa. The colour is `--text-primary` rather than
 * Bootstrap's `#000`, matching the rest of the app's body copy.
 *
 * Used on `<thead>` (the common case), and on the `<tr>`/`<tfoot>` rows that
 * want the same recessed treatment. */
.table-subtle {
    --bs-table-bg: var(--surface-tertiary);
    --bs-table-color: var(--text-primary);
    --bs-table-border-color: var(--border-default);
    --bs-table-striped-bg: var(--surface-secondary);
    --bs-table-striped-color: var(--text-primary);
    --bs-table-active-bg: var(--surface-secondary);
    --bs-table-active-color: var(--text-primary);
    --bs-table-hover-bg: var(--surface-secondary);
    --bs-table-hover-color: var(--text-primary);
    color: var(--bs-table-color);
    border-color: var(--bs-table-border-color);
}

/* The OTHER five contextual table variants, in dark mode only.
 *
 * `.table-subtle` above replaced `.table-light` and stopped there; the same
 * defect applies verbatim to `.table-primary` / `-secondary` / `-info` /
 * `-warning` / `-danger` / `-success`, which are used on 24 rows across 11
 * templates. Both halves of the stock class bite, and they bite independently:
 *
 *   --bs-table-bg    a light tint. The `/admin/resources` nested rows
 *                    (#e2e3e5) and the resource-details month row (#cfe2ff),
 *                    which put a `.text-muted` chevron at 1.01:1.
 *   --bs-table-color #000. Survives on its own wherever a SAM rule already
 *                    supplies a dark background — that is the black "Total"
 *                    row in the `/allocations/projects` facility table, whose
 *                    <th> cells were already painting --surface-secondary.
 *
 * Deviation from the `.table-subtle` precedent, which migrated its call sites
 * onto a SAM class: these keep the stock class name at the call site because
 * the tint is load-bearing there in a way `.table-light` on a <thead> never
 * was — project_directories_card.html marks an orphaned row `table-warning`
 * *inside* a `table-secondary` table, and that reads at a glance. Overriding
 * in a dark-only block also leaves light mode byte-identical by construction.
 *
 * `-secondary` is the group-header / subtotal row, so it takes SAM's recess
 * (--surface-secondary, LIGHTER than the card — the dark ladder inverts)
 * rather than Bootstrap's --bs-secondary-bg-subtle, which is #161719 and would
 * make a header darker than the surface it sits on. The five that carry a hue
 * take Bootstrap's `-bg-subtle` palette, which does retheme itself — the same
 * lever status.css:17 uses for the status badges — because for those the hue
 * IS the message. All six take --text-primary rather than the stock #000 or
 * the `-text-emphasis` tint, matching .table-subtle and the app's body copy. */
:root[data-bs-theme="dark"] .table-secondary {
    --bs-table-bg: var(--surface-secondary);
    --bs-table-striped-bg: var(--surface-raised);
    --bs-table-active-bg: var(--surface-raised);
    --bs-table-hover-bg: var(--surface-raised);
}

:root[data-bs-theme="dark"] .table-primary {
    --bs-table-bg: var(--bs-primary-bg-subtle);
    --bs-table-striped-bg: var(--bs-primary-bg-subtle);
    --bs-table-active-bg: var(--bs-primary-border-subtle);
    --bs-table-hover-bg: var(--bs-primary-border-subtle);
}

:root[data-bs-theme="dark"] .table-info {
    --bs-table-bg: var(--bs-info-bg-subtle);
    --bs-table-striped-bg: var(--bs-info-bg-subtle);
    --bs-table-active-bg: var(--bs-info-border-subtle);
    --bs-table-hover-bg: var(--bs-info-border-subtle);
}

:root[data-bs-theme="dark"] .table-warning {
    --bs-table-bg: var(--bs-warning-bg-subtle);
    --bs-table-striped-bg: var(--bs-warning-bg-subtle);
    --bs-table-active-bg: var(--bs-warning-border-subtle);
    --bs-table-hover-bg: var(--bs-warning-border-subtle);
}

:root[data-bs-theme="dark"] .table-success {
    --bs-table-bg: var(--bs-success-bg-subtle);
    --bs-table-striped-bg: var(--bs-success-bg-subtle);
    --bs-table-active-bg: var(--bs-success-border-subtle);
    --bs-table-hover-bg: var(--bs-success-border-subtle);
}

:root[data-bs-theme="dark"] .table-danger {
    --bs-table-bg: var(--bs-danger-bg-subtle);
    --bs-table-striped-bg: var(--bs-danger-bg-subtle);
    --bs-table-active-bg: var(--bs-danger-border-subtle);
    --bs-table-hover-bg: var(--bs-danger-border-subtle);
}

/* The colour half, shared. Separate from the per-variant blocks above so the
 * one thing every variant gets wrong the same way is stated once. */
:root[data-bs-theme="dark"] :is(.table-primary, .table-secondary, .table-success,
                                .table-info, .table-warning, .table-danger) {
    --bs-table-color: var(--text-primary);
    --bs-table-striped-color: var(--text-primary);
    --bs-table-active-color: var(--text-primary);
    --bs-table-hover-color: var(--text-primary);
    --bs-table-border-color: var(--border-default);
    color: var(--bs-table-color);
    border-color: var(--bs-table-border-color);
}

.table-hover tbody tr:hover {
    background-color: rgba(var(--ncar-teal-rgb), 0.05);
}

.table-bordered {
    border: 1px solid var(--border-default);
}

.table-bordered th,
.table-bordered td {
    border: 1px solid var(--border-default);
}

.table-sm th,
.table-sm td {
    padding: 0.5rem;
}

/* Clickable table rows */
.resource-row {
    cursor: pointer;
    transition: all var(--transition-fast);
}

.resource-row:hover {
    background-color: rgba(var(--ncar-teal-rgb), 0.08) !important;
    transform: scale(1.01);
}

/* Date-bounds group header row in resources table */
.date-group-header td {
    background-color: var(--surface-tertiary);
    border-top: 2px solid var(--border-default) !important;
}

/* ============================================================================
   ALERTS
   ========================================================================= */

/* Unity flat-fill treatment (source/scss/components/_alerts.scss): solid
   color fill, no border, no left accent, 0 radius. Color carries the
   semantic; text auto-picks for legibility. Info kept as NCAR blue rather
   than Unity's literal yellow — most users expect info=blue, yellow reads
   as warning. */
.alert {
    border: 0;
    border-radius: 0;
    box-shadow: none;
    color: var(--text-heading);
    padding: 0.875rem 1rem;
}

.alert a,
.alert button {
    color: var(--text-heading);
    text-decoration: underline;
    font-weight: var(--font-weight-semi-bold);
}

.alert a:hover,
.alert button:hover {
    color: var(--text-title);
}

.alert-info {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
}

.alert-info a,
.alert-info button {
    color: var(--text-on-brand);
}

/* The one alert whose fill is LIGHT, so it is the one that cannot take
 * `--text-on-brand`. It used `--text-heading`, which is space-blue in light and
 * near-white in dark — 1.77:1 on orange, found by the browser sweep on the
 * /status outage banner. `--text-on-brand-dark` IS that space-blue, pinned
 * invariant: light mode does not move, dark stops inheriting a flipped token
 * onto a fill that never flips. */
.alert-warning {
    background-color: var(--ncar-orange);
    color: var(--text-on-brand-dark);
}

.alert-warning a,
.alert-warning button {
    color: var(--text-on-brand-dark);
}

/* Descendants that set their own colour have the same problem one level down:
 * `.text-muted` inside the outage banner resolved to rgba(222,226,230,.75),
 * i.e. 1.39:1 on orange. Inheriting the alert's ink and de-emphasising with
 * opacity keeps the "muted" intent without reintroducing a theme-dependent
 * colour on an invariant fill.
 *
 * `!important` because Bootstrap's colour utilities carry it — a plain
 * declaration here loses to `.text-muted` regardless of specificity, which is
 * how the first pass at this silently did nothing. */
.alert .text-muted {
    color: inherit !important;
    opacity: 0.8;
}

.alert-danger {
    background-color: var(--ncar-vermilion);
    color: var(--text-on-brand);
}

.alert-danger a,
.alert-danger button {
    color: var(--text-on-brand);
}

.alert-success {
    background-color: #10b981;
    color: var(--text-on-brand);
}

.alert-success a,
.alert-success button {
    color: var(--text-on-brand);
}

/* ============================================================================
   MODALS — Unity NCAR style. The HTMX modal system (modal_scaffold +
   htmx_form macros) predates the Unity restyle, so templates still emit
   Bootstrap utility classes (bg-success/warning/danger/primary/secondary on
   .modal-header, .btn-secondary on Cancel). The rules below repaint those
   to NCAR palette tokens, flatten the surface, and scope a Cancel-button
   restyle to .modal-footer so toggle groups using .btn-secondary elsewhere
   stay untouched. CSS-only — no template edits needed.
   ========================================================================= */

.modal-content {
    border-radius: 0;
    border: 1px solid var(--ncar-gray-light);
    box-shadow: var(--shadow-md);
}

/* Create variant + hand-coded bg-primary (e.g. user/allocation_modals.html). */
.modal-header.bg-success,
.modal-header.bg-primary {
    background-color: var(--ncar-blue) !important;
    color: var(--text-on-brand);
    border-bottom: none;
}

/* Edit variant — darker palette blue, subtle UX cue for modifying existing data. */
.modal-header.bg-warning {
    background-color: var(--ncar-navy) !important;
    color: var(--text-on-brand);
    border-bottom: none;
}

/* Destructive confirmation (samConfirmModal, outage delete). */
.modal-header.bg-danger {
    background-color: var(--ncar-vermilion) !important;
    color: var(--text-on-brand);
    border-bottom: none;
}

/* Neutral variant (one outage_modals case). */
.modal-header.bg-secondary {
    background-color: var(--ncar-gray) !important;
    color: var(--text-on-brand);
    border-bottom: none;
}

/* bg-success/danger/primary already get .btn-close-white from the template;
   bg-warning + bg-secondary headers don't, so invert the close button on those
   two so it's legible against the dark fill. */
.modal-header.bg-warning .btn-close,
.modal-header.bg-secondary .btn-close {
    filter: invert(1) grayscale(100%) brightness(200%);
}

.modal-title {
    font-size: 1.125rem;
    font-weight: var(--font-weight-semi-bold);
    letter-spacing: 0.02em;
}

.modal-header {
    padding: 0.875rem 1.25rem;
}

.modal-footer {
    border-top: 1px solid var(--ncar-gray-light);
    padding: 0.875rem 1.25rem;
}

/* Cancel button — scoped to .modal-footer so .btn-secondary used as a toggle
   active-state in time-range / date-range pickers stays Bootstrap-stock. */
.modal-footer .btn-secondary {
    --bs-btn-bg: transparent;
    --bs-btn-border-color: var(--border-default);
    --bs-btn-color: var(--text-title);
    --bs-btn-hover-bg: var(--ncar-navy);
    --bs-btn-hover-border-color: var(--ncar-navy);
    --bs-btn-hover-color: var(--text-on-brand);
    --bs-btn-active-bg: var(--ncar-navy);
    --bs-btn-active-border-color: var(--ncar-navy);
    --bs-btn-active-color: var(--text-on-brand);
}

/* ============================================================================
   TABS — Unity NCAR style: inactive = solid blue, active = white with blue text
   Mirrors Unity's cascade: base color set first, :not(.active) overrides inactive.
   ========================================================================= */

/* Pills — same white-is-active convention as .nav-tabs below and the
   .btn-group selector rows above, at the lighter rounded-pill weight.
   Pills carry the machine / filesystem / chart-series choosers (jobs and
   filesystem-scan subtabs, the allocations pie tabs, the allocation-tree
   resource types); they used to run blue-is-active, which read backwards
   next to every other selector on the same page.

   Bootstrap 5 exposes custom properties for the ACTIVE pill only, so the
   inactive treatment needs the explicit :not(.active) rules — mirroring
   how .nav-tabs is written. */
.nav-pills {
    --bs-nav-link-color: var(--text-link);
    --bs-nav-link-hover-color: var(--text-title);
    --bs-nav-pills-link-active-color: var(--text-link);
    --bs-nav-pills-link-active-bg: var(--surface-card);
}

.nav-pills .nav-link:not(.active) {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
}

.nav-pills .nav-link:not(.active):hover {
    background-color: var(--ncar-navy);
    color: var(--text-on-brand);
}

/* Counter badges sit inside pills whose background flips with state, so they
   have to flip too — a stock .bg-light badge vanishes on the white active
   pill. Both declarations need !important: the background beats .badge.bg-X
   (same as the tinted badge palette further down this file) and the color
   beats the .text-dark / .text-* utilities, which Bootstrap ships as
   !important. Callers therefore don't have to strip those utilities off
   badges they drop into a pill. */
.nav-pills .nav-link:not(.active) .badge {
    background-color: var(--surface-on-brand) !important;
    color: var(--text-link) !important;
}

.nav-pills .nav-link.active .badge {
    background-color: var(--ncar-blue) !important;
    color: var(--text-on-brand) !important;
}

.nav-tabs {
    border-bottom: 0;
    /* Never wrap to a second row — horizontal scroll if necessary. Explicitly
       clamp overflow-y to hidden: setting only overflow-x:auto causes the
       browser to also force overflow-y:auto (CSS spec quirk — the orthogonal
       axis can't stay `visible` when one axis is scrollable), which produces
       a stray 1px vertical scrollbar from sub-pixel layout rounding. */
    flex-wrap: nowrap;
    overflow-x: auto;
    overflow-y: hidden;
}

.nav-tabs .nav-item {
    flex-shrink: 0;
    font-size: 1rem !important;
    font-weight: 600;
    color: var(--text-link);
}

/* When tabs are followed by tab-content, kill any mb-* utility margin so the
   active tab attaches seamlessly to the panel below. !important matches
   Bootstrap utility specificity. */
.nav-tabs:has(+ .tab-content) {
    margin-bottom: 0 !important;
}

/* Bootstrap's .card-header-tabs pulls the strip down over the header's cap
   padding with a negative bottom margin — correct only when the tabs are the
   header's LAST child. The usage card puts a custom date-range row after
   them, and that negative margin dropped the tab bottoms ~16px into a ~30px
   row, overlapping the range readout by half. Reset it whenever something
   follows; the seamless-attach case above is unaffected because tab-content
   is a sibling of the strip, not part of the header. */
.card-header-tabs:not(:last-child) {
    margin-bottom: 0;
}

.nav-tabs .nav-link {
    color: var(--text-link);
    font-weight: var(--font-weight-semi-bold);
    background-color: var(--surface-card);
    border: none;
    border-radius: 0;
    padding: 1.125rem 1.875rem;
    transition: background-color var(--transition-base), color var(--transition-base);
}

.nav-tabs .nav-link:not(.active) {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
}

.nav-tabs .nav-link:not(.active):hover {
    background-color: var(--ncar-navy);
    color: var(--text-on-brand);
    border-color: transparent;
}

.nav-tabs .nav-link.active {
    color: var(--text-link);
    background-color: var(--surface-card);
    border: none;
}

/* Tab content panel — flat white surface attached to .nav-tabs above, matching
   Unity's seamless tab→panel transition. No borders — content just flows. */
.tab-content {
    background-color: var(--surface-card);
    padding: 1.25rem;
}

/* ============================================================================
   JOB FACET CHIPS — the live value-count strip between the jobs explorer's
   filter panel and its tab strip (_jobs_facet_chips.html).

   One grid row per dimension: the label column self-sizes to the widest
   label and the values wrap inside their own cell, so "Exit code" can
   never end up mid-line with its chips orphaned under "QoS". White
   surface with the bottom edge open, so the strip reads as the top of the
   card the .nav-tabs below continue.
   ========================================================================= */

.jobs-facets {
    display: grid;
    grid-template-columns: max-content minmax(0, 1fr);
    column-gap: 0.75rem;
    row-gap: 0.375rem;
    align-items: baseline;
    padding: 0.625rem 0.875rem;
    background-color: var(--surface-card);
    border: 1px solid var(--border-default);
    border-bottom: 0;
}

.jobs-facet-label {
    justify-self: end;
    white-space: nowrap;
    font-size: 0.75rem;
    font-weight: var(--font-weight-semi-bold);
    letter-spacing: 0.04em;
    text-transform: uppercase;
    color: var(--text-tertiary);
}

.jobs-facet-values {
    display: flex;
    flex-wrap: wrap;
    gap: 0.25rem;
}

/* Deliberately not a .btn. The Unity button treatment above (uppercase,
   700 weight, 3px border, 1.25rem type) is right for an action and far
   too loud for two dozen read-mostly value tokens — and its uppercasing
   would misreport identifiers, the same reason .btn code carves itself
   out. These stay <button>s for the keyboard and for the shared
   set-filter-submit action; only the styling opts out. */
.facet-chip {
    display: inline-flex;
    align-items: baseline;
    gap: 0.375rem;
    padding: 0.125rem 0.5rem;
    background-color: var(--surface-tertiary);
    border: 1px solid var(--border-default);
    color: var(--text-primary);
    /* Both inherited from .btn until now: a bare <button> takes the
       system UI font and the default arrow cursor. */
    cursor: pointer;
    font-family: inherit;
    font-size: 0.8125rem;
    line-height: 1.6;
    transition: background-color var(--transition-fast),
                border-color var(--transition-fast),
                color var(--transition-fast);
}

.facet-chip:hover {
    background-color: var(--surface-raised);
    border-color: var(--ncar-blue);
    color: var(--text-link);
}

.facet-chip:focus-visible {
    outline: 2px solid var(--ncar-blue);
    outline-offset: 1px;
}

/* Counts are a secondary reading — subdued, and tabular so a column of
   chips doesn't jitter as the digits change. */
.facet-chip-count {
    font-size: 0.75rem;
    color: var(--text-tertiary);
    font-variant-numeric: tabular-nums;
}

.facet-chip.is-active {
    background-color: var(--ncar-blue);
    border-color: var(--ncar-blue);
    color: var(--text-on-brand);
}

.facet-chip.is-active .facet-chip-count {
    color: rgba(255, 255, 255, 0.75);
}

/* Phones: the label column costs more than it aligns — give each
   dimension its own line above its values. */
@media (max-width: 575.98px) {
    .jobs-facets {
        grid-template-columns: minmax(0, 1fr);
        row-gap: 0.125rem;
    }

    .jobs-facet-label {
        justify-self: start;
    }

    .jobs-facet-label:not(:first-child) {
        margin-top: 0.375rem;
    }
}

/* ============================================================================
   FILTER SIDEBAR — Unity NCAR navy panel for any filter form on the site.
   Defined here (not allocations.css) so it's available on every page.
   ========================================================================= */

.filter-sidebar {
    background-color: var(--ncar-navy);
    color: var(--text-on-brand);
    padding: 1.5rem;
}

.filter-sidebar-header {
    display: flex;
    justify-content: space-between;
    align-items: baseline;
    /* Negative horizontal margin cancels .filter-sidebar's 1.5rem padding so
       the divider spans the full panel width; inner padding re-establishes
       the text inset. */
    margin: 0 -1.5rem 1.25rem;
    padding: 0 1.5rem 0.75rem;
    border-bottom: 1px solid var(--ncar-gray-light);
}

/* Selector needs to beat .main-content h2 (specificity 0,1,1) — chain the
   parent class so we hit 0,2,1 and the gold color wins over navy-on-navy.
   Fixed 1rem font keeps it from inheriting the giant h2 desktop scale. */
.filter-sidebar .filter-sidebar-title {
    color: var(--ncar-gold);
    font-size: 1rem;
    line-height: 1.5;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    margin: 0;
}

/* Collapsible filter panels: the "Filters" title is a collapse toggle.
   The toggle is the title only — NOT the whole header row — because the
   Bootstrap collapse data-api handles clicks in the capture phase, so the
   sibling "Clear filters" link could never stopPropagation out of a
   row-level toggle. Chevron tracks aria-expanded, which Bootstrap
   maintains on the toggle. */
.filter-sidebar-toggle {
    background: none;
    border: 0;
    padding: 0;
    font: inherit;
    color: inherit;
    text-transform: inherit;
    letter-spacing: inherit;
    cursor: pointer;
}

.filter-sidebar-chevron {
    font-size: 0.75rem;
    transition: transform 0.2s ease;
}

.filter-sidebar-toggle[aria-expanded="false"] .filter-sidebar-chevron {
    transform: rotate(-90deg);
}

/* Collapsed panel: drop the divider and reclaim the header's bottom
   margin so the closed state reads as a tidy title bar rather than an
   empty box. (During the .collapsing animation neither state matches —
   the margin snaps when the transition ends, which reads fine.) */
.filter-sidebar-header:has(+ .collapse:not(.show)) {
    border-bottom: none;
    margin-bottom: -0.75rem;
}

.filter-sidebar-clear {
    color: var(--text-on-brand);
    font-size: 0.875rem;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    text-decoration: none;
    font-weight: var(--font-weight-semi-bold);
}

.filter-sidebar-clear:hover {
    color: var(--ncar-sky);
}

.filter-sidebar .form-label,
.filter-sidebar .form-check-label {
    color: var(--text-on-brand);
}

.filter-sidebar .form-text {
    color: rgba(255, 255, 255, 0.7);
}

.filter-sidebar select,
.filter-sidebar input[type="date"],
.filter-sidebar input[type="text"],
.filter-sidebar input[type="search"],
.filter-sidebar input[type="email"],
.filter-sidebar input[type="number"] {
    background-color: var(--surface-raised);
    color: var(--text-heading);
}

.filter-sidebar input::placeholder {
    color: var(--text-tertiary);
}

/* fk-pickers embedded in a horizontal align-items-end filter row (jobs +
   disk-scans panels, which pass wrapper_class='' to drop the stacked-form
   mb-3): the empty typeahead dropdown's mt-1 still makes the cell 4px
   taller than its siblings, floating the picker's label above the other
   columns' labels. !important is required to beat the utility class. */
.filter-sidebar .align-items-end .fk-picker-results:empty {
    margin-top: 0 !important;
}

/* On phones the horizontal filter rows wrap into a ragged multi-column mess:
   stack every field full-width instead. !important is required to beat the
   inline style="width:###px" attributes that size the fields on desktop
   (audit_filters.html, allocations/projects.html, admin/projects.html). */
@media (max-width: 575.98px) {
    .filter-sidebar .d-flex.flex-wrap > div {
        width: 100%;
    }

    .filter-sidebar input.form-control,
    .filter-sidebar select.form-control,
    .filter-sidebar select.form-select {
        width: 100% !important;
    }
}

/* ============================================================================
   PROJECT CARDS (User Dashboard Specific)
   ========================================================================= */

.project-card {
    margin-bottom: 0px !important;
}

/* Project-card headers follow the same invert pattern as .nav-tabs and
   .btn-group toggles: collapsed (inactive) = solid NCAR blue + white text,
   expanded (active) = white + blue text. Matches Unity's tab/accordion
   convention. Badge children keep their own subtle palette — only the
   title text, icons, and chevron flip with the header state. */
.project-card .card-header {
    cursor: pointer;
    user-select: none;
    padding: 16px;
    background-color: var(--surface-page);
    color: var(--text-link);
    border-bottom: 1px solid var(--border-default);
    transition: background-color var(--transition-base), color var(--transition-base);
}

/* Force the title's folder icon (.text-primary overrides default inheritance)
   and the chevron to flip with the header. !important needed to win against
   the .text-primary utility class on the icon. */
.project-card .card-header h5 i,
.project-card .card-header .accordion-chevron {
    color: var(--text-heading) !important;
}

/* Match Unity's .accordion-button: fixed 1rem font, semi-bold, single weight
   (the inner <strong> tag inherits so the title stays one consistent weight). */
.project-card .card-header h5 {
    font-size: 1rem;
    line-height: 1.5;
    font-weight: var(--font-weight-semi-bold);
    color: inherit;
}

.project-card .card-header h5 strong {
    font-weight: inherit;
}

/* Expanded (active) state: white surface with blue text — the "settled" look
   matching .nav-tabs.active and .btn-group .btn-secondary.active. */
.project-card .card-header[aria-expanded="true"] {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
    border-bottom-color: var(--ncar-gray-light);
}

.project-card .card-header[aria-expanded="true"] h5 i,
.project-card .card-header[aria-expanded="true"] .accordion-chevron {
    color: var(--text-on-brand) !important;
}

/* Accordion chevron — reusable affordance for any collapsible header.
   Rotates 180° when the parent toggle is expanded. */
.accordion-chevron {
    transition: transform var(--transition-base);
}

[aria-expanded="true"] .accordion-chevron {
    transform: rotate(180deg);
}

/* Fluid 1800px cap: smoother than Bootstrap's stepped .container breakpoints
   on laptop/desktop, without stretching to ultra-wide monitor edges.  Used
   on navbar, flash messages, footer, and any content block that opts in via
   the content_container_class block override. */
.sam-fluid-1800 {
    max-width: 88.25rem;
    margin-left: auto;
    margin-right: auto;
}

.project-stats-box {
    background-color: var(--surface-tertiary);
    border-radius: 0;
    padding: 12px 16px;
    margin-bottom: 16px;
    border-left: 4px solid var(--ncar-blue);
    /* Paired auto/1fr tracks per column so labels share a per-column auto
       width and values start at a consistent x-position within each column.
       Stat-items use display:contents so their label+value become direct
       children of this grid. Column count steps by breakpoint. */
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    column-gap: 24px;
    row-gap: 0;
    transition: all var(--transition-base);
}

@media (min-width: 768px) {
    .project-stats-box {
        grid-template-columns: auto minmax(0, 1fr) auto minmax(0, 1fr);
    }
}

@media (min-width: 1200px) {
    .project-stats-box {
        grid-template-columns: auto minmax(0, 1fr) auto minmax(0, 1fr) auto minmax(0, 1fr);
    }
}

.project-stats-box:hover {
    border-left-color: var(--ncar-navy);
    box-shadow: 0 2px 4px rgba(0, 0, 0, 0.08);
}

.project-stats-box h6 {
    color: var(--text-title);
    font-weight: 700;
    margin-bottom: 6px;
    font-size: 0.9rem;
    text-transform: uppercase;
    grid-column: 1 / -1;
    letter-spacing: 0.5px;
}

/* Single-line stat-items dissolve into the parent grid so labels share
   auto-tracks within each column (see .project-stats-box above). */
.stat-item {
    display: contents;
}

.stat-item > .stat-label,
.stat-item > .stat-value {
    padding: 2px 0;
}

.stat-item > .stat-label {
    padding-right: 0.5rem;
}

/* Multi-line items (Organizations, Contracts, Directories) opt back out
   of display:contents so they can span all columns of the parent grid.
   Tighter top margin than Bootstrap's .mt-2 to keep the box compact. */
.stat-item-block {
    display: block;
    grid-column: 1 / -1;
    padding: 2px 0;
    margin-top: 4px !important;
}

.stat-label {
    color: var(--text-tertiary);
    font-weight: var(--font-weight-semi-bold);
}

.stat-value {
    font-weight: 700;
    color: var(--text-title);
}

/* ============================================================================
   PROJECT TREE (Hierarchy Display)
   ========================================================================= */

.tree-list {
    list-style: none;
    padding-left: 0;
    margin: 0;
}

.tree-list ul {
    list-style: none;
    padding-left: 30px;
    margin: 8px 0;
}

.tree-list li {
    padding: 8px 12px;
    margin: 4px 0;
    background: var(--surface-tertiary);
    border-left: 3px solid var(--ncar-blue);
    border-radius: var(--radius-sm);
    transition: all var(--transition-fast);
}

.tree-list li:hover {
    background: var(--surface-secondary);
    border-left-color: var(--ncar-navy);
    transform: translateX(2px);
}

.tree-list li strong {
    color: var(--text-title);
    font-weight: 700;
}

/* "You are here" in a project tree — the node whose projcode is the current
 * scope, and the row form of the same thing in the disk fileset table.
 *
 * Was five copies of an inline `background: #fff3cd; border-left-color:
 * #ffc107` across resource_details.html, resource_details_disk.html (twice)
 * and shared/project_tree.html (twice). An inline literal is the one surface
 * a stylesheet cannot reach, so in dark mode the outermost node stayed a
 * bright pastel with --text-primary (#e9ecef) written on it.
 *
 * --bs-warning-bg-subtle IS #fff3cd in light — byte-identical to what the
 * inline style painted — and #332701 in dark. It is one of the few Bootstrap
 * families that rethemes itself (see status.css:17). The left border keeps
 * --bs-warning, which is #ffc107 in both themes: it is the same gold as the
 * `text-warning` arrow icon the templates put next to it, and a marker on a
 * tinted ground is meant to stay put.
 *
 * The <tr> form sets --bs-table-bg rather than `background`, because
 * Bootstrap paints every <td> opaquely over any row-level background —
 * the trap already documented at components.css:14. */
/* `.tree-list li` (0,1,1) sets the node background, so the bare class would
 * lose to it on specificity and the current node would be indistinguishable —
 * which is exactly what the first draft of this shipped. The second selector
 * carries the tree case; the first carries anything outside a `.tree-list`. */
.tree-node-current,
.tree-list li.tree-node-current {
    background: var(--bs-warning-bg-subtle);
    border-left-color: var(--bs-warning);
    font-weight: 700;
}

tr.tree-node-current {
    --bs-table-bg: var(--bs-warning-bg-subtle);
    --bs-table-color: var(--text-primary);
    color: var(--bs-table-color);
}

/* The other half of the same inline block: a node whose project is inactive.
 * `#6c757d` -> --text-secondary (#718096 light) is a declared shift; the 0.6
 * opacity is carried over exactly rather than rounded to Bootstrap's
 * `.opacity-50`, which would have moved light mode for no reason. */
.tree-node-inactive {
    color: var(--text-secondary);
    opacity: 0.6;
}

/* ============================================================================
   COLLAPSIBLE SECTIONS
   ========================================================================= */

.collapse-toggle {
    cursor: pointer;
    user-select: none;
    border-bottom: 1px solid var(--ncar-gray-light);
}

.collapse-toggle::after {
    content: '\f078';
    font-family: 'Font Awesome 6 Free';
    font-weight: 900;
    float: right;
    transition: transform var(--transition-base);
}

.collapse-toggle.collapsed::after {
    transform: rotate(-90deg);
}

/* ============================================================================
   FORMS
   ========================================================================= */

.form-control:focus {
    border-color: var(--ncar-blue);
    box-shadow: 0 0 0 0.2rem rgba(var(--ncar-teal-rgb), 0.25);
}

.form-label {
    font-weight: 600;
    color: var(--text-title);
    margin-bottom: 0.5rem;
}

.input-group-text {
    background-color: var(--ncar-blue);
    color: var(--text-on-brand);
    border: none;
    font-weight: 600;
}

/* ============================================================================
   UTILITY CLASSES
   ========================================================================= */

.text-ncar-navy {
    color: var(--text-title) !important;
}

.text-ncar-blue {
    color: var(--text-link) !important;
}

.text-muted-custom {
    color: var(--text-tertiary) !important;
}

.border-ncar-blue {
    border-color: var(--ncar-blue) !important;
}

.bg-ncar-light {
    background-color: var(--surface-page) !important;
}

/* Text color utilities for table cells */
.text-primary {
    color: var(--text-link) !important;
}

.text-success {
    color: var(--success-color) !important;
}

.text-warning {
    color: var(--warning-color) !important;
}

.text-danger {
    color: var(--danger-color) !important;
}

/* ============================================================================
   RESPONSIVE ADJUSTMENTS
   ========================================================================= */

@media (max-width: 768px) {
    .page-header h1 {
        font-size: 1.75rem;
    }

    .navbar-brand {
        font-size: 1.5rem;
    }

    .card-body {
        padding: 16px;
    }

    .project-stats-box {
        padding: 12px;
        /* Stack single-column on tablet/mobile — one auto/1fr pair. */
        grid-template-columns: auto minmax(0, 1fr);
        column-gap: 16px;
    }

    .table {
        font-size: 0.875rem;
    }
}

@media (max-width: 576px) {

    .page-header {
        margin-bottom: 20px;
    }
}

/* ===================================================================
   Chart container — global centering for SVG charts.
   Allocations dashboard further constrains pies to 720px in
   allocations.css, which is loaded after this file on those pages.
   =================================================================== */
.chart-container {
    text-align: center;
}

.chart-container svg {
    display: block;
    margin: 0 auto;
    max-width: 100%;
    height: auto;
}

/* Disk-scans entity pie (By User / By Group tab). matplotlib renders it at a
   ~670px native width (≈ half the card); scale it up to read better without
   going full width. Centered by the wrapper's flex justify-content. */
.disk-entity-pie svg {
    width: 100%;
    max-width: 880px;
    height: auto;
}

/* Job-history charts. These use bare `d-flex justify-content-center` wrappers
   rather than `.chart-container`, and had no CSS at all.

   They do NOT overflow — a flex item shrinks below its intrinsic width by
   default, so the page stays within the viewport. The bug is subtler: without
   `height: auto` the box keeps the SVG's intrinsic `height` attribute while
   flexbox shrinks its width, and the viewBox letterboxes the drawing inside
   it. Measured at 390px, the jobs histogram's 2.50:1 figure rendered into a
   277x446px box (0.62:1) — the chart drawn ~277x111 with ~335px of empty
   space padded around it.

   Matching `.chart-container svg` restores the aspect ratio. Note this does
   NOT make the charts legible on a phone: an 18x5in figure scaled to ~350px
   renders 9-11pt text at ~2px regardless. That needs a different figsize from
   the server — the `layout` render axis, wired in the mobile pass. */
.jobs-histogram-chart svg,
.jobs-timeline-chart svg,
.jobs-user-pie svg {
    display: block;
    margin: 0 auto;
    max-width: 100%;
    height: auto;
}

/* Chart gutters below desktop.
   ------------------------------------------------------------------
   The server renders a phone- or tablet-sized figure (see charts/layout.py),
   which only pays off if the figure gets the width. Measured at a 375px
   viewport on /status/derecho, it does not: the chart sits in a card inside a
   card, and each `.card-body` takes 16px a side, so a 375px viewport hands the
   chart 287px. The figure is then scaled DOWN to fit, undoing part of the
   point.

   Cards nest on several surfaces and un-nesting them is not a chart change,
   so instead the chart bleeds back over its immediate card padding. 16px a
   side, matching `.card-body` exactly — it lines the SVG up with the card
   edge rather than pushing past it, so nothing can overflow. Charts are
   self-contained rectangles with their own internal margins; unlike text they
   do not need the gutter to read.

   The two halves have different bands, which is measurement, not oversight:

   - the **gutter** runs the whole non-desktop range. The nested card bodies
     cost the same 32px at 768 as at 375, and it buys a real 5%: measured on
     /status/derecho at a 768 viewport the chart's box goes 625 -> 657px and
     its smallest label 9.0 -> 9.4px. Verified symmetric and non-overflowing at
     both edges of the tablet band, and on /status/partition-history, which
     nests one card body rather than two.
   - `width: 100%` stays on phones only. It exists to *upscale* a figure
     narrower than its card, and no tablet figure is: every one measured
     renders at 100% of its card across the whole band under `max-width`
     alone. Extending it would only reach the pies, whose tablet profile is
     deliberately the desktop figure — it would blow them up, not fix them.
     Desktop keeps `max-width` alone for the original reason: upscaling an
     18in figure on a wide screen would just blur it. */
@media (max-width: 1199.98px) {
    .chart-container,
    .jobs-histogram-chart,
    .jobs-timeline-chart,
    .jobs-user-pie,
    .disk-entity-pie {
        margin-left: -1rem;
        margin-right: -1rem;
    }
}

@media (max-width: 767.98px) {
    .chart-container svg,
    .jobs-histogram-chart svg,
    .jobs-timeline-chart svg,
    .jobs-user-pie svg {
        width: 100%;
    }
}

/* ============================================================================
   MUTED BADGE PALETTE — saturated Bootstrap defaults (bg-primary/info/success/
   warning/danger) read as aggressive next to the flat Unity surfaces, especially
   when a dozen+ badges stack on a single line (group memberships, permissions,
   etc.). Override the .badge .bg-X compound so badges adopt the subtle/tinted
   palette Bootstrap 5.3 already ships (--bs-X-bg-subtle / -text-emphasis /
   -border-subtle). Scoped to .badge so non-badge .bg-X usages (progress bar
   fills, alert backgrounds, status indicators) keep their existing styling.
   The !important is required to beat Bootstrap's own .bg-X !important.
   ========================================================================= */
.badge.bg-primary,
.badge.bg-info,
.badge.bg-success,
.badge.bg-warning,
.badge.bg-danger {
    font-weight: var(--font-weight-semi-bold);
    border: 1px solid;
}

.badge.bg-primary {
    background-color: var(--bs-primary-bg-subtle) !important;
    color: var(--bs-primary-text-emphasis) !important;
    border-color: var(--bs-primary-border-subtle);
}

.badge.bg-info {
    background-color: var(--bs-info-bg-subtle) !important;
    color: var(--bs-info-text-emphasis) !important;
    border-color: var(--bs-info-border-subtle);
}

.badge.bg-success {
    background-color: var(--bs-success-bg-subtle) !important;
    color: var(--bs-success-text-emphasis) !important;
    border-color: var(--bs-success-border-subtle);
}

.badge.bg-warning {
    background-color: var(--bs-warning-bg-subtle) !important;
    color: var(--bs-warning-text-emphasis) !important;
    border-color: var(--bs-warning-border-subtle);
}

.badge.bg-danger {
    background-color: var(--bs-danger-bg-subtle) !important;
    color: var(--bs-danger-text-emphasis) !important;
    border-color: var(--bs-danger-border-subtle);
}
