/* ============================================================================
   ViyaBook — Global Design System
   Single source of truth for SIZES · SPACING · TYPOGRAPHY · CONTROLS.
   Loaded LAST on every page so it standardises the shared UI patterns.

   RULES:
   • Colours & branding are NEVER set here — only height, width, radius,
     font, spacing. Component classes inherit existing colour variables
     (--primary, --border, --success, --danger …) so branding is untouched.
   • Tokens are namespaced --ds-* to avoid clashing with existing variables.
   ========================================================================== */

:root {
  /* ── Layout / control tokens (added 2026-07-10) ──────────────────────────
     ADDITIVE design tokens for future standardization. They are NOT wired into
     any rule yet, so they change nothing at runtime — adopt them page-by-page
     in later, visually-verified steps (that's when spacing/sizes would actually
     change). `--sidebar-width` mirrors the app's real `--vb-sidebar-w` so it is
     safe to adopt without shifting the sidebar. Kept here (loaded last on every
     page) so they're globally available once adopted. */
  --header-height:     56px;
  --bottom-nav-height: 64px;
  --sidebar-width:     var(--vb-sidebar-w, 264px);
  --radius-card:       16px;
  --spacing-page:      16px;
  --control-height:    40px;

  /* Fonts */
  --ds-font:        'Inter', system-ui, -apple-system, Segoe UI, Roboto, Arial, sans-serif;
  --ds-font-dhivehi:'MV Waheed';   /* Dhivehi = MV Waheed only */

  /* Type scale — ONE typography system for every page */
  --ds-fs-page-title:    32px;  /* weight 700 */
  --ds-fs-section-title: 22px;  /* weight 600 */
  --ds-fs-card-title:    18px;  /* weight 600 */
  --ds-fs-normal:        14px;  /* body text */
  --ds-fs-small:         12px;
  --ds-fs-table-head:    13px;  /* weight 600 */
  --ds-fs-table-cell:    14px;
  --ds-fs-button:        14px;  /* weight 600 */
  --ds-fs-input:         14px;
  --ds-fs-badge:         12px;
  --ds-fs-sidebar:       14px;  /* sidebar menu */

  /* Control heights */
  --ds-btn-sm:      36px;
  --ds-btn-md:      44px;
  --ds-btn-lg:      48px;
  --ds-input-h:     44px;
  --ds-textarea-min:110px;

  /* Radius */
  --ds-radius-btn:    12px;  /* normal button radius (small button uses 10px) */
  --ds-radius-input:  12px;
  --ds-radius-card:   18px;
  --ds-radius-badge:  999px;

  /* Table heights */
  --ds-row-h:    60px;
  --ds-head-h:   52px;

  /* Spacing */
  --ds-pad-card:   24px;
  --ds-gap-section:24px;
  --ds-gap-btn:    12px;
  --ds-gap-input:  12px;

  /* Icon sizes */
  --ds-ic-menu:   20px;
  --ds-ic-action: 18px;
  --ds-ic-card:   24px;
  --ds-ic-quick:  24px;

  /* Elevation */
  --ds-shadow-card: 0 12px 30px rgba(8, 27, 68, 0.07);

  /* Page container (Wave-style centred content max width) */
  --ds-container: 1440px;
}

/* =========================================================================
   1 · TYPOGRAPHY  — reusable title classes (opt-in, exact spec sizes)
   ========================================================================= */
.page-title    { font-family: var(--ds-font); font-size: var(--ds-fs-page-title);    font-weight: 700; line-height: 1.15; letter-spacing: -0.01em; }
.section-title { font-family: var(--ds-font); font-size: var(--ds-fs-section-title); font-weight: 600; line-height: 1.2; }
.card-title    { font-family: var(--ds-font); font-size: var(--ds-fs-card-title);    font-weight: 600; line-height: 1.25; }
.text-normal   { font-size: var(--ds-fs-normal); }
.text-small    { font-size: var(--ds-fs-small); }

@media (max-width: 767px) {
  .page-title    { font-size: 26px; }
  .section-title { font-size: 19px; }
  .card-title    { font-size: 17px; }
}

/* Dhivehi (Thaana) text uses Faruma wherever flagged */
[lang="dv"], .dhivehi, .thaana { font-family: var(--ds-font-dhivehi); direction: rtl; }

/* =========================================================================
   2 · BUTTONS  — reusable component classes
   ========================================================================= */
.ds-btn,
.btn-primary, .btn-secondary, .btn-danger, .btn-success {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  height: var(--ds-btn-md);
  min-height: var(--ds-btn-md);
  padding: 0 18px;
  border: 1.5px solid transparent;
  border-radius: var(--ds-radius-btn);
  font-family: var(--ds-font);
  font-size: var(--ds-fs-button);
  font-weight: 600;
  line-height: 1;
  cursor: pointer;
  white-space: nowrap;
  box-sizing: border-box;
  text-decoration: none;
  transition: filter .15s ease, background .15s ease, opacity .15s ease;
}
.ds-btn:disabled, .btn-primary:disabled, .btn-secondary:disabled,
.btn-danger:disabled, .btn-success:disabled { opacity: .55; cursor: not-allowed; }

.btn-sm  { height: var(--ds-btn-sm);  min-height: var(--ds-btn-sm);  padding: 0 14px; border-radius: 10px; font-size: 13px; }
.btn-md  { height: var(--ds-btn-md);  min-height: var(--ds-btn-md); }
.btn-lg  { height: var(--ds-btn-lg);  min-height: var(--ds-btn-lg);  padding: 0 22px; font-size: 15px; }
.btn-block { width: 100%; }

/* NOTE: colours/branding for .btn-primary/.btn-secondary/.btn-danger/.btn-success
   are intentionally NOT set here — they come from the existing brand CSS
   (vb-buttons.css / viyabook.css) so branding is never changed. This file only
   standardises their geometry above. */

/* Action-button fixed sizes (per spec) */
.btn-action      { height: 40px; min-height: 40px; border-radius: var(--ds-radius-btn); font-size: var(--ds-fs-button); font-weight: 600; }
.btn-action-wide { width: 140px; }
.btn-action-90   { width: 90px;  }
.btn-icon        { width: 44px; height: 44px; min-height: 44px; padding: 0; }

/* Icon sizing inside buttons */
.ds-btn .ti, .btn-primary .ti, .btn-secondary .ti, .btn-danger .ti, .btn-success .ti,
.ds-btn svg, .btn-primary svg, .btn-secondary svg, .btn-danger svg, .btn-success svg {
  width: var(--ds-ic-action); height: var(--ds-ic-action); font-size: var(--ds-ic-action); flex-shrink: 0;
}

/* =========================================================================
   3 · INPUTS  — reusable component classes
   ========================================================================= */
