/* ============================================================================
   NexRx — Detail-view restyle (XAF Form Layout groups + tabs)

   Targets DevExpress Blazor XAF detail-view rendering. Real DX class names
   (confirmed via DevTools inspection on the live ScanSession_DetailView):

     Root form-layout group → DXBL-FORM-LAYOUT-GROUP.dxbl-fl-group.dxbl-fl-gd
       The .dxbl-fl-gd modifier marks the OUTERMOST group; nested column
       groups carry only .dxbl-fl-group and should NOT get card framing.
     Collapsible wrapper inside → DXBL-GROUP-CONTROL.dxbl-group
     Caption strip ("Scan Session") → div.dxbl-group-header.dxbl-fl-caption-tmpl
     Body container → div.dxbl-group-body-content (inside .dxbl-fl-group-body)
     Tab list → DXBL-TAB-LIST.dxbl-tabs-tablist
     Tab item → DXBL-TAB-ITEM.dxbl-tabs-item (active: .dxbl-tabs-item.dxbl-active)

   `!important` is required on typography/color because legacy
   `arex.bs5.css * { font-size: 14px !important; color: rgb(0,30,75) !important }`
   wins specificity otherwise.

   Tokens come from nexrx.tokens.css.
   ============================================================================ */

/* ---------- Root form-layout group → .grp (card) ----------
   Only the outermost group gets the card framing. .dxbl-fl-gd marks it.
   Use a stronger shadow than --shadow-card so the card actually reads as
   a panel against the canvas background — the default token shadow is
   too subtle on the empty-state detail view. */
.dxbl-fl-group.dxbl-fl-gd {
    background: var(--white) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) !important;
    box-shadow: 0 1px 2px rgba(15, 23, 48, .06), 0 4px 12px -4px rgba(15, 23, 48, .08) !important;
    overflow: hidden;
    margin-bottom: 14px;
}

/* DX form-layout wrappers (`.dxbl-fl-gd` form-layout root, `.dxbl-fl-gt`
   tab-group wrapper) ship with `padding: 0 7px` that creates a 7 px
   white sliver inside the card — gradient header/tab strip then doesn't
   reach card edges. Strip the padding so inner content fills full card
   width. */
.dxbl-fl-gd,
.dxbl-fl-gt {
    padding: 0 !important;
}

/* Nested column groups inside the card: strip any border/shadow they may
   inherit from DX defaults — they are layout helpers, not cards. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group:not(.dxbl-fl-gd) {
    background: transparent !important;
    border: 0 !important;
    box-shadow: none !important;
    border-radius: 0 !important;
    margin: 0 !important;
}

/* ---------- Group caption bar → .grp__head ----------
   teal-50 → white gradient strip with Lexend semibold navy-900 title.
   Bumped to teal-100 → teal-50 → white triple-stop so the gradient
   actually reads.
   `border: 5px solid white` on top/right/left is what DX defaults
   ship for `.dxbl-group-header` — we strip it so the gradient reaches
   the card's rounded corners flush. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-group-header.dxbl-fl-caption-tmpl,
.dxbl-fl-group.dxbl-fl-gd .dxbl-group-header.dxbl-fl-caption-tmpl {
    display: flex !important;
    align-items: center !important;
    gap: 10px !important;
    padding: 10px 16px !important;
    background: linear-gradient(180deg, var(--teal-100) 0%, var(--teal-50) 60%, var(--white) 100%) !important;
    border-top: 0 !important;
    border-right: 0 !important;
    border-left: 0 !important;
    /* Use ink-200 (same as card outer border) so the line reads as a
       clean separator between the gradient header and the body —
       teal-100 against the gradient's white tail looked floating. */
    border-bottom: 1px solid var(--ink-200) !important;
    min-height: 44px !important;
    font-family: var(--font-display) !important;
    font-weight: 600 !important;
    font-size: 13px !important;
    color: var(--navy-900) !important;
    letter-spacing: 0 !important;
}

/* Body padding for the card. Top padding sized so the first field
   row has visible breathing room below the header. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body .dxbl-group-body-content,
.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group-body .dxbl-group-body-content {
    padding: 18px 18px 16px !important;
}

/* ---------- Nested .dxbl-fl-gd → flat subsection ----------
   A .dxbl-fl-gd nested inside another .dxbl-fl-gd (e.g. Pack / Product
   inside ScanHistoryRecord) shouldn't repeat the heavy outer treatment:
   no big gradient header, no card-level shadow. Spec: small uppercase
   header strip on ink-50, ink-200 outline, gray body for visual
   contrast against the white parent card. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group.dxbl-fl-gd {
    background: var(--ink-50) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) !important;
    box-shadow: none !important;
    margin-bottom: 10px !important;
    overflow: hidden;
}

.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-group-header.dxbl-fl-caption-tmpl,
.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group.dxbl-fl-gd .dxbl-group-header.dxbl-fl-caption-tmpl {
    background: var(--white) !important;
    border: 0 !important;
    border-bottom: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) var(--r-lg) 0 0 !important;
    padding: 10px 16px !important;
    min-height: 44px !important;
    font-family: var(--font-display) !important;
    font-size: 13px !important;
    font-weight: 600 !important;
    color: var(--navy-900) !important;
    text-transform: none !important;
    letter-spacing: 0 !important;
}

.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body .dxbl-group-body-content,
.dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group.dxbl-fl-gd .dxbl-fl-group-body .dxbl-group-body-content {
    background: var(--ink-50) !important;
    padding: 18px 18px 16px !important;
}

/* ---------- 2-column grid for nested sub-cards (Pack ⟂ Product etc.) ----------
   XAFML defines Pack and Product as SEPARATE top-level groups inside the
   ScanHistoryRecord_DetailView root group. Each lands in its own `.dxbl-row`
   with `.dxbl-col-md-12` (= 100% width), so they stack vertically. We
   detect bodies that contain nested sub-cards (`.dxbl-fl-group.dxbl-fl-gd`
   inside `.dxbl-row`) and convert them to a 2-column CSS grid. Rows that
   carry only field-level items (not sub-cards) span full width via `:has()`. */

