/* ══════════════════════════════════════════════════════════════════
   UI atoms — small, reusable bits that compose into pages.

   Grouped by kind rather than by file-per-component. A component
   graduates out to its own file only when it gets truly large or
   its concerns diverge from the rest of this group (rough rule: if
   this file crosses ~1500 lines or a section stops sharing tokens
   with its neighbors, promote it).

   Sections (numbering is historical — not all numbers are unique):
     1.  Button (c-button)
     2.  Choice list (c-choice-list / c-choice / c-choice-actions)
     3.  Persona card + grid (c-persona-card)
     3.  Checklist (c-checklist)
     4.  Form error (c-form-error)
         Notice (c-notice)
     5.  Upload (c-upload, app-upload tag helper)
     6.  Readout (c-readout)
     7.  Form field (c-form-field)
     8.  Card (c-card)
     9.  Disclosure (c-disclosure — <details>/<summary> accordion)
     10. Page note (c-page-note — hairline-topped muted page footer)
   ══════════════════════════════════════════════════════════════════ */

@layer components {

    /* ─── 1. Button ───────────────────────────────────────────────── */

    .c-button {
        display: inline-flex;
        align-items: center;
        gap: var(--space-2);
        font: inherit;
        font-weight: 500;
        line-height: 1;
        padding: var(--space-2) var(--space-4);
        border: 1px solid transparent;
        border-radius: var(--radius-pill);
        background: transparent;
        color: inherit;
        cursor: pointer;
        text-decoration: none;
        transition: background var(--dur-base) var(--ease),
                    color var(--dur-base) var(--ease),
                    border-color var(--dur-base) var(--ease);
    }

    .c-button:focus-visible {
        outline: 2px solid var(--color-accent);
        outline-offset: 2px;
    }

    .c-button:disabled,
    .c-button[aria-disabled="true"] {
        opacity: 0.5;
        pointer-events: none;
    }

    /* Variants */

    /* Primary CTA — the page's most important action ("Continue",
       "Subscribe", "Select Plan", etc.). Uses the host's brand colour.
       Hosts rebind --color-accent in their brand layer; unbranded contexts
       fall back to a near-black neutral so the button still reads as primary. */
    .c-button--solid {
        background: var(--color-accent);
        color: var(--color-on-dark);
    }

    .c-button--solid:hover {
        background: var(--color-accent-deep);
    }

    .c-button--ghost {
        border-color: var(--color-line);
    }

    .c-button--ghost:hover {
        border-color: var(--color-ink);
    }

    .c-button--link {
        padding-inline: 0;
        color: var(--color-accent);
        text-decoration: underline;
        text-underline-offset: 0.2em;
    }

    /* Destructive action — delete / hard-reset / irreversible. First-class
       button variant (app-button variant="Danger" → this class); also used
       by app-confirm.js for the OK button when type=danger. */
    .c-button--danger {
        background: var(--color-danger, #b91c1c);
        border-color: var(--color-danger, #b91c1c);
        color: var(--color-on-danger, #ffffff);
    }

    .c-button--danger:hover,
    .c-button--danger:focus-visible {
        background: var(--color-danger-strong, #991b1b);
        border-color: var(--color-danger-strong, #991b1b);
    }

    /* Sizes */
    .c-button--sm {
        padding: var(--space-1) var(--space-3);
        font-size: var(--fs-ui-sm);
    }

    .c-button--lg {
        padding: var(--space-3) var(--space-5);
        font-size: var(--fs-body-lg);
    }


    /* ─── 2. Choice list ──────────────────────────────────────────────
     Stacked toggle-card list: each card pairs a control (switch /
     radio / checkbox) with a title + description block. Used for
     settings panels — privacy choices, notification prefs, feature
     opt-ins. Grid layout (not flex) is deterministic when controls
     mount via JS after first paint, avoiding the layout shifts that
     a flex-with-fixed-width-toggle pattern can produce. */

    .c-choice-list {
        list-style: none;
        margin: 0 0 var(--space-7);
        padding: 0;
        display: grid;
        gap: var(--space-4);
    }

    .c-choice {
        display: grid;
        grid-template-columns: auto 1fr;
        column-gap: var(--space-5);
        align-items: start;
        padding: var(--space-5);
        background: var(--color-surface-alt);
        border: 1px solid var(--color-line);
        border-radius: var(--radius-md);
    }

    .c-choice__toggle {
        /* No width constraint — let the control size itself.
           Optical-alignment nudge so a switch sits with the first
           line of the title rather than the very top of the card. */
        padding-top: 0.125rem;
    }

    .c-choice__title {
        margin: 0 0 var(--space-1);
        font-family: var(--font-display);
        font-size: var(--fs-body-lg);
        font-weight: 500;
        line-height: 1.2;
        color: var(--color-ink-h3);
    }

    .c-choice__desc {
        margin: 0;
        font-size: var(--fs-body);
        line-height: 1.55;
        color: var(--color-ink-soft);
    }

    /* Action row sitting below a .c-choice-list — right-aligned button
       group, wraps on narrow viewports. */
    .c-choice-actions {
        display: flex;
        gap: var(--space-3);
        justify-content: flex-end;
        flex-wrap: wrap;
    }


    /* ─── 3. Persona card + grid ──────────────────────────────────── */

    /* Used on the onboarding picker (/onboarding) where a new user
       chooses their path: Company / Professional / Credentialing
       Authority / Relying Party. Each card is a self-contained block
       with icon, heading, description, and a primary + secondary
       action row. Responsive grid:
         ≥1200px  — 4 across (wide desktop)
         600-1199 — 2 across (tablet, small desktop; 4 columns at this
                    width squeeze the descriptions too tightly)
         <600px   — 1 across (phone) */

    .c-persona-grid {
        display: grid;
        grid-template-columns: repeat(4, 1fr);
        gap: var(--space-5);
    }

    @media (max-width: 1199px) {
        .c-persona-grid {
            grid-template-columns: repeat(2, 1fr);
        }
    }

    @media (max-width: 599px) {
        .c-persona-grid {
            grid-template-columns: 1fr;
        }
    }

    .c-persona-card {
        display: flex;
        flex-direction: column;
        padding: var(--space-6);
        background: var(--color-surface);
        border: 1px solid var(--color-line);
        border-radius: var(--radius-lg, 12px);
        transition: border-color var(--dur-fast) var(--ease),
                    box-shadow var(--dur-fast) var(--ease),
                    transform var(--dur-fast) var(--ease);
    }

    .c-persona-card:hover {
        border-color: var(--color-ink);
        box-shadow: 0 6px 20px -6px rgb(0 0 0 / .08);
    }

    /* Fixed-square icon badge; FontAwesome glyph centered inside. */
    .c-persona-card__icon {
        display: inline-flex;
        align-items: center;
        justify-content: center;
        width: 3rem;
        height: 3rem;
        margin-bottom: var(--space-4);
        font-size: 1.5rem;
        color: var(--color-accent);
        background: color-mix(in srgb, var(--color-accent) 10%, transparent);
        border-radius: var(--radius-md, 8px);
    }

    .c-persona-card__title {
        margin: 0 0 var(--space-2);
        font-family: var(--font-display);
        font-size: var(--fs-heading);
        font-weight: 500;
        line-height: 1.2;
        color: var(--color-ink-h3);
    }

    /* flex: 1 pushes the action row to the bottom so buttons align
       across cards even when descriptions differ in length. */
    .c-persona-card__desc {
        flex: 1;
        margin: 0 0 var(--space-5);
        font-size: var(--fs-body);
        line-height: 1.5;
        color: var(--color-ink-soft);
    }

    .c-persona-card__actions {
        display: flex;
        align-items: center;
        justify-content: space-between;
        gap: var(--space-4);
    }

    .c-persona-card__learn {
        font-size: var(--fs-ui-sm);
        color: var(--color-accent);
        text-decoration: none;
        white-space: nowrap;
    }

    .c-persona-card__learn:hover,
    .c-persona-card__learn:focus-visible {
        text-decoration: underline;
        text-underline-offset: 0.2em;
    }

    /* .c-persona-card--unavailable and .c-persona-card__unavailable
       live in the host (AfricaDocumentsWebSite/wwwroot/css/custom/) —
       they're AD-specific until another product needs the sales-gated
       persona variant. */

    /* ─── 2b. Country-unavailable hero ───────────────────────────────
       Used by Commerce/CommerceCountry/CountrySalesUnavailable.cshtml.
       Forward-looking conversion-recovery moment (user came with buying
       intent; the page tells them "not yet, here's what's next"). Pairs
       with .c-persona-card below for the action cards. Host-agnostic,
       semantic tokens only — country names render in --color-accent. */

    .c-unavailable {
        max-width: 56rem;
        margin-inline: auto;
        padding: var(--space-6) 0 var(--space-8);
    }

    .c-unavailable__heading {
        font-family: var(--font-display);
        font-weight: 300;
        font-size: clamp(2.25rem, 5vw, 4rem);
        line-height: 1.05;
        letter-spacing: -0.02em;
        margin: 0 0 var(--space-5);
        color: var(--color-ink);
    }

    .c-unavailable__heading em {
        font-style: italic;
        font-weight: 400;
        color: var(--color-accent);
    }

    .c-unavailable__lede {
        font-size: var(--fs-body-lg);
        line-height: 1.55;
        color: var(--color-ink-soft);
        max-width: 56ch;
        margin: 0;
    }

    /* ─── 3. Checklist ────────────────────────────────────────────────
       Tick + label list. Used in marketing pages (homepage, trust
       center) and in the wizard welcome step. */

    .c-checklist {
        list-style: none;
        margin: 0;
        padding: 0;
    }

    .c-checklist__item {
        padding: var(--space-4) 0;
        border-top: 1px solid var(--color-line);
        display: flex;
        align-items: center;
        gap: var(--space-4);
        font-size: var(--fs-ui);
    }

    .c-checklist__item:last-child {
        border-bottom: 1px solid var(--color-line);
    }

    .c-checklist__tick {
        width: 1.25rem;
        height: 1.25rem;
        border-radius: var(--radius-circle);
        background: var(--color-accent);
        color: var(--color-on-dark);
        display: grid;
        place-items: center;
        font-size: var(--fs-caption);
        flex-shrink: 0;
    }

    /* ─── 4. Form error ───────────────────────────────────────────────
       Form-level error callout — emitted by the <app-form-error> tag
       helper. Sits at the top of a form to announce submission errors
       (validation failures, server problems, network errors). Field-level
       errors live next to their input via <app-form-field-wrapper>; this
       is the global "something went wrong with this submission" target.

       Visual treatment: left-stripe + tinted background + error-deep
       text — the same shape as .c-wizard__warning but in error red
       rather than warn amber. No icon; modern form-error convention
       (Stripe / Sumsub / Onfido / GOV.UK) skips it because the visual
       treatment alone is sufficient signal.

       role="alert" on the element gives screen-reader announcement when
       content changes. The :empty rule auto-hides the element when
       there's no error content (defensive — current JS helpers also set
       display explicitly, but :empty protects against future callers
       that forget to). */

    .c-form-error {
        padding: var(--space-3) var(--space-4);
        border-left: 4px solid var(--color-error);
        background: var(--color-error-soft);
        border-radius: var(--radius-sm);
        color: var(--color-error-deep);
        font-size: var(--fs-body);
        font-weight: 500;
        line-height: var(--lh-normal);
        margin-bottom: var(--space-5);
    }

    .c-form-error:empty {
        display: none;
    }

    /* ─── Notice ──────────────────────────────────────────────────────
       Generic informational / state callout. Same structural pattern as
       c-form-error (left-stripe + soft tint + deep text), tone-by-modifier.
       Default: info. Modifiers: --warn. (Error specialization stays in
       c-form-error for now — alert role + JS-driven content.) */

    .c-notice {
        padding: var(--space-3) var(--space-4);
        border-left: 4px solid var(--color-info);
        background: var(--color-info-soft);
        border-radius: var(--radius-sm);
        color: var(--color-info-deep);
        font-size: var(--fs-body);
        line-height: var(--lh-normal);
        margin-bottom: var(--space-5);
    }

    .c-notice--warn {
        border-left-color: var(--color-warn);
        background: var(--color-warn-soft);
        color: var(--color-warn-deep);
    }

    /* ─── Usage meter (c-meter) ────────────────────────────────────────
       Consumption of a metered quota (seats, storage, …) against a limit:
       a neutral bordered panel with a count, a progress bar, and a
       contextual message when near/at the limit. NOT a content card
       (c-card) or a notice (c-notice) — state colour lives on the bar,
       the count, and the alert (--warn nearing the limit, --full at it). */
    .c-meter {
        border: 1px solid var(--color-line);
        border-radius: var(--radius-md);
        padding: var(--space-3) var(--space-4);
        font-size: var(--fs-ui);
    }

    .c-meter__row {
        display: flex;
        align-items: center;
        justify-content: space-between;
        gap: var(--space-4);
    }

    .c-meter__count {
        font-weight: 600;
    }

    .c-meter__detail {
        color: var(--color-ink-mute);
        font-size: var(--fs-ui-sm);
    }

    .c-meter__bar {
        height: 4px;
        margin-top: var(--space-2);
        background: var(--color-line);
        border-radius: var(--radius-pill);
        overflow: hidden;
    }

    .c-meter__fill {
        height: 100%;
        background: var(--color-success);
        border-radius: var(--radius-pill);
    }

    .c-meter--warn .c-meter__fill {
        background: var(--color-warn);
    }

    .c-meter--warn .c-meter__count {
        color: var(--color-warn-deep);
    }

    .c-meter--full .c-meter__fill {
        background: var(--color-error);
    }

    .c-meter--full .c-meter__count {
        color: var(--color-error-deep);
    }

    .c-meter__alert {
        display: flex;
        align-items: center;
        gap: var(--space-2);
        margin-top: var(--space-2);
        padding: var(--space-2) var(--space-4);
        border-radius: var(--radius-md);
        background: var(--color-warn-soft);
        color: var(--color-warn-deep);
    }

    .c-meter--full .c-meter__alert {
        background: var(--color-error-soft);
        color: var(--color-error-deep);
    }

    .c-meter__alert a {
        color: inherit;
        text-decoration: underline;
        font-weight: 600;
    }

    /* ─── 5. Upload (app-upload tag helper) ───────────────────────────
       Two-block form: idle (file picker + actions) and in-flight
       (progress bar + status label). JS toggles which is visible.

       Real upload progress drives the determinate bar; once bytes are
       sent the bar goes indeterminate (sliding stripe) while server-side
       processing runs. */

    /* width:100% stops .app-section's flex `align-items:flex-start` from
       shrinking the widget to content width; max-width caps it at a usable
       form width. NO margin auto — it left-aligns with the rest of the page
       instead of centering. (Onboarding's .c-wizard column governs that shell;
       this cap just keeps the field usable in the wider app shell.) */
    .c-upload {
        width: 100%;
        max-width: 44rem;
    }

    /* Left-aligned content column for KYC step / form pages in the app shell.
       The app's .c-page is full-width, so without this the editor form fields
       balloon across the whole screen. Caps the column at the onboarding
       wizard width (44rem) and does NOT center — content stays at the page's
       left edge. Wrap a page's <app-section> content in it. */
    .c-form-column {
        width: 100%;
        max-width: 44rem;
    }

    .c-upload__field {
        display: flex;
        flex-direction: column;
        gap: var(--space-2);
    }

    .c-upload__field-label {
        font-size: var(--fs-ui);
        font-weight: 500;
    }

    .c-upload__field-hint {
        font-size: var(--fs-ui-sm);
        color: var(--color-ink-mute);
        margin: 0;
    }

    .c-upload__field input[type="file"] {
        padding: var(--space-3);
        border: 1px dashed var(--color-line);
        border-radius: var(--radius-sm);
        background: var(--color-surface-alt);
        width: 100%;
    }

    .c-upload__actions {
        display: flex;
        gap: var(--space-3);
        justify-content: flex-end;
        margin-top: var(--space-6);
    }

    .c-upload__progress {
        display: flex;
        flex-direction: column;
        gap: var(--space-3);
        padding-block: var(--space-7);
        align-items: stretch;
        text-align: center;
    }

    .c-upload__progress progress {
        width: 100%;
        height: 0.5rem;
        border: none;
        border-radius: var(--radius-pill);
        background: var(--color-line);
        overflow: hidden;
        appearance: none;
    }

    .c-upload__progress progress::-webkit-progress-bar {
        background: var(--color-line);
        border-radius: var(--radius-pill);
    }
    .c-upload__progress progress::-webkit-progress-value {
        background: var(--color-accent);
        border-radius: var(--radius-pill);
        transition: width var(--dur-fast) var(--ease-out);
    }
    .c-upload__progress progress::-moz-progress-bar {
        background: var(--color-accent);
        border-radius: var(--radius-pill);
    }

    /* Indeterminate during post-upload phases — sliding stripe. */
    .c-upload__progress progress:indeterminate {
        background: linear-gradient(
            90deg,
            var(--color-line) 0%,
            var(--color-accent) 50%,
            var(--color-line) 100%
        );
        background-size: 200% 100%;
        animation: c-upload-progress-indeterminate 1.5s linear infinite;
    }
    .c-upload__progress progress:indeterminate::-webkit-progress-bar {
        background: transparent;
    }
    .c-upload__progress progress:indeterminate::-webkit-progress-value {
        background: transparent;
    }
    .c-upload__progress progress:indeterminate::-moz-progress-bar {
        background: transparent;
    }

    @keyframes c-upload-progress-indeterminate {
        0%   { background-position: 200% 0; }
        100% { background-position: -200% 0; }
    }

    .c-upload__progress-label {
        font-size: var(--fs-ui);
        color: var(--color-ink-soft);
        margin: 0;
    }

    @media (max-width: 48rem) {
        .c-upload__actions {
            flex-direction: column-reverse;
        }
        .c-upload__actions .c-button {
            width: 100%;
            text-align: center;
            justify-content: center;
        }
    }

    /* ─── 6. Readout ──────────────────────────────────────────────────
       Definition-list-style key/value display for read-only record
       summaries. Container-independent: rows stay as rows regardless
       of where the readout is dropped. Collapses to stacked
       label/value at narrow viewports.
       ─────────────────────────────────────────────────────────────── */

    .c-readout {
        display: flex;
        flex-direction: column;
        gap: var(--space-2);
    }

    .c-readout__row {
        display: flex;
        gap: var(--space-3);
    }

    .c-readout__label {
        font-size: var(--fs-ui-sm);
        color: var(--color-ink-mute);
        min-width: 12rem;
        flex-shrink: 0;
    }

    @media (max-width: 48rem) {
        .c-readout__row {
            flex-direction: column;
            gap: var(--space-1);
        }

        .c-readout__label {
            min-width: 0;
        }
    }

    /* Responsive grid of readout cards — the data-driven <app-readout-cards>
       renderer over a ReadoutCardCollection. 1→N columns with no media queries:
       one card per row on mobile, more as the viewport allows. Cards size to
       content (align-items: start).

       auto-FILL (not auto-fit): auto-fit COLLAPSES empty tracks, so with only a
       few cards they stretch to swallow all the free space — on a wide screen
       two cards balloon to ~50% each, sparse and far apart, hurting readability.
       auto-fill KEEPS the empty tracks, so cards hold a comfortable ~18–22rem
       reading width and a wide screen simply gets more columns instead of wider
       cards.

       align-self: stretch is REQUIRED — .app-section lays its content out as a
       flex column with align-items: flex-start, so without this the grid box
       shrinks to its content width and collapses to a single column. Same fix
       .c-card itself uses for the same reason. */
    .c-readout-cards {
        display: grid;
        /* --readout-card-min (set inline by <app-readout-cards minCardWidth="..">) can only
           WIDEN the track; max(18rem, ..) floors it so cards never go below the default. */
        grid-template-columns: repeat(auto-fill, minmax(max(18rem, var(--readout-card-min, 18rem)), 1fr));
        gap: var(--space-4);
        align-items: start;
        align-self: stretch;
        width: 100%;
        /* Breathing room above/below the grid so it reads as its own block,
           separated from the surrounding page elements. Matches the inter-card
           gap for a consistent rhythm. */
        margin-block: var(--space-4);
    }

    /* Compact card chrome — tighter padding, no shadow, and a transparent fill
       so the card reads as a thin-bordered outline on the page rather than a
       heavy filled panel (the .c-card surface-alt fill was visually heavy and
       also put the muted label below AA contrast — see .c-readout__label). The
       inherited 1px var(--color-line) border does the delineation. Grid gap
       handles inter-card spacing, so suppress .c-card's own margin. */
    .c-readout-cards .c-card {
        /* Denser grid variant — only the spacing differs from the shared shell. */
        margin-bottom: 0;
        padding: var(--space-4);
    }

    /* Compact rows: label left (muted), value right-aligned on the same line;
       long values wrap below the value column, not under the label. Denser than
       the default full-width readout — the 12rem label min-width drops to ~5rem
       so the value gets the room. (Document-properties redesign.) */
    /* Row padding (below) is the only inter-row spacer — no list gap on top of
       it, or the two stack and rows sit too far apart. */
    .c-readout-cards .c-readout {
        gap: 0;
    }
    .c-readout-cards .c-readout__row {
        flex-direction: row;
        gap: var(--space-3);
        padding: var(--space-1) 0;
        font-size: var(--fs-ui-sm);
    }
    .c-readout-cards .c-readout__label {
        /* --readout-label-min (set inline by <app-readout-cards labelMinWidth="..">) can only
           WIDEN; max(5rem, ..) floors it so the label column never goes below the default. */
        min-width: max(5rem, var(--readout-label-min, 5rem));
        flex-shrink: 0;
    }
    .c-readout-cards .c-readout__row dd {
        flex: 1;
        min-width: 0;
        margin: 0;
        overflow-wrap: break-word;
        /* Alignment is per-item, driven by ReadoutItem.ValueAlignment via the
           .c-readout__value--* class below (default left; numbers set Right) —
           NOT a blanket right-align. Value one rung above the 13px label
           (--fs-ui = 14px): the value is the content the user came for; the
           label is a navigation aid. rem-based, so it respects the user's
           browser font-size preference. */
        font-size: var(--fs-ui);
    }

    /* Per-item value alignment, driven by ReadoutItem.ValueAlignment. Default is
       left (the readout norm); numbers/sizes opt into right. */
    .c-readout__value--left    { text-align: left; }
    .c-readout__value--center  { text-align: center; }
    .c-readout__value--right   { text-align: right; }
    .c-readout__value--justify { text-align: justify; }

    /* Quiet, section-marker card titles with a divider — scoped, because the
       global .c-card__title is a large heading used elsewhere. */
    .c-readout-cards .c-card__head {
        margin-bottom: var(--space-3);
        padding-bottom: var(--space-2);
        border-bottom: 1px solid var(--color-line);
    }
    .c-readout-cards .c-card__title {
        display: inline-flex;
        align-items: center;
        gap: var(--space-2);
        font-size: var(--fs-body);
        font-weight: 600;
    }
    .c-readout-cards .c-card__title i {
        color: var(--color-ink-mute);
        font-size: 1.1em;
    }

    /* Optional top-right card-header action (e.g. an Edit pen). The head is
       flex space-between, so it sits hard right of the title. Muted by default,
       accent on hover/focus. */
    .c-readout-cards .c-readout-card__action {
        display: inline-flex;
        align-items: center;
        justify-content: center;
        padding: var(--space-1);
        border: none;
        background: transparent;
        color: var(--color-ink-mute);
        border-radius: var(--radius-sm);
        line-height: 1;
        cursor: pointer;
    }
    .c-readout-cards .c-readout-card__action:hover,
    .c-readout-cards .c-readout-card__action:focus-visible {
        color: var(--color-accent);
        background: var(--color-surface-alt);
    }

    /* A card that spans all columns of the readout grid (e.g. a wide audit card). */
    .c-readout-cards__card--full {
        grid-column: 1 / -1;
    }

    /* ----- app-dialog — native <dialog> modal (the <app-dialog> tag helper) --
       Opened NON-MODALLY (app-dialog.js show(), not showModal) so it stays OUT of the
       browser top layer — that lets Syncfusion popups (which append to <body> and compute
       a z-index above the dialog) render in front, with no reparenting. So the backdrop is
       a real overlay (a top-layer ::backdrop only exists for showModal), and we position
       the dialog ourselves. z-index is high so the dialog clears page content; Syncfusion
       still computes its popups above it. */
    .app-dialog {
        position: fixed;
        top: 50%;
        left: 50%;
        transform: translate(-50%, -50%);
        margin: 0;
        z-index: 1000;
        width: min(32rem, calc(100vw - var(--space-6)));
        max-height: calc(100vh - var(--space-6));
        overflow: auto;
        padding: var(--space-5);
        border: 1px solid var(--color-line);
        border-radius: var(--radius-md, 0.5rem);
        background: var(--color-surface);
        color: var(--color-ink);
    }
    body.app-dialog-open::before {
        content: '';
        position: fixed;
        inset: 0;
        background: rgb(0 0 0 / 0.4);
        z-index: 999;
    }
    .app-dialog__head {
        display: flex;
        align-items: center;
        justify-content: space-between;
        gap: var(--space-3);
        margin-bottom: var(--space-4);
    }
    .app-dialog__title {
        font-size: var(--fs-body);
        font-weight: 600;
    }
    .app-dialog__close {
        display: inline-flex;
        align-items: center;
        justify-content: center;
        padding: var(--space-1);
        border: none;
        background: transparent;
        color: var(--color-ink-mute);
        border-radius: var(--radius-sm);
        cursor: pointer;
    }
    .app-dialog__close:hover,
    .app-dialog__close:focus-visible {
        color: var(--color-ink);
        background: var(--color-surface-alt);
    }
    /* Stack the form fields with consistent spacing so the native controls
       don't run together. */
    .app-dialog__body form {
        display: flex;
        flex-direction: column;
        gap: var(--space-4);
    }

    /* Monospaced identifier value (ReadoutItem Kind=Code) — codes/reference
       numbers read as identifiers, not prose. */
    .c-readout__code {
        font-family: var(--font-mono, ui-monospace, SFMono-Regular, Menlo, monospace);
        font-size: var(--fs-ui-sm);
    }

    /* Small status dot + text (ReadoutItem Kind=Status) — the lighter sibling of
       the pill badge, coloured by tone. Same status palette as the badge. */
    .c-readout__status {
        display: inline-flex;
        align-items: center;
        gap: var(--space-2);
    }
    .c-readout__dot {
        width: var(--space-2);
        height: var(--space-2);
        border-radius: 50%;
        flex-shrink: 0;
    }
    .c-readout__dot--neutral { background: var(--color-ink-mute); }
    .c-readout__dot--info    { background: var(--color-info); }
    .c-readout__dot--success { background: var(--color-success); }
    .c-readout__dot--warning { background: var(--color-warn); }
    .c-readout__dot--danger  { background: var(--color-error); }

    /* Generic tone badge for a ReadoutItem with Kind=Badge. Same shape and
       token palette as .app-doc-expiry-pill, but tone-driven (Neutral / Info /
       Success / Warning / Danger) so any readout can use it without coupling to
       a domain. */
    .c-readout__badge {
        display: inline-flex;
        align-items: center;
        gap: var(--space-1);
        padding: var(--space-1) var(--space-2);
        border: 1px solid transparent;
        border-radius: var(--radius-pill);
        font-size: var(--fs-ui-sm);
        font-weight: 500;
        line-height: 1;
        white-space: nowrap;
    }
    .c-readout__badge--neutral { background: var(--color-surface-alt);  color: var(--color-ink-soft);     border-color: var(--color-line); }
    .c-readout__badge--info    { background: var(--color-info-soft);    color: var(--color-info-deep);    border-color: var(--color-info); }
    .c-readout__badge--success { background: var(--color-success-soft); color: var(--color-success-deep); border-color: var(--color-success); }
    .c-readout__badge--warning { background: var(--color-warn-soft);    color: var(--color-warn-deep);    border-color: var(--color-warn); }
    .c-readout__badge--danger  { background: var(--color-error-soft);   color: var(--color-error-deep);   border-color: var(--color-error); }

    /* ─── 7. Form field ───────────────────────────────────────────────
       Editable field cluster — label on top, input below. Container-
       independent: renders the same regardless of where it's dropped.
       Use .c-form-field-row to put two fields side-by-side; collapses
       to stacked at narrow viewports.

       Mirrors the wizard's .c-wizard__field set so anything moving from
       a wizard context to a generic form context can swap class prefixes
       and look identical.
       ─────────────────────────────────────────────────────────────── */

    .c-form-field {
        display: flex;
        flex-direction: column;
        gap: var(--space-2);
    }

    .c-form-field-label {
        font-size: var(--fs-ui);
        font-weight: 500;
    }

    .c-form-field-hint {
        font-size: var(--fs-ui-sm);
        color: var(--color-ink-mute);
    }

    .c-form-field input[type="text"],
    .c-form-field input[type="date"],
    .c-form-field input[type="email"],
    .c-form-field input[type="tel"],
    .c-form-field input[type="number"],
    .c-form-field select,
    .c-form-field textarea {
        width: 100%;
        padding: var(--space-3);
        border: 1px solid var(--color-line);
        border-radius: var(--radius-sm);
        font: inherit;
    }

    .c-form-field input[type="file"] {
        padding: var(--space-3);
        border: 1px dashed var(--color-line);
        border-radius: var(--radius-sm);
        background: var(--color-surface-alt);
        width: 100%;
    }

    .c-form-field--flagged input,
    .c-form-field--flagged select {
        border-color: var(--color-warn);
        box-shadow: 0 0 0 3px var(--color-warn-glow);
    }

    .c-form-field--flagged .c-form-field-flag {
        font-size: var(--fs-ui-sm);
        color: var(--color-warn-deep);
        font-weight: 500;
    }

    .c-form-field-row {
        display: flex;
        gap: var(--space-3);
    }

    .c-form-field-row > .c-form-field {
        flex: 1;
    }

    @media (max-width: 48rem) {
        .c-form-field-row {
            flex-direction: column;
        }
    }

    /* ─── 8. Card ─────────────────────────────────────────────────────
       Boxed content panel with optional head row (title + action link).
       Generic — wraps any content. The head row is not rendered when
       neither title nor action is supplied. Container-independent.
       ─────────────────────────────────────────────────────────────── */

    /* Shared card shell — both the readout cards (<app-readout-card> /
       <app-readout-cards>) and the wizard cards (.c-wizard__card, incl. the
       registry-extract viewer) render the same flat, transparent, bordered
       shell. One definition so the look can't drift between them; the
       wizard-specific head/title/subtitle rules live in app-c-wizard.css. */
    .c-card,
    .c-wizard__card {
        border: 1px solid var(--color-line);
        border-radius: var(--radius-md);
        padding: var(--space-5);
        margin-bottom: var(--space-5);
        background: transparent;
        /* Fill the cross-axis when dropped inside a flex container that doesn't
           stretch its children (the common .app-section sets align-items:
           flex-start) — otherwise sibling cards shrink to their own content and
           render at different widths. No-op in normal block flow. */
        align-self: stretch;
    }

    .c-card__head {
        display: flex;
        justify-content: space-between;
        align-items: center;
        margin-bottom: var(--space-4);
    }

    .c-card__title {
        font-size: var(--fs-heading);
        font-weight: 600;
        margin: 0;
    }

    /* ─── 9. Disclosure ───────────────────────────────────────────────
       Native <details>/<summary> accordion styled to the design
       system. Use anywhere a row should expand to reveal more text
       — FAQs, glossary entries, expandable policy clauses,
       "Read more" panels, settings sections. Zero JS.

       Markup:
         <details class="c-disclosure">
             <summary class="c-disclosure__summary">Question</summary>
             <div class="c-disclosure__body">
                 <p>Answer paragraph(s).</p>
             </div>
         </details>

       Rows separate themselves with hairline borders. Use a
       <section class="u-mb-9"> wrapper to group several together. */

    .c-disclosure {
        border-bottom: 1px solid var(--color-line);
    }

    .c-disclosure:first-of-type {
        border-top: 1px solid var(--color-line);
    }

    /* The summary is the disclosure trigger. We suppress the
       browser's default marker on both Blink (list-style) and
       WebKit (::-webkit-details-marker) and provide our own
       chevron via ::after. */
    .c-disclosure__summary {
        list-style: none;
        font-family: var(--font-display);
        font-size: var(--fs-body-lg);
        font-weight: 400;
        color: var(--color-ink);
        padding: var(--space-5) var(--space-2);
        cursor: pointer;
        display: flex;
        align-items: center;
        gap: var(--space-4);
        line-height: 1.3;
        transition: color var(--dur-base) var(--ease);
    }

    .c-disclosure__summary::-webkit-details-marker {
        display: none;
    }

    /* Chevron pointing down when closed, up when open. Pure CSS
       — two adjacent borders rotated 45°. */
    .c-disclosure__summary::after {
        content: "";
        flex-shrink: 0;
        margin-left: auto;
        width: 0.5rem;
        height: 0.5rem;
        border-right: 1.5px solid currentColor;
        border-bottom: 1.5px solid currentColor;
        transform: rotate(45deg) translate(-2px, -2px);
        transition: transform var(--dur-base) var(--ease);
        color: var(--color-ink-mute);
    }

    .c-disclosure[open] > .c-disclosure__summary::after {
        transform: rotate(-135deg) translate(-2px, -2px);
    }

    .c-disclosure__summary:hover,
    .c-disclosure__summary:hover::after {
        color: var(--color-accent);
    }

    .c-disclosure__summary:focus-visible {
        outline: 2px solid var(--color-accent);
        outline-offset: 4px;
        border-radius: 2px;
    }

    /* The expanded body. Constrained reading measure, muted body
       colour, ink-strong emphasis, brand-coloured links. */
    .c-disclosure__body {
        padding: 0 var(--space-2) var(--space-6);
        color: var(--color-ink-soft);
        font-size: var(--fs-body);
        line-height: 1.6;
        max-width: 70ch;
    }

    .c-disclosure__body > * + * {
        margin-top: var(--space-4);
    }

    .c-disclosure__body p {
        margin: 0;
    }

    .c-disclosure__body strong {
        color: var(--color-ink);
        font-weight: 500;
    }

    .c-disclosure__body ul {
        margin: 0;
        padding-left: var(--space-5);
    }

    .c-disclosure__body li {
        margin: 0;
    }

    .c-disclosure__body li + li {
        margin-top: var(--space-2);
    }

    .c-disclosure__body a {
        color: var(--color-accent);
        text-decoration: underline;
        text-underline-offset: 0.2em;
    }

    .c-disclosure__body a:hover {
        color: var(--color-accent-deep);
    }

    @media (prefers-reduced-motion: reduce) {
        .c-disclosure__summary,
        .c-disclosure__summary::after {
            transition: none;
        }
    }

    /* ─── 10. Page note ───────────────────────────────────────────────
       Hairline-topped muted text block at the bottom of a reference
       page — typically contact info or a "for more information"
       footer. Generic; use on any page that needs a low-key
       end-of-content note. */
    .c-page-note {
        margin-top: var(--space-9);
        padding-top: var(--space-6);
        border-top: 1px solid var(--color-line);
        color: var(--color-ink-mute);
        font-size: var(--fs-body-sm);
    }

    .c-page-note p {
        margin: 0;
    }

    .c-page-note a {
        color: var(--color-accent);
        text-decoration: underline;
        text-underline-offset: 0.2em;
    }

    .c-page-note a:hover {
        color: var(--color-accent-deep);
    }
}