.input-standard, select.input-standard {
  height: var(--ds-input-h);
  min-height: var(--ds-input-h);
  border: 1.5px solid var(--border, #e2e8f0);
  border-radius: var(--ds-radius-input);
  padding: 0 14px;
  font-family: var(--ds-font);
  font-size: var(--ds-fs-input);
  font-weight: 600;
  color: var(--text, #0f172a);
  background: #fff;
  box-sizing: border-box;
  width: 100%;
}
textarea.input-standard { height: auto; min-height: var(--ds-textarea-min); padding: 14px; resize: vertical; line-height: 1.5; }
.input-standard:focus { outline: none; border-color: var(--primary, #185FA5); }

/* =========================================================================
   4 · TABLES
   ========================================================================= */
.table-standard { width: 100%; border-collapse: collapse; font-family: var(--ds-font); }
.table-standard thead th {
  height: var(--ds-head-h);
  font-size: var(--ds-fs-table-head);
  font-weight: 700;
  color: var(--muted, #64748b);
  text-align: left;
  padding: 0 14px;
  border-bottom: 1px solid var(--border, #e2e8f0);
  white-space: nowrap;
}
.table-standard tbody td {
  height: var(--ds-row-h);
  font-size: var(--ds-fs-table-cell);
  padding: 0 14px;
  border-bottom: 1px solid var(--border, #eef2f7);
  vertical-align: middle;
}
.table-standard th.center, .table-standard td.center { text-align: center; }
.table-standard th.right,  .table-standard td.right  { text-align: right; }
.table-standard td .ds-btn, .table-standard td .btn-action { vertical-align: middle; }

/* =========================================================================
   5 · CARDS
   ========================================================================= */
.card-standard {
  background: #fff;
  border: 1px solid #e5eaf3;
  border-radius: var(--ds-radius-card);
  padding: var(--ds-pad-card);
  box-shadow: var(--ds-shadow-card);
  box-sizing: border-box;
}
.card-grid { display: grid; gap: var(--ds-gap-section); }

/* =========================================================================
   6 · BADGES
   ========================================================================= */
.badge-standard {
  display: inline-flex; align-items: center; gap: 5px;
  font-family: var(--ds-font);
  font-size: var(--ds-fs-badge);
  font-weight: 700;
  line-height: 1;
  padding: 5px 10px;
  border-radius: var(--ds-radius-badge);
}

/* =========================================================================
   7 · LAYOUT — one container width, consistent gaps
   ========================================================================= */
.page-container { max-width: var(--ds-container); margin-inline: auto; width: 100%; box-sizing: border-box; }
.stack-24 > * + * { margin-top: var(--ds-gap-section); }
.row-gap-12 { display: flex; gap: var(--ds-gap-btn); flex-wrap: wrap; }

/* =========================================================================
   8 · SAFE GLOBAL NORMALISATION
   Standardises the shared, ubiquitous patterns (font, radius, control font
   size, icon sizes) WITHOUT touching colours and WITHOUT forcing heights on
   small/inline table controls. Scoped to page content (.main-content) so the
   sidebar/login chrome are untouched.
   ========================================================================= */

/* Single font family everywhere (English + Dhivehi fallback) */
body, .main-content, .main-content button, .main-content input,
.main-content select, .main-content textarea {
  font-family: var(--ds-font);
}

/* One base body-text size for every page (14px). Element-level sizes below
   (titles, table, controls) still apply; this only sets the inherited default
   so plain text is identical across pages. Font-size only — no layout change. */
body, .main-content { font-size: var(--ds-fs-normal); }

/* Sidebar menu items — single 14px size. */
.sidebar .nav-link, .sidebar a.nav-link { font-size: var(--ds-fs-sidebar); }

/* Buttons: single geometry for every .btn-family button on every page. This is
   the global authority (design-system loads last on all pages). Colours come
   from the existing brand CSS — only size/shape/font are set here. */
.btn, .vb-btn, button.btn {
  border-radius: var(--ds-radius-btn) !important;
  font-size: var(--ds-fs-button) !important;
  font-weight: 600 !important;
  font-family: var(--ds-font) !important;
  display: inline-flex !important;
  align-items: center !important;
  justify-content: center !important;
  gap: 8px !important;
  box-sizing: border-box !important;
}
/* Standard 44px height. Small/large/icon and dense in-table / tab / pager /
   category / payment controls keep their own size (listed exclusions). */
.btn:not(.btn-sm):not(.btn-lg):not(.btn-icon):not(.btn-xs):not(.page-btn):not(.qty-btn):not(.row-btn):not(.row-del):not(.icon-btn):not(.act-btn):not(.td-tab):not(.cat):not(.pay-method):not(.chip):not(.tab):not(.seg-btn) {
  height: var(--ds-btn-md) !important;
  min-height: var(--ds-btn-md) !important;
  padding: 0 18px !important;
}
.btn-sm { height: var(--ds-btn-sm) !important; min-height: var(--ds-btn-sm) !important; border-radius: 10px !important; font-size: 13px !important; padding: 0 14px !important; }
.btn-lg { height: var(--ds-btn-lg) !important; min-height: var(--ds-btn-lg) !important; border-radius: var(--ds-radius-btn) !important; }
.btn-icon { width: 44px !important; height: 44px !important; min-height: 44px !important; padding: 0 !important; border-radius: var(--ds-radius-btn) !important; }

/* ── One button standard (colours + 12px gap + 18px icons). Last block = authority
   over page-level and brand button CSS. Geometry (44 / radius 12 / 14·600) is set
   above; this fixes the COLOUR + spacing inconsistency between pages. ─────────── */
:root{ --ds-btn-primary:#2563eb; --ds-btn-primary-hover:#1d4ed8; --ds-btn-danger:#ef4444; --ds-btn-success:#16a34a; --ds-btn-secondary-bd:#d5deea; }
.btn, .ds-btn, .btn-primary, .btn-secondary, .btn-light, .btn-danger, .btn-success { gap: 12px !important; }
.btn > .ti, .btn > i, .btn > svg,
.ds-btn .ti, .ds-btn svg,
.btn-primary .ti, .btn-primary svg, .btn-secondary .ti, .btn-secondary svg,
.btn-danger .ti, .btn-danger svg, .btn-success .ti, .btn-success svg {
  width: 18px !important; height: 18px !important; font-size: 18px !important; flex-shrink: 0;
}
.btn-primary { background: var(--ds-btn-primary) !important; border: 1px solid var(--ds-btn-primary) !important; color: #fff !important; box-shadow: none !important; }
.btn-primary:hover { background: var(--ds-btn-primary-hover) !important; }
.btn-secondary, .btn-light { background: #fff !important; color: #0f172a !important; border: 1px solid var(--ds-btn-secondary-bd) !important; }
.btn-danger { background: var(--ds-btn-danger) !important; border: 1px solid var(--ds-btn-danger) !important; color: #fff !important; }
.btn-success { background: var(--ds-btn-success) !important; border: 1px solid var(--ds-btn-success) !important; color: #fff !important; }

/* ── Disabled buttons: ALWAYS readable (never invisible / never white-on-light).
   One muted-grey scheme for every button family, overriding the old opacity:.5
   fade (vb-buttons.css) and any page/inline disabled styling. opacity stays 1. */
.btn:disabled, .btn[disabled], .btn.disabled,
.ds-btn:disabled, .ds-btn[disabled],
.btn-primary:disabled, .btn-primary[disabled], .btn-primary.disabled,
.btn-secondary:disabled, .btn-secondary[disabled],
.btn-light:disabled, .btn-light[disabled],
.btn-danger:disabled, .btn-danger[disabled],
.btn-success:disabled, .btn-success[disabled],
.btn-approve:disabled, .btn-reject:disabled, .btn-view:disabled,
.btn-icon:disabled, .act-btn:disabled, .vac-btn:disabled, .vac-btn[disabled],
.send-btn:disabled, .save-btn:disabled, .primary-button:disabled {
  background: #e5eaf3 !important;
  color: #64748b !important;
  border: 1px solid #d5deea !important;
  opacity: 1 !important;
  cursor: not-allowed !important;
  box-shadow: none !important;
  filter: none !important;
  text-shadow: none !important;
  background-image: none !important;
}
/* Icons inside disabled buttons follow the muted text colour (not white). */
.btn:disabled .ti, .btn:disabled svg, .btn[disabled] .ti, .btn[disabled] svg,
.btn-primary:disabled .ti, .btn-primary:disabled svg,
.btn-danger:disabled .ti, .btn-danger:disabled svg,
.btn-success:disabled .ti, .btn-success:disabled svg,
.btn-approve:disabled .ti, .btn-reject:disabled .ti,
.act-btn:disabled .ti, .send-btn:disabled .ti, .send-btn:disabled svg {
  color: #64748b !important; stroke: #64748b !important;
}

/* Form controls — ONE standard for every input / dropdown / search / date /
   number field: 44px height, radius 12, 14px, padding 0 14px. EXCLUDES dense
   in-table / inline controls (so table density is kept) and checkbox/radio/
   range/file/color (which aren't text fields). This is the global authority,
   so it supersedes page-level input height/padding rules. */
.main-content input:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]):not([type=color]):not(.mini-input):not(.row-input):not(.row-desc):not(.qty-val):not(.addr-phone-input):not(.editable-price),
.main-content select:not(.mini-input):not(.row-input) {
  height: var(--ds-input-h) !important;
  min-height: var(--ds-input-h) !important;
  padding: 0 14px !important;
  border-radius: var(--ds-radius-input) !important;
  font-size: var(--ds-fs-input) !important;
  box-sizing: border-box !important;
}
.main-content textarea:not(.row-desc) {
  min-height: var(--ds-textarea-min) !important;
  padding: 14px !important;
  border-radius: var(--ds-radius-input) !important;
  font-size: var(--ds-fs-input) !important;
  box-sizing: border-box !important;
}
/* One search-bar standard: 44px tall, radius 14, 14px font, and 44px of left
   padding so the leading icon (sits at left:14) NEVER overlaps the placeholder.
   This restores the canonical spec the generic input rule above would shrink. */
.main-content .vb-search input:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]):not([type=color]):not(.mini-input):not(.row-input):not(.row-desc):not(.qty-val):not(.addr-phone-input):not(.editable-price),
.main-content input.vb-filter-search:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]):not([type=color]):not(.mini-input):not(.row-input):not(.row-desc):not(.qty-val):not(.addr-phone-input):not(.editable-price) {
  height: 44px !important;
  border-radius: 14px !important;
  font-size: 14px !important;
  padding: 0 14px 0 44px !important;
}
/* RTL / Dhivehi: icon flips to the right (handled in viyabook.css), so flip the
   padding too — text keeps clear of the icon. Higher specificity + !important so it
   wins over the LTR rule above in Dhivehi mode. */
body.lang-dv .main-content .vb-search input,
body.lang-dv .main-content input.vb-filter-search,
html[lang="dv"] .main-content .vb-search input,
html[lang="dv"] .main-content input.vb-filter-search,
[dir="rtl"] .main-content .vb-search input,
[dir="rtl"] .main-content input.vb-filter-search {
  padding: 0 44px 0 14px !important;
}
/* Ancestor-agnostic icon-clearance guarantee — the single global authority.
   The leading search icon sits at left:14px on EVERY search bar, but the
   Quotations / Customers / Trips / Projects / Staff pages wrap content in
   .main (not .main-content), so the .main-content rules above never reached
   them; they relied on a non-!important canonical that a page/generic rule
   could shrink back to 14px, dropping the icon on top of the text. This makes
   the 44px clearance authoritative on every .vb-filter-search input regardless
   of the content-root class. Only padding-left is set, so per-page height /
   font-size / mobile overrides are preserved (no layout change). */
input.vb-filter-search:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]):not([type=color]),
.vb-filter-search-wrap > input:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]):not([type=color]) {
  padding-left: 44px !important;
  box-sizing: border-box !important;
}
/* RTL / Dhivehi: icon flips to the right edge (see viyabook.css / vb-global.css),
   so the clearance flips too — Thaana text never lands under the icon. */
body.lang-dv input.vb-filter-search,
html[lang="dv"] input.vb-filter-search,
[dir="rtl"] input.vb-filter-search,
body.lang-dv .vb-filter-search-wrap > input,
html[lang="dv"] .vb-filter-search-wrap > input,
[dir="rtl"] .vb-filter-search-wrap > input {
  padding-left: 14px !important;
  padding-right: 44px !important;
}

/* =========================================================================
   CARDS — one consistent shell on every page: 18px radius · 24px padding ·
   soft shadow · 1px #e5eaf3 border. Enforced with !important (loaded last) so
   it supersedes page-level card radius/padding/shadow overrides. Scoped to BOTH
   content roots (.main-content and the dashboard's .main).
   NOTE: background is deliberately NOT forced — cards are already white in light
   mode, and forcing it would whiten intentionally coloured/gradient feature
   cards and break dark mode. The border colour is mode-aware (dark override
   below). Panels (which wrap full-width tables/lists) get the shell but NOT
   forced inner padding, so their content is never inset.
   ========================================================================= */
/* Content cards — full shell INCLUDING 24px padding. */
:is(.main-content, .main) :is(.card, .summary-card, .dashboard-card, .insights-card, .report-card, .info-card),
.card-standard {
  border-radius: 18px !important;
  padding: 24px !important;
  border: 1px solid #e5eaf3 !important;
  box-shadow: 0 12px 30px rgba(8, 27, 68, 0.07) !important;
}
/* KPI / stat cards + panels — same shell but keep their OWN padding (these are
   compact + mobile-responsive, or wrap full-width tables), so padding is not
   forced; only radius/border/shadow are unified. */
:is(.main-content, .main) :is(.metric-card, .stat-card, .kpi-card, .panel) {
  border-radius: 18px !important;
  border: 1px solid #e5eaf3 !important;
  box-shadow: 0 12px 30px rgba(8, 27, 68, 0.07) !important;
}
/* Dark mode: keep the card border dark (don't force the light #e5eaf3 line). */
html.viya-dv :is(.main-content, .main) :is(.card, .metric-card, .stat-card, .summary-card, .kpi-card, .dashboard-card, .insights-card, .report-card, .info-card, .panel),
html.dark :is(.main-content, .main) :is(.card, .metric-card, .stat-card, .summary-card, .kpi-card, .dashboard-card, .insights-card, .report-card, .info-card, .panel) {
  border-color: #22324f !important;
}

/* =========================================================================
   TABLES — one consistent layout: 52px header, 60px rows, 13/14px text,
   middle-aligned, fixed action/view columns, 40px centered buttons.
   ========================================================================= */
/* Fonts + vertical centering apply at every size. */
:is(.main-content, .main) table th { font-size: 13px; font-weight: 600; vertical-align: middle; }
:is(.main-content, .main) table td { font-size: 14px; vertical-align: middle; }

/* Header / row heights — DESKTOP ONLY, so the mobile data-label "cardify"
   layout (rows become stacked cards) is never forced to 60px per field. */
@media (min-width: 769px) {
  :is(.main-content, .main) table th { height: 52px !important; }
  :is(.main-content, .main) table td { height: 60px !important; }
}

/* Action / View / Send columns — fixed width, centered, no-wrap so the buttons
   line up and never overlap or stretch the column. */
:is(.main-content, .main) td[data-label="Actions"],
:is(.main-content, .main) td[data-label="Action"] { width: 170px; min-width: 170px; text-align: center !important; white-space: nowrap; }
:is(.main-content, .main) td[data-label="View"],
:is(.main-content, .main) td[data-label="Send"] { width: 110px; min-width: 110px; text-align: center !important; white-space: nowrap; }
:is(.main-content, .main) td[data-label="Approve"],
:is(.main-content, .main) td[data-label="Reject"] { text-align: center !important; white-space: nowrap; }

/* Buttons inside tables: 40px tall, vertically centered, spaced so adjacent
   buttons never overlap. The selector carries the full button-exclusion chain
   so it out-specifies the global 44px button rule WITHOUT altering the button
   system itself (small/icon/dropdown/row controls keep their own size). */
:is(.main-content, .main) td .btn:not(.btn-sm):not(.btn-lg):not(.btn-icon):not(.btn-xs):not(.page-btn):not(.qty-btn):not(.row-btn):not(.row-del):not(.icon-btn):not(.act-btn):not(.td-tab):not(.cat):not(.pay-method):not(.chip):not(.tab):not(.seg-btn) {
  height: 40px !important;
  min-height: 40px !important;
  vertical-align: middle;
}
/* NOTE: written as two explicit selectors instead of
   `:is(.main-content, .main) td .btn + .btn`. Paged.js (assets/js/vendor/
   paged.polyfill.min.js) parses every stylesheet on the page and splits
   selector lists on commas WITHOUT respecting parentheses, so the comma inside
   :is(...) was shredded into the invalid fragment " .main) td .btn+.btn",
   throwing a SyntaxError from processSelectors() and aborting the polyfill on
   every page that loads it (checkout, sales, invoices, quotation, …).
   These two selectors are exactly equivalent and comma-safe. */
.main-content td .btn + .btn,
.main td .btn + .btn { margin-left: 6px; }

/* Table wrapper corners + internal horizontal scroll (so a wide table scrolls
   INSIDE its wrapper instead of scrolling the whole page). */
:is(.main-content, .main) .table-wrap,
:is(.main-content, .main) .td-table-wrap,
:is(.main-content, .main) .table-container,
:is(.main-content, .main) .table-responsive { border-radius: 16px; overflow-x: auto; max-width: 100%; }

/* =========================================================================
   No page-level horizontal scroll (audit #6). On mobile/tablet the body
   scrolls normally, so clip any horizontal overflow there. overflow-x:clip
   (not hidden) does NOT create a scroll container, so position:sticky headers
   keep working. Desktop ≥993px already contains scroll via the app-shell rules.
   ========================================================================= */
@media (max-width: 992px) {
  html, body { overflow-x: clip; max-width: 100%; }
}

/* =========================================================================
   PAYMENT METHOD BUTTONS — one consistent component on every page & modal.
   Covers .pay-method (Checkout, Create/Trip/Project Invoice) and .pay-btn
   (Sales/POS). Fixes the "blank white selected button": SELECTED = solid blue
   fill + white text/icon + blue border + green check badge. UNSELECTED = white
   bg, dark text, gray border, visible icon. Same 150×74 size everywhere; on
   mobile 2 per row at 64px. Not a .btn, so the global button rules don't touch
   these — this is their single source of truth.
   ========================================================================= */
.pay-method, .pay-btn {
  position: relative !important;
  box-sizing: border-box !important;
  width: 150px !important;
  height: 74px !important;
  min-height: 74px !important;
  display: inline-flex !important;
  flex-direction: column !important;
  align-items: center !important;
  justify-content: center !important;
  gap: 6px !important;
  padding: 0 8px !important;
  border: 1.5px solid #d7e0ee !important;
  border-radius: 14px !important;
  background: #fff !important;
  color: #1f2937 !important;
  font-size: 13px !important;
  font-weight: 700 !important;
  line-height: 1.15 !important;
  text-align: center !important;
  cursor: pointer !important;
  box-shadow: none !important;
  transition: background .15s, border-color .15s, color .15s, box-shadow .15s !important;
}
.pay-method .pay-icon, .pay-method > i, .pay-method > svg,
.pay-btn .pay-icon, .pay-btn > i, .pay-btn > svg {
  font-size: 24px !important; width: auto !important; height: auto !important; line-height: 1 !important; color: inherit !important; flex-shrink: 0 !important;
}
.pay-method:hover, .pay-btn:hover { border-color: var(--primary, #185FA5) !important; }
.pay-method:focus-visible, .pay-btn:focus-visible { outline: 3px solid rgba(24, 95, 165, .45) !important; outline-offset: 2px !important; }

/* SELECTED — unmistakable: solid blue, white text + icon, green check badge. */
.pay-method.active, .pay-method.selected, .pay-method[aria-pressed="true"],
.pay-btn.active, .pay-btn.selected, .pay-btn[aria-pressed="true"] {
  background: var(--primary, #185FA5) !important;
  border-color: var(--primary, #185FA5) !important;
  color: #fff !important;
  box-shadow: 0 8px 18px rgba(24, 95, 165, .30) !important;
}
.pay-method.active .pay-icon, .pay-method.active > i, .pay-method.active > svg,
.pay-method[aria-pressed="true"] .pay-icon, .pay-method[aria-pressed="true"] > i,
.pay-btn.active > i, .pay-btn.active > svg, .pay-btn[aria-pressed="true"] > i,
.pay-method.selected > i, .pay-btn.selected > i { color: #fff !important; }
.pay-method.active::after, .pay-method.selected::after, .pay-method[aria-pressed="true"]::after,
.pay-btn.active::after, .pay-btn.selected::after, .pay-btn[aria-pressed="true"]::after {
  content: "\2713";
  position: absolute; top: 6px; right: 6px;
  width: 20px; height: 20px;
  background: #16a34a; color: #fff;
  border: 2px solid #fff; border-radius: 50%;
  font-size: 11px; font-weight: 900;
  display: flex; align-items: center; justify-content: center;
  box-shadow: 0 2px 6px rgba(8, 27, 68, .25);
}

/* Grid: even 12px gaps, wraps so there's no horizontal scroll. */
.payment-grid, .pay-grid {
  display: flex !important;
  flex-wrap: wrap !important;
  gap: 12px !important;
  align-items: stretch !important;
}

/* Mobile: exactly 2 buttons per row, 64px tall. */
@media (max-width: 767px) {
  .pay-method, .pay-btn {
    width: calc(50% - 6px) !important;
    flex: 0 0 calc(50% - 6px) !important;
    height: 64px !important;
    min-height: 64px !important;
  }
}

/* Icons: consistent action-icon size inside content buttons + menus. */
.main-content .btn .ti, .main-content .btn svg:not([width]) { width: var(--ds-ic-action); height: var(--ds-ic-action); }

/* =========================================================================
   PAGINATION — one compact component on every page. Targets the shared
   .pagination container + .page-btn buttons that each page's table renders.
   Page numbers = 36x36 square; Previous/Next stay compact (auto width for
   their label, same 36px height + radius). Active = primary blue. Loaded last
   so it supersedes each page's own (oversized/inconsistent) pagination CSS.
   ========================================================================= */
.pagination {
  display: flex !important;
  align-items: center !important;
  gap: 6px !important;
  flex-wrap: wrap !important;
  row-gap: 8px !important;
}
/* Inner button group — most pages wrap the page numbers in .pages/#paginationPages,
   so the container keeps its "Showing … | buttons" split; gap the buttons here too. */
.pagination .pages, #paginationPages, .pagination .page-numbers {
  display: flex !important;
  align-items: center !important;
  gap: 6px !important;
  flex-wrap: wrap !important;
}
/* The "Showing 1–10 of 25" summary — 13px medium grey. */
.pagination #showingText, .pagination .count-text,
#showingText, .count-text {
  font-size: 13px !important;
  font-weight: 500 !important;
  color: #64748b !important;
}
/* Every pagination button: 36px tall, radius 8, white. Numbers are 36x36
   square (min-width); Previous/Next grow only as wide as their label needs. */
.page-btn {
  display: inline-flex !important;
  align-items: center !important;
  justify-content: center !important;
  gap: 5px !important;
  min-width: 36px !important;
  width: auto !important;
  height: 36px !important;
  min-height: 36px !important;
  padding: 0 9px !important;
  border: 1px solid var(--border, #e2e8f0) !important;
  border-radius: 8px !important;
  background: #fff !important;
  color: var(--text, #0f172a) !important;
  font-size: 14px !important;
  font-weight: 600 !important;
  line-height: 1 !important;
  cursor: pointer !important;
  box-shadow: none !important;
  flex: 0 0 auto !important;
  transition: background .15s ease, border-color .15s ease, color .15s ease !important;
}
.page-btn:hover:not(:disabled):not(.active):not([aria-current="page"]) {
  background: #f1f5f9 !important;
  border-color: #cbd5e1 !important;
}
.page-btn.active, .page-btn[aria-current="page"] {
  background: var(--primary, #185FA5) !important;
  border-color: var(--primary, #185FA5) !important;
  color: #fff !important;
}
.page-btn:disabled, .page-btn[disabled] { opacity: .45 !important; cursor: not-allowed !important; }
.page-btn:focus-visible { outline: 2px solid rgba(24, 95, 165, .5) !important; outline-offset: 2px !important; }
.page-btn .ti, .page-btn svg { width: 16px !important; height: 16px !important; font-size: 16px !important; flex-shrink: 0 !important; }
/* Icon-only Prev/Next (when a page renders them as a single-glyph button) stay square. */
.page-btn.page-prev, .page-btn.page-next, .page-btn.page-nav { width: 34px !important; min-width: 34px !important; padding: 0 !important; }

/* Dark mode */
html.viya-dv .page-btn, html.dark .page-btn { background: #0f1830 !important; border-color: #22324f !important; color: #e6edf7 !important; }
html.viya-dv .page-btn.active, html.dark .page-btn.active { background: var(--primary, #185FA5) !important; border-color: var(--primary, #185FA5) !important; color: #fff !important; }

/* Tablet/mobile: same compact sizes, just allow the row to wrap centred. */
@media (max-width: 640px) {
  .pagination { justify-content: center !important; }
}

/* Reduce-motion friendliness */
@media (prefers-reduced-motion: reduce) {
  .ds-btn, .btn-primary, .btn-secondary, .btn-danger, .btn-success { transition: none; }
}

/* ════════════════════════════════════════════════════════════════════
   Global app-shell scroll containment (desktop ≥ 993px).
   The dark sidebar and the topbar stay fixed; ONLY the main content area
   scrolls — no body-level page scroll, no double scrollbars, no horizontal
   scroll. Two shells are supported: most pages use .dashboard-shell >
   .sidebar + .main-content (topbar injected as .viya-app-header); the
   dashboard uses .app > .sidebar + .main (its .topbar is already sticky).
   The body lock is gated with :has(...) so simple pages WITHOUT the app
   shell (customer portal, login, register) are never affected. Below 993px
   the existing mobile/tablet drawer + normal page scroll are left intact.
   ════════════════════════════════════════════════════════════════════ */
@media (min-width: 993px) {
  html:has(.dashboard-shell), html:has(.app) { height: 100%; }
  body:has(.dashboard-shell), body:has(.app) { height: 100%; overflow: hidden; }

  .dashboard-shell, .app { height: 100vh !important;
 height: 100dvh !important; min-height: 0 !important; overflow: hidden !important; }

  /* Sidebar: fixed in place (the shell doesn't scroll), with its own scroll if the menu is long. */
  .dashboard-shell > .sidebar, .app > .sidebar { height: 100vh !important;
 height: 100dvh !important; overflow-y: auto !important; overflow-x: hidden !important; }

  /* Main area is the ONLY scroller. Excluded (via body class, so the rule is valid on
     every browser — no :has dependency here): Settings (manages its own inner left-menu
     + content scroll) and Checkout/POS (self-contained fixed two-pane shell with its own
     internal scroll + pinned action bar). */
  body:not(.checkout-page):not(.settings-page) .dashboard-shell > .main-content,
  .app > .main { height: 100vh !important;
 height: 100dvh !important; overflow-y: auto !important; overflow-x: hidden !important; }

  /* Topbar stays pinned to the top of the scroller (sticky = occupies flow, never overlaps content). */
  .main-content > .viya-app-header, .app > .main > .topbar { position: sticky !important; top: 0 !important; z-index: 50 !important; }
}

/* =========================================================================
   UI consistency master — cards + standard table rows. (Buttons 44/12,
   inputs/search 44, font Inter/Faruma and button gap 12 are already enforced
   above.) Scoped to .main-content / .app so login + customer-portal pages are
   untouched. This file loads LAST on every page, so it wins over page CSS
   without deleting any page overrides (safer + reversible).
   ========================================================================= */
/* One card radius everywhere. Stat / summary / mini cards use their own classes,
   so this only normalises the standard ".card" surface. */
.main-content .card, .app .card { border-radius: var(--ds-radius-card) !important; }

/* Standard content tables → 60px rows. Dense POS / compact / mobile-card tables are
   excluded so their tight layouts stay intact. No !important, so any page that sets a
   deliberate row height still wins. */
@media (min-width: 769px) {
  .main-content table:not(.cart-table):not(.cart-items):not(.today-table):not(.pos-table):not(.qty):not(.vb-cardify) tbody tr,
  .app .content table:not(.cart-table):not(.today-table) tbody tr {
    height: var(--ds-row-h);
  }
}

/* ════════════════════════════════════════════════════════════════════════
   Prompt 111 — ONE compact "Actions" button + dropdown menu, everywhere.
   GEOMETRY ONLY (size · radius · font · icon · spacing · hover/active) so each
   page keeps its own colours / dark-mode palette. Targets the canonical labeled
   Actions triggers (.act-btn, .td-row-btn) and the reusable .vb-actions-btn.
   Icon-only kebab triggers (.dots, ti-dots) are a different paradigm and are
   intentionally NOT reshaped here.
   Desktop 36/13 · Tablet 34/12 · Mobile 32/12 (88px). Loaded last so it wins
   over loosely-styled page rules; deeply id-nested table rules still override.
   ════════════════════════════════════════════════════════════════════════ */
.act-btn, .td-row-btn, .vb-actions-btn {
  display: inline-flex !important;
  align-items: center !important;
  justify-content: center !important;
  gap: 6px !important;
  height: 36px !important;
  min-height: 36px !important;
  width: auto !important;
  min-width: 95px !important;
  max-width: 110px !important;
  padding: 0 10px 0 12px !important;
  border-radius: 10px !important;
  font-family: var(--ds-font, Inter, sans-serif) !important;
  font-size: 13px !important;
  font-weight: 500 !important;
  line-height: 1 !important;
  white-space: nowrap !important;
  box-sizing: border-box !important;
  cursor: pointer !important;
  transition: box-shadow .15s ease, background .15s ease, transform .05s ease !important;
}
/* Leading icon 16px, trailing caret 14px (req: icon 16 / arrow 14). */
.act-btn > .ti, .td-row-btn > .ti, .vb-actions-btn > .ti,
.act-btn > svg, .td-row-btn > svg, .vb-actions-btn > svg { font-size: 16px !important; width: 16px !important; height: 16px !important; flex: 0 0 auto !important; }
.act-btn > .ti:last-child, .td-row-btn > .ti:last-child, .vb-actions-btn > .ti:last-child,
.act-btn > svg:last-child, .td-row-btn > svg:last-child, .vb-actions-btn > svg:last-child { font-size: 14px !important; width: 14px !important; height: 14px !important; }
/* Same hover + active feedback everywhere (colour-neutral). */
.act-btn:hover, .td-row-btn:hover, .vb-actions-btn:hover { box-shadow: 0 2px 8px rgba(8,27,68,.12) !important; }
.act-btn:active, .td-row-btn:active, .vb-actions-btn:active { transform: translateY(1px) !important; }
/* (3) Never let a long table stretch the button. */
.main-content td .act-btn, .main-content td .td-row-btn, .main-content td .vb-actions-btn { flex: 0 0 auto !important; }
/* (4) Responsive — same design, slightly smaller. */
@media (min-width: 768px) and (max-width: 991px) {
  .act-btn, .td-row-btn, .vb-actions-btn { height: 34px !important; min-height: 34px !important; font-size: 12px !important; }
}
@media (max-width: 767px) {
  .act-btn, .td-row-btn, .vb-actions-btn { height: 32px !important; min-height: 32px !important; font-size: 12px !important; width: 88px !important; min-width: 88px !important; max-width: 88px !important; }
}

/* (2) Dropdown menu standard — same radius / shadow / padding / 36px items.
   Geometry only; positioning stays with each page's JS. */
.dd-menu, .td-row-menu, .more-menu, .actions-menu, .vb-actions-menu {
  border-radius: 10px !important;
  box-shadow: 0 12px 30px rgba(8,27,68,.14) !important;
  padding: 6px !important;
  min-width: 180px !important;
  box-sizing: border-box !important;
}
.dd-menu .dd-item, .dd-menu > button, .dd-menu > a,
.td-row-menu > button, .td-row-menu > a,
.more-menu > button, .more-menu > a,
.actions-menu > button, .actions-menu > a,
.vb-actions-menu > button, .vb-actions-menu > a {
  display: flex !important;
  align-items: center !important;
  gap: 8px !important;
  width: 100% !important;
  height: 36px !important;
  min-height: 36px !important;
  padding: 0 10px !important;
  border-radius: 8px !important;
  font-size: 13px !important;
  font-weight: 500 !important;
  white-space: nowrap !important;
  box-sizing: border-box !important;
}

/* ════════════════════════════════════════════════════════════════════════
   Prompt 118 — ONE compact pagination standard everywhere. Targets the existing
   classes (.pagination/.page-btn/.pg-btn/.td-pg-btn) AND the reusable .vb-pagination
   component (window.ViyaPagination). 36px-tall buttons · 8px radius · active = primary
   blue · "Showing X–Y of Z" = 13px/500 #64748b. Loaded last so it wins over page CSS.
   NOTE: prev/next that hold TEXT ("Prev"/"Next") stay compact text pills — CSS can't
   turn text into an icon; migrate a page to ViyaPagination for true icon-only arrows.
   ════════════════════════════════════════════════════════════════════════ */
.pagination, .pagination-btns, .td-pagination, .vb-pagination {
  display: flex !important; align-items: center !important; justify-content: center !important;
  gap: 6px !important; flex-wrap: wrap !important; min-height: 36px !important; margin: 0 !important; padding: 0 !important;
}
.pagination-row, .vb-pagination-row {
  display: flex !important; align-items: center !important; justify-content: space-between !important;
  gap: 12px !important; flex-wrap: wrap !important;
}
.page-btn, .pg-btn, .td-pg-btn, .vb-page-num {
  height: 36px !important; min-width: 36px !important; padding: 0 9px !important;
  border-radius: 8px !important; border: 1px solid #d5deea !important;
  background: #fff !important; color: #334155 !important;
  font-size: 14px !important; font-weight: 600 !important; line-height: 1 !important;
  display: inline-flex !important; align-items: center !important; justify-content: center !important;
  cursor: pointer !important; box-sizing: border-box !important; font-family: var(--ds-font, Inter, sans-serif) !important;
  transition: background .15s ease, border-color .15s ease, color .15s ease !important;
}
.page-btn:hover:not(:disabled), .pg-btn:hover:not(:disabled), .td-pg-btn:hover:not(:disabled),
.vb-page-num:hover:not(:disabled), .vb-page-btn:hover:not(:disabled) { background: #f1f5f9 !important; border-color: #c3cfe0 !important; }
.page-btn.active, .pg-btn.active, .td-pg-btn.active, .vb-page-num.active,
.page-btn[aria-current="page"], .vb-page-num[aria-current="page"] {
  background: #2563eb !important; border-color: #2563eb !important; color: #fff !important;
}
.page-btn:disabled, .pg-btn:disabled, .td-pg-btn:disabled, .vb-page-btn:disabled, .vb-page-num:disabled {
  opacity: .45 !important; cursor: not-allowed !important;
}
.page-btn:focus-visible, .pg-btn:focus-visible, .td-pg-btn:focus-visible,
.vb-page-btn:focus-visible, .vb-page-num:focus-visible { outline: 2px solid #2563eb !important; outline-offset: 2px !important; }
/* Icon-only prev/next (34×34): gst .pg-btn.arrow + the reusable .vb-page-btn */
.pg-btn.arrow, .vb-page-btn {
  width: 34px !important; min-width: 34px !important; height: 34px !important; padding: 0 !important;
  border-radius: 8px !important; border: 1px solid #d5deea !important; background: #fff !important;
  color: #475569 !important; display: inline-flex !important; align-items: center !important; justify-content: center !important;
  cursor: pointer !important; box-sizing: border-box !important;
}
.pg-btn.arrow svg, .vb-page-btn svg { width: 16px !important; height: 16px !important; }
.pg-dots, .vb-page-dots { min-width: 22px !important; color: #94a3b8 !important; font-weight: 700 !important; display: inline-flex !important; align-items: center !important; justify-content: center !important; }
.pagination-info, .vb-page-info { font-size: 13px !important; font-weight: 500 !important; color: #64748b !important; }
@media (max-width: 640px) {
  .pagination-row, .vb-pagination-row { justify-content: center !important; }
  .page-btn, .pg-btn, .td-pg-btn, .vb-page-num { height: 34px !important; min-width: 34px !important; font-size: 13px !important; }
}

/* =========================================================================
   STEP 2 — Additive, OPT-IN UI utilities (added 2026-07-09)
   New reusable helpers for the shared card / button / table / form system.

   SAFETY CONTRACT:
   • Every selector below is one of these NEW class names — data-card, form-card,
     amount-cell, mobile-card-list, button-row, safe-wrap, truncate-2-line — or a
     descendant of one. All seven were verified UNUSED across every page/CSS/JS.
   • NO !important and NO bare element selectors, so nothing on any existing page
     changes until that page explicitly adds one of these classes. Dashboard,
     Invoice, Trip and every other page are therefore untouched.
   • Classes that ALREADY exist (.stat-card, .table-card, .status-pill) are the
     canonical components and are intentionally NOT redefined here.
   • Colours use existing brand variables (--border, --text, --muted, --danger…)
     with light fallbacks; a dark-mode block at the end keeps surfaces correct.
   ========================================================================= */

/* 1 · CARD — generic content card. White surface, #E5E7EB border, 16–20px radius,
   soft shadow, equal height in a grid, and never overflows its text (Task 1). */
.data-card {
  display: flex;
  flex-direction: column;
  min-width: 0;                       /* shrink inside a grid track (no overflow) */
  height: 100%;                       /* equal height across a grid row */
  background: var(--surface, #fff);
  border: 1px solid var(--border, #e5e7eb);
  border-radius: var(--ds-radius-card, 18px);
  padding: var(--ds-pad-card, 24px);
  box-shadow: var(--ds-shadow-card, 0 12px 30px rgba(8, 27, 68, 0.07));
  box-sizing: border-box;
  overflow-wrap: anywhere;            /* long unbroken text wraps, never overflows */
}
.data-card > * { min-width: 0; }
@media (max-width: 767px) {
  .data-card { padding: 16px; border-radius: 16px; }
}

/* 2 · FORM CARD — a card that lays its fields out 2-up on desktop, 1-up on mobile,
   with full-width inputs, clear labels, error text under the field, and an aligned
   Save/Cancel row that spans the full width (Task 5). Usage:
     <form class="form-card">
       <div class="field"> <label>…</label> <input> <span class="field-error">…</span> </div>
       <div class="field span-2"> … full-width field … </div>
       <div class="form-actions"> <button class="btn-secondary">Cancel</button>
                                  <button class="btn-primary">Save</button> </div>
     </form>                                                                        */
.form-card {
  background: var(--surface, #fff);
  border: 1px solid var(--border, #e5e7eb);
  border-radius: var(--ds-radius-card, 18px);
  padding: var(--ds-pad-card, 24px);
  box-shadow: var(--ds-shadow-card, 0 12px 30px rgba(8, 27, 68, 0.07));
  box-sizing: border-box;
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));  /* desktop: 2 columns */
  gap: 16px 20px;
  align-items: start;
}
.form-card .field { display: flex; flex-direction: column; gap: 6px; min-width: 0; }
.form-card .field.span-2 { grid-column: 1 / -1; }     /* full-width field */
.form-card label,
.form-card .field-label { font-size: 13px; font-weight: 600; color: var(--muted, #64748b); }
.form-card input,
.form-card select,
.form-card textarea { width: 100%; box-sizing: border-box; }
.form-card .field-error { font-size: 12px; font-weight: 600; color: var(--danger, #ef4444); }
.form-card .form-actions {
  grid-column: 1 / -1;                 /* Save/Cancel row spans both columns */
  display: flex; gap: 12px; flex-wrap: wrap; justify-content: flex-end;
  margin-top: 4px;
}
@media (max-width: 767px) {
  .form-card { grid-template-columns: 1fr; padding: 16px; gap: 14px; }  /* mobile: 1 column */
}
@media (max-width: 480px) {
  .form-card .form-actions { justify-content: stretch; }
  .form-card .form-actions > * { flex: 1 1 auto; }   /* full-width buttons on small screens */
}

/* 3 · BUTTON ROW — an action row that sits inline on desktop and wraps cleanly on
   tablet/mobile; add .end/.center to align, .stack to go full-width column on the
   smallest screens (Task 3). */
.button-row { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }
.button-row.end    { justify-content: flex-end; }
.button-row.center { justify-content: center; }
.button-row.between{ justify-content: space-between; }
@media (max-width: 480px) {
  .button-row.stack { flex-direction: column; align-items: stretch; }
  .button-row.stack > * { width: 100%; }
}

/* 4 · AMOUNT CELL — right-aligned money value with tabular figures, never wraps
   (Task 4). Drop on a <td> or a value <span>. */
.amount-cell {
  text-align: right;
  white-space: nowrap;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
}

/* 5 · MOBILE CARD LIST — the card-list alternative to a wide table on small screens
   (Task 4). Container is a stacked list; each direct child renders as a compact
   card. The page decides when to show it (e.g. behind its own mobile media query),
   so no existing table is hidden by this rule. */
.mobile-card-list { display: flex; flex-direction: column; gap: 10px; min-width: 0; }
.mobile-card-list > * {
  background: var(--surface, #fff);
  border: 1px solid var(--border, #e5e7eb);
  border-radius: 14px;
  padding: 14px;
  box-sizing: border-box;
  min-width: 0;
  overflow-wrap: anywhere;
}

/* 6 · SAFE WRAP — drop on any flex/grid child that would otherwise overflow: it can
   shrink and long text breaks instead of pushing the layout wide (Task 6). */
.safe-wrap {
  min-width: 0;
  max-width: 100%;
  overflow-wrap: anywhere;
  word-break: break-word;
}

/* 7 · TRUNCATE 2 LINES — clamp text to two lines with an ellipsis (Task 6). */
.truncate-2-line {
  display: -webkit-box;
  -webkit-line-clamp: 2;
  line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
  overflow-wrap: anywhere;
}

/* Dark-mode surfaces for the new cards (mirrors the app's dark palette). */
html.viya-dv .data-card,        html.dark .data-card,
html.viya-dv .form-card,        html.dark .form-card,
html.viya-dv .mobile-card-list > *, html.dark .mobile-card-list > * {
  background: #0f1830;
  border-color: #22324f;
}

/* ═══════════════════════════════════════════════════════════════════════════════
   DHIVEHI FONT — AUTHORITATIVE OVERRIDE (2026-07-10). design-system.css is the LAST
   static stylesheet on every page, so this block wins over page CSS in the cascade
   WITHOUT depending on layout.js's JS running. NOTE: no Faruma web file exists in the
   repo — "Faruma" resolves to a device-installed Faruma or the Noto Sans Thaana
   fallback. Drop assets/fonts/Faruma.woff2 in and it upgrades automatically. Numbers
   stay LTR + Inter/Space Mono. English (Inter/Sora) is untouched.
   ═══════════════════════════════════════════════════════════════════════════════ */
/* MV Waheed — the ONE Dhivehi font (woff2 + .ttf). Legacy names aliased to the
   same file so Dhivehi never downgrades and the Noto font file never loads.
   Absolute /assets path (pages use <base href="/pages/">). */
@font-face {
  font-family: "MV Waheed";
  src: url('/assets/fonts/MVWaheed.woff2') format('woff2'),
       url('/assets/fonts/MV_A_Waheed_Bold.ttf') format('truetype');
  font-weight: 400 900; font-style: normal; font-display: swap;
}
@font-face { font-family: "Faruma";           src: url('/assets/fonts/MVWaheed.woff2') format('woff2'); font-weight: 400 900; font-display: swap; }
@font-face { font-family: "MV Faruma";        src: url('/assets/fonts/MVWaheed.woff2') format('woff2'); font-weight: 400 900; font-display: swap; }
@font-face { font-family: "ViyaFaruma";       src: url('/assets/fonts/MVWaheed.woff2') format('woff2'); font-weight: 400 900; font-display: swap; }
@font-face { font-family: "Noto Sans Thaana"; src: url('/assets/fonts/MVWaheed.woff2') format('woff2'); font-weight: 400 900; font-display: swap; }
html[lang="dv"] *:not([data-keep-ltr]),
html[dir="rtl"] *:not([data-keep-ltr]) {
  font-family: "MV Waheed", Inter, Arial, sans-serif !important;
  font-weight: 700 !important;
  line-height: 1.8 !important;
  letter-spacing: normal !important;
}
/* Numbers / amounts / dates / codes stay LTR + Latin (NOT Faruma). */
html[lang="dv"] .amount,  html[lang="dv"] .money,      html[lang="dv"] .number,
html[lang="dv"] .date,    html[lang="dv"] .trip-no,     html[lang="dv"] .invoice-no,
html[lang="dv"] .code,    html[lang="dv"] .email,       html[lang="dv"] .sku,
html[lang="dv"] .mono,    html[lang="dv"] .vbd-amt,     html[lang="dv"] .vbd-stat-num,
html[lang="dv"] .t-inv,   html[lang="dv"] [data-keep-ltr],
html[lang="dv"] input[type="number"], html[lang="dv"] input[type="tel"], html[lang="dv"] input[type="email"] {
  font-family: "Inter", "Inter", ui-monospace, monospace !important;
  direction: ltr !important;
  unicode-bidi: isolate !important;
  font-weight: 700 !important;
}
/* Sizes (req) — large, bold, Maldives-gov style. */
html[lang="dv"] body { font-size:clamp(16px,1.9vw,20px) !important; }
html[lang="dv"] h1 { font-size:clamp(28px,3vw,34px) !important; line-height: 1.6 !important; }
html[lang="dv"] h2 { font-size:clamp(25px,2.5vw,30px) !important; line-height: 1.6 !important; }
html[lang="dv"] h3, html[lang="dv"] .section-title, html[lang="dv"] .card-title { font-size:clamp(21px,2vw,25px) !important; line-height: 1.7 !important; }
html[lang="dv"] .card,      html[lang="dv"] .trip-card,   html[lang="dv"] .stat-card,
html[lang="dv"] .dashboard-card, html[lang="dv"] .vbd-card, html[lang="dv"] .metric,
html[lang="dv"] button,     html[lang="dv"] input,        html[lang="dv"] select,
html[lang="dv"] label,      html[lang="dv"] p,            html[lang="dv"] span,
html[lang="dv"] td,         html[lang="dv"] a,            html[lang="dv"] li {
  font-size: 20px !important;
}
html[lang="dv"] .amount, html[lang="dv"] .vbd-amt, html[lang="dv"] .money, html[lang="dv"] .vbd-stat-num { font-size: max(24px, 1em) !important; }
html[lang="dv"] .pill, html[lang="dv"] .badge, html[lang="dv"] .vbd-pill, html[lang="dv"] .status-pill { font-size: 18px !important; }
@media (max-width: 640px) {
  html[lang="dv"] h1 { font-size: 30px !important; }
  html[lang="dv"] h2 { font-size: 26px !important; }
  html[lang="dv"] .card, html[lang="dv"] .trip-card, html[lang="dv"] .vbd-card, html[lang="dv"] .metric,
  html[lang="dv"] button, html[lang="dv"] input, html[lang="dv"] select,
  html[lang="dv"] label, html[lang="dv"] p, html[lang="dv"] span { font-size: 19px !important; }
}

/* ═══════════════════════════════════════════════════════════════════════════════
   DHIVEHI = MV Waheed, NORMAL weight (2026-07-10 whole-app spec). No synthetic bold /
   text-stroke (removed — the spec wants clean weight 400). Excludes numbers (LTR/Latin)
   AND icon/SVG elements so icon glyphs are never restyled. Icons (viya-icons) render as
   SVG anyway, so they are unaffected. ═══════════════════════════════════════════════ */
html[lang="dv"] *:not(.amount):not(.money):not(.number):not(.date):not(.trip-no):not(.invoice-no):not(i):not(svg):not(path):not(use):not(code):not(pre):not([class*="ti-"]):not([class*="icon"]):not(.material-icons):not(.lucide):not(.fa):not(.fas):not(.far):not(.fab),
html[dir="rtl"] *:not(.amount):not(.money):not(.number):not(.date):not(.trip-no):not(.invoice-no):not(i):not(svg):not(path):not(use):not(code):not(pre):not([class*="ti-"]):not([class*="icon"]):not(.material-icons):not(.lucide):not(.fa):not(.fas):not(.far):not(.fab) {
  font-family: "MV Waheed", Inter, Arial, sans-serif !important;
  font-weight: 400 !important;
  -webkit-text-stroke: 0 !important;
  text-shadow: none !important;
  letter-spacing: normal;
}

/* ── Numeric inputs stay Latin + LTR (never MV Waheed). ── */
html[lang="dv"] input[type="number"], html[lang="dv"] input[type="date"], html[lang="dv"] input[type="time"],
html[lang="dv"] input[type="email"], html[lang="dv"] input[type="tel"] {
  font-family: Inter, Arial, sans-serif !important; direction: ltr !important; unicode-bidi: isolate !important;
}
/* Tabular numbers on the numeric utility classes. */
html[lang="dv"] .amount, html[lang="dv"] .money, html[lang="dv"] .number, html[lang="dv"] .amount-fit,
html[lang="dv"] .vbd-amt, html[lang="dv"] .vbd-stat-num, html[lang="dv"] .price, html[lang="dv"] .quantity {
  font-variant-numeric: tabular-nums;
}
/* Compact items must NOT become oversized (badges / pills / pagination / bottom-nav / meta). */
html[lang="dv"] .badge, html[lang="dv"] .status-badge, html[lang="dv"] .helper-text, html[lang="dv"] .meta-text,
html[lang="dv"] .bottom-nav-label, html[lang="dv"] .viya-bottom-nav-item, html[lang="dv"] .viya-bottom-nav-item span,
html[lang="dv"] .pill, html[lang="dv"] .vbd-pill, html[lang="dv"] .status-pill, html[lang="dv"] .chip,
html[lang="dv"] .pagination, html[lang="dv"] .page-btn, html[lang="dv"] #showingText, html[lang="dv"] small {
  font-size: 15px !important; line-height: 1.5 !important;
}

/* ════════════════════════════════════════════════════════════════════════
   GLOBAL RESPONSIVE — WAVE-STYLE CENTERED CONTENT + ZOOM CONTAINMENT
   ------------------------------------------------------------------------
   ONE shared layer (this file loads LAST on every page). Scoped to the app
   shell (:has(.dashboard-shell)/(.app)) so login / signup / register /
   customer-portal are untouched. Fully reversible: delete this block.
   Goal (Wave parity): sidebar fixed & stable, content centred at a max
   width with side space on wide monitors / zoom-out, cards wrap when zoomed
   in, and the PAGE never scrolls horizontally (only .table-scroll wrappers
   do). No markup change required.
   ════════════════════════════════════════════════════════════════════════ */

/* 1 · No horizontal PAGE overflow at ANY width or zoom (was ≤992px only).
      Covers all three app shells: standard (.dashboard-shell), legacy (.app)
      and dashboard (.vbd-app). */
html:has(.dashboard-shell), html:has(.app), html:has(.vbd-app),
body:has(.dashboard-shell), body:has(.app), body:has(.vbd-app) { overflow-x: clip; max-width: 100%; }

/* 2 · Sidebar zoom-stable: never flex-shrinks, keeps its px width. Main area
      is allowed to shrink (min-width:0) so its children can't force overflow. */
.dashboard-shell > .sidebar, .app > .sidebar, .vbd-app > .sidebar { flex: 0 0 auto !important; }
.dashboard-shell > .main-content, .app > .main, .vbd-main { min-width: 0 !important; }

/* 3 · Wave-style centred content — cap the content column and centre it with
      background space on wide monitors / zoom-out. Done as symmetric side
      padding so existing full-width children simply fill the centred zone
      (no markup change; the max() floor guarantees it can never go negative,
      so it cannot create overflow). Desktop only. Checkout/POS (.sales-pos-page)
      and Settings (.settings-page) keep their self-contained full-width shells. */
@media (min-width: 1025px) {
  body:not(.sales-pos-page):not(.checkout-page):not(.settings-page) .dashboard-shell > .main-content,
  body:not(.sales-pos-page):not(.settings-page) .app > .main,
  body:not(.sales-pos-page):not(.settings-page) .vbd-main {
    padding-inline: max(clamp(16px, 1.6vw, 28px), calc((100% - var(--ds-container)) / 2)) !important;
  }
}

/* 4 · Overflow-safety on existing card & grid surfaces — geometry only, NO
      restyle and (deliberately) NO overflow:hidden so Action dropdowns, date
      pickers and tooltips are never clipped. min-width:0 lets a wide child
      (long amount, table) shrink instead of pushing the page sideways. */
:is(.main-content, .main, .vbd-main) :is(.card, .panel, .stat-card, .table-card, .form-card,
  .summary-card, .dashboard-card, .metric-card, .kpi-card, .info-card, .report-card, .insights-card) {
  min-width: 0; max-width: 100%;
}
:is(.main-content, .main, .vbd-main) > *,
:is(.main-content, .main, .vbd-main) .grid,
:is(.main-content, .main, .vbd-main) [class*="-grid"] { min-width: 0; }

/* 5 · Shared responsive UTILITIES (opt-in — add these classes on any page). ── */
.auto-grid {
  display: grid; gap: clamp(12px, 1.4vw, 20px);
  grid-template-columns: repeat(auto-fit, minmax(min(240px, 100%), 1fr));
}
.kpi-grid {
  display: grid; gap: clamp(12px, 1.4vw, 20px);
  grid-template-columns: repeat(auto-fit, minmax(min(220px, 100%), 1fr));
}
.content-with-sidebar {
  display: grid; gap: clamp(14px, 1.8vw, 22px);
  grid-template-columns: minmax(0, 1fr) minmax(300px, 360px);
}
@media (max-width: 1100px) { .content-with-sidebar { grid-template-columns: 1fr; } }
.form-grid {
  display: grid; gap: 16px;
  grid-template-columns: repeat(auto-fit, minmax(min(280px, 100%), 1fr));
}
.filter-row { display: flex; flex-wrap: wrap; gap: 12px; min-width: 0; }
.filter-row > * { flex: 1 1 180px; min-width: 0; max-width: 100%; }
.table-scroll { width: 100%; max-width: 100%; overflow-x: auto; -webkit-overflow-scrolling: touch; }
.amount-fit { font-size: clamp(18px, 2vw, 30px); line-height: 1.1; overflow-wrap: anywhere; }
.page-container { width: min(100%, var(--ds-container)); margin-inline: auto; min-width: 0; }

/* Topbar helpers — align an injected/custom topbar to the same centred width. */
.topbar-inner { width: min(100%, var(--ds-container)); margin-inline: auto; display: flex; align-items: center; gap: 10px; min-width: 0; }
.topbar-search { flex: 1 1 280px; min-width: 0; max-width: 520px; }
.topbar-actions { display: flex; flex: 0 0 auto; gap: 8px; flex-wrap: wrap; }

/* ══════════════════════════════════════════════════════════════════════════
   SHARED MOBILE STAT-CARD SIZE SYSTEM  (added 2026-07-12)
   One place that normalises EVERY page's summary/stat cards to the Trip-Detail
   reference size on phones. It only RESIZES the existing card systems in place
   (grid, height, padding, radius, icon box, font sizes) — it never restructures
   markup, changes colours/meanings, or touches desktop (>767px). Each page keeps
   its own card classes and JS value injection.
   Systems normalised: .stat-card | .summary-grid .metric-card | .metrics .metric
   | .summary-card | .kpi | .vbd-cards .vbd-card. Excluded on purpose: product /
   customer-detail / invoice-row / form / checkout / modal cards and the joined
   .detail-stat-grid segment strip.
   The `html body` prefix + !important guarantees these win over each page's own
   inline mobile CSS regardless of load order. ═══════════════════════════════ */
@media (max-width: 767px) {
  /* Grid: exactly two equal cards per row. */
  html body .stat-cards,
  html body .stat-grid,
  html body .stats-grid,
  html body .metrics,
  html body .kpi-grid,
  html body .summary-cards,
  html body .summary-grid,
  html body .vbd-cards {
    display: grid !important;
    grid-template-columns: repeat(2, minmax(0, 1fr)) !important;
    gap: 14px !important;
    width: 100% !important;
    padding-inline: 14px !important;
    box-sizing: border-box !important;
    align-items: stretch !important;
  }

  /* Card: uniform 140px height, 16px padding, 20px radius. Existing internal
     layout (flex/grid, icon side) is preserved — only the box is normalised. */
  html body .stat-card,
  html body .summary-grid .metric-card,
  html body .metrics .metric,
  html body .summary-card,
  html body .kpi,
  html body .vbd-cards .vbd-card {
    height: auto !important;            /* grow if content needs it — never clip */
    min-height: 140px !important;
    min-width: 0 !important;
    padding: 16px !important;
    border-radius: 20px !important;
    box-sizing: border-box !important;
    overflow: visible !important;
  }
  /* .summary-card is a horizontal flex row by default — stack it so the title
     sits above the value like the reference card. */
  html body .summary-card {
    flex-direction: column !important;
    align-items: flex-start !important;
    justify-content: center !important;
    gap: 6px !important;
  }

  /* Icon box: 50×50, 15px radius, glyph 24px. */
  html body .stat-icon,
  html body .summary-grid .metric-icon,
  html body .metrics .metric .micon,
  html body .kpi-icon,
  html body .vbd-cards .vbd-ci {
    width: 50px !important;
    height: 50px !important;
    min-width: 50px !important;
    flex: 0 0 50px !important;
    border-radius: 15px !important;
    display: inline-flex !important;
    align-items: center !important;
    justify-content: center !important;
  }
  html body .stat-icon i,
  html body .stat-icon svg,
  html body .summary-grid .metric-icon i,
  html body .summary-grid .metric-icon svg,
  html body .metrics .metric .micon i,
  html body .metrics .metric .micon svg,
  html body .kpi-icon i,
  html body .kpi-icon svg,
  html body .vbd-cards .vbd-ci i,
  html body .vbd-cards .vbd-ci svg {
    font-size: 24px !important;
    width: 24px !important;
    height: 24px !important;
    line-height: 1 !important;
  }

  /* Title (label) — 22px, single line, ellipsis so long labels never grow the
     card. Dhivehi already renders in MV Waheed globally (html.viya-dv). */
  html body .stat-card .stat-label,
  html body .stat-card > div > span,
  html body .summary-grid .metric-text h3,
  html body .metrics .metric h3,
  html body .kpi .kpi-title,
  html body .vbd-cards .vbd-card-top > span:first-child,
  html body .summary-card > span {
    font-size: 22px !important;
    line-height: 1.2 !important;
    font-weight: 400 !important;
    white-space: normal !important;      /* wrap — never clip the title */
    overflow: visible !important;
    text-overflow: clip !important;
    overflow-wrap: anywhere !important;
    max-width: 100% !important;
  }
  html.viya-dv body .stat-card .stat-label,
  html.viya-dv body .stat-card > div > span,
  html.viya-dv body .summary-grid .metric-text h3,
  html.viya-dv body .metrics .metric h3,
  html.viya-dv body .kpi .kpi-title,
  html.viya-dv body .vbd-cards .vbd-card-top > span:first-child,
  html.viya-dv body .summary-card > span {
    font-family: "MV Waheed", Inter, Arial, sans-serif !important;
    font-size: 22px !important;
    line-height: 1.25 !important;
  }
  /* English / LTR titles are smaller so long words (e.g. "Outstanding") show in
     full — the 22px reference size is a Dhivehi (MV Waheed) requirement only. */
  html:not(.viya-dv) body .stat-card .stat-label,
  html:not(.viya-dv) body .stat-card > div > span,
  html:not(.viya-dv) body .summary-grid .metric-text h3,
  html:not(.viya-dv) body .metrics .metric h3,
  html:not(.viya-dv) body .kpi .kpi-title,
  html:not(.viya-dv) body .vbd-cards .vbd-card-top > span:first-child,
  html:not(.viya-dv) body .summary-card > span {
    font-size: 15px !important;
    line-height: 1.25 !important;
    font-weight: 700 !important;
  }

  /* Main amount — 17px. */
  html body .stat-card .stat-value,
  html body .stat-card > div > strong,
  html body .summary-grid .metric-text h2,
  html body .metrics .metric h2,
  html body .kpi .kpi-value,
  html body .vbd-cards .vbd-amt,
  html body .summary-card > strong {
    font-size: 17px !important;
    line-height: 1.15 !important;
    font-weight: 700 !important;
    white-space: normal !important;      /* full amount always visible */
    overflow: visible !important;
    text-overflow: clip !important;
    overflow-wrap: anywhere !important;
    max-width: 100% !important;
  }

  /* Supporting text — 11px, wraps so it stays fully visible. */
  html body .stat-card .stat-sub,
  html body .summary-grid .metric-text p,
  html body .metrics .metric p,
  html body .kpi .kpi-sub,
  html body .vbd-cards .vbd-trend {
    font-size: 11px !important;
    line-height: 1.2 !important;
    font-weight: 500 !important;
    white-space: normal !important;
    overflow: visible !important;
    text-overflow: clip !important;
    overflow-wrap: anywhere !important;
    max-width: 100% !important;
  }
}

/* Very small phones (<360px): keep two per row, ease the internal sizes down. */
@media (max-width: 359px) {
  html body .stat-cards,
  html body .stat-grid,
  html body .stats-grid,
  html body .metrics,
  html body .kpi-grid,
  html body .summary-cards,
  html body .summary-grid,
  html body .vbd-cards {
    gap: 10px !important;
    padding-inline: 10px !important;
  }
  html body .stat-card,
  html body .summary-grid .metric-card,
  html body .metrics .metric,
  html body .summary-card,
  html body .kpi,
  html body .vbd-cards .vbd-card {
    height: auto !important;
    min-height: 132px !important;
    padding: 13px !important;
    border-radius: 18px !important;
  }
  html body .stat-icon,
  html body .summary-grid .metric-icon,
  html body .metrics .metric .micon,
  html body .kpi-icon,
  html body .vbd-cards .vbd-ci {
    width: 44px !important;
    height: 44px !important;
    min-width: 44px !important;
    flex: 0 0 44px !important;
    border-radius: 13px !important;
  }
  html body .stat-icon i, html body .stat-icon svg,
  html body .summary-grid .metric-icon i, html body .summary-grid .metric-icon svg,
  html body .metrics .metric .micon i, html body .metrics .metric .micon svg,
  html body .kpi-icon i, html body .kpi-icon svg,
  html body .vbd-cards .vbd-ci i, html body .vbd-cards .vbd-ci svg {
    font-size: 21px !important;
    width: 21px !important;
    height: 21px !important;
  }
  html body .stat-card .stat-label,
  html body .summary-grid .metric-text h3,
  html body .metrics .metric h3,
  html body .kpi .kpi-title,
  html body .vbd-cards .vbd-card-top > span:first-child,
  html body .summary-card > span,
  html.viya-dv body .stat-card .stat-label,
  html.viya-dv body .summary-grid .metric-text h3,
  html.viya-dv body .metrics .metric h3,
  html.viya-dv body .kpi .kpi-title,
  html.viya-dv body .vbd-cards .vbd-card-top > span:first-child,
  html.viya-dv body .summary-card > span {
    font-size: 19px !important;
  }
  html body .stat-card .stat-value,
  html body .summary-grid .metric-text h2,
  html body .metrics .metric h2,
  html body .kpi .kpi-value,
  html body .vbd-cards .vbd-amt,
  html body .summary-card > strong {
    font-size: 15px !important;
  }
  html body .stat-card .stat-sub,
  html body .summary-grid .metric-text p,
  html body .metrics .metric p,
  html body .kpi .kpi-sub,
  html body .vbd-cards .vbd-trend {
    font-size: 9px !important;
  }
}
/* ═══════════════ end shared mobile stat-card size system ═══════════════════ */

/* Final mobile summary-card reference: match Trip Detail exactly. */
@media (max-width: 767px) {
  html body .vbd-cards,
  html body .dashboard-shell .summary-grid:has(> .summary),
  html body .dashboard-shell .summary-grid:has(> .summary-card),
  html body .dashboard-shell .summary-grid:has(> .metric-card),
  html body .dashboard-shell .metrics:has(> .metric),
  html body .dashboard-shell .stats-grid:has(> .stat-card),
  html body .dashboard-shell .stat-cards:has(> .stat-card),
  html body .dashboard-shell .stat-row:has(> .stat-card) {
    display:grid !important;
    grid-template-columns:repeat(2,minmax(0,1fr)) !important;
    gap:12px !important;
    width:100% !important;
    padding-inline:6px !important;
    box-sizing:border-box !important;
    align-items:stretch !important;
  }

  html body .vbd-cards > .vbd-card,
  html body .dashboard-shell .summary-grid > .summary,
  html body .dashboard-shell .summary-grid > .summary-card,
  html body .dashboard-shell .summary-grid > .metric-card,
  html body .dashboard-shell .metrics > .metric,
  html body .dashboard-shell .stats-grid > .stat-card,
  html body .dashboard-shell .stat-cards > .stat-card,
  html body .dashboard-shell .stat-row > .stat-card {
    height:112px !important;
    min-height:112px !important;
    width:100% !important;
    min-width:0 !important;
    padding:12px 14px !important;
    border-radius:18px !important;
    box-sizing:border-box !important;
    display:grid !important;
    grid-template-columns:minmax(0,1fr) 40px !important;
    grid-template-rows:auto auto 1fr !important;
    column-gap:8px !important;
    overflow:hidden !important;
  }

  html body .vbd-card-top,
  html body .dashboard-shell .stat-card .stat-top { display:contents !important; }

  html body .dashboard-shell .summary > div:not(.sicon),
  html body .dashboard-shell .summary-card > div:not(.sum-icon),
  html body .dashboard-shell .metric-card > div:not(.metric-icon),
  html body .dashboard-shell .metric > div:not(.micon),
  html body .dashboard-shell .stat-row > .stat-card > .stat-body,
  html body .dashboard-shell .stats-grid > .stat-card > div:not(.stat-icon):not(.stat-top),
  html body .dashboard-shell .stat-cards > .stat-card .stat-top > div:not(.stat-icon) {
    grid-column:1 !important;
    grid-row:1 / 4 !important;
    min-width:0 !important;
    height:100% !important;
    display:grid !important;
    grid-template-rows:auto auto 1fr !important;
  }

  html body .vbd-card-top > span:first-child,
  html body .dashboard-shell .summary span,
  html body .dashboard-shell .summary-card span,
  html body .dashboard-shell .metric-card h3,
  html body .dashboard-shell .metric h3,
  html body .dashboard-shell .stat-card .stat-label,
  html body .dashboard-shell .stats-grid > .stat-card span,
  html body .dashboard-shell .stat-cards > .stat-card span,
  html body .dashboard-shell .stat-row > .stat-card .stat-label {
    grid-column:1 !important;
    grid-row:1 !important;
    margin:0 !important;
    font-family:Inter,Arial,sans-serif !important;
    font-size:15px !important;
    line-height:1.15 !important;
    font-weight:700 !important;
    white-space:nowrap !important;
    overflow:hidden !important;
    text-overflow:ellipsis !important;
    text-transform:none !important;
    letter-spacing:0 !important;
  }

  html body .vbd-card .vbd-amt,
  html body .dashboard-shell .summary strong,
  html body .dashboard-shell .summary-card strong,
  html body .dashboard-shell .metric-card h2,
  html body .dashboard-shell .metric h2,
  html body .dashboard-shell .stat-card .stat-value,
  html body .dashboard-shell .stats-grid > .stat-card strong,
  html body .dashboard-shell .stat-cards > .stat-card h2,
  html body .dashboard-shell .stat-row > .stat-card .stat-value {
    grid-column:1 !important;
    grid-row:2 !important;
    margin:6px 0 0 !important;
    font-family:Inter,Arial,sans-serif !important;
    font-size:15px !important;
    line-height:1 !important;
    font-weight:700 !important;
    letter-spacing:0 !important;
    white-space:nowrap !important;
    overflow:hidden !important;
    text-overflow:clip !important;
    overflow-wrap:normal !important;
    word-break:keep-all !important;
    direction:ltr !important;
    unicode-bidi:isolate !important;
    font-variant-numeric:tabular-nums !important;
  }

  html body .vbd-card .vbd-trend,
  html body .dashboard-shell .summary .sub,
  html body .dashboard-shell .summary-card small,
  html body .dashboard-shell .metric-card p,
  html body .dashboard-shell .metric p,
  html body .dashboard-shell .stat-card .stat-sub,
  html body .dashboard-shell .stat-cards > .stat-card .stat-foot,
  html body .dashboard-shell .stat-row > .stat-card .stat-sub {
    grid-column:1 !important;
    grid-row:3 !important;
    align-self:end !important;
    margin:4px 0 0 !important;
    font-family:Inter,Arial,sans-serif !important;
    font-size:9px !important;
    line-height:1.1 !important;
    font-weight:700 !important;
    white-space:nowrap !important;
    overflow:hidden !important;
    text-overflow:ellipsis !important;
    letter-spacing:0 !important;
  }

  html body .vbd-card .vbd-ci,
  html body .dashboard-shell .summary .sicon,
  html body .dashboard-shell .summary-card .sum-icon,
  html body .dashboard-shell .metric-card .metric-icon,
  html body .dashboard-shell .metric .micon,
  html body .dashboard-shell .stat-card .stat-icon {
    grid-column:2 !important;
    grid-row:1 / 4 !important;
    width:40px !important;
    height:40px !important;
    min-width:40px !important;
    flex:0 0 40px !important;
    border-radius:12px !important;
    display:flex !important;
    align-items:center !important;
    justify-content:center !important;
    align-self:center !important;
    justify-self:end !important;
    font-size:19px !important;
    line-height:1 !important;
    position:static !important;
  }

  html body .vbd-card .vbd-ci i,
  html body .vbd-card .vbd-ci svg,
  html body .dashboard-shell .summary .sicon i,
  html body .dashboard-shell .summary .sicon svg,
  html body .dashboard-shell .summary-card .sum-icon i,
  html body .dashboard-shell .summary-card .sum-icon svg,
  html body .dashboard-shell .metric-card .metric-icon i,
  html body .dashboard-shell .metric-card .metric-icon svg,
  html body .dashboard-shell .metric .micon i,
  html body .dashboard-shell .metric .micon svg,
  html body .dashboard-shell .stat-card .stat-icon i,
  html body .dashboard-shell .stat-card .stat-icon svg {
    width:19px !important;
    height:19px !important;
    font-size:19px !important;
    line-height:1 !important;
  }

  html[lang="dv"] body .vbd-card-top > span:first-child,
  html[lang="dv"] body .dashboard-shell .summary span,
  html[lang="dv"] body .dashboard-shell .summary-card span,
  html[lang="dv"] body .dashboard-shell .metric-card h3,
  html[lang="dv"] body .dashboard-shell .metric h3,
  html[lang="dv"] body .dashboard-shell .stat-card .stat-label,
  html[lang="dv"] body .dashboard-shell .stats-grid > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-cards > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-row > .stat-card .stat-label {
    font-family:"MV Waheed",Inter,Arial,sans-serif !important;
    font-size:20px !important;
    line-height:1.05 !important;
    font-weight:400 !important;
    direction:rtl !important;
    text-align:start !important;
  }
}

@media (max-width: 359px) {
  html body .vbd-cards,
  html body .dashboard-shell .summary-grid:has(> .summary),
  html body .dashboard-shell .summary-grid:has(> .summary-card),
  html body .dashboard-shell .summary-grid:has(> .metric-card),
  html body .dashboard-shell .metrics:has(> .metric),
  html body .dashboard-shell .stats-grid:has(> .stat-card),
  html body .dashboard-shell .stat-cards:has(> .stat-card),
  html body .dashboard-shell .stat-row:has(> .stat-card) {
    gap:8px !important;
    padding-inline:4px !important;
  }

  html body .vbd-cards > .vbd-card,
  html body .dashboard-shell .summary-grid > .summary,
  html body .dashboard-shell .summary-grid > .summary-card,
  html body .dashboard-shell .summary-grid > .metric-card,
  html body .dashboard-shell .metrics > .metric,
  html body .dashboard-shell .stats-grid > .stat-card,
  html body .dashboard-shell .stat-cards > .stat-card,
  html body .dashboard-shell .stat-row > .stat-card {
    height:106px !important;
    min-height:106px !important;
    padding:10px 12px !important;
    grid-template-columns:minmax(0,1fr) 36px !important;
  }

  html body .vbd-card-top > span:first-child,
  html body .dashboard-shell .summary span,
  html body .dashboard-shell .summary-card span,
  html body .dashboard-shell .metric-card h3,
  html body .dashboard-shell .metric h3,
  html body .dashboard-shell .stat-card .stat-label,
  html body .dashboard-shell .stats-grid > .stat-card span,
  html body .dashboard-shell .stat-cards > .stat-card span,
  html body .dashboard-shell .stat-row > .stat-card .stat-label { font-size:14px !important; }

  html[lang="dv"] body .vbd-card-top > span:first-child,
  html[lang="dv"] body .dashboard-shell .summary span,
  html[lang="dv"] body .dashboard-shell .summary-card span,
  html[lang="dv"] body .dashboard-shell .metric-card h3,
  html[lang="dv"] body .dashboard-shell .metric h3,
  html[lang="dv"] body .dashboard-shell .stat-card .stat-label,
  html[lang="dv"] body .dashboard-shell .stats-grid > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-cards > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-row > .stat-card .stat-label { font-size:18px !important; }

  html body .vbd-card .vbd-amt,
  html body .dashboard-shell .summary strong,
  html body .dashboard-shell .summary-card strong,
  html body .dashboard-shell .metric-card h2,
  html body .dashboard-shell .metric h2,
  html body .dashboard-shell .stat-card .stat-value,
  html body .dashboard-shell .stats-grid > .stat-card strong,
  html body .dashboard-shell .stat-cards > .stat-card h2,
  html body .dashboard-shell .stat-row > .stat-card .stat-value { font-size:14px !important; }

  html body .vbd-card .vbd-trend,
  html body .dashboard-shell .summary .sub,
  html body .dashboard-shell .summary-card small,
  html body .dashboard-shell .metric-card p,
  html body .dashboard-shell .metric p,
  html body .dashboard-shell .stat-card .stat-sub,
  html body .dashboard-shell .stat-cards > .stat-card .stat-foot,
  html body .dashboard-shell .stat-row > .stat-card .stat-sub { font-size:8px !important; }

  html body .vbd-card .vbd-ci,
  html body .dashboard-shell .summary .sicon,
  html body .dashboard-shell .summary-card .sum-icon,
  html body .dashboard-shell .metric-card .metric-icon,
  html body .dashboard-shell .metric .micon,
  html body .dashboard-shell .stat-card .stat-icon {
    width:36px !important;
    height:36px !important;
    min-width:36px !important;
    flex-basis:36px !important;
  }

  html body .vbd-card .vbd-ci i,
  html body .vbd-card .vbd-ci svg,
  html body .dashboard-shell .summary .sicon i,
  html body .dashboard-shell .summary .sicon svg,
  html body .dashboard-shell .summary-card .sum-icon i,
  html body .dashboard-shell .summary-card .sum-icon svg,
  html body .dashboard-shell .metric-card .metric-icon i,
  html body .dashboard-shell .metric-card .metric-icon svg,
  html body .dashboard-shell .metric .micon i,
  html body .dashboard-shell .metric .micon svg,
  html body .dashboard-shell .stat-card .stat-icon i,
  html body .dashboard-shell .stat-card .stat-icon svg {
    width:17px !important;
    height:17px !important;
    font-size:17px !important;
  }
}

/* Final conflict guards for late page-specific summary rules. */
@media (max-width: 767px) {
  html body .vbd-cards .vbd-card-top > span:first-child,
  html body.trips-page .dashboard-shell .metrics > .metric h3 {
    font-family:Inter,Arial,sans-serif !important;
    font-size:15px !important;
    line-height:1.15 !important;
    font-weight:700 !important;
    margin:0 !important;
    padding:0 !important;
  }

  html body .vbd-cards .vbd-amt,
  html[lang="dv"] body .vbd-cards .vbd-amt,
  html body.trips-page .dashboard-shell .metrics > .metric h2,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric h2 {
    font-family:Inter,Arial,sans-serif !important;
    font-size:15px !important;
    line-height:1 !important;
    font-weight:700 !important;
    margin:6px 0 0 !important;
    direction:ltr !important;
    unicode-bidi:isolate !important;
  }

  html body .vbd-cards .vbd-trend,
  html[lang="dv"] body .vbd-cards .vbd-trend,
  html body.trips-page .dashboard-shell .metrics > .metric p,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric p {
    font-family:Inter,Arial,sans-serif !important;
    font-size:9px !important;
    line-height:1.1 !important;
    font-weight:700 !important;
    margin:4px 0 0 !important;
  }

  html[lang="dv"] body .vbd-cards .vbd-card-top > span:first-child,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric h3 {
    font-family:"MV Waheed",Inter,Arial,sans-serif !important;
    font-size:20px !important;
    line-height:1.05 !important;
    font-weight:400 !important;
  }

  html[lang="dv"] body .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card,
  html.viya-dv body .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card,
  body.lang-dv .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card {
    height:112px !important;
    min-height:112px !important;
  }
}

@media (max-width: 359px) {
  html body .vbd-cards .vbd-card-top > span:first-child,
  html body.trips-page .dashboard-shell .metrics > .metric h3 { font-size:14px !important; }
  html[lang="dv"] body .vbd-cards .vbd-card-top > span:first-child,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric h3 { font-size:18px !important; }
  html body .vbd-cards .vbd-amt,
  html[lang="dv"] body .vbd-cards .vbd-amt,
  html body.trips-page .dashboard-shell .metrics > .metric h2,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric h2 { font-size:14px !important; }
  html body .vbd-cards .vbd-trend,
  html[lang="dv"] body .vbd-cards .vbd-trend,
  html body.trips-page .dashboard-shell .metrics > .metric p,
  html[lang="dv"] body.trips-page .dashboard-shell .metrics > .metric p { font-size:8px !important; }
  html[lang="dv"] body .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card,
  html.viya-dv body .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card,
  body.lang-dv .dashboard-shell .stats-grid:has(> .stat-card) > .stat-card {
    height:106px !important;
    min-height:106px !important;
  }
}

/* Mobile summary cards: keep layout LTR so icons stay on the visual right in Dhivehi. */
@media (max-width: 767px) {
  html body .vbd-cards,
  html body .vbd-cards > .vbd-card,
  html body .dashboard-shell .summary-grid:has(> .summary),
  html body .dashboard-shell .summary-grid:has(> .summary-card),
  html body .dashboard-shell .summary-grid:has(> .metric-card),
  html body .dashboard-shell .metrics:has(> .metric),
  html body .dashboard-shell .stats-grid:has(> .stat-card),
  html body .dashboard-shell .stat-cards:has(> .stat-card),
  html body .dashboard-shell .stat-row:has(> .stat-card),
  html body .dashboard-shell .summary-grid > .summary,
  html body .dashboard-shell .summary-grid > .summary-card,
  html body .dashboard-shell .summary-grid > .metric-card,
  html body .dashboard-shell .metrics > .metric,
  html body .dashboard-shell .stats-grid > .stat-card,
  html body .dashboard-shell .stat-cards > .stat-card,
  html body .dashboard-shell .stat-row > .stat-card {
    direction:ltr !important;
    text-align:start !important;
  }

  html[lang="dv"] body .vbd-cards .vbd-card-top > span:first-child,
  html[lang="dv"] body .dashboard-shell .summary span,
  html[lang="dv"] body .dashboard-shell .summary-card span,
  html[lang="dv"] body .dashboard-shell .metric-card h3,
  html[lang="dv"] body .dashboard-shell .metric h3,
  html[lang="dv"] body .dashboard-shell .stat-card .stat-label,
  html[lang="dv"] body .dashboard-shell .stats-grid > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-cards > .stat-card span,
  html[lang="dv"] body .dashboard-shell .stat-row > .stat-card .stat-label {
    direction:rtl !important;
    text-align:start !important;
  }

  html body .vbd-cards .vbd-amt,
  html body .dashboard-shell .summary strong,
  html body .dashboard-shell .summary-card strong,
  html body .dashboard-shell .metric-card h2,
  html body .dashboard-shell .metric h2,
  html body .dashboard-shell .stat-card .stat-value,
  html body .dashboard-shell .stats-grid > .stat-card strong,
  html body .dashboard-shell .stat-cards > .stat-card h2,
  html body .dashboard-shell .stat-row > .stat-card .stat-value {
    direction:ltr !important;
    text-align:start !important;
    unicode-bidi:isolate !important;
  }
}

/* ══════════════════════════════════════════════════════════════════════════
   MOBILE (≤599px): "Please select a customer first…" item-lock warning banner
   (#invItemLockBanner on Create Invoice · .item-lock-banner on Checkout). ONE
   line, smaller font + padding; ellipsis only when the screen is too narrow to
   fit. Does NOT touch `display` (the JS show/hide toggle uses inline display),
   colours are unchanged, tablet/desktop untouched. ════════════════════════ */
@media (max-width: 599px) {
  #invItemLockBanner, .item-lock-banner {
    font-size: 12px !important;
    padding: 7px 12px !important;
    line-height: 1.35 !important;
    white-space: nowrap !important;
    overflow: hidden !important;
    text-overflow: ellipsis !important;
  }
  #invItemLockBanner { margin: 0 12px 10px !important; }  /* was 0 20px 14px — more width to fit one line */
}