/* Only apply the 2-column grid when the body-content contains AT
   LEAST TWO rows with a direct `.dxbl-fl-gd` child (genuine paired
   sub-cards like Pack & Product). Without this guard the grid also
   activates on popup bodies that have a single row containing one
   `.dxbl-fl-gd` (e.g. "Advanced") next to a field item, which would
   wrongly shrink the lone row to half the body width. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body > .dxbl-group-body-content:has(> .dxbl-row:nth-child(2) > .dxbl-fl-group.dxbl-fl-gd) {
    display: grid !important;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 14px;
}

/* Inside the grid layout, every `.dxbl-row` is a single grid cell by
   default — its inner flex layout still positions a single sub-card or
   field group nicely. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body > .dxbl-group-body-content:has(> .dxbl-row:nth-child(2) > .dxbl-fl-group.dxbl-fl-gd) > .dxbl-row {
    margin: 0 !important;
    display: block !important;
}

/* Rows that don't contain a sub-card (e.g., FMD field block, action-results
   table) span both grid columns to keep wide content full-width. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body > .dxbl-group-body-content:has(> .dxbl-row > .dxbl-fl-group.dxbl-fl-gd) > .dxbl-row:not(:has(> .dxbl-fl-group.dxbl-fl-gd)) {
    grid-column: 1 / -1;
}

/* ---------- Tab area as a card → .tabcard ----------
   The whole `.dxbl-tabs` wrapper (strip + content) gets card framing so
   the Scans/Tags grid sits inside a panel matching the form-layout cards
   above, not floating freely on the canvas. */
.dxbl-tabs {
    background: var(--white) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) !important;
    box-shadow: 0 1px 2px rgba(15, 23, 48, .06), 0 4px 12px -4px rgba(15, 23, 48, .08) !important;
    overflow: hidden !important;
    margin-bottom: 14px;
}

/* ---------- Tabs (Scans / Tags) → .tabcard ----------
   DX exposes tab theming via CSS custom properties on `.dxbl-tabs`. We
   override them rather than fight specificity — DX's own selector chain
   (`.dxbl-tabs > .dxbl-tabs-tablist > .dxbl-scroll-viewer > ... > li > .dxbl-tabs-item:not(...):not(...).dxbl-active`)
   has specificity around (0,9,2), so plain class selectors lose. */
.dxbl-tabs {
    --dxbl-tabs-bg: var(--ink-50) !important;
    --dxbl-tabs-color: var(--ink-500) !important;

    /* Tab buttons */
    --dxbl-tabs-tab-btn-bg: transparent !important;
    --dxbl-tabs-tab-btn-color: var(--ink-500) !important;
    --dxbl-tabs-tab-border-color: transparent !important;
    --dxbl-tabs-tab-border-width: 0 !important;
    --dxbl-tabs-tab-hover-bg: transparent !important;
    --dxbl-tabs-tab-hover-color: var(--navy-900) !important;

    /* Active tab — flat white surface, no pill */
    --dxbl-tabs-tab-selected-bg: var(--white) !important;
    --dxbl-tabs-tab-selected-color: var(--navy-900) !important;
}

/* Strip itself: teal-50 tint reads as a discrete header band above the
   white grid below. The original ink-50 (#F6F8FC) was too close to
   --canvas (#F2F5FA) and visually disappeared. teal-50 also matches the
   form-group caption gradient. */
.dxbl-tabs > .dxbl-tabs-tablist {
    background: var(--teal-50) !important;
    /* 2 px so the divider reads as a proper separator and aligns with
       the 2 px teal-500 active-tab underline. */
    border-bottom: 2px solid var(--teal-100) !important;
    padding: 0 16px !important;
}

