/* ============================================================================
   hub-tables.css  -  the reference table system for the freedata hub.

   Owner : TABLES builder.  Loads AFTER hub-theme.css, custom.css, data-tables.css
           (order in <head>: vendors, app, poppins, hub-theme, custom, data-tables,
           hub-tables, $pageStyles).

   What lives here (one source of truth - nothing below is duplicated elsewhere):
     1. Tokens                      reference table palette (:root --tn-*)
     2. Table skin  ("T" aliases)   .table-neo look on the hub's legacy table wrappers:
                                    .txn-table table, .approval-table table, .data-table > table,
                                    .dt-container table.dataTable, .table-responsive > table.table,
                                    .card-body > table.table, .card > table.table.
                                    Opt out with .table-borderless, .table-dark or [data-plain]; tables that
                                    already carry .table-neo are left to hub-theme.css.
     3. Cell vocabulary             .u-* / .id-link / .cell-trunc for aliased tables, plus the hub's
                                    legacy helpers .cell-id .cell-amount .cell-time* .cell-muted
                                    .txn-id .txn-amount .txn-status .approval-id, row tints.
     4. Pills                       .status-badge(--*), .badge-soft-* and .badge bg-*-subtle inside
                                    tables, .ul-chip/.chip-*, per-console dot badges -> reference pills.
     5. Row actions                 .txn-actions, .dt-actions (kebab), .act-cell (SIM consoles).
     6. Hoisted inline families     .txn-clean, .atx-stat/.atx-ico, SIM-console cell helpers
                                    (zone chips, sim cells, select column ...). Views may DELETE
                                    their inline copies; everything functional is kept here.
     7. DataTables 2.x chrome       .dt-container, .dt-toolbar*, .dt-export-btn, .dt-length,
                                    .dt-search, .dt-footer/.dt-paginate, .dt-filter-panel*,
                                    empty state, sort glyph, responsive child rows, .dt-refreshing.

   Specificity note: the hoisted families are prefixed with .content-page so they also win
   against the not-yet-deleted per-view <style> copies (equal specificity + later in the
   document would otherwise let the inline copy win). Harmless once the copies are gone.
   ============================================================================ */

/* ----------------------------------------------------------------------------
   1. TOKENS  (reference the reference stylesheet values)
   ---------------------------------------------------------------------------- */