/* Active tab — flat white surface, teal-500 underline. Must match the
   exact specificity of the legacy `arex.bs5.css` rule that hardcodes
   `background: rgb(211, 240, 246) !important` for the active tab. */
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled).dxbl-active,
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled).dxbl-active {
    background: var(--white) !important;
    color: var(--navy-900) !important;
    border: 0 !important;
    border-bottom: 2px solid var(--teal-500) !important;
    border-radius: 0 !important;
    margin-bottom: -1px !important;
    font-weight: 600 !important;
    padding: 4px 14px 6px !important;
    font-size: 13px !important;
}

/* Inactive tab — flat, ink-500 muted, transparent underline placeholder.
   Use the same DX selector specificity to beat the legacy
   `arex.bs5.css * { color: rgb(0,30,75) !important }` rule. The selector
   covers default + :hover state because legacy `arex.bs5.css` ships a
   separate `:hover` rule that re-introduces the teal-100 pill background
   and DX defaults change padding from our 4/14/6 to 8/14/10 → shift. */
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled),
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled),
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled):hover,
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled):hover {
    color: var(--ink-500) !important;
    background: transparent !important;
    border: 0 !important;
    border-bottom: 2px solid transparent !important;
    border-radius: 0 !important;
    font-weight: 500 !important;
    font-size: 13px !important;
    padding: 4px 14px 6px !important;
    margin-bottom: -1px !important;
    transition: color .12s ease, border-color .12s ease, background-color .12s ease;
}

/* On hover, accent the tab subtly without the legacy teal pill — promote
   text color to navy-900 and add a 2px teal-300 bottom-border preview.
   The bg override beats the `arex.bs5.css .dxbl-btn:not(.dxbl-disabled):not(:disabled):hover { background: rgb(211,240,246) !important }`
   that paints every hovered button with a teal pill. */
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled):not(.dxbl-active):hover,
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled):not(.dxbl-active):hover {
    background: transparent !important;
    color: var(--navy-900) !important;
    border-bottom-color: var(--teal-300) !important;
}

/* Tablist height — match tab-item so there's no teal-50 strip showing
   below the active tab (was 47 px tall while tab-item is 38 px,
   leaving a 9 px sliver pod tabama). */
.dxbl-tabs > .dxbl-tabs-tablist {
    min-height: 36px !important;
}

.dxbl-tabs > .dxbl-tabs-tablist > .dxbl-scroll-viewer,
.dxbl-tabs > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content,
.dxbl-tabs > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul {
    min-height: 0 !important;
}

/* ---------- Kill all hover/focus/active effects on toolbar buttons ----------
   `arex.bs5.css` ships `.dxbl-btn:not(...):not(...):hover { background: rgb(211,240,246) !important }`
   which paints every toolbar / nested-toolbar button with a teal-100
   pill on hover.
   `nexrx.shell.css` adds a teal-500 border + teal-100 box-shadow ring
   on `:focus-visible` for main-toolbar buttons.
   Combined these cause the "probliknutí" (flash) when user hovers,
   focuses or clicks. Disable all interactive surface changes — only
   the cursor signals interactivity. */
.main-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):hover,
.main-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus,
.main-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus-visible,
.main-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):active,
.nested-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):hover,
.nested-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus,
.nested-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus-visible,
.nested-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):active,
.nested-frame .dxbl-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):hover,
.nested-frame .dxbl-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus,
.nested-frame .dxbl-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):focus-visible,
.nested-frame .dxbl-toolbar .dxbl-btn:not(.dxbl-disabled):not(:disabled):active {
    background: transparent !important;
    border-color: transparent !important;
    box-shadow: none !important;
    outline: none !important;
}

/* The `nexrx.shell.css` `#main-window-template-component .main-toolbar .dxbl-btn.dxbl-btn-secondary:focus-visible`
   rule has high specificity (id + descendant + 2 classes + pseudo). Match it. */
#main-window-template-component .main-toolbar .dxbl-btn.dxbl-btn-secondary:focus-visible,
#main-window-template-component .main-toolbar .dxbl-btn.dxbl-btn-outline-secondary:focus-visible,
#main-window-template-component .main-toolbar .dxbl-btn.dxbl-btn-primary:focus-visible {
    border-color: transparent !important;
    box-shadow: none !important;
    outline: none !important;
}

/* Kill the 120 ms background-color / color / box-shadow transition on
   toolbar buttons. With both rest and hover states identical, the
   transition could otherwise flicker through DX's intermediate teal-100
   `:hover` paint before our `transparent !important` lands (the
   "probliknutí" / shitty animation). Match nexrx.shell.css's id-scoped
   selector to win specificity. */
#main-window-template-component .main-toolbar .dxbl-btn,
.nested-frame .main-toolbar .dxbl-btn,
.main-toolbar.main-toolbar .dxbl-btn,
.nested-toolbar .dxbl-btn,
.nested-frame .dxbl-toolbar .dxbl-btn {
    transition: none !important;
}

/* The text label inside the tab inherits color from the tab item. The
   legacy `arex.bs5.css * { color: rgb(0,30,75) !important }` would
   otherwise force navy on every tab regardless of state. */
.dxbl-tabs .dxbl-tabs-item .dxbl-text,
.dxbl-tabs .dxbl-tabs-item .dxbl-tabs-text-container,
.dxbl-tabs .dxbl-tabs-item .dxbl-tabs-text-overflow {
    color: inherit !important;
    font: inherit !important;
    font-size: 13px !important;
    font-weight: inherit !important;
}

/* Explicit font-size on both tab states so DX defaults / legacy globals
   can't push them to 10.5 px (inactive) or 16 px (active).
   NOTE: padding/min-height moved to the per-state rules below (4/14/6
   inactive + active, no min-height) to keep all tab geometry in one
   place — old 8/14/10 was overriding the newer compact rule. */
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > .dxbl-scroll-viewer > .dxbl-scroll-viewer-content > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled),
.dxbl-tabs.dxbl-tabs-top > .dxbl-tabs-tablist > ul > li > .dxbl-tabs-item:not(.dxbl-tabs-tmpl):not(.dxbl-disabled):not(:disabled) {
    font-size: 13px !important;
    font-family: var(--font-ui) !important;
}

/* ---------- Form rows: typography color normalization ----------
   Legacy `arex.bs5.css * { color: rgb(0,30,75) !important }` paints every
   element with the old #001E4B navy, including field labels and values
   in the detail-view form. We force them onto the NexRx --navy-900 token
   so the detail view shares the same ink with cards / KPI headings. */

/* Field labels in form layout (Device, User, Start Date, Focus, ...). */
.dxbl-fl-item.dxbl-fl-item-horizontal > .dxbl-fl-cpt,
.dxbl-fl-cpt {
    color: var(--navy-900) !important;
    font-family: var(--font-ui) !important;
    font-size: 13px !important;
    font-weight: 500 !important;
    letter-spacing: 0 !important;
}

/* Field values (input text, plain-text displays). */
.dxbl-fl-item.dxbl-fl-item-horizontal,
.dxbl-fl-item.dxbl-fl-item-horizontal .dxbl-text {
    color: var(--navy-900) !important;
}

/* Form row min-height — XAF default sits at 30 px which looks cramped on a
   13 px label baseline. Push to 32 px for breathing room. */
.dxbl-fl-item.dxbl-fl-item-horizontal {
    min-height: 32px !important;
}

/* ---------- Form group flex gaps ----------
   XAF Form Layout leaves row/column gap on `normal`. We add gap for
   FIELD rows only (children are `.dxbl-fl-item`). Sub-card rows
   (children are `.dxbl-fl-group` with `.dxbl-col-md-6`) MUST NOT get
   the gap — Bootstrap-style 50% column widths already sum to 100% and
   adding 22 px column-gap pushes them over and triggers flex-wrap,
   stacking Pack/Product vertically instead of side-by-side. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-row:has(> .dxbl-fl-item) {
    row-gap: 6px !important;
    column-gap: 22px !important;
}

/* Real sub-card rows (children are framed .dxbl-fl-gd cards): keep
   row-gap for stacked sub-cards. Horizontal gap is handled via inner
   margin on the card (see below) because the XAF layout typically
   wraps each card in an unframed col-md-6 wrapper that fills 100 %
   of its share — column-gap on the outer row has nothing to shrink. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-row:has(> .dxbl-fl-group.dxbl-fl-gd) {
    row-gap: 14px !important;
}

/* Paired sub-cards (.dxbl-fl-gd inside a col-md-6 wrapper). Shrink
   each wrapper by padding so the card inside leaves a visible
   horizontal gap between adjacent pairs. Padding on the wrapper
   (vs margin on the card) works because the card's col-md-12 inside
   the wrapper fills the wrapper's content-box, not its padding-box. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body > .dxbl-group-body-content > .dxbl-row > .dxbl-fl-group:not(.dxbl-fl-gd).dxbl-col-md-6:nth-child(odd) {
    padding-right: 19px !important;
}
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-fl-group-body > .dxbl-group-body-content > .dxbl-row > .dxbl-fl-group:not(.dxbl-fl-gd).dxbl-col-md-6:nth-child(even) {
    padding-left: 19px !important;
}

/* Header-less layout-only wrapper groups (.dxbl-fl-group WITHOUT
   .dxbl-fl-gd): these are pure structural containers XAF inserts
   around nested item groups — they have no caption, no card framing,
   no visual presence. They must contribute zero vertical rhythm so
   nested fields read as one continuous stack. Treat their rows like
   field rows (6 px row-gap, no column-gap). */
.dxbl-fl-group.dxbl-fl-gd .dxbl-row:has(> .dxbl-fl-group:not(.dxbl-fl-gd)) {
    row-gap: 6px !important;
    column-gap: 0 !important;
}

/* ---------- Orphan memo items (Note field) ----------
   XAFML places ScanSession.Note as a top-level layout-item outside any
   `.dxbl-fl-gd` group, so by default it sits naked on the canvas without
   card framing. Detect by the XAF-emitted item class and wrap in card
   styling that matches sibling form cards. */