:root {
    /* Neutrals follow hub-theme.css (--hub-*) when it is loaded, so retuning the theme retunes
       the tables; the literals are the reference stylesheet values and are the fallback. */

    /* table skin */
    --tn-head-bg:   var(--hub-head-bg, #eef1f6);
    --tn-head-ink:  var(--hub-th, #5b6472);
    --tn-head-rule: var(--hub-head-border, #e8ecf3);
    --tn-cell-ink:  var(--hub-td, #3f4a5a);
    --tn-row-rule:  var(--hub-divider, #f0f2f6);
    --tn-row-hover: var(--hub-row-hover, #f7faff);
    --tn-foot-bg:   #f4f6fa;
    --tn-foot-rule: #e3e7ee;

    /* ink ladder */
    --tn-strong: var(--hub-ink-2, #1f2a3d);
    --tn-muted:  var(--hub-muted, #667085);
    --tn-sub:    var(--hub-sub, #98a2b3);
    --tn-faint:  var(--hub-faint, #c0c6d0);

    /* lines / surfaces */
    --tn-line:       var(--hub-border, #e7e9eb);
    --tn-input-line: var(--hub-input-border, #cfd4dc);
    --tn-surface-2:  #fafbfd;
    --tn-radius:     var(--hub-radius-card, 10px);
    --tn-focus:      var(--hub-focus, #1ab394);
    --tn-focus-ring: var(--hub-focus-ring, rgba(26, 179, 148, .14));

    /* pills (bg / ink) */
    /* inks follow hub-theme.css (--hub-pill-*-ink, all 4.65:1 or better on their tint); the literals are the fallback */
    --tn-green-bg:  #e6f7f1;  --tn-green-ink:  var(--hub-pill-green-ink, #087c57);
    --tn-blue-bg:   #e8f0fe;  --tn-blue-ink:   var(--hub-pill-blue-ink, #2966d2);
    --tn-info-bg:   #e4f4fb;  --tn-info-ink:   var(--hub-pill-info-ink, #0d7595);
    --tn-orange-bg: #fdf1e3;  --tn-orange-ink: var(--hub-pill-orange-ink, #9c5f07);
    --tn-red-bg:    #fdeaea;  --tn-red-ink:    var(--hub-pill-red-ink, #c92c2c);
    --tn-grey-bg:   #eef1f5;  --tn-grey-ink:   var(--hub-pill-grey-ink, #626c80);
    --tn-purple-bg: #efeaff;  --tn-purple-ink: var(--hub-pill-purple-ink, #6b4ee0);
}

/* ----------------------------------------------------------------------------
   2. TABLE SKIN  -  .table-neo look for the legacy wrappers ("T" aliases)
      T = :is( .txn-table table, .approval-table table, .data-table > table,
               .dt-container table.dataTable, .table-responsive > table.table,
               .card-body > table.table, .card > table.table )
          :not( .table-neo, .table-borderless, [data-plain] )
   ---------------------------------------------------------------------------- */

/* 2.0 wrappers: the table box is the card, so the legacy outline goes away.
       (.data-table keeps its own rounded outline - see data-tables.css.) */
.content-page :is(.txn-table, .apb-tbl).table-responsive {
    border: 0;
    border-radius: 0;
    overflow-x: auto;
}
.content-page :is(.txn-table, .apb-tbl) {
    scrollbar-width: thin;
    scrollbar-color: rgba(138, 150, 156, .45) transparent;
}
.content-page :is(.txn-table, .apb-tbl)::-webkit-scrollbar { height: 9px; }
.content-page :is(.txn-table, .apb-tbl)::-webkit-scrollbar-track { background: transparent; }
.content-page :is(.txn-table, .apb-tbl)::-webkit-scrollbar-thumb { background: rgba(138, 150, 156, .45); border-radius: 6px; }
.content-page :is(.txn-table, .apb-tbl)::-webkit-scrollbar-thumb:hover { background: rgba(138, 150, 156, .7); }

/* 2.1 table element */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) {
    --ins-table-hover-bg: transparent;      /* hover is painted by the td rule below, not by the theme overlay */
    margin-bottom: 0;
}

/* 2.2 header band */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > thead > tr > th {
    background-color: var(--tn-head-bg);
    color: var(--tn-head-ink);
    font-size: 10.5px;
    font-weight: 700;
    letter-spacing: .05em;
    text-transform: uppercase;
    line-height: 1.15;
    padding: .72rem 1rem;
    border: 0;
    border-bottom: 2px solid var(--tn-head-rule);
    white-space: nowrap;
    vertical-align: middle;
}

/* 2.3 body cells */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr > :is(td, th) {
    padding: .8rem 1rem;
    border: 0;
    border-bottom: 1px solid var(--tn-row-rule);
    vertical-align: middle;
    font-size: 13px;
    color: var(--tn-cell-ink);
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr:last-child > :is(td, th) {
    border-bottom: 0;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr:not(.child):hover > :is(td, th) {
    background-color: var(--tn-row-hover);
}

/* the single "nothing here" row (partials/dt_empty.php) is not a record: no hover highlight */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr.dt-state-row:hover > :is(td, th) {
    background-color: transparent;
}

/* 2.4 totals row */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tfoot > tr > :is(td, th) {
    background-color: var(--tn-foot-bg);
    border: 0;
    border-top: 2px solid var(--tn-foot-rule);
    padding: .8rem 1rem;
    font-size: 13px;
    font-weight: 600;
    color: var(--tn-strong);
    font-variant-numeric: tabular-nums;
}

/* 2.5 phones: slightly tighter cells (the density variants below still win) */
@media (max-width: 767.98px) {
    :is(.txn-table table, .dt-container table.dataTable,
        .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > thead > tr > th {
        padding: .6rem .75rem;
    }
    :is(.txn-table table, .dt-container table.dataTable,
        .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr > :is(td, th) {
        padding: .65rem .75rem;
    }
}

/* 2.5b density: .table-sm / .table-compact */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]):is(.table-sm) > thead > tr > th {
    padding: .55rem .85rem;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]):is(.table-sm) > tbody > tr > :is(td, th),
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]):is(.table-sm) > tfoot > tr > :is(td, th) {
    padding: .5rem .85rem;
}
/* .data-table--compact (wrapper variant of .table-sm; reports/dashboard mini tables) */

/* 2.6 the three families whose inline CSS forced one-line cells + tabular figures keep doing so */
:is(.txn-table table, .apb-tbl table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr > td {
    white-space: nowrap;
    font-variant-numeric: tabular-nums;
}
/* ...except cells that opt in to wrapping (.cell-wrap, .col-msg), and DataTables responsive child rows */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr > :is(td, th).cell-wrap {
    white-space: normal;
    max-width: 260px;
}
:is(.txn-table table, .dt-container table.dataTable):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr.child > td {
    white-space: normal;
}

/* ----------------------------------------------------------------------------
   3. CELL VOCABULARY
   ---------------------------------------------------------------------------- */

/* 3.1 reference helpers, made available inside the aliased tables as well */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-name {
    font-weight: 600;
    color: var(--tn-strong);
    text-decoration: none;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-name:hover {
    text-decoration: underline;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-sub {
    display: block;
    margin-top: 1px;
    font-size: 11px;
    color: var(--tn-sub);
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-mobile {
    font-weight: 700;
    color: var(--tn-strong);
    letter-spacing: .01em;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-amt {
    font-variant-numeric: tabular-nums;
    font-weight: 600;
    color: var(--tn-strong);
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .u-amt.muted {
    font-weight: 400;
    color: var(--tn-faint);
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .cell-trunc {
    display: inline-block;
    max-width: 160px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    vertical-align: bottom;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .cell-trunc-sm {
    max-width: 110px;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .id-link {
    font-size: 11px;
    font-weight: 500;
    color: var(--tn-muted);
    text-decoration: none;
}
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) .id-link:hover {
    color: var(--tn-strong);
    text-decoration: underline;
}
/* in-cell links (the hub's  <a class="link-primary fw-semibold"> ) read as the row's headline value */

/* 3.2 hub legacy helpers (data-tables.css / txn_table_style.php / approvals_table_style.php) */
                /* functional: keeps money columns from collapsing */
.content-page .cell-muted { color: var(--tn-sub); }
.content-page .cell-wrap { white-space: normal; min-width: 240px; max-width: 340px; }

/* column width helpers used by the transaction lists (functional: keep columns from collapsing) */
.content-page .op-code { font-size: 11px; color: var(--tn-sub); }

/* fmtDateTime(): date over time  (reference: date + .u-sub time) */
.content-page .cell-time {
    display: inline-flex;
    flex-direction: column;
    line-height: 1.25;
}
.content-page .cell-time__d {
    font-size: 12px;
    font-weight: 500;
    color: var(--tn-muted);
}
.content-page .cell-time__t {
    margin-top: 1px;
    font-size: 11px;
    color: var(--tn-sub);
    font-variant-numeric: tabular-nums;
}

/* 3.3 row tints  (very quiet; hover wins) */
/* "stale" (automation recharges): red wash + a 3px red edge on the first cell (box-shadow, so the cell padding is untouched) */
tr:is(.txn-row-stale)                 > td { background-color: rgba(214, 69, 69, .07); }
tr:is(.txn-row-stale) > td:first-child { box-shadow: inset 3px 0 0 var(--tn-red-ink); }
@media (hover: hover) {
    tr:is(.txn-row-stale):not(.child):hover > td {
        background-color: var(--tn-row-hover);
    }
}

/* ----------------------------------------------------------------------------
   4. PILLS  -  every status vocabulary the hub has ends up as a reference .pill
   ---------------------------------------------------------------------------- */

/* 4.1 geometry (identical to .pill) */
.status-badge,
td .badge[class*="badge-soft-"],
td .badge[class*="-subtle"],
td .badge.bg-light,
.content-page .ul-chip {
    display: inline-block;
    padding: .22rem .6rem;
    border: 0;
    border-radius: 999px;
    font-size: 11px;
    font-weight: 600;
    line-height: 1.4;
    letter-spacing: 0;
    text-transform: none;
    white-space: nowrap;
    vertical-align: middle;
}
.status-badge::before { content: none; }                       /* the old dot is retired; the pill is the signal */
td .badge[class*="badge-soft-"],
td .badge[class*="-subtle"],
td .badge.bg-light { position: static; }

/* 4.3 tones: theme soft badges inside table cells */
td .badge.badge-soft-success   { background-color: var(--tn-green-bg);  color: var(--tn-green-ink); }
td .badge.badge-soft-danger    { background-color: var(--tn-red-bg);    color: var(--tn-red-ink); }
td .badge.badge-soft-warning   { background-color: var(--tn-orange-bg); color: var(--tn-orange-ink); }
td .badge.badge-soft-info      { background-color: var(--tn-info-bg);   color: var(--tn-info-ink); }
td .badge.badge-soft-primary   { background-color: var(--tn-blue-bg);   color: var(--tn-blue-ink); }
td .badge.badge-soft-purple    { background-color: var(--tn-purple-bg); color: var(--tn-purple-ink); }
td .badge.badge-soft-secondary,
td .badge.badge-soft-dark,
td .badge.badge-soft-light     { background-color: var(--tn-grey-bg);   color: var(--tn-grey-ink); }

/* 4.4 tones: Bootstrap subtle badges (utilities are !important, so these have to be too) */
td .badge.bg-success-subtle   { background-color: var(--tn-green-bg)  !important; color: var(--tn-green-ink)  !important; }
td .badge.bg-danger-subtle    { background-color: var(--tn-red-bg)    !important; color: var(--tn-red-ink)    !important; }
td .badge.bg-warning-subtle   { background-color: var(--tn-orange-bg) !important; color: var(--tn-orange-ink) !important; }
td .badge.bg-info-subtle      { background-color: var(--tn-info-bg)   !important; color: var(--tn-info-ink)   !important; }
td .badge.bg-primary-subtle   { background-color: var(--tn-blue-bg)   !important; color: var(--tn-blue-ink)   !important; }
td .badge.bg-secondary-subtle,
td .badge.bg-light            { background-color: var(--tn-grey-bg)   !important; color: var(--tn-grey-ink)   !important; }
td .badge.bg-light.border     { border: 0 !important; }

/* 4.5 limit chips (SIM consoles) */
.content-page .ul-chip { font-variant-numeric: tabular-nums; }
.content-page .chip-blue  { background-color: var(--tn-blue-bg);   color: var(--tn-blue-ink); }
.content-page .chip-amber { background-color: var(--tn-orange-bg); color: var(--tn-orange-ink); }
.content-page .chip-red   { background-color: var(--tn-red-bg);    color: var(--tn-red-ink); }
.content-page .chip-gray  { background-color: var(--tn-grey-bg);   color: var(--tn-grey-ink); }

/* 4.6 per-console status badges.
       Markup / JS keep emitting  <span class="badge badge-soft-{success|danger|warning|info|secondary|dark} {op}-status-badge">.
       The old copies were a dot + label drawn with !important; this one shared list turns them into pills
       (it wins over any remaining inline copy through the extra .badge + .content-page specificity). */
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge,
.content-page .apb-status-badge {
    display: inline-block !important;
    padding: .22rem .6rem !important;
    border: 0 !important;
    border-radius: 999px;
    font-size: 11px;
    font-weight: 600;
    line-height: 1.4;
    letter-spacing: 0;
    text-transform: none;
    white-space: nowrap;
    gap: 0;
    background-color: var(--tn-grey-bg) !important;
    color: var(--tn-grey-ink) !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge::before,
.content-page .apb-status-badge::before {
    content: none !important;
    display: none !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge.badge-soft-success,
.content-page .apb-status-badge:is(.apb-ACTIVE) {
    background-color: var(--tn-green-bg) !important;  color: var(--tn-green-ink) !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge.badge-soft-danger,
.content-page .apb-status-badge:is(.apb-LOGGED_OUT, .apb-ERROR) {
    background-color: var(--tn-red-bg) !important;    color: var(--tn-red-ink) !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge.badge-soft-warning,
.content-page .apb-status-badge:is(.apb-PENDING, .apb-LOW_BALANCE) {
    background-color: var(--tn-orange-bg) !important; color: var(--tn-orange-ink) !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge.badge-soft-info {
    background-color: var(--tn-info-bg) !important;   color: var(--tn-info-ink) !important;
}
.content-page :is(.vi-status-badge, .jio-status-badge, .bsnl-status-badge, .airtel-status-badge, .dish-status-badge,
                  .dth-status-badge, .sd-status-badge, .tp-status-badge, .bt-status-badge).badge:is(.badge-soft-secondary, .badge-soft-dark),
.content-page .apb-status-badge:is(.apb-DISABLED) {
    background-color: var(--tn-grey-bg) !important;   color: var(--tn-grey-ink) !important;
}
/* Bank-transfer console (seller/automation/transfer.php + automation-transfer.js) is the one console whose badge
   carries Bootstrap *subtle* tones (bg-success-subtle text-success ...) instead of badge-soft-*; without these the
   .bt-status-badge base above would paint every status grey. */
.content-page .bt-status-badge.badge.bg-success-subtle {
    background-color: var(--tn-green-bg) !important;  color: var(--tn-green-ink) !important;
}
.content-page .bt-status-badge.badge.bg-danger-subtle {
    background-color: var(--tn-red-bg) !important;    color: var(--tn-red-ink) !important;
}
.content-page .bt-status-badge.badge.bg-warning-subtle {
    background-color: var(--tn-orange-bg) !important; color: var(--tn-orange-ink) !important;
}
.content-page .bt-status-badge.badge.bg-info-subtle {
    background-color: var(--tn-info-bg) !important;   color: var(--tn-info-ink) !important;
}

/* ----------------------------------------------------------------------------
   5. ROW ACTIONS
   ---------------------------------------------------------------------------- */

/* 5.1 compact in-cell buttons = reference .act-btns .btn metrics (any .btn-sm inside an aliased cell) */
:is(.txn-table table, .dt-container table.dataTable,
    .table-responsive > table.table, .card-body > table.table, .card > table.table):not(.table-neo, .table-borderless, .table-dark, [data-plain]) > tbody > tr > td .btn.btn-sm:not(.btn-kebab, .btn-icon) {
    padding: .3rem .7rem;
    font-size: 12px;
    font-weight: 600;
    border-radius: 7px;
    line-height: 1.3;
}

/* (the kebab row menu .dt-actions / .btn-kebab lives in data-tables.css) */

/* 5.2 SIM-console action strip: uniform 26px squares, neutral at rest, intent on hover (delete keeps red) */
.content-page .act-cell { min-width: 132px; white-space: nowrap; }
.content-page .act-cell .d-flex { gap: 4px !important; }
.content-page .act-cell .btn {
    width: 26px;
    height: 26px;
    min-height: 26px;
    padding: 0 !important;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 7px;
    line-height: 1.3;
}
.content-page .act-cell .btn i { font-size: 15px; }
.content-page .act-cell .btn.btn-login { width: auto; padding: 0 .5rem !important; }   /* Login / Re-login keeps a wider pill */
.content-page .act-cell input[name="otp"] { width: 64px; height: 26px; min-height: 26px; }
.content-page .act-cell :is(.btn-outline-info, .btn-outline-secondary, .btn-outline-warning) {
    color: var(--tn-muted) !important;
    border-color: var(--tn-line) !important;
    background-color: #fff !important;
}
.content-page .act-cell :is(.btn-outline-info, .btn-outline-secondary, .btn-outline-warning):hover {
    color: #1d2939 !important;
    border-color: var(--tn-input-line) !important;
    background-color: #f6f7fb !important;
}
.content-page .apb-act .btn {                                     /* Airtel Payments Bank variant (28px) */
    width: 28px;
    height: 28px;
    min-height: 28px;
    padding: 0 !important;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 7px;
}
.content-page .apb-act .btn i { font-size: 15px; }

/* ----------------------------------------------------------------------------
   6. HOISTED INLINE FAMILIES
   ---------------------------------------------------------------------------- */

/* 6.3 SIM-console cell helpers (vi / jio / bsnl / airtel / airtelpb / dish / dth / sundirect / tatasky) */
.content-page .zone-chip {
    display: inline-block;
    margin-left: 6px;
    padding: 1px 6px;
    border-radius: 4px;
    background: var(--tn-grey-bg);
    color: var(--tn-muted);
    font-size: 10px;
    font-weight: 600;
    letter-spacing: .03em;
    vertical-align: middle;
}
.content-page .muted-dash { color: var(--tn-faint); }
.content-page .sim-cell .lapu { display: block; }
.content-page .sim-label {
    margin-top: 1px;
    font-size: 10px;
    line-height: 1.3;
    color: var(--tn-sub);
}
/* number / agent code: reference .u-mobile (bold ink, not the red monospace <code>) */
.content-page :is(.txn-table, .apb-tbl) td .lapu {
    font-family: inherit;
    font-size: 13px;
    font-weight: 700;
    letter-spacing: .01em;
    color: var(--tn-strong);
    font-variant-numeric: tabular-nums;
}
/* numeric / state columns */
.content-page :is(.txn-table, .apb-tbl) :is(th.num, td.num) { text-align: right; font-variant-numeric: tabular-nums; }
.content-page :is(.txn-table, .apb-tbl) td:is(.ctopup, .balance-cell, .bal, .tp-balance) { font-weight: 600; color: var(--tn-strong); }
.content-page :is(.txn-table, .apb-tbl) td:is(.ctopup, .balance-cell, .bal, .tp-balance) .rs { font-weight: 500; color: var(--tn-sub); }
.content-page .apb-tbl td.bal.low span { color: var(--tn-red-ink); }
.content-page .txn-table td:is(.ctopup, .balance-cell, .tp-balance):is(.ctopup-low, .tp-balance-low) span:last-child { color: var(--tn-red-ink); }
.content-page .txn-table td.ul { font-size: 12.5px; color: var(--tn-muted); }
.content-page .txn-table td:is(.cell-circle, .cell-state) { font-weight: 500; color: var(--tn-cell-ink); }
.content-page .txn-table th:last-child,
.content-page .txn-table td:last-child { padding-right: 16px; }
/* select-all / row checkbox column: tight and centred */
.content-page .txn-table thead > tr > th:first-child:has(> input.form-check-input:only-child),
.content-page .txn-table thead > tr > th:first-child:has(> .dt-column-header > .dt-column-title > input.form-check-input:only-child),
.content-page .txn-table tbody > tr > td:first-child:has(> input.form-check-input:only-child) {
    width: 34px;
    padding-left: 12px;
    padding-right: 4px;
    text-align: center;
}
.content-page .txn-table .form-check-input { margin: 0; cursor: pointer; }
/* priority select: compact, matches the 26px control strip */
.content-page :is(.txn-table, .apb-tbl) td select[name="priority"] {
    width: 56px !important;
    height: 26px;
    min-height: 26px;
    padding: .15rem 1.1rem .15rem .5rem;
    font-size: 12.5px;
}

/* ----------------------------------------------------------------------------
   7. DATATABLES 2.x CHROME  (.dt-container; replaces the dead .dataTables_wrapper rules)
      hub dom string:  .dt-toolbar > ( .dt-toolbar-left > .dt-export + .dt-length ) + .dt-toolbar-right.dt-search
                       table.dataTable  /  .dt-footer > .dt-paginate
   ---------------------------------------------------------------------------- */

/* 7.1 container: undo the theme's negative top margin (it clipped the toolbar's first pixels) */
div.dt-container { margin-top: 0; }

/* 7.2 toolbar */
div.dt-container .dt-toolbar { gap: .75rem; }
div.dt-container .dt-toolbar .dt-toolbar-left,
div.dt-container .dt-toolbar .dt-toolbar-right {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: .625rem;
}
div.dt-container .dt-toolbar .dt-toolbar-right { margin-left: auto; }
div.dt-container .dt-export .dt-buttons { display: inline-flex; flex-wrap: wrap; gap: .5rem; }

/* search: reference input with the magnifier on the left; the visible "Search:" label is replaced by the placeholder */
div.dt-container .dt-search > label {
    position: absolute !important;
    width: 1px;
    height: 1px;
    margin: -1px !important;
    padding: 0;
    overflow: hidden;
    clip: rect(0, 0, 0, 0);
    white-space: nowrap;
    border: 0;
}
div.dt-container .dt-search input,
div.dt-container .dt-search input[type="search"] {
    min-width: 240px;
    min-height: 38px;
    margin-left: 0;
    padding: .45rem .75rem .45rem 2rem;
    border: 1px solid var(--tn-input-line);
    border-radius: 6px;
    background: #fff url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='16' height='16' viewBox='0 0 24 24' fill='none' stroke='%2398a2b3' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'%3E%3Ccircle cx='11' cy='11' r='8'/%3E%3Cpath d='m21 21-4.3-4.3'/%3E%3C/svg%3E") no-repeat .6rem center;
    font-size: 13.5px;
    box-shadow: none;
}
div.dt-container .dt-search input:focus {
    border-color: var(--tn-focus);
    box-shadow: 0 0 0 3px var(--tn-focus-ring);
    outline: 0;
}
/* Console pages build their own search box and hide the built-in one with  el.style.display = 'none'
   (automation-vi.js ...). initComplete adds the d-flex utility, which is !important and silently
   defeated that, so the duplicate search box showed. This makes the inline hide effective again. */
div.dt-container .dt-search[style*="display: none"],
div.dt-container .dt-search[style*="display:none"] { display: none !important; }

/* rows-per-page */
div.dt-container .dt-length { gap: .5rem; }
div.dt-container .dt-length select {
    width: auto;
    min-width: 4.6rem;
    min-height: 38px;
    margin-right: 0;
    border: 1px solid var(--tn-input-line);
    border-radius: 6px;
    font-size: 13.5px;
}
div.dt-container .dt-length select:focus {
    border-color: var(--tn-focus);
    box-shadow: 0 0 0 3px var(--tn-focus-ring);
    outline: 0;
}
div.dt-container .dt-length label {
    margin: 0;
    font-size: 12.5px;
    font-weight: 500;
    color: var(--tn-muted);
    white-space: nowrap;
}

/* Export = reference green Download button (white text), whatever Buttons adds (btn-secondary ...) */
div.dt-container .dt-buttons .btn.dt-export-btn,
div.dt-container .dt-buttons .btn.buttons-excel {
    display: inline-flex;
    align-items: center;
    gap: .15rem;
    min-height: 38px;
    padding: .45rem .95rem;
    border: 1px solid var(--hub-success-solid, #0b7d44);
    border-radius: 6px;
    background-color: var(--hub-success-solid, #0b7d44);
    color: #fff;
    font-size: 12.6px;
    font-weight: 500;
    box-shadow: none;
}
div.dt-container .dt-buttons .btn.dt-export-btn:hover,
div.dt-container .dt-buttons .btn.dt-export-btn:focus-visible,
div.dt-container .dt-buttons .btn.buttons-excel:hover,
div.dt-container .dt-buttons .btn.buttons-excel:focus-visible {
    border-color: var(--hub-success-solid-hover, #086a39);
    background-color: var(--hub-success-solid-hover, #086a39);
    color: #fff;
}
div.dt-container .dt-buttons .btn { border-radius: 6px; }

/* 7.3 info + pager */
div.dt-container .dt-info {
    padding-top: 0;
    font-size: 12.5px;
    color: var(--tn-muted);
}
div.dt-container .dt-footer { align-items: center; gap: .75rem; }
div.dt-container .dt-paginate,
div.dt-container .dt-paging,
div.dt-container .dt-layout-cell:has(.dt-paging) {
    display: flex;
    justify-content: flex-end;
}
div.dt-container .pagination {
    justify-content: flex-end !important;
    margin-bottom: 0;
}
/* the non-Bootstrap markup variant (kept as in reference; the Bootstrap 5 integration uses .page-item.active) */
div.dt-container .dt-paging .dt-paging-button.current {
    border-color: var(--tn-focus) !important;
    background: var(--tn-focus) !important;
    color: #fff !important;
}
@media (max-width: 575.98px) {
    div.dt-container .dt-toolbar .dt-toolbar-right { margin-left: 0; width: 100%; }
    div.dt-container .dt-search input,
    div.dt-container .dt-search input[type="search"] { min-width: 0; width: 100%; }
    div.dt-container .dt-search { width: 100%; }
    div.dt-container .dt-paginate,
    div.dt-container .dt-paging,
    div.dt-container .dt-layout-cell:has(.dt-paging),
    div.dt-container .pagination { justify-content: flex-start !important; }
    /* A pager with 6+ pages is 430px wide (First, Previous, 1-5, ..., last, Next, Last): wider than the 308px a 390px phone
       leaves, and the list does not wrap, so it overflowed to the LEFT (First, Previous and page 1 sat at negative x and
       could not be reached). Let it wrap onto a second row instead. */
    div.dt-container .pagination { flex-wrap: wrap; }
}

/* 7.4 header: no reserved 30px icon gutter on every column, sort glyph centred in the cell.
       (reference nudges the label with translateY(7px); here the cell is centred properly instead,
       so that hack is NOT used - it is neutralised for table-neo tables too.) */
div.dt-container table.dataTable > thead > tr > th .dt-column-header,
div.dt-container table.dataTable > thead > tr > th .dt-column-title {
    padding-right: 0;
    transform: none;
}
div.dt-container table.dataTable.dataTable > thead > tr > th:is(.dt-orderable-asc, .dt-orderable-desc) {
    padding-right: 1.9rem;
    cursor: pointer;
}
/* totals row: DataTables wraps tfoot text in .dt-column-title too, and the theme gives that span a 30px right pad
   (made for the sort glyph) - a footer has no glyph, so without this the totals sit 30px left of their column. */
div.dt-container table.dataTable > tfoot > tr > :is(th, td) .dt-column-title { padding-right: 0; }
div.dt-container table.dataTable thead th::after {
    top: 50%;
    bottom: auto;
    right: .6rem;
    transform: translateY(-50%);
    font-size: 14px;
    line-height: 1;
    color: var(--tn-sub);
}
div.dt-container table.dataTable thead th.dt-ordering-asc::after,
div.dt-container table.dataTable thead th.dt-ordering-desc::after { color: var(--ins-primary, #5e6cc1); }

/* 7.5 empty / no-match message */
div.dt-container table.dataTable > tbody > tr > td.dt-empty {
    padding: 2.5rem 1rem;
    text-align: center;
    font-size: 13px;
    color: var(--tn-sub);
}
div.dt-container table.dataTable > tbody > tr > td.dt-empty::before {
    content: "\eac4";                              /* ti-inbox */
    display: block;
    margin-bottom: .4rem;
    font-family: "tabler-icons";
    font-size: 28px;
    line-height: 1;
    opacity: .5;
}

/* 7.6 responsive child rows (Responsive extension, dtr-inline collapsed) */
div.dt-container table.dataTable.dtr-inline.collapsed > tbody > tr > td.dtr-control::before,
div.dt-container table.dataTable.dtr-inline.collapsed > tbody > tr > th.dtr-control::before {
    content: "+";
    width: 18px;
    height: 18px;
    margin-right: .65rem;
    display: inline-block;
    box-sizing: border-box;
    vertical-align: middle;
    border: 0;
    border-radius: 50%;
    background: rgba(var(--ins-primary-rgb, 94, 108, 193), .14);
    color: var(--ins-primary, #5e6cc1);
    font-size: 13px;
    font-weight: 700;
    line-height: 18px;
    text-align: center;
}
div.dt-container table.dataTable.dtr-inline.collapsed > tbody > tr.dtr-expanded > td.dtr-control::before,
div.dt-container table.dataTable.dtr-inline.collapsed > tbody > tr.dtr-expanded > th.dtr-control::before {
    content: "\2212";
    border: 0;
    background: var(--ins-primary, #5e6cc1);
    color: #fff;
}
div.dt-container table.dataTable > tbody > tr.child > td.child {
    padding: .9rem 1rem 1rem 3rem;
    background-color: var(--tn-surface-2);
}
div.dt-container table.dataTable > tbody > tr.child ul.dtr-details {
    display: block;
    width: 100%;
}
div.dt-container table.dataTable > tbody > tr.child ul.dtr-details > li {
    display: flex;
    gap: 1rem;
    align-items: baseline;
    padding: .5rem 0;
    border-bottom: 1px solid var(--tn-row-rule);
}
div.dt-container table.dataTable > tbody > tr.child ul.dtr-details > li:last-child { border-bottom: 0; }
div.dt-container table.dataTable > tbody > tr.child span.dtr-title {
    min-width: 140px;
    font-size: 10.5px;
    font-weight: 700;
    letter-spacing: .05em;
    text-transform: uppercase;
    color: var(--tn-head-ink);
}
div.dt-container table.dataTable > tbody > tr.child span.dtr-data {
    font-size: 13px;
    color: var(--tn-cell-ink);
}

/* 7.7 JS-built filter panel (options.filters)  ->  filter-card look */
.content-page div.dt-container .dt-filter-panel {
    width: 100%;
    overflow: visible;
    padding: 1rem 1.25rem;
    border: 1px solid var(--tn-line);
    border-radius: var(--tn-radius);
    background: #fff;
    box-shadow: 0 1px 2px rgba(16, 24, 40, .04);
}
.content-page div.dt-container .dt-filter-panel .dt-filter-fields {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(190px, 1fr));
    gap: .625rem;
}
.content-page div.dt-container .dt-filter-panel .dt-filter-group {
    display: flex;
    flex-direction: column;
    gap: .25rem;
}
.content-page div.dt-container .dt-filter-panel .dt-filter-label {
    margin: 0;
    font-size: 11px;
    font-weight: 700;
    letter-spacing: .04em;
    text-transform: uppercase;
    color: var(--tn-muted);
}
.content-page div.dt-container .dt-filter-panel :is(.form-control, .form-select) {
    min-width: 0;
    height: auto;
    min-height: 40px;
}
.content-page div.dt-container .dt-filter-panel .dt-filter-actions {
    display: flex;
    align-items: center;
    gap: .5rem;
    margin-top: .75rem;
}
.content-page div.dt-container .dt-filter-panel .dt-filter-actions .btn {
    min-width: 96px;
    min-height: 40px;
    height: auto;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 6px;
}
.content-page div.dt-container .dt-filter-panel .dt-filter-actions .btn-light {
    border: 1px solid var(--tn-line);
}

/* ==========================================================================
   8. REVIEW FIXES (phones, empty states, console overflow) - each verified in headless Chrome by the reviewers
   ========================================================================== */

/* 8.1 Phones: let identifying cells wrap so DataTables Responsive keeps the name/id column visible next to the
   pinned Action column instead of collapsing every row to just "+ [Edit]". Buttons stay on one line. */
@media (max-width: 767.98px) {
    /* ONLY cells that hold a name may wrap (ids, numbers, dates and header labels stay on one line - wrapping every
       cell squeezed ids and dates to one character per line). break-word, not anywhere: break only when needed. */
    table.table-neo.table-nowrap td:has(.u-name) { white-space: normal; }
    table.table-neo .u-name { overflow-wrap: break-word; }
    table.table-neo .act-btns .btn { white-space: nowrap; }
    /* dates, ids and money never break mid-value */
    .cell-time, .cell-time__d, .cell-time__t, .u-amt, .id-link { white-space: nowrap; }
    /* DataTables' own empty row is as wide as the whole table: left-align it so the message is on screen */
    .table-responsive td.dt-empty { text-align: left !important; padding-left: 1rem; }
}

/* 8.2 Phones: an expanded Responsive child row must fit inside its card (it was 20-160px too wide), and stack
   label over value. */
@media (max-width: 575.98px) {
    div.dt-container table.dataTable > tbody > tr.child > td.child { padding: .75rem 1rem; }
    div.dt-container table.dataTable > tbody > tr.child ul.dtr-details > li { flex-wrap: wrap; gap: .15rem 1rem; }
    div.dt-container table.dataTable > tbody > tr.child span.dtr-title { min-width: 0; flex: 0 0 100%; }
    div.dt-container table.dataTable > tbody > tr.child span.dtr-data { min-width: 0; max-width: 100%; white-space: normal; overflow-wrap: anywhere; }
}

/* 8.3 Empty state inside a wide (nowrap) table: the colspan cell is as wide as the whole table, so on a phone its
   centred message sat off-screen. Pin it to the visible width of the scroll container. */
.table-responsive { container-type: inline-size; }
.table-responsive .dt-state { position: sticky; left: 0; width: 100cqw; box-sizing: border-box; }
/* 8.3b The colspan cell around .dt-state kept its own padding (16px a side, 12px on phones) ON TOP of the 100cqw box, so every
   empty table was 32px (24px on phones) wider than its card: a pointless sideways scroll with the shadow cue, a clipped last
   header and a clipped message. .dt-state has its own padding, so the cell drops its padding. The selector out-ranks the table skin (2.3 / 2.5). */
.content-page .table-responsive table.table > tbody > tr.dt-state-row > td { padding-left: 0; padding-right: 0; }

/* 8.4 Visually-hidden text inside table cells is position:absolute with no offset; its containing block is the
   card, so on the consoles it stretched the whole document (scrollWidth 684-944 at 375px). Anchor it to the cell's
   own left edge (do NOT make .table-responsive position:relative - that would clip row dropdown menus). */
.table-responsive .visually-hidden,
td .visually-hidden,
th .visually-hidden { left: 0; }

/* 8.5 An empty export slot (table with no rows has no Export button) must not take the flex gap, or the page-size
   select no longer lines up with the filter panel below. */
.dt-toolbar-left > .dt-export:not(:has(.btn)) { display: none; }

/* 8.5b Wide list tables. A list with 10-16 nowrap columns is 1.1-1.6x wider than its card at 1366px (the card is 1074px beside
   the 235px sidebar) and scrolls sideways, and the row actions sit in the LAST column, behind the scroll. While such a table is
   scrolled (hub-ui.js adds .fin-x-start / .fin-x-mid to the scroller; none when it fits, none at the far end) its last column is
   pinned to the right edge with a soft left shadow, but ONLY when that column holds row-action buttons (judged by the first row),
   so the actions and the header over them stay reachable. Tablet and up: on a phone a pinned column would eat a third of the screen.
   A sticky cell is its own stacking context, so a row's open dropdown menu (admin operators, seller transactions) would be painted
   under the pinned cells of the rows below it: the cell that holds an open menu is lifted to the menu's own level (1000, below the
   topbar/sidenav) for as long as the menu is open. The cell paints its own row rule, because a collapsed border does not travel
   with a sticky cell. */
@media (min-width: 768px) {
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > :is(thead, tbody, tfoot) > tr > :is(th, td):last-child {
        position: sticky;
        right: 0;
        box-shadow: -10px 0 8px -8px rgba(16, 24, 40, .2);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > thead > tr > th:last-child {
        background-color: var(--tn-head-bg);
        box-shadow: -10px 0 8px -8px rgba(16, 24, 40, .2), inset 0 -2px 0 var(--tn-head-rule);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > tbody > tr > td:last-child {
        background-color: #fff;
        box-shadow: -10px 0 8px -8px rgba(16, 24, 40, .2), inset 0 -1px 0 var(--tn-row-rule);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > tbody > tr:last-child > td:last-child {
        box-shadow: -10px 0 8px -8px rgba(16, 24, 40, .2);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > tbody > tr:not(.child):hover > td:last-child {
        background-color: var(--tn-row-hover);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table:has(> tbody > tr:first-child > td:last-child :is(.act-btns, .btn, .dt-actions)) > tfoot > tr > :is(th, td):last-child {
        background-color: var(--tn-foot-bg);
    }
    :is(.table-responsive:is(.fin-x-start, .fin-x-mid), .table-responsive:is(.fin-x-start, .fin-x-mid) > .dt-container) > table.table > tbody > tr > td:last-child:has(.dropdown-menu.show) {
        z-index: 1000;
    }
}

/* 8.6 DataTables toolbar / filter panel / footer stay put while a wide table scrolls sideways: the filter panel used to
   scroll away with the table (its right border clipped under the scroll shadow). Pin them to the visible width of the
   scroll container (8.3 makes .table-responsive the size container). */
.table-responsive .dt-container .dt-filter-panel,
.table-responsive .dt-container .dt-toolbar,
.table-responsive .dt-container .dt-footer {
    position: sticky;
    left: 0;
    width: 100cqw;
    box-sizing: border-box;
}

/* 8.7 JS-built date filters (user-funds.js / user-payouts.js put two date inputs in one narrow grid cell): keep the
   date readable instead of clipping it under the calendar icon.
   The rule at the end asked for min-width 9.5rem, but 7.7's `min-width: 0` on every filter-panel control out-ranks it, so each date
   input was squeezed to 86-110px (a date input needs about 149px) and read "mm/dd/yy" under the icon. The min-width is restated here at
   7.7's specificity, the date group takes two grid columns so both inputs sit on one line, and on a phone the two inputs stack. */
.content-page div.dt-container .dt-filter-panel input[type="date"] { min-width: 9.5rem; }
@media (min-width: 576px) {
    .content-page div.dt-container .dt-filter-panel .dt-filter-group:has(input[type="date"]) { grid-column: span 2; }
}
@media (max-width: 575.98px) {
    .content-page div.dt-container .dt-filter-panel .dt-filter-group > .d-flex:has(input[type="date"]) { flex-direction: column; align-items: stretch !important; }
}
.dt-filter-panel input[type="date"] { min-width: 9.5rem; padding-left: .5rem; padding-right: .5rem; }