.dxbl-fl-item:has(> label.xaf-item-note),
.dxbl-fl-item:has(> .dxbl-fl-cpt.xaf-item-note) {
    background: var(--white) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) !important;
    box-shadow: 0 1px 2px rgba(15, 23, 48, .06), 0 4px 12px -4px rgba(15, 23, 48, .08);
    padding: 14px 18px !important;
    margin: 0 0 16px !important;
}

/* ---------- Vertical rhythm between groups & fields ----------
   `arex.bs5.css` sets `.dxbl-col { margin-top: var(--dxbl-row-item-spacing-y) }`
   = 7 px on every column. Stacked with cards' own `margin-bottom: 14 px`
   that produces 21+ px gaps between sections — loose & uneven.

   Solution:
   - Top-level columns (cards, Note) get `margin-top: 0` + clean
     `margin-bottom: 16 px` for consistent 16 px between cards.
   - The VERY FIRST top-level card keeps 12 px top breathing room from
     the toolbar above.
   - Inner field-row columns (inside a `.dxbl-fl-gd` card body) keep an
     8 px row rhythm so fields breathe but stay compact. */
.detail-view-content .dxbl-fl > .dxbl-row > .dxbl-col,
.detail-view-content .dxbl-fl > .dxbl-row > .dxbl-fl-group > .dxbl-row > .dxbl-col {
    margin-top: 0 !important;
}

/* Breathing room from the top toolbar above. XAF nests the user's
   group inside several `.dxbl-fl-group:not(.dxbl-fl-gd)` wrappers
   whose first inner `.dxbl-row` carries `margin-top: -7 px` (DX
   gutter compensation). Two effective rows stack → -14 px, which
   eats any padding on `.detail-view-content`. Zero the negative
   margin on those wrapper rows and add explicit top padding to
   guarantee a visible gap below the toolbar. */
.detail-view-content {
    padding-top: 14px !important;
}
.detail-view-content .dxbl-fl-group:not(.dxbl-fl-gd) > .dxbl-row {
    margin-top: 0 !important;
}

/* Unified rhythm: row-gap on the parent row carries all vertical
   spacing (6 px), so columns themselves don't add margin. Matches the
   compact look of nested sub-card bodies. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-group-body-content .dxbl-col {
    margin-top: 0 !important;
}

/* First row inside a card body — no top margin so it sits flush with
   the gradient header strip's 14 px body padding. */
.dxbl-fl-group.dxbl-fl-gd .dxbl-group-body-content > .dxbl-row:first-child > .dxbl-col,
.dxbl-fl-group.dxbl-fl-gd .dxbl-group-body-content > .dxbl-col:first-child {
    margin-top: 0 !important;
}

/* Consistent 16 px vertical gap between top-level cards. Override DX
   `.dxbl-fl-group { margin: 7px 0 14px }`. We only set top/bottom (not
   the full shorthand) so the `:first-child { margin-top: 12px }` rule
   above can still apply breathing room from the toolbar. */
.dxbl-fl-group.dxbl-fl-gd,
.dxbl-tabs {
    margin-top: 0 !important;
    margin-bottom: 16px !important;
}

/* ---------- Field labels & inputs typography ----------
   Tighten label / input dimensions to a denser, more professional 30 px
   row height. 12 px labels + 12.5 px input text balance information
   density with legibility. */
.dxbl-fl-cpt {
    font-size: 12px !important;
}

.dxbl-fl-item.dxbl-fl-item-horizontal {
    min-height: 28px !important;
}

.dxbl-text-edit input,
.dxbl-text-edit .dxbl-textbox-input,
.dxbl-textbox input,
.dxbl-spin-edit input,
.dxbl-date-edit input,
.dxbl-combobox input,
.dxbl-memo textarea {
    font-size: 12.5px !important;
    line-height: 18px !important;
}

/* ---------- Nested toolbar — flat style matching main toolbar ----------
   `arex.bs5.css` paints all `.dxbl-btn-secondary` with a 1 px #ced4da
   bootstrap-gray border. `nexrx.shell.css` overrides this for the main
   toolbar (`#main-window-template-component .main-toolbar`) to make
   buttons flat/transparent. The nested toolbar (action toolbar inside
   tab content) lives under `.nested-toolbar` / `.nested-frame` and
   wasn't covered. Apply the same flat treatment for visual consistency. */
.nested-toolbar .dxbl-btn.dxbl-btn-secondary,
.nested-toolbar .dxbl-btn.dxbl-btn-outline-secondary,
.nested-frame .dxbl-toolbar .dxbl-btn.dxbl-btn-secondary,
.nested-frame .dxbl-toolbar .dxbl-btn.dxbl-btn-outline-secondary {
    background-color: transparent !important;
    border-color: transparent !important;
    color: var(--ink-700) !important;
    box-shadow: none !important;
}

/* Match main-toolbar hover (nexrx.shell.css uses var(--ink-100) +
   navy-900 text + transparent border) so the two toolbars feel
   consistent. */
.nested-toolbar .dxbl-btn.dxbl-btn-secondary:hover:not(.dxbl-disabled):not([disabled]),
.nested-toolbar .dxbl-btn.dxbl-btn-outline-secondary:hover:not(.dxbl-disabled):not([disabled]),
.nested-frame .dxbl-toolbar .dxbl-btn.dxbl-btn-secondary:hover:not(.dxbl-disabled):not([disabled]),
.nested-frame .dxbl-toolbar .dxbl-btn.dxbl-btn-outline-secondary:hover:not(.dxbl-disabled):not([disabled]) {
    background-color: var(--ink-100) !important;
    border-color: transparent !important;
    color: var(--navy-900) !important;
    box-shadow: none !important;
}

/* Match main-toolbar font metrics (12.5 px Inter / weight 500 / no
   transform, see `nexrx.shell.css` `#main-window-template-component
   .main-toolbar .dxbl-btn` rule). DX default leaks 14 px here because
   nested toolbar isn't in the main-toolbar selector scope.
   `arex.bs5.css` ships
   `.dxbl-toolbar > .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-secondary
    { font-size: 14 px !important }` (4 classes + child combinator);
   match its specificity by scoping the same chain under our nested
   ancestors. */
.nested-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-secondary,
.nested-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-outline-secondary,
.nested-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-primary,
.nested-frame .dxbl-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-secondary,
.nested-frame .dxbl-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-outline-secondary,
.nested-frame .dxbl-toolbar .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-primary,
.nested-toolbar .dxbl-btn,
.nested-frame .dxbl-toolbar .dxbl-btn {
    font-family: var(--font-ui) !important;
    font-size: 12.5px !important;
    font-weight: 500 !important;
    line-height: 1 !important;
    letter-spacing: 0 !important;
    text-transform: none !important;
}

/* ---------- Flush nested grids inside tabs ----------
   `.dxbl-fl-tab-content` (the tab body container) and the wrapping
   `.dxbl-fl-item` each add `padding: 7px` (DX form-layout gutter).
   For a grid that fills the tab they stack → ~16 px dead space each
   side, making the grid look detached from the tab/card edges.
   Zero them when the tab item is a non-captioned full-width control
   like a grid. */
.dxbl-tabs .dxbl-fl-tab-content,
.dxbl-tabs .dxbl-fl-tab-content > .dxbl-row,
.dxbl-tabs .dxbl-fl-tab-content .dxbl-fl-item.dxbl-fl-tab-item {
    padding-left: 0 !important;
    padding-right: 0 !important;
    padding-bottom: 0 !important;
}
.dxbl-tabs .dxbl-fl-tab-content > .dxbl-row {
    margin-left: 0 !important;
    margin-right: 0 !important;
}

/* ---------- Grid corners flush with card ----------
   Inner grid + grid header/footer have their own border-radius (14 px on
   grid, 2.625 px legacy fractional on header-row) that fight the parent
   card's `overflow: hidden`. Reset to 0 so the surrounding card cleanly
   clips the corners. */
.dxbl-tabs .dxbl-grid,
.dxbl-fl-group.dxbl-fl-gd .dxbl-grid {
    border-radius: 0 !important;
}

.dxbl-tabs .dxbl-grid-header-row,
.dxbl-tabs .dxbl-grid-header-content,
.dxbl-tabs .dxbl-grid-footer,
.dxbl-fl-group.dxbl-fl-gd .dxbl-grid-header-row,
.dxbl-fl-group.dxbl-fl-gd .dxbl-grid-header-content,
.dxbl-fl-group.dxbl-fl-gd .dxbl-grid-footer {
    border-radius: 0 !important;
}

/* ---------- Pager footer cleanup ----------
   DX default page-size selector ships fractional 2.625 px padding on the
   label and a 10.5/11.5 px font mix that looks unfinished. Normalize. */
.dxbl-pager-page-size-selector {
    gap: 8px;
    font-size: 12.5px !important;
}

.dxbl-pager-page-size-selector > label.dxbl-text,
.dxbl-pager .dxbl-text {
    padding: 0 !important;
    font-size: 12.5px !important;
    color: var(--ink-700) !important;
}

.dxbl-pager-page-size-selector .dxbl-combobox,
.dxbl-pager-page-size-selector .dxbl-text-edit {
    font-size: 12.5px !important;
}

.dxbl-pager,
.dxbl-grid .dxbl-pager {
    padding: 4px 14px !important;
    gap: 8px !important;
    min-height: 0 !important;
}

/* DX `.dxbl-grid-bottom-panel.dxbl-pager-container` wraps the pager with
   its own 10/14 padding, stacking with the pager's padding to ~74 px.
   Slim it down. */
.dxbl-grid-bottom-panel,
.dxbl-grid .dxbl-pager-container,
.dxbl-grid-bottom-panel.dxbl-pager-container {
    padding: 4px 8px !important;
    min-height: 0 !important;
}

/* ---------- Input fields (DX inputs / spinners / dates) ----------
   Legacy `arex.bs5.css` sets text-edit `border-width: 0` and tints
   border-color with the legacy `rgb(0,30,75)` navy, leaving inputs as
   bare text on canvas. We re-introduce a 1 px ink-200 border at 6 px
   radius and white surface so fields read as discrete controls.
   `.dxbl-text-edit` is the actual DX 25.1.3 wrapper class (older docs
   call it `.dxbl-textbox`); cover both spellings. */
.dxbl-text-edit,
.dxbl-textbox,
.dxbl-textbox-readonly,
.dxbl-textbox-disabled,
.dxbl-spin-edit,
.dxbl-date-edit,
.dxbl-combobox,
.dxbl-memo,
.dxbl-edit-host {
    background: var(--white) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-sm) !important; /* 6 px */
    color: var(--navy-900) !important;
    padding: 3px 10px !important;
    min-height: 30px !important;
}

/* The inner `<input>` element inherits typography but DX paints its own
   color/border that we have to neutralize so the wrapper styling shows. */
.dxbl-text-edit input,
.dxbl-text-edit .dxbl-textbox-input,
.dxbl-textbox input,
.dxbl-textbox .dxbl-textbox-input,
.dxbl-spin-edit input,
.dxbl-date-edit input,
.dxbl-combobox input,
.dxbl-memo textarea,
.dxbl-fl-item.dxbl-fl-item-horizontal input[type="text"],
.dxbl-fl-item.dxbl-fl-item-horizontal input[type="number"],
.dxbl-fl-item.dxbl-fl-item-horizontal textarea {
    background: transparent !important;
    border: 0 !important;
    color: var(--navy-900) !important;
    padding: 0 !important;
    font-family: var(--font-ui) !important;
    font-size: 13px !important;
}

.dxbl-textbox:focus-within,
.dxbl-spin-edit:focus-within,
.dxbl-date-edit:focus-within,
.dxbl-combobox:focus-within,
.dxbl-memo:focus-within {
    border-color: var(--teal-500) !important;
    box-shadow: 0 0 0 3px var(--teal-100) !important;
}

/* ---------- Caption header — radius flush with card edge ----------
   DX defaults the group-header `border-radius` to 5 px. The outer card
   has `overflow: hidden` AND `border-radius: 14 px`, so the 9-px
   difference between header curve (5) and card curve (14) leaves a
   visible white sliver at the top corners. Force the header to match
   the card's top corners. */
.dxbl-fl-group.dxbl-fl-gd > .dxbl-group > .dxbl-group-header.dxbl-fl-caption-tmpl,
.dxbl-fl-group.dxbl-fl-gd .dxbl-group-header.dxbl-fl-caption-tmpl {
    border-radius: var(--r-lg) var(--r-lg) 0 0 !important; /* 14 14 0 0 */
}

/* ========================================================================
   POPUP / MODAL — match the card visual language
   DX modal classes (confirmed via DevTools):
     Dialog box       → .dxbl-popup[role="dialog"]
     Content wrapper  → .dxbl-modal-content
     Header strip     → .dxbl-modal-header.dxbl-popup-header
     Title spans      → .xaf-view-caption-sm + .xaf-object-caption
     Body             → .dxbl-modal-body
     Footer toolbar   → .dxbl-modal-footer
   DX defaults ship 5.25 px radius, 12.25 px header font, 7 px body
   padding — fractional bootstrap values that look unfinished. Apply
   the same tokens used for `.dxbl-fl-gd` cards so popups feel like a
   floating version of the same surface.
   ======================================================================== */
.dxbl-popup[role="dialog"],
.dxbl-popup[role="dialog"] .dxbl-modal-content {
    background: var(--white) !important;
    border: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) !important;
    box-shadow: 0 12px 28px -8px rgba(15, 23, 48, .25), 0 4px 12px rgba(15, 23, 48, .08) !important;
    overflow: hidden;
}

/* Neutralize the `.main` shell wrapper bg inside popup bodies.
   site.css ships `.main { background: var(--canvas) }` for the page
   shell; XAF re-uses the same wrapper inside popups, which paints
   the popup body ink-50 grey (visible as stray bands above the first
   card and below the records grid where no content covers it). */
.dxbl-popup[role="dialog"] .dxbl-modal-body .main,
.dxbl-popup[role="dialog"] .dxbl-modal-body .main-content {
    background: transparent !important;
}

/* Header strip — gradient + Lexend title, matching the card caption.
   Use the same 3-stop teal-100→teal-50→white gradient so popups and
   card headers feel like one design family. */
.dxbl-popup[role="dialog"] .dxbl-modal-header.dxbl-popup-header {
    background: linear-gradient(180deg, var(--teal-100) 0%, var(--teal-50) 60%, var(--white) 100%) !important;
    border: 0 !important;
    border-bottom: 1px solid var(--ink-200) !important;
    border-radius: var(--r-lg) var(--r-lg) 0 0 !important;
    padding: 10px 16px !important;
    min-height: 48px !important;
    font-family: var(--font-display) !important;
    font-weight: 600 !important;
    font-size: 13px !important;
    color: var(--navy-900) !important;
    letter-spacing: 0 !important;
}

.dxbl-popup[role="dialog"] .dxbl-modal-header .xaf-view-caption-sm,
.dxbl-popup[role="dialog"] .dxbl-modal-header .xaf-object-caption {
    font-family: var(--font-display) !important;
    font-size: 13px !important;
    font-weight: 600 !important;
    color: var(--navy-900) !important;
}
/* Object caption (subtitle, e.g. "Verify") — lighter weight to read as
   secondary, same line. */
.dxbl-popup[role="dialog"] .dxbl-modal-header .xaf-object-caption {
    font-weight: 500 !important;
    color: var(--ink-500) !important;
    margin-left: 8px !important;
}

/* Close button (the `×` glyph) — flat ghost matching toolbar buttons. */
.dxbl-popup[role="dialog"] .dxbl-modal-header .dxbl-btn-close,
.dxbl-popup[role="dialog"] .dxbl-modal-header .dxbl-popup-close-button {
    background: transparent !important;
    border: 0 !important;
    color: var(--ink-700) !important;
    box-shadow: none !important;
    border-radius: 6px !important;
}
.dxbl-popup[role="dialog"] .dxbl-modal-header .dxbl-btn-close:hover:not(:disabled),
.dxbl-popup[role="dialog"] .dxbl-modal-header .dxbl-popup-close-button:hover:not(:disabled) {
    background: var(--ink-100) !important;
    color: var(--navy-900) !important;
}

/* Body — comfortable padding matching card body. */
.dxbl-popup[role="dialog"] .dxbl-modal-body {
    background: var(--white) !important;
    padding: 18px 18px 16px !important;
    color: var(--navy-900) !important;
}

/* Footer — subtle ink-50 strip with a clean separator above so action
   buttons feel anchored. */
.dxbl-popup[role="dialog"] .dxbl-modal-footer {
    background: var(--ink-50) !important;
    border-top: 1px solid var(--ink-200) !important;
    border-radius: 0 0 var(--r-lg) var(--r-lg) !important;
    padding: 10px 16px !important;
    min-height: 52px !important;
    gap: 8px;
}

/* Footer buttons — match toolbar font metrics (12.5 px Inter), use
   the same hover treatment as main / nested toolbars. arex.bs5.css
   ships `.dxbl-toolbar > .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-secondary
   { font-size: 14 px !important }` (4-class specificity), so scope the
   same chain under the popup footer to win. */
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-secondary,
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn-toolbar .dxbl-toolbar-btn.dxbl-btn.dxbl-btn-outline-secondary,
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn {
    font-family: var(--font-ui) !important;
    font-size: 12.5px !important;
    font-weight: 500 !important;
    line-height: 1 !important;
    letter-spacing: 0 !important;
    text-transform: none !important;
    border-radius: 6px !important;
    padding: 0 14px !important;
    height: 32px !important;
}

/* Secondary / ghost footer buttons (Cancel, Preview) — transparent
   surface, ink-100 hover. */
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-secondary,
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-outline-secondary {
    background: transparent !important;
    border: 1px solid transparent !important;
    color: var(--ink-700) !important;
    box-shadow: none !important;
}
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-secondary:hover:not(.dxbl-disabled):not(:disabled),
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-outline-secondary:hover:not(.dxbl-disabled):not(:disabled) {
    background: var(--ink-100) !important;
    color: var(--navy-900) !important;
    border-color: transparent !important;
}

/* Primary footer button (OK) — solid navy-900 to match the popup
   header title color and the page-level app shell. */
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-primary {
    background: var(--navy-900) !important;
    border: 1px solid var(--navy-900) !important;
    color: var(--white) !important;
    font-weight: 600 !important;
    box-shadow: none !important;
}
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn.dxbl-btn-primary:hover:not(.dxbl-disabled):not(:disabled) {
    background: var(--navy-800) !important;
    border-color: var(--navy-800) !important;
    color: var(--white) !important;
}

/* Kill transitions in the footer too — same flash issue as toolbar. */
.dxbl-popup[role="dialog"] .dxbl-modal-footer .dxbl-btn {
    transition: none !important;
}

/* ---------- Inline action-wrapper search box (Records filter etc.) ----------
   DX `.parametrized-action-wrapper.xaf-action-fulltextsearch` ships a
   bigger inner input (height 30px) and renders the outer `dxbl-text-edit`
   at 38px (3px y-padding + 30px input + 2px border) — much taller than
   regular inputs (30px). Snap the outer to 30px so it matches sibling
   editors and the design's input rhythm. */
.dxbl-text-edit.parametrized-action-wrapper,
.dxbl-text-edit.xaf-action-fulltextsearch {
    height: 30px !important;
    min-height: 30px !important;
    padding-top: 0 !important;
    padding-bottom: 0 !important;
}
.dxbl-text-edit.parametrized-action-wrapper > .dxbl-text-edit-input,
.dxbl-text-edit.xaf-action-fulltextsearch > .dxbl-text-edit-input,
.dxbl-text-edit.parametrized-action-wrapper > input,
.dxbl-text-edit.xaf-action-fulltextsearch > input {
    height: auto !important;
    min-height: 0 !important;
}
