/* ================================================================
   SHIELD / KATALIS — Modern theme override
   Loaded last: overrides all Metronic default styles.
   Brand:  Navy #24246D  |  Red #DB2424
   ================================================================ */

/* ----------------------------------------------------------------
   GLOBAL — Font & base colors
   NOTE: Do NOT use * selector here — it breaks icon fonts (FA, Simple-Line-Icons)
   ---------------------------------------------------------------- */
body, .form-control, .btn, .table, .dropdown-menu,
h1, h2, h3, h4, h5, h6, p, a, td, th, label, input, select, textarea,
.portlet .portlet-title .caption, .page-title, .page-breadcrumb,
.page-sidebar-menu > li > a > .title,
.page-sidebar-menu .sub-menu > li > a,
.modal-title, .modal-body, .modal-footer,
.nav-tabs > li > a, .alert, .pagination > li > a {
  font-family: 'Inter', 'Open Sans', sans-serif !important;
}

/* Explicitly restore icon fonts — must come AFTER the Inter rule */
i.fa, i[class^="fa-"], .fa:before, [class^="fa-"]:before,
[class*=" fa-"]:before {
  font-family: 'FontAwesome' !important;
}
i.icon-home, i.icon-briefcase, i.icon-paper-plane, i.icon-clock,
i.icon-docs, i.icon-credit-card, i.icon-users, i.icon-user, i.icon-key,
i.icon-bell, i.icon-tag, i.icon-bar-chart, i.icon-settings,
i.icon-info, i.icon-envelope, i.icon-calendar, i.icon-layers,
i.icon-grid, i.icon-list, i.icon-cursor, i.icon-note, i.icon-loop,
i.icon-pin, i.icon-chart, i.icon-fire, i.icon-plane, i.icon-map,
i.icon-speech, i.icon-graph, i.icon-lock, i.icon-phone,
i[class^="icon-"], i[class*=" icon-"] {
  font-family: 'Simple-Line-Icons' !important;
}

body {
  background-color: #f0f2f7 !important;
  color: #1e293b !important;
}

a { color: #24246D; }
a:hover { color: #DB2424; }

/* ----------------------------------------------------------------
   HEADER
   ---------------------------------------------------------------- */
.page-header.navbar {
  background-color: #ffffff !important;
  background-image: none !important;
  filter: none !important;
  border-bottom: none !important;
  box-shadow: 0 2px 12px rgba(36,36,109,0.08), 0 1px 3px rgba(0,0,0,0.04) !important;
  height: 56px !important;
  min-height: 56px !important;
}

/* Logo zone — navy strip matching sidebar */
.page-header.navbar .page-logo {
  background-color: #24246D !important;
  border-right: none !important;
  width: 235px !important;
  height: 56px !important;
  display: flex !important;
  align-items: center !important;
  justify-content: center !important;
  padding: 0 16px !important;
}

/* Full logo (icon + SHIELD text) — visible when sidebar is expanded */
.page-header.navbar .page-logo a img.logo-full {
  height: 50px !important;
  width: auto !important;
  max-width: 230px !important;
  display: inline-block !important;
}

/* Icon-only logo — hidden when sidebar is expanded */
.page-header.navbar .page-logo a img.logo-icon {
  display: none !important;
}

/* Top nav icons */
.page-header.navbar .top-menu .navbar-nav > li.dropdown .dropdown-toggle > i {
  color: #475569 !important;
  font-size: 16px !important;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown .dropdown-toggle:hover,
.page-header.navbar .top-menu .navbar-nav > li.dropdown.open .dropdown-toggle {
  background-color: #f8fafc !important;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown.open .dropdown-toggle > i {
  color: #24246D !important;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown-user > .dropdown-toggle > .username {
  color: #334155 !important;
  font-weight: 500 !important;
}

/* The profile dropdown is 175px wide in layout.css — a number that fitted "Change Password" and
   "Log Out" and nothing longer. "Two-Factor Authentication" ran straight past the panel's right
   edge. Sized to its content instead of to another magic number, so the next item added does not
   reopen this. min-width keeps the panel from shrinking to the width of "Log Out". */
.page-header.navbar .top-menu .navbar-nav > li.dropdown-user .dropdown-menu {
  width: auto !important;
  min-width: 175px !important;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown-user .dropdown-menu > li > a {
  white-space: nowrap !important;
}

/* Dropdown panels */
.page-header.navbar .top-menu .navbar-nav > li.dropdown-extended .dropdown-menu > li.external {
  background: #f8fafc !important;
  border-radius: 6px 6px 0 0 !important;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown-extended .dropdown-menu > li.external > h3 {
  color: #334155 !important;
  font-size: 13px !important;
  font-weight: 600 !important;
}

/* Header toggler (replace PNG sprite) */
.page-header.navbar .menu-toggler {
  background-image: none !important;
}
.page-header.navbar .menu-toggler::before {
  content: "\f0c9";
  font-family: FontAwesome !important;
  font-size: 15px !important;
  color: #ffffff !important;
  line-height: 1 !important;
}

/* ----------------------------------------------------------------
   COLLAPSED HEADER — show icon only
   ---------------------------------------------------------------- */
.page-sidebar-closed.page-sidebar-fixed .page-header.navbar .page-logo {
  width: 46px !important;
  padding: 0 !important;
  overflow: hidden !important;
  justify-content: center !important;
}
/* Hide full logo, show icon-only */
.page-sidebar-closed.page-sidebar-fixed .page-header.navbar .page-logo a img.logo-full {
  display: none !important;
}
.page-sidebar-closed.page-sidebar-fixed .page-header.navbar .page-logo a img.logo-icon {
  display: inline-block !important;
  height: 34px !important;
  width: auto !important;
  max-width: none !important;
}

/* ----------------------------------------------------------------
   SIDEBAR
   ---------------------------------------------------------------- */
.page-sidebar-wrapper .page-sidebar,
.page-sidebar {
  background-color: #24246D !important;
  border-right: none !important;
  box-shadow: 4px 0 20px rgba(36,36,109,0.18) !important;
}

/* Sidebar toggler row (replace JPG sprite) */
.page-sidebar .sidebar-toggler,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar .sidebar-toggler,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .sidebar-toggler {
  background: transparent !important;
  background-image: none !important;
  opacity: 1 !important;
  display: inline-flex !important;
  align-items: center !important;
  justify-content: center !important;
  /* No border or shadow at rest — it is a single chevron, not a button.
     Hover supplies the affordance. */
  border: none !important;
  box-shadow: none !important;
  border-radius: 6px !important;
  width: 28px !important;
  height: 28px !important;
  margin-top: 14px !important;
  margin-right: 14px !important;
}
/* A double chevron, not a single one: a single "<" is the same glyph the menu
   groups use for their expand arrows, so it read as one more nav item. "«" is
   the conventional collapse-panel mark and is unmistakable at a glance. It is
   also set larger than the 14px nav icons so size alone separates it. */
.page-sidebar .sidebar-toggler::before,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .sidebar-toggler::before {
  content: "\f100" !important;
  font-family: FontAwesome !important;
  font-size: 17px !important;
  color: rgba(255,255,255,0.75) !important;
  line-height: 1 !important;
  transition: color 0.12s !important;
}
/* Collapsed: point right, "expand". This has to match the specificity of the
   :hover rule above, or hovering the rail flipped the arrow back to «. */
.page-sidebar-closed .page-sidebar .sidebar-toggler::before,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar .sidebar-toggler::before,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .sidebar-toggler::before {
  content: "\f101" !important;
}
/* Hover: the glyph brightens. No box, no border, no shadow. */
.page-sidebar .sidebar-toggler:hover,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .sidebar-toggler:hover {
  background: transparent !important;
  border: none !important;
  box-shadow: none !important;
}
.page-sidebar .sidebar-toggler:hover::before {
  color: #ffffff !important;
}
/* A hairline under the toggler row separates chrome from the menu proper. */
.page-sidebar .page-sidebar-menu > li.sidebar-toggler-wrapper {
  border-bottom: 1px solid rgba(255,255,255,0.12) !important;
  margin-bottom: 6px !important;
}

/* Nav items */
.page-sidebar-menu > li > a {
  color: rgba(255,255,255,0.72) !important;
  font-size: 13px !important;
  font-weight: 400 !important;
  border: none !important;
  border-bottom: none !important;
  padding: 10px 20px !important;
  transition: background 0.12s, color 0.12s !important;
}
.page-sidebar-menu > li > a > i {
  color: rgba(255,255,255,0.45) !important;
  width: 18px !important;
  text-align: center !important;
}
.page-sidebar-menu > li > a:hover,
.page-sidebar-menu > li:hover > a {
  background-color: rgba(255,255,255,0.10) !important;
  color: #ffffff !important;
}
.page-sidebar-menu > li:hover > a > i {
  color: rgba(255,255,255,0.85) !important;
}
.page-sidebar-menu > li.active > a,
.page-sidebar-menu > li.active > a:hover {
  background-color: rgba(219,36,36,0.85) !important;
  color: #ffffff !important;
  border: none !important;
}
.page-sidebar-menu > li.active > a > i {
  color: #ffffff !important;
}
.page-sidebar-menu > li > a > .arrow:before,
.page-sidebar-menu > li > a > .arrow.open:before {
  color: rgba(255,255,255,0.3) !important;
}
.page-sidebar-menu > li.active > a > .arrow:before,
.page-sidebar-menu > li.active > a > .arrow.open:before {
  color: rgba(255,255,255,0.9) !important;
}

/* Sub-menu */
.page-sidebar-menu .sub-menu {
  background-color: rgba(0,0,0,0.18) !important;
}
.page-sidebar-menu .sub-menu > li > a {
  color: rgba(255,255,255,0.60) !important;
  font-size: 12.5px !important;
  padding: 8px 20px 8px 44px !important;
  border: none !important;
  border-bottom: none !important;
}
.page-sidebar-menu .sub-menu > li > a:hover {
  background-color: rgba(255,255,255,0.10) !important;
  color: #ffffff !important;
}
.page-sidebar-menu .sub-menu > li.active > a {
  color: #ffffff !important;
  font-weight: 500 !important;
  background-color: rgba(219,36,36,0.55) !important;
}

/* ----------------------------------------------------------------
   COLLAPSED SIDEBAR — icon-only rail + flyout overlay
   All flyout backgrounds must be opaque (they overlay page content)
   ---------------------------------------------------------------- */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar {
  background-color: #24246D !important;
}

/* Icon rail — center icon in the 46px-wide collapsed strip.
   Sidebar = 46px, icon = 18px → left-pad = (46-18)/2 = 14px.
   Use padding only — no flex, which would break the flyout sub-menu layout. */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li > a {
  padding-left: 14px !important;
  padding-right: 0 !important;
}
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li > a > i {
  color: rgba(255,255,255,0.55) !important;
  width: 18px !important;
  text-align: center !important;
  display: inline-block !important;
}

/* Restore full-width padding when flyout is open (li expands to 256px) */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > a {
  padding-left: 18px !important;
  padding-right: 10px !important;
}
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li.active > a {
  background-color: rgba(219,36,36,0.85) !important;
  color: #ffffff !important;
}

/* Hover-to-peek on the collapsed rail.
   Metronic widens .page-sidebar from 46px to 235px on hover but reveals the
   label of the hovered item only (layout.css:1337), so the other 190px is an
   empty panel. Rather than fight the width — which breaks the flyout, since
   the sub-menus are positioned against the expanded sidebar — show every
   label while the rail is hovered. The expansion then means something.

   Only the label is revealed — the expand/collapse arrow stays hidden. Adding
   it back pushed the label of the open group onto a second line, and the
   flyout already shows which items have children. */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li > a > .title {
  display: inline !important;
  padding-left: 12px !important;
}
/* The open group's own <a> stays at the 45px rail width even after the sidebar
   expands, so its label had nowhere to go and dropped under the icon.
   `min-width` forces the row open regardless of what Metronic computes.

   265px rather than Metronic's 235px: at 235 the longest label ("Contract
   Management System") wrapped, and its second line then poked out from behind
   an open flyout, across the icon rail. One line, no clipping, no leftovers. */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu {
  width: 265px !important;
}
/* The <ul> has to grow too — it stays at Metronic's 235px otherwise and clips
   the labels even though the sidebar around it is wider.

   z-index: the sidebar is position:fixed with z-index:auto, so it only paints
   above the page because Metronic adds .navbar-collapse on mouseenter. If that
   handler has not fired the expanded panel ends up *under* the table. Set it
   explicitly — below the fixed header (9995), above page content. */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover {
  z-index: 1000 !important;
}
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li > a {
  display: block !important;
  min-width: 265px !important;
  white-space: nowrap !important;
}

/* Flyout LI — must be fully opaque with shadow.
   `li.open` is deliberately NOT in this list: the group containing the current
   page carries .open permanently, so including it painted a second, empty
   panel beside the real flyout every time the sidebar was hovered.

   The toggler and search rows are excluded too: they are chrome, not
   navigation, and without that exclusion hovering the collapse chevron gave
   it the full flyout treatment — a border and a drop shadow around a bare
   icon. */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover:not(.sidebar-toggler-wrapper):not(.sidebar-search-wrapper),
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li:hover:not(.sidebar-toggler-wrapper):not(.sidebar-search-wrapper) {
  background-color: #24246D !important;
  box-shadow: 6px 2px 16px rgba(0,0,0,0.22) !important;
}
/* Belt and braces: nothing may draw a box around the toggler row. */
.page-sidebar .page-sidebar-menu > li.sidebar-toggler-wrapper,
.page-sidebar .page-sidebar-menu > li.sidebar-toggler-wrapper:hover {
  background: transparent !important;
  border: none !important;
  box-shadow: none !important;
}

/* Flyout item link — hovered item only, never `li.open` (see note below). */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > a,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li:hover > a {
  background-color: rgba(255,255,255,0.12) !important;
  color: #ffffff !important;
}
/* `li.open` dropped here for the same reason as the panel rule above: the
   group holding the current page is permanently .open, so this painted its
   icon white the moment the rail was hovered — invisible on the light theme,
   and it outranked the active-icon colour. Only the hovered item recolours. */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > a > i,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li:hover > a > i {
  color: #ffffff !important;
}

/* Flyout active */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li.active > a,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu > li.active.open > a {
  background-color: rgba(219,36,36,0.85) !important;
  color: #ffffff !important;
}

/* Flyout sub-menu */
.page-sidebar-closed.page-sidebar-fixed .page-sidebar .page-sidebar-menu .sub-menu,
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > .sub-menu,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu .sub-menu {
  background-color: #1e1e62 !important;
}
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > .sub-menu > li > a,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu .sub-menu > li > a {
  color: rgba(255,255,255,0.75) !important;
  padding: 8px 16px !important;
  background-color: transparent !important;
}
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > .sub-menu > li:hover > a,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu .sub-menu > li:hover > a,
.page-sidebar-closed.page-sidebar-fixed .page-sidebar:hover .page-sidebar-menu .sub-menu > li.active > a {
  background-color: rgba(255,255,255,0.12) !important;
  color: #ffffff !important;
}

/* Show title text in flyout */
.page-sidebar-closed .page-sidebar .page-sidebar-menu.page-sidebar-menu-closed > li:hover > a > .title {
  display: inline !important;
  padding-left: 10px !important;
  color: #ffffff !important;
}

/* ----------------------------------------------------------------
   LAYOUT SPACING
   ---------------------------------------------------------------- */
.page-header-fixed .page-container {
  margin-top: 56px !important;
}
@media (min-width: 992px) {
  .page-sidebar-fixed .page-sidebar {
    top: 56px !important;
  }
}

/* ----------------------------------------------------------------
   PAGE CONTENT
   ---------------------------------------------------------------- */
.page-content-wrapper .page-content {
  background-color: #f0f2f7 !important;
  padding: 16px 20px !important;
  min-height: calc(100vh - 56px - 36px) !important;
}

/* ----------------------------------------------------------------
   PAGE BAR / BREADCRUMB
   ---------------------------------------------------------------- */
.page-bar {
  background-color: #ffffff !important;
  border: none !important;
  border-radius: 10px !important;
  margin-bottom: 16px !important;
  padding: 6px 14px !important;
  box-shadow: 0 1px 4px rgba(0,0,0,0.06) !important;
}
.page-bar .page-breadcrumb > li > a {
  color: #475569 !important;
  font-size: 12px !important;
}
.page-bar .page-breadcrumb > li > i {
  color: #7c8798 !important;
}
.page-breadcrumb > li.active {
  color: #24246D !important;
  font-weight: 600 !important;
  font-size: 12px !important;
}
.page-title {
  font-size: 19px !important;
  font-weight: 600 !important;
  color: #1e293b !important;
  margin-top: 12px !important;
  margin-bottom: 12px !important;
}

/* ----------------------------------------------------------------
   PORTLETS
   ---------------------------------------------------------------- */
.portlet {
  background-color: #ffffff !important;
  border-radius: 10px !important;
  box-shadow: 0 2px 8px rgba(36,36,109,0.07), 0 1px 2px rgba(0,0,0,0.04) !important;
  border: 1px solid rgba(226,232,240,0.7) !important;
  margin-bottom: 16px !important;
}
.portlet .portlet-title {
  border-bottom: 1px solid #f1f5f9 !important;
  padding: 7px 12px !important;
  min-height: auto !important;
}
.portlet:not(.box) .portlet-title .caption {
  font-size: 14px !important;
  font-weight: 600 !important;
  color: #1e293b !important;
}
.portlet:not(.box) .portlet-title .caption > i {
  color: #24246D !important;
  margin-right: 6px !important;
}
.portlet .portlet-title .tools > a {
  opacity: 0.45 !important;
}
.portlet .portlet-title .tools > a:hover {
  opacity: 1 !important;
}
.portlet .portlet-body {
  padding: 12px 16px !important;
  border-radius: 0 0 9px 9px !important;
}
/* Portlet with no title — full radius on the body */
.portlet > .portlet-body:only-child {
  border-radius: 9px !important;
}

/* Box portlets — flat card, no coloured header bar.
   The markup class is still `.box.blue` in 765 views, but the navy gradient it
   used to paint carried no information: it repeated the page title in a
   saturated bar above every table. Header is now a quiet section label; the
   navy survives as the caption icon only. */
.portlet.box > .portlet-title {
  background-color: revert !important;
}
.portlet.box.blue > .portlet-title {
  background: #ffffff !important;
  background-image: none !important;
  border-radius: 9px 9px 0 0 !important;
  border-bottom: 1px solid #eceff5 !important;
  padding: 9px 14px !important;
}
.portlet.box.blue > .portlet-title .caption {
  color: #1e293b !important;
  font-size: 13.5px !important;
  font-weight: 600 !important;
}
.portlet.box.blue > .portlet-title .caption > i {
  color: #24246D !important;
  margin-right: 7px !important;
}
.portlet.box.blue > .portlet-title .tools > a,
.portlet.box.blue > .portlet-title .tools > a > i {
  color: #5f6b7a !important;
  opacity: 1 !important;
}
.portlet.box.blue > .portlet-title .tools > a:hover,
.portlet.box.blue > .portlet-title .tools > a:hover > i {
  color: #24246D !important;
  opacity: 1 !important;
}
.portlet.box.blue {
  border: 1px solid #e6e9f0 !important;
}
.portlet.box.blue > .portlet-body {
  background-color: #ffffff !important;
  border: none !important;
}

/* Filter portlet — a tinted strip so it still reads as a control, not data */
.portlet.box.blue:has(.caption-filter) > .portlet-title {
  background: #f7f9fc !important;
  background-image: none !important;
  border-bottom: 1px solid #e6ebf3 !important;
}
.portlet.box.blue:has(.caption-filter) > .portlet-title .caption {
  color: #475569 !important;
}
.portlet.box.blue:has(.caption-filter) > .portlet-title .caption > i {
  color: #475569 !important;
}
.portlet.box.blue:has(.caption-filter) {
  border-color: #e2e8f0 !important;

  /* Never painted at all, rather than painted and then taken away.

     custom.js converts this portlet into a modal plus a "Filter" button on DOM ready, and does it
     last per portlet: clone the form, rebuild the select2 widgets, inject the button, draw the
     active-filter chips, then hide the row. Until that finished the blue title bar was on screen
     reading its own caption -- "Purchase Order Filter", "Purchase Order (Palladium) Filter" --
     exactly where the Filter button was about to appear, and on a long index or a tabbed screen
     like erp_bank_transactions (one portlet per tab) it was there long enough to read. Reported
     2026-09-24 as "the Filter button is missing at first".

     This stylesheet is loaded in <head>, so the rule applies before first paint. custom.js still
     reads the caption and the form out of the portlet and still hides the row -- display: none
     stops neither.

     The tinting above is now only a fallback, for a browser without :has() support: there the
     portlet stays visible and should still look like a control. */
  display: none !important;
}
.portlet.box.blue:has(.caption-filter) > .portlet-body {
  background-color: #f8fafc !important;
  border: none !important;
}

/* ----------------------------------------------------------------
   FORMS
   ---------------------------------------------------------------- */
.form-control {
  border: 1px solid #dde1ea !important;
  border-radius: 7px !important;
  padding: 5px 10px !important;
  font-size: 13px !important;
  color: #1e293b !important;
  background-color: #ffffff !important;
  box-shadow: inset 0 1px 2px rgba(0,0,0,0.04) !important;
  transition: border-color 0.15s, box-shadow 0.15s, background-color 0.15s !important;
}
.form-control:focus {
  border-color: #24246D !important;
  background-color: #ffffff !important;
  box-shadow: 0 0 0 3px rgba(36,36,109,0.10), inset 0 1px 2px rgba(0,0,0,0.02) !important;
  outline: none !important;
}
/* The fixed height belongs to the single-line controls only. It is written as
   :not(textarea) rather than as `input, select` because Select2 3.x copies the
   source select's class list onto its container <div>, so plain divs wear
   .form-control here too and still need the height.

   This used to sit on .form-control itself, undone for textareas by
   `textarea.form-control { height: auto !important }`. Two !important rules
   fighting meant a textarea could never be resized by hand: dragging the corner
   makes the browser write a plain inline height, which lost to `auto !important`
   every time — the box snapped back and only the width ever changed. Not
   asserting a height for textareas at all means both the autosize in
   shield-ui.js and the user's own drag are ordinary inline styles that work. */
.form-control:not(textarea) {
  height: 34px !important;
}
/* Readonly inputs — still distinctly non-editable, but calmer than the old
   #d1d9e6 slab, which read as an error state rather than as "display only". */
input[readonly],
input[readonly="readonly"],
textarea[readonly],
textarea[readonly="readonly"] {
  background-color: #eef1f6 !important;
  color: #43506b !important;
  cursor: not-allowed !important;
  border-color: #dfe4ec !important;
  box-shadow: none !important;
}
input[readonly]:focus,
input[readonly="readonly"]:focus,
textarea[readonly]:focus,
textarea[readonly="readonly"]:focus {
  border-color: #dfe4ec !important;
  box-shadow: none !important;
  background-color: #eef1f6 !important;
}
/* Disabled fields — same non-editable treatment */
input[disabled],
input.disabled,
textarea[disabled],
select[disabled],
.form-control[disabled],
.form-control.disabled {
  background-color: #eef1f6 !important;
  color: #43506b !important;
  cursor: not-allowed !important;
  border-color: #dfe4ec !important;
  box-shadow: none !important;
  opacity: 1 !important;
}

/* EXCEPTION — date fields.
   bootstrap-datepicker requires `readonly` on its input to stop mobile
   keyboards popping up, but the field IS editable: clicking it opens the
   picker. Styling it like a locked field told the user the opposite. These
   must look and feel exactly like a normal input. */
.input-group.date .form-control[readonly],
.input-group.date-picker .form-control[readonly],
.form-control.date-picker[readonly],
input.date-picker[readonly] {
  background-color: #ffffff !important;
  color: #1e293b !important;
  cursor: pointer !important;
  border-color: #dde1ea !important;
  box-shadow: inset 0 1px 2px rgba(0,0,0,0.04) !important;
}
.input-group.date .form-control[readonly]:hover,
.input-group.date-picker .form-control[readonly]:hover {
  border-color: #c3cbdb !important;
}
.input-group.date .form-control[readonly]:focus,
.input-group.date-picker .form-control[readonly]:focus,
.form-control.date-picker[readonly]:focus,
input.date-picker[readonly]:focus {
  border-color: #24246D !important;
  background-color: #ffffff !important;
  box-shadow: 0 0 0 3px rgba(36,36,109,0.10), inset 0 1px 2px rgba(0,0,0,0.02) !important;
}
/* The calendar trigger belongs to the same control — light it up together. */
.input-group.date:hover .input-group-btn > .btn,
.input-group.date:hover .input-group-btn > a.btn {
  background-color: #e8edf5 !important;
  border-color: #c3cbdb !important;
  color: #24246D !important;
}
/* INPUT GROUPS — integrated calendar, search, and addon buttons */
/* NOTE: hidden inputs before visible inputs fool :first-child/:last-child selectors.
   Strategy: always give .form-control the LEFT radius; btn always gets right-only radius. */
.input-group .form-control {
  z-index: 2 !important;
  border-top-left-radius: 7px !important;
  border-bottom-left-radius: 7px !important;
  border-top-right-radius: 0 !important;
  border-bottom-right-radius: 0 !important;
  border-right: none !important;
}
/* ...but only because something is assumed to sit to its right and draw that
   edge. When nothing does, the field is left open-sided and square: no right
   border at all, and the group just stops. Swept app/views -- 379 input groups,
   377 of them [input][button], one [addon][input][button], and exactly one with
   the input alone (cms_contract_tracker_history_invoices/_form_view, the
   disabled Invoice Date). That one rendered as a broken box and nothing said so.
   erp_groups hit the same thing and worked around it in its own markup.

   :last-child is safe here in a way :first-child is not. The note above is about
   a hidden input BEFORE the visible one, which breaks :first-child; it cannot
   make a trailing element vanish. Where a hidden input does follow, this simply
   does not fire -- a miss, not a break.

   Longhands, not the `border-right` shorthand: measured in the browser, the
   shorthand set the width but left the colour at currentColor, so the edge drew
   in the text colour. */
.input-group > .form-control:last-child {
  border-top-right-radius: 7px !important;
  border-bottom-right-radius: 7px !important;
  border-right-width: 1px !important;
  border-right-style: solid !important;
  border-right-color: #dde1ea !important;
}
/* Rare case: btn-group BEFORE the input (input has no left border) */
.input-group-btn:first-child ~ .form-control,
.input-group-btn:first-child + .form-control {
  border-top-left-radius: 0 !important;
  border-bottom-left-radius: 0 !important;
  border-top-right-radius: 7px !important;
  border-bottom-right-radius: 7px !important;
  border-right: 1px solid #dde1ea !important;
  border-left: none !important;
}
/* Addon spans (e.g. £ symbol)
   line-height is 32, not 34. The box is border-box and 34px high, but a 34px
   line box does not fit inside it once the 1px borders are taken out, so the
   content stretched the cell to 36 -- 2px taller than the .form-control beside
   it, which really is 34. The addon set the table row's height, the input and
   the trigger button did not reach it, and the group rendered as three boxes
   with a white sliver above and below the middle one. Measured on
   erp_groups/edit: addon 36, input 34, button 34. */
.input-group-addon {
  background-color: #f1f5f9 !important;
  border: 1px solid #dde1ea !important;
  border-radius: 0 !important;
  color: #475569 !important;
  padding: 0 10px !important;
  line-height: 32px !important;
  height: 34px !important;
  font-size: 13px !important;
}
.input-group-addon:first-child {
  border-right: none !important;
  border-radius: 7px 0 0 7px !important;
}
/* An input with an addon before it is not the start of the group, so it must
   not round its left edge. The base rule above gives every .input-group
   .form-control a 7px left radius, which is right for [input][button] and
   wrong for [addon][input] -- the field's curve sat against the addon's square
   edge and read as a gap. The right edge is already squared by that same rule.
   Written as an adjacency rather than :first-child because a hidden input
   before a visible one fools the positional selectors here; see the note
   above. */
.input-group-addon:first-child + .form-control {
  border-top-left-radius: 0 !important;
  border-bottom-left-radius: 0 !important;
}
.input-group-addon:last-child {
  border-left: none !important;
  border-radius: 0 7px 7px 0 !important;
}
/* Input-group trigger buttons (calendar, search, modal openers)
   The button carries all four borders. It used to drop the one facing the input, on the
   theory that input and button read as a single control — but the input drops its facing
   border too (see .input-group .form-control above), so nothing drew the seam. At rest that
   is invisible: the button's fill is within a shade of the input's. On hover the fill darkens
   and the shape becomes legible, at which point it reads as a box with one side missing.
   Bootstrap's -1px margin between the two means the button's border lands on the input's last
   pixel, so restoring it costs no width and shifts nothing. This is also what the date-picker
   trigger has always done; the two buttons sit on the same screens and did not match. */
.input-group-btn > .btn,
.input-group-btn > a.btn {
  height: 34px !important;
  min-width: 36px !important;
  padding: 0 10px !important;
  background-color: #f1f5f9 !important;
  background-image: none !important;
  border: 1px solid #dde1ea !important;
  border-radius: 0 7px 7px 0 !important;
  color: #475569 !important;
  box-shadow: none !important;
  font-size: 13px !important;
  line-height: 32px !important;
  transform: none !important;
  vertical-align: top !important;
}
.input-group-btn:first-child > .btn,
.input-group-btn:first-child > a.btn {
  border-radius: 7px 0 0 7px !important;
}
/* A button that is not the last part must not round the edge it shares with
   whatever follows it. The rule above rounds every trailing button's right
   edge, which is right for one button and wrong for two: the first drew a curve
   in the middle of the group, against the second's square left edge. Measured
   before: [input][btn][btn] gave 7px/0, 0/7px, 0/7px.

   At rest this is nearly invisible, because the button fill is within a shade
   of white -- the same reason the missing border above went unnoticed for so
   long. On hover the fill darkens and the shape becomes legible.

   :not(:last-child) is safe here: swept all 379 groups and every one of the 378
   with a button has nothing after that button, confirmed in the live DOM across
   five forms (23 groups, 0 buttons that were not :last-child). Where something
   does follow, squaring the edge is what this wants anyway. */
.input-group-btn:not(:last-child) > .btn,
.input-group-btn:not(:last-child) > a.btn {
  border-top-right-radius: 0 !important;
  border-bottom-right-radius: 0 !important;
}
/* The same fault on the input, in the [btn][input][btn] shape. The rule for a
   button BEFORE the input hands the input a rounded right edge and its right
   border back, on the assumption that the input ends the group. With a second
   button after it, it does not: measured before, the input was 0/7px with a
   1px right border sitting against the button's own left border. */
.input-group-btn:first-child ~ .form-control:not(:last-child) {
  border-top-right-radius: 0 !important;
  border-bottom-right-radius: 0 !important;
  border-right-width: 0 !important;
}
/* Hover set only the fill, so the outline stayed at its resting weight while the fill moved
   two steps darker. Move them together, as .input-group.date:hover already does. */
.input-group-btn > .btn:hover,
.input-group-btn > a.btn:hover {
  background-color: #e2e8f0 !important;
  border-color: #c3cbdb !important;
  color: #24246D !important;
  transform: none !important;
  box-shadow: none !important;
}
.form-group label {
  font-size: 12.5px !important;
  font-weight: 500 !important;
  color: #475569 !important;
  margin-bottom: 5px !important;
}
/* Required marker — was rendering as "Doc Number*" with no separation. */
.control-label .required,
label .required,
span.required {
  color: #DB2424 !important;
  margin-left: 3px !important;
  font-weight: 600 !important;
}
.input-icon > i {
  color: #5f6b7a !important;
}

/* ================================================================
   RECORD SHEET  (app/views/ui/_record_sheet.html.erb)
   A shared Odoo-style document surface for create, edit and detail pages.
   Sections and fields remain ordinary Rails form markup; these classes own
   grouping, rhythm and the read-only presentation.
   ================================================================ */
.record-sheet {
  width: 100% !important;
  max-width: none !important;
  margin: 0 auto 24px !important;
  overflow: hidden !important;
  background: #ffffff !important;
  border: 1px solid #e1e6ef !important;
  border-radius: 12px !important;
  box-shadow: 0 10px 30px rgba(36,36,109,0.07), 0 2px 7px rgba(15,23,42,0.04) !important;
}
.record-sheet__header {
  display: flex !important;
  align-items: flex-start !important;
  gap: 14px !important;
  padding: 20px 24px !important;
  background: linear-gradient(135deg, #f7f7fc 0%, #fbfcfe 62%, #fff8f8 100%) !important;
  border-bottom: 1px solid #e8ebf2 !important;
}
.record-sheet__icon {
  width: 42px !important;
  height: 42px !important;
  flex: 0 0 42px !important;
  display: inline-flex !important;
  align-items: center !important;
  justify-content: center !important;
  border-radius: 10px !important;
  background: #ececf7 !important;
  color: #24246D !important;
  font-size: 17px !important;
}
.record-sheet__heading { min-width: 0 !important; }
.record-sheet__eyebrow {
  display: block !important;
  margin-bottom: 3px !important;
  color: #656f80 !important;
  font-size: 10.5px !important;
  font-weight: 700 !important;
  letter-spacing: 0.09em !important;
  text-transform: uppercase !important;
}
.record-sheet__title {
  margin: 0 !important;
  color: #1c1c26 !important;
  font-size: 18px !important;
  font-weight: 650 !important;
  line-height: 1.3 !important;
}
.record-sheet__subtitle {
  max-width: 720px !important;
  margin: 4px 0 0 !important;
  color: #647084 !important;
  font-size: 12.5px !important;
  line-height: 1.55 !important;
}
.record-sheet__body { padding: 0 24px 22px !important; }

.record-section { padding: 12px 0 0 !important; }
/* Air above the divider, not just below it. The rule used to sit 10px under the
   previous section's last field and 12px over the next heading, so it read as
   belonging to the fields above rather than separating two groups. */
.record-section + .record-section {
  margin-top: 26px !important;
  padding-top: 20px !important;
  border-top: 1px solid #e6eaf2 !important;
}
/* A section title and a field label were both dark cool text one pixel apart
   (13.5px/650 navy against 12.5px/500 slate), so in a dense form they read as
   the same thing. Separating them by shade alone does not work -- they are
   separated by kind of type instead: the heading is small, heavy, tracked and
   upper-case over a rule, the same device .record-sheet__eyebrow already uses.
   Near-black rather than navy also keeps navy meaning "interactive" on these
   screens, where it is already the colour of links and breadcrumbs. */
/* No underline: upper-case and tracking already mark this as a heading, and a
   second rule so close to the section divider above it just added noise. */
.record-section__heading {
  margin-bottom: 14px !important;
}
.record-section__title {
  margin: 0 !important;
  color: #1c1c26 !important;
  font-size: 11.5px !important;
  font-weight: 700 !important;
  letter-spacing: 0.1em !important;
  text-transform: uppercase !important;
}
/* The description sits under the rule, so it needs its own breathing room. */
.record-section__heading .record-section__description { margin-top: 4px !important; }
.record-section__description {
  margin: 2px 0 0 !important;
  color: #748094 !important;
  font-size: 11.5px !important;
  line-height: 1.4 !important;
}
.record-form-grid,
.record-detail-grid {
  display: grid !important;
  grid-template-columns: repeat(2, minmax(0, 1fr)) !important;
  gap: 9px 26px !important;
}
.record-field,
.record-detail {
  min-width: 0 !important;
}
.record-field--wide,
.record-detail--wide { grid-column: 1 / -1 !important; }
.record-field > label {
  display: block !important;
  margin: 0 0 6px !important;
  color: #475569 !important;
  font-size: 12.5px !important;
  font-weight: 600 !important;
}
/* One label over several controls that belong together: a radio or checkbox
   group, or a value split across two inputs such as the NPWP marital code. */
.record-field__controls {
  display: flex !important;
  flex-wrap: wrap !important;
  gap: 8px !important;
  align-items: flex-start !important;
}
.record-field__controls > * { flex: 1 1 0 !important; min-width: 0 !important; }
.record-field__controls .select2-container { width: 100% !important; }
.record-field > label.radio-inline,
.record-field > label.checkbox-inline,
.record-field__controls > label.radio-inline,
.record-field__controls > label.checkbox-inline {
  flex: 0 0 auto !important;
  display: inline-flex !important;
  align-items: center !important;
  gap: 5px !important;
  min-height: 32px !important;
  margin: 0 14px 0 0 !important;
  padding: 0 !important;
  font-weight: 400 !important;
  white-space: nowrap !important;
}

.record-field .form-control,
.record-field .select2-container { width: 100% !important; }
.record-field textarea.form-control {
  min-height: 82px !important;
  line-height: 1.5 !important;
  /* The width is pinned by .record-field .form-control above, so a sideways drag could
     never move anything — the both-ways handle was advertising something it could not do.
     Vertical is the direction that works, so it is the only one offered. */
  resize: vertical !important;
}
.record-field__help {
  display: block !important;
  margin-top: 5px !important;
  color: #7a8496 !important;
  font-size: 11.5px !important;
  line-height: 1.4 !important;
}
/* Wraps, because it can hold more than one thing: the regular payment review puts an
   account code and the account's name in one box. Without the wrap the code, a long string
   with nothing to break on, took the whole row and pushed the name out over the next column. */
.record-static-control {
  min-height: 32px !important;
  display: flex !important;
  flex-wrap: wrap !important;
  column-gap: 6px !important;
  min-width: 0 !important;
  overflow-wrap: anywhere !important;
  align-items: center !important;
  padding: 5px 10px !important;
  color: #43506b !important;
  font-size: 13px !important;
  line-height: 1.45 !important;
  background: #f2f4f8 !important;
  border: 1px solid #e1e5ec !important;
  border-radius: 7px !important;
}
.record-sheet__actions {
  display: flex !important;
  align-items: center !important;
  justify-content: flex-end !important;
  flex-wrap: wrap !important;
  gap: 8px !important;
  margin: 24px -24px -22px !important;
  padding: 13px 24px !important;
  background: #f8fafc !important;
  border-top: 1px solid #e9edf3 !important;
}
.record-sheet__actions .btn > i { margin-right: 5px !important; }
.record-sheet__errors { margin: 20px 0 0 !important; }
.record-sheet__errors > :last-child { margin-bottom: 0 !important; }
/* The first line of a sheet body sits hard against the header rule without
   this: .record-sheet__body has no top padding of its own. */
.record-sheet__note { margin: 14px 0 12px !important; }

.record-detail {
  padding: 13px 15px !important;
  background: #fafbfd !important;
  border: 1px solid #edf0f5 !important;
  border-radius: 8px !important;
}
.record-detail dt {
  margin: 0 0 5px !important;
  color: #727d8f !important;
  font-size: 10.5px !important;
  font-weight: 700 !important;
  letter-spacing: 0.065em !important;
  text-transform: uppercase !important;
}
.record-detail dd {
  margin: 0 !important;
  color: #273244 !important;
  font-size: 13px !important;
  line-height: 1.55 !important;
  overflow-wrap: anywhere !important;
  white-space: pre-wrap !important;
}
.record-detail dd.record-detail__primary {
  color: #24246D !important;
  font-size: 14px !important;
  font-weight: 650 !important;
}
.record-detail__empty { color: #9099a8 !important; }

/* ---------------------------------------------------------------------------
   Line items inside a record sheet (New Form UI).

   These tables are NOT ours to restructure. Twenty view directories drive them
   with the Metronic table-editable-*.js scripts, which address cells by index
   (jqTds[0..4]), generate the row markup with Rails nested-attribute names, and
   rely on DataTables wrapping the table in #<id>_wrapper. So: keep the <table>,
   its id and its column count exactly as they are, and add .record-lines to it
   for styling. Wrap it in .record-lines-wrap for horizontal scrolling.

   Deliberately no display:none on .dataTables_length / _filter / _info /
   _paginate: this module's script disables paging, but other modules' scripts
   may not, and hiding a live pager would strand rows past page one.
--------------------------------------------------------------------------- */
.record-lines-wrap {
  overflow-x: auto !important;
  -webkit-overflow-scrolling: touch !important;
}
.record-sheet table.record-lines {
  width: 100% !important;
  margin: 0 !important;
  background: #fff !important;
  border: 1px solid #e9edf3 !important;
  border-radius: 8px !important;
  border-collapse: separate !important;
  border-spacing: 0 !important;
  font-size: 12.5px !important;
}
.record-sheet table.record-lines > thead > tr > th {
  padding: 8px 10px !important;
  color: #46536e !important;
  font-size: 11px !important;
  font-weight: 700 !important;
  letter-spacing: .04em !important;
  text-transform: uppercase !important;
  white-space: nowrap !important;
  background: #f4f6fa !important;
  border-top: 0 !important;
  border-bottom: 1px solid #e4e9f1 !important;
}
.record-sheet table.record-lines > tbody > tr > td {
  padding: 5px 10px !important;
  vertical-align: middle !important;
  border-top: 1px solid #eef1f6 !important;
}
.record-sheet table.record-lines > tbody > tr:first-child > td { border-top: 0 !important; }
.record-sheet table.record-lines > tbody > tr:hover > td { background: #f7f9fc !important; }
/* Sizing for the real single-line controls in a cell. Two exclusions, both by selector
   rather than undone afterwards, because this rule counts four classes and beats anything
   a `.select2-container` or `textarea.form-control` rule can reasonably assert:

     .select2-container — wears .form-control only because Select2 3.x copies the source
       select's class list. Padding here pushed the visible .select2-choice 4px down and 8px
       in from its own box, which is what put a dropdown out of line with the plain input
       beside it and left a sliver of bordered container showing past the arrow.
     textarea — a fixed 30px both clipped two lines of text to one and a half, and blocked
       the manual resize again, because the inline height a drag writes cannot beat an
       !important one. Free text is sized by the rule further up. */
.record-sheet table.record-lines > tbody > tr > td .form-control:not(.select2-container):not(textarea) {
  height: 30px !important;
  min-height: 30px !important;
  padding: 4px 8px !important;
  font-size: 12.5px !important;
}
/* Free text in a line cell. `height: auto !important` used to sit here, which is the
   same trap the .form-control:not(textarea) comment describes: dragging the resize
   corner writes a plain inline height, and `auto !important` beat it every time, so the
   box snapped back and only the WIDTH ever changed — and an unconstrained width grew the
   textarea straight over the next column. min-height leaves the drag and shield-ui.js's
   autosize as ordinary inline styles that work, width pins it to the cell, and the
   handle is limited to the one direction that can actually move. */
.record-sheet table.record-lines > tbody > tr > td textarea.form-control {
  min-height: 46px !important;
  width: 100% !important;
  resize: vertical !important;
  line-height: 1.45 !important;
}

/* Select2 3.x copies the source select's class list onto its container <div>, so the
   container wears .form-control and picks up its height, padding, border and background.
   The visible control is the .select2-choice INSIDE it, so all of that pushed the choice
   down and in: the choice sat 4px below a plain input in the neighbouring cell, and 8px
   of bordered container showed to the right of the arrow as a stray sliver. Strip the
   container back to a positioning box and let the choice be the control. */
.record-sheet .select2-container.form-control {
  height: auto !important;
  min-height: 0 !important;
  padding: 0 !important;
  border: 0 !important;
  background: none !important;
  box-shadow: none !important;
}
.record-sheet table.record-lines .select2-container { min-width: 0 !important; }
.record-sheet table.record-lines .select2-container .select2-choice {
  height: 30px !important;
  line-height: 28px !important;
  font-size: 12.5px !important;
}
.record-sheet table.record-lines .select2-container .select2-choice > .select2-chosen {
  margin-right: 30px !important;
  line-height: 28px !important;
}
.record-sheet table.record-lines .select2-container .select2-choice .select2-arrow {
  width: 26px !important;
}

/* An input-group inside a line cell: .record-lines shrinks the field to 30px but the
   attached button kept Bootstrap's 34px, so the calendar sat proud of the input at both
   edges and read as an oversized icon of its own. */
.record-sheet table.record-lines > tbody > tr > td .input-group-btn > .btn {
  height: 30px !important;
  min-height: 30px !important;
  padding: 0 9px !important;
  line-height: 28px !important;
  font-size: 12.5px !important;
}
/* numeric cells line up on the decimal; tabular figures stop them dancing */
.record-sheet table.record-lines td.record-lines__num,
.record-sheet table.record-lines th.record-lines__num { text-align: right !important; }
.record-sheet table.record-lines td.record-lines__num .form-control {
  text-align: right !important;
  font-variant-numeric: tabular-nums !important;
}
/* The action column gets a real width, and one a form can override. It used to be
   1% !important. Most line tables here are table-layout: fixed, where 1% means 1% of the
   table, about 12px, and the !important also beat the widths the forms set themselves
   (style="width: 100px"). The Delete button hung out of a 16px column on the journal entry
   and travel request forms. 84px holds the delete button; a form that needs more says so
   inline, and that now wins. */
.record-sheet table.record-lines th.record-lines__action {
  width: 84px;
}
.record-sheet table.record-lines td.record-lines__action,
.record-sheet table.record-lines th.record-lines__action {
  white-space: nowrap !important;
  text-align: center !important;
}
.record-lines__toolbar {
  display: flex !important;
  align-items: center !important;
  gap: 8px !important;
  margin-top: 9px !important;
}
.record-lines__empty {
  padding: 15px 10px !important;
  color: #8a93a6 !important;
  font-size: 12.5px !important;
  font-style: italic !important;
  text-align: center !important;
}
.record-sheet .dataTables_wrapper { margin: 0 !important; }

/* ---------------------------------------------------------------------------
   Tabs inside a record sheet.

   Generalised from the Employee profile, which proved the shape and still carries
   its own copy in pages/css/hr-employees.css (.employee-record-tabs). That private
   copy can retire once Employee is re-verified against this one; until then the two
   are deliberately identical in behaviour, so do not "fix" one without the other.

   The rules that matter, both from the standard: the navigation is ONE row that
   never wraps and scrolls horizontally instead, and an active tab has exactly the
   same font weight and padding as an inactive one — otherwise selecting a tab
   reflows the row and the last tab jumps to a second line.
--------------------------------------------------------------------------- */
.record-tabs.nav-tabs {
  display: flex !important;
  flex-wrap: nowrap !important;
  gap: 4px !important;
  width: 100% !important;
  margin: 0 !important;
  padding: 10px 0 0 !important;
  overflow-x: auto !important;
  overflow-y: hidden !important;
  border-bottom: 1px solid #e5e9f0 !important;
  scrollbar-width: thin;
  scrollbar-color: #c7ceda transparent;
  -webkit-overflow-scrolling: touch;
}
.record-tabs.nav-tabs::before,
.record-tabs.nav-tabs::after { display: none !important; }
.record-tabs.nav-tabs > li {
  float: none !important;
  flex: 0 0 auto !important;
  margin: 0 !important;
}
.record-tabs.nav-tabs > li > a,
.record-tabs.nav-tabs > li.active > a,
.record-tabs.nav-tabs > li.active > a:hover,
.record-tabs.nav-tabs > li.active > a:focus {
  min-height: 44px !important;
  margin: 0 !important;
  padding: 12px 14px 10px !important;
  white-space: nowrap !important;
  color: #4d596c !important;
  font-size: 13px !important;
  font-weight: 600 !important;
  line-height: 20px !important;
  background: transparent !important;
  border: 0 !important;
  border-bottom: 3px solid transparent !important;
  border-radius: 0 !important;
}
.record-tabs.nav-tabs > li > a:hover,
.record-tabs.nav-tabs > li > a:focus {
  color: #24246D !important;
  background: #f6f7fb !important;
}
.record-tabs.nav-tabs > li.active > a,
.record-tabs.nav-tabs > li.active > a:hover,
.record-tabs.nav-tabs > li.active > a:focus {
  color: #DB2424 !important;
  border-bottom-color: #DB2424 !important;
}
.record-tab-content.tab-content {
  margin: 0 !important;
  padding: 0 !important;
  background: transparent !important;
  border: 0 !important;
}

/* ---- Totals strip ------------------------------------------------------- */
.record-totals {
  display: flex !important;
  flex-direction: column !important;
  gap: 4px !important;
  width: 100% !important;
  max-width: 360px !important;
  margin: 11px 0 0 auto !important;
}
.record-totals__row {
  display: flex !important;
  align-items: center !important;
  justify-content: space-between !important;
  gap: 14px !important;
  padding: 5px 11px !important;
  border-radius: 7px !important;
}
.record-totals__label {
  color: #5b6884 !important;
  font-size: 12px !important;
  font-weight: 600 !important;
}
.record-totals__value {
  color: #24246D !important;
  font-size: 13px !important;
  font-weight: 700 !important;
  font-variant-numeric: tabular-nums !important;
}
.record-totals__row--grand {
  background: #f2f4f8 !important;
  border: 1px solid #e1e5ec !important;
}
.record-totals__row--grand .record-totals__label { color: #43506b !important; }
.record-totals__row--grand .record-totals__value { font-size: 14.5px !important; }
.record-totals .form-control {
  width: 150px !important;
  height: 30px !important;
  min-height: 30px !important;
  padding: 4px 9px !important;
  text-align: right !important;
  font-size: 13px !important;
  font-weight: 700 !important;
  font-variant-numeric: tabular-nums !important;
  color: #24246D !important;
}
@media (max-width: 767px) {
  .record-totals { max-width: none !important; }
}


/* Compact rows: the label sits beside its control from 992px up, and stacks
   above it below that. Stacked labels cost 24px per field — measured at 58px per
   row against 34px for the form-horizontal layout they replaced, which is what
   turned a 1.4-screen form into a 2.1-screen one.

   The label is taken out of flow and the row padded instead of using grid or
   flex columns, because a field may legitimately hold more than one child: an
   input-group wrapper with its button, a help note under the control, or several
   inputs. Those all keep flowing normally inside the padded area. Hidden inputs
   generate no box, so they cost nothing either way. */
@media (min-width: 992px) {
  .record-field {
    position: relative !important;
    min-height: 32px !important;
    padding-left: 38% !important;
  }
  /* The detail row is always exactly a dt + dd pair — verified across all 119 of
     them — so it can use flex, and flex can do what absolute positioning cannot:
     put the label on the SAME BASELINE as its value. Pinning the label to the top
     of the card left it floating above the value, which reads as misaligned, and
     worse for a record-detail__primary value whose larger type sits lower still.
     A multi-line value aligns to its first line, which is the conventional
     behaviour. .record-field keeps absolute positioning because it may hold more
     than one child. */
  .record-detail {
    display: flex !important;
    align-items: baseline !important;
    gap: 0 14px !important;
    min-height: 32px !important;
    padding: 10px 15px !important;
  }
  .record-detail > dd {
    flex: 1 1 auto !important;
    min-width: 0 !important;
  }
  /* The label occupies a band the same height as one control row and centres its
     text inside it, so it lines up with an input without a hand-tuned padding.
     A tall control such as a textarea keeps the band at the top of the row, which
     puts the label against the control's first line — the conventional place for
     it. Padding was tried first and only moves the centre by half its value,
     which is how you end up with magic numbers that drift. */
  /* :not() matters. Bootstrap renders a radio or checkbox group as
     <label class="radio-inline"><input> Yes</label> siblings, so a bare
     `.record-field > label` claimed those too and stacked all three labels at the
     same absolute position — the field label and both options on top of each
     other. That shipped in a4fcb7d0 and broke the radio fields on
     hr_employee_trainings and hr_employee_contact_people as well as Employee. */
  .record-field > label:not(.radio-inline):not(.checkbox-inline) {
    position: absolute !important;
    left: 0 !important;
    top: 0 !important;
    width: calc(38% - 14px) !important;
    min-height: 32px !important;
    margin: 0 !important;
    padding: 0 !important;
    display: flex !important;
    align-items: center !important;
    line-height: 1.35 !important;
    overflow-wrap: break-word !important;
  }
  /* Overrides the 5px bottom margin the stacked layout needs. */
  .record-detail > dt {
    flex: 0 0 34% !important;
    max-width: 34% !important;
    margin: 0 !important;
    padding: 0 !important;
    line-height: 1.35 !important;
    overflow-wrap: break-word !important;
  }
  /* A wide field spans both grid columns, so its label can afford less width. */
  /* A wide field spans both grid columns and its label is usually a sentence, not
     a noun, so it goes back ABOVE the control at full width. Percentages cannot be
     used to give it a side column: `padding-left: 19%` on the field resolves
     against the field's own inline size, while `width: calc(19% - 14px)` on the
     absolutely positioned label resolves against its containing block's padding
     box — and for an item spanning both tracks those differ. Measured at 1440px:
     211px of reserved padding against a 410px label box, which put "Contribution
     to improved individual and project performance" straight through its
     textarea. Stacking cannot collide at any width or label length. */
  .record-field--wide { padding-left: 0 !important; }
  .record-field--wide > label:not(.radio-inline):not(.checkbox-inline) {
    position: static !important;
    display: block !important;
    width: auto !important;
    min-height: 0 !important;
    margin: 0 0 6px !important;
  }
  .record-detail--wide {
    display: block !important;
    padding: 10px 15px !important;
  }
  .record-detail--wide > dt {
    flex: none !important;
    max-width: none !important;
    margin: 0 0 4px !important;
  }
}

@media (max-width: 767px) {
  .record-sheet__header { padding: 17px 18px !important; }
  .record-sheet__body { padding: 0 18px 18px !important; }
  .record-form-grid,
  .record-detail-grid { grid-template-columns: minmax(0, 1fr) !important; }
  .record-field--wide,
  .record-detail--wide { grid-column: auto !important; }
  .record-sheet__actions {
    margin: 22px -18px -18px !important;
    padding: 12px 18px !important;
  }
}

/* ----------------------------------------------------------------
   BUTTONS
   ---------------------------------------------------------------- */
.btn {
  border-radius: 7px !important;
  font-size: 13px !important;
  font-weight: 500 !important;
  padding: 5px 13px !important;
  border: none !important;
  /* box-shadow: 0 1px 2px rgba(0,0,0,0.06) !important; */
  transition: background 0.12s, box-shadow 0.12s, transform 0.08s !important;
}
.btn:active {
  transform: translateY(1px) !important;
  box-shadow: none !important;
}
/* Brand primary — navy gradient */
.btn-primary {
  background: linear-gradient(135deg, #24246D 0%, #3a3a9c 100%) !important;
  background-image: linear-gradient(135deg, #24246D 0%, #3a3a9c 100%) !important;
  color: #ffffff !important;
}
/* A primary button used as a dropdown trigger keeps its fill. Metronic's
   components.css carries
     .btn.dropdown-toggle, .btn-group .btn.dropdown-toggle, .btn:hover, .btn:disabled
       { background-image: none !important }
   and .btn.dropdown-toggle is two classes against .btn-primary's one, so with
   both marked !important the specificity decides and the gradient above loses.
   The button then drew white text on nothing — the same fault as the invisible
   Reject, from the same kind of !important race. Three classes settles it. */
.btn.btn-primary.dropdown-toggle,
.btn-group .btn.btn-primary.dropdown-toggle {
  background: linear-gradient(135deg, #24246D 0%, #3a3a9c 100%) !important;
  background-image: linear-gradient(135deg, #24246D 0%, #3a3a9c 100%) !important;
  color: #ffffff !important;
}
.btn.btn-primary.dropdown-toggle:hover,
.btn.btn-primary.dropdown-toggle:focus,
.btn-group .btn.btn-primary.dropdown-toggle:hover {
  background: linear-gradient(135deg, #1b1b55 0%, #2e2e84 100%) !important;
  background-image: linear-gradient(135deg, #1b1b55 0%, #2e2e84 100%) !important;
  color: #ffffff !important;
}
.btn-primary:hover,
.btn-primary:focus {
  background: linear-gradient(135deg, #1b1b55 0%, #2e2e84 100%) !important;
  background-image: linear-gradient(135deg, #1b1b55 0%, #2e2e84 100%) !important;
  box-shadow: 0 4px 14px rgba(36,36,109,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
/* Approve / confirm — emerald */
.btn-success {
  background-color: #16a34a !important;
  background-image: none !important;
  color: #ffffff !important;
}
.btn-success:hover,
.btn-success:focus {
  background-color: #15803d !important;
  box-shadow: 0 4px 14px rgba(22,163,74,0.28) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
/* Delete / reject — red */
.btn-danger {
  background-color: #ef4444 !important;
  background-image: none !important;
  color: #ffffff !important;
}
.btn-danger:hover,
.btn-danger:focus {
  background-color: #dc2626 !important;
  box-shadow: 0 4px 14px rgba(239,68,68,0.28) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
/* Edit / caution — amber */
.btn-warning {
  background-color: #f59e0b !important;
  background-image: none !important;
  color: #ffffff !important;
}
.btn-warning:hover,
.btn-warning:focus {
  background-color: #d97706 !important;
  box-shadow: 0 4px 14px rgba(245,158,11,0.28) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
/* View / info — sky blue */
.btn-info {
  background-color: #0ea5e9 !important;
  background-image: none !important;
  color: #ffffff !important;
}
.btn-info:hover,
.btn-info:focus {
  background-color: #0284c7 !important;
  box-shadow: 0 4px 14px rgba(14,165,233,0.28) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
/* Neutral / cancel — ghost */
.btn-default {
  background-color: #ffffff !important;
  background-image: none !important;
  border: 1px solid #d0d7e2 !important;
  color: #374151 !important;
  /* The same resting lift `.btn.default` has. Without it the two spellings of
     the neutral button were not interchangeable, which is the only thing that
     made choosing between them matter. */
  box-shadow: 0 1px 2px rgba(0,0,0,0.04) !important;
}
/* Metronic's components.css ships `.btn-default > i { color: #aaa }` and no
   counterpart for `.btn.default`, so the SAME neutral button drew a dark icon
   spelled one way and a washed-out grey one spelled the other. Measured on
   erp_ious/new, where both appear together: icon #aaa against a #374151 label.
   Six of them on erp_groups/edit alone.

   `inherit` rather than a literal: the icon then follows whatever the button's
   own colour is, which is right for the input-group triggers that carry
   .btn-default at #475569 as well as for the ordinary #374151 ones. Checked
   across three screens — every icon it moved landed on its own button's colour
   and nothing else changed. */
.btn-default > i {
  color: inherit !important;
}
.btn-default:hover,
.btn-default:focus {
  background-color: #f1f5f9 !important;
  border-color: #94a3b8 !important;
  box-shadow: 0 2px 8px rgba(0,0,0,0.08) !important;
  transform: translateY(-1px) !important;
}

/* ----------------------------------------------------------------
   TABLES
   ---------------------------------------------------------------- */
.table {
  font-size: 13px !important;
}
.table > thead > tr > th {
  font-size: 10.5px !important;
  font-weight: 700 !important;
  text-transform: uppercase !important;
  letter-spacing: 0.07em !important;
  color: #475569 !important;
  border-bottom: 2px solid #e8edf4 !important;
  background-color: #f7f9fc !important;
  padding: 8px 12px !important;
}
/* NOTE: every tbody rule must name `th` as well as `td`. Several tables use a
   row-header layout (<tr><th>label</th><td>value</td></tr>) — for instance the
   totals block on the activity request form. Styling only `td` leaves the
   label cell on Bootstrap's defaults: a hard #ddd rule against our faint
   #f0f3f8 one, and a different stripe colour, so the row looks half-drawn. */
.table > tbody > tr > td,
.table > tbody > tr > th {
  border-color: #f0f3f8 !important;
  vertical-align: middle !important;
  padding: 8px 12px !important;
  color: #374151 !important;
}
.table > tbody > tr:hover > td,
.table > tbody > tr:hover > th {
  background-color: #f5f7fd !important;
  transition: background-color 0.1s !important;
}
.table-striped > tbody > tr:nth-of-type(odd) > td,
.table-striped > tbody > tr:nth-of-type(odd) > th {
  background-color: #f9fafc !important;
}

/* De-grid `.table-bordered` (302 views) — horizontal rules only.
   Vertical rules chop a wide row into unrelated cells and make long text
   columns much harder to follow. The outer box is already drawn by .portlet. */
.table-bordered,
.table-bordered > thead > tr > th,
.table-bordered > thead > tr > td,
.table-bordered > tbody > tr > th,
.table-bordered > tbody > tr > td,
.table-bordered > tfoot > tr > th,
.table-bordered > tfoot > tr > td {
  border-left: none !important;
  border-right: none !important;
}
.table-bordered { border-top: none !important; border-bottom: none !important; }
.table-bordered > tbody > tr:last-child > td,
.table-bordered > tbody > tr:last-child > th { border-bottom: none !important; }

/* Digits that sit in a column should line up. */
.table { font-variant-numeric: tabular-nums !important; }

.dataTables_wrapper .dataTables_filter input {
  border-radius: 7px !important;
  border: 1px solid #d0d7e2 !important;
  padding: 5px 10px !important;
}

/* ----------------------------------------------------------------
   MODALS
   ---------------------------------------------------------------- */
.modal-content {
  border-radius: 14px !important;
  border: none !important;
  box-shadow: 0 24px 80px rgba(0,0,0,0.18), 0 8px 24px rgba(0,0,0,0.08) !important;
}
.modal-header {
  border-bottom: 1px solid #f1f5f9 !important;
  padding: 12px 18px !important;
  border-radius: 12px 12px 0 0 !important;
}
.modal-header .modal-title {
  font-size: 15px !important;
  font-weight: 600 !important;
  color: #1e293b !important;
}
.modal-body {
  padding: 14px 18px !important;
}
.modal-footer {
  border-top: 1px solid #f1f5f9 !important;
  padding: 10px 18px !important;
  border-radius: 0 0 12px 12px !important;
}

/* ----------------------------------------------------------------
   DROPDOWNS
   ---------------------------------------------------------------- */
.dropdown-menu {
  border-radius: 10px !important;
  border: 1px solid #e8edf4 !important;
  box-shadow: 0 8px 32px rgba(36,36,109,0.12), 0 2px 8px rgba(0,0,0,0.06) !important;
  padding: 6px !important;
}
.dropdown-menu > li > a {
  border-radius: 6px !important;
  font-size: 13px !important;
  color: #374151 !important;
  padding: 7px 12px !important;
}
.dropdown-menu > li > a:hover {
  background-color: #f3f4f6 !important;
  color: #111827 !important;
}

/* ----------------------------------------------------------------
   TABS
   ---------------------------------------------------------------- */
.nav-tabs {
  border-bottom: 2px solid #e2e8f0 !important;
}
.nav-tabs > li > a {
  font-size: 13px !important;
  font-weight: 500 !important;
  color: #475569 !important;
  border: none !important;
  border-radius: 0 !important;
  padding: 7px 14px !important;
}
.nav-tabs > li > a:hover {
  background: transparent !important;
  color: #1e293b !important;
  border: none !important;
}
.nav-tabs > li.active > a,
.nav-tabs > li.active > a:hover,
.nav-tabs > li.active > a:focus {
  border: none !important;
  border-bottom: 2px solid #DB2424 !important;
  color: #DB2424 !important;
  font-weight: 600 !important;
  background: transparent !important;
  margin-bottom: -2px !important;
}

/* Tab content pane */
.tab-content {
  background-color: transparent !important;
  border: none !important;
  border-radius: 0 !important;
  padding: 16px 0 !important;
}
/* Remove the portlet's outer margin when it sits directly inside a tab pane */
.tab-content > .tab-pane > .portlet:last-child,
.tab-content > .tab-pane > .row:last-child {
  margin-bottom: 0 !important;
}

/* ----------------------------------------------------------------
   ALERTS
   ---------------------------------------------------------------- */
.alert {
  border-radius: 7px !important;
  border: none !important;
  font-size: 12.5px !important;
  padding: 8px 14px !important;
}
.alert-info    { background-color: #eff6ff !important; color: #1d4ed8 !important; }
.alert-success { background-color: #f0fdf4 !important; color: #0f6b32 !important; }
.alert-warning { background-color: #fffbeb !important; color: #92400e !important; }
.alert-danger  { background-color: #fef2f2 !important; color: #b91c1c !important; }

/* ----------------------------------------------------------------
   PAGINATION
   ---------------------------------------------------------------- */
.pagination > li > a,
.pagination > li > span {
  color: #24246D !important;
  border-color: #e2e8f0 !important;
  font-size: 13px !important;
  border-radius: 6px !important;
  margin: 0 2px !important;
}
.pagination > .active > a,
.pagination > .active > span {
  background: linear-gradient(135deg, #24246D 0%, #3a3a9c 100%) !important;
  border-color: transparent !important;
  color: #ffffff !important;
}
.pagination > li > a:hover {
  background-color: #f3f4f6 !important;
  border-color: #d0d7e2 !important;
  color: #24246D !important;
}

/* ----------------------------------------------------------------
   LABELS & BADGES
   ---------------------------------------------------------------- */
.label-primary, .badge-primary { background-color: #24246D !important; }
.label-success, .badge-success { background-color: #16a34a !important; }
.label-danger,  .badge-danger  { background-color: #DB2424 !important; }
.label-warning, .badge-warning { background-color: #f59e0b !important; }
.label-info,    .badge-info    { background-color: #0ea5e9 !important; }
.label, .badge {
  font-size: 11px !important;
  font-weight: 500 !important;
  border-radius: 4px !important;
}

/* ================================================================
   CONTROL PANEL  (app/views/ui/_control_panel.html.erb)
   One strip carrying breadcrumb, title and actions, replacing the old
   page-title + page-bar + floating button row.
   ================================================================ */
.control-panel {
  background: #ffffff !important;
  border: 1px solid #e6e9f0 !important;
  border-radius: 10px !important;
  padding: 10px 16px 12px !important;
  margin-bottom: 16px !important;
  box-shadow: 0 1px 3px rgba(36,36,109,0.05) !important;
}
.control-panel .cp-crumbs {
  list-style: none !important;
  margin: 0 0 4px !important;
  padding: 0 !important;
  display: flex !important;
  flex-wrap: wrap !important;
  align-items: center !important;
  gap: 6px !important;
  font-size: 12px !important;
}
.control-panel .cp-crumbs > li { display: inline-flex !important; align-items: center !important; gap: 6px !important; }
.control-panel .cp-crumbs > li + li::before {
  content: "\203A";
  color: #8b94a5;
  font-size: 13px;
  line-height: 1;
}
.control-panel .cp-crumbs a { color: #475569 !important; text-decoration: none !important; }
.control-panel .cp-crumbs a:hover { color: #24246D !important; text-decoration: underline !important; }
.control-panel .cp-crumbs span[aria-current] { color: #46506180 !important; color: #334155 !important; }

.control-panel .cp-main {
  display: flex !important;
  align-items: center !important;
  flex-wrap: wrap !important;
  gap: 10px 14px !important;
}
.control-panel .cp-title {
  font-size: 20px !important;
  font-weight: 650 !important;
  letter-spacing: -0.015em !important;
  color: #1c1c26 !important;
  margin: 0 !important;
  line-height: 1.25 !important;
}
.control-panel .cp-meta {
  font-size: 12.5px !important;
  color: #475569 !important;
  font-variant-numeric: tabular-nums !important;
}
.control-panel .cp-actions {
  margin-left: auto !important;
  display: flex !important;
  align-items: center !important;
  flex-wrap: wrap !important;
  gap: 8px !important;
}
/* Buttons inside the control panel never float — the flex row owns layout. */
.control-panel .cp-actions .btn,
.control-panel .cp-actions .btn-group { float: none !important; margin: 0 !important; }
.control-panel .cp-actions .btn > i { margin-right: 5px !important; }

/* Labelled dropdown (app/views/ui/_action_menu.html.erb) */
/* Metronic's components.css redefines `.dropdown-menu { left: 0 }` after
   Bootstrap, at equal specificity, so Bootstrap's `.dropdown-menu-right`
   loses the cascade and every right-aligned menu opens rightwards — off the
   edge of the viewport for anything near the right of the page. */
.dropdown-menu.dropdown-menu-right {
  left: auto !important;
  right: 0 !important;
}
/* Metronic draws the little pointer triangle with :before/:after pinned to
   `left: 9px`. It ships `.pull-left` / `.pull-right` variants but none for
   Bootstrap's own `.dropdown-menu-right`, so on a right-aligned menu the
   pointer stayed at the far left instead of under its button. */
.dropdown > .dropdown-menu.dropdown-menu-right:before,
.dropdown-toggle > .dropdown-menu.dropdown-menu-right:before,
.btn-group > .dropdown-menu.dropdown-menu-right:before {
  left: auto !important;
  right: 9px !important;
}
.dropdown > .dropdown-menu.dropdown-menu-right:after,
.dropdown-toggle > .dropdown-menu.dropdown-menu-right:after,
.btn-group > .dropdown-menu.dropdown-menu-right:after {
  left: auto !important;
  right: 10px !important;
}

.cp-menu { position: relative !important; }
.cp-menu > .dropdown-toggle > .caret { margin-left: 6px !important; }
.cp-menu-list {
  min-width: 216px !important;
  margin-top: 4px !important;
}
.cp-menu-list > li > a {
  display: flex !important;
  align-items: center !important;
  gap: 9px !important;
  font-size: 12.5px !important;
  white-space: nowrap !important;
}
.cp-menu-list > li > a > i {
  width: 14px !important;
  text-align: center !important;
  color: #5f6b7a !important;
}
.cp-menu-list > li > a:hover > i { color: #24246D !important; }
.cp-menu-list > li > a.row-action-danger { color: #a81a1a !important; }
.cp-menu-list > li > a.row-action-danger > i,
.cp-menu-list > li > a.row-action-danger:hover > i { color: #a81a1a !important; }
.cp-menu-list > li > a.row-action-danger:hover { background: #fdecec !important; color: #8f1616 !important; }

/* ================================================================
   LIST TOOLBAR  (app/views/ui/_list_toolbar.html.erb)
   Record count + compact pager at the top of a list card.
   ================================================================ */
.list-toolbar {
  display: flex !important;
  align-items: center !important;
  gap: 12px !important;
  padding: 7px 14px !important;
  border-bottom: 1px solid #eef0f5 !important;
  background: #ffffff !important;
  font-size: 12.5px !important;
  color: #475569 !important;
}
/* The toolbar is now the card's top element (the repeated portlet title was
   removed), so it owns the rounded top corners. */
.portlet > .list-toolbar:first-child { border-radius: 9px 9px 0 0 !important; }
.list-toolbar .lt-count { font-variant-numeric: tabular-nums !important; }
.list-toolbar .lt-count b { color: #33333f !important; font-weight: 600 !important; }
.list-toolbar .lt-pager { margin-left: auto !important; }
.list-toolbar .lt-pager .pagination { margin: 0 !important; }
.list-toolbar .lt-pager .pagination > li > a,
.list-toolbar .lt-pager .pagination > li > span {
  padding: 1px 9px !important;
  font-size: 14px !important;
  line-height: 1.5 !important;
}

/* ================================================================
   ROW ACTIONS  (app/views/ui/_row_actions.html.erb)
   ================================================================ */
.row-actions { display: inline-block !important; position: relative !important; }
.row-actions-toggle {
  background: transparent !important;
  border: 1px solid transparent !important;
  border-radius: 6px !important;
  color: #5f6b7a !important;
  font-size: 16px !important;
  line-height: 1 !important;
  padding: 2px 8px !important;
  cursor: pointer !important;
  transition: background 0.12s, color 0.12s, border-color 0.12s !important;
}
.row-actions-toggle:hover,
.row-actions.open > .row-actions-toggle {
  background: #eef0f8 !important;
  border-color: #dce1ec !important;
  color: #24246D !important;
}
.row-actions-toggle:focus-visible {
  outline: none !important;
  border-color: #24246D !important;
  box-shadow: 0 0 0 3px rgba(36,36,109,0.14) !important;
  color: #24246D !important;
}
.row-actions-menu { min-width: 172px !important; }
.row-actions-menu > li > a {
  display: flex !important;
  align-items: center !important;
  gap: 9px !important;
  font-size: 12.5px !important;
}
.row-actions-menu > li > a > i { width: 14px !important; text-align: center !important; color: #5f6b7a !important; }
.row-actions-menu > li > a:hover > i { color: #24246D !important; }
.row-actions-menu > li > a.row-action-danger { color: #b91c1c !important; }
.row-actions-menu > li > a.row-action-danger > i,
.row-actions-menu > li > a.row-action-danger:hover > i { color: #b91c1c !important; }
.row-actions-menu > li > a.row-action-danger:hover { background: #fdecec !important; color: #991b1b !important; }

/* The action column reads left, header and controls together. Right-aligning the
   cells put the buttons under the far edge of the column while the "Action"
   heading stayed at its left edge, so the two never lined up. Aligning both left
   also keeps the first control in a fixed place regardless of how many a row
   has, which right alignment does not. */
/* The actions column shrinks to its content. In a wide, many-column list the
   browser already keeps it tight, but a sparse list (a two-column master table:
   Name + Action) has no other column to absorb the slack of table-wide's 100%,
   so the browser split the width evenly and the "…" toggle stranded itself in
   the middle of a ~400px column. width:1% + nowrap is the standard trick: it
   pins the column to its minimum content width and hands the slack to the
   identity column, matching the dense lists. */
th.td-actions,
td.td-actions { width: 1% !important; white-space: nowrap !important; }
td.td-actions { text-align: left !important; }

/* Approve and Reject are two halves of one decision, so they are one pair of
   ghost buttons — same shape and weight, told apart by icon and hue. Neither is
   a solid fill: making Approve the primary would have the screen leaning on the
   reviewer to approve, which is not the interface's call to make.
   The greens are matched to the reds by contrast ratio rather than by HSL
   lightness. Green is perceptually far lighter than red at equal lightness —
   mirroring hsl(0,74%,42%) as hsl(148,74%,42%) lands at 2.6:1, well under AA —
   so each tone here is picked to sit at the same ratio as its red counterpart:
   text 6.52 vs 6.47, border 1.56 vs 1.55, hover text 8.13 vs 8.31. */
.btn.btn-approve {
  color: #196b40 !important;
  border: 1px solid #b0d8c3 !important;
  background-color: #ffffff !important;
}
.btn.btn-approve:hover,
.btn.btn-approve:focus {
  background-color: #effbf4 !important;
  border-color: #70c296 !important;
  color: #155b36 !important;
}
.btn.btn-reject {
  color: #b91c1c !important;
  border: 1px solid #e6c9c9 !important;
  background-color: #ffffff !important;
}
.btn.btn-reject:hover,
.btn.btn-reject:focus {
  background-color: #fdecec !important;
  border-color: #dda4a4 !important;
  color: #991b1b !important;
}

/* Clickable rows -------------------------------------------------- */
tr[data-row-href] { cursor: pointer !important; }
/* The reference cell keeps a real link so keyboard users are unaffected. */
td .row-link {
  color: #24246D !important;
  font-weight: 500 !important;
  text-decoration: none !important;
}
td .row-link:hover { text-decoration: underline !important; }
td .row-link:focus-visible {
  outline: 2px solid #24246D !important;
  outline-offset: 2px !important;
  border-radius: 3px !important;
}

/* ----------------------------------------------------------------
   STATUS PILLS
   Rendered by ApplicationHelper#status_badge. Five tones cover the
   thirteen strings the various `get_status` methods return.
   Colour is never the only signal — the label is always present, and
   the dot gives a second, non-chromatic cue.
   ---------------------------------------------------------------- */
.status-pill {
  display: inline-flex !important;
  align-items: center !important;
  gap: 5px !important;
  font-size: 11.5px !important;
  font-weight: 500 !important;
  line-height: 1.5 !important;
  padding: 2px 9px !important;
  border-radius: 999px !important;
  white-space: nowrap !important;
  vertical-align: middle !important;
}
.status-pill::before {
  content: "" !important;
  width: 5px !important;
  height: 5px !important;
  border-radius: 50% !important;
  background: currentColor !important;
  flex: none !important;
}
/* Approved · Paid · Settled · Posted */
.status-pill.status-positive { background: #e7f6ec !important; color: #0f6b32 !important; }
/* Checked · Open */
.status-pill.status-progress { background: #e6f3fb !important; color: #03608f !important; }
/* Submitted */
.status-pill.status-pending  { background: #fdf3e3 !important; color: #835205 !important; }
/* Draft · Closed · History · anything unrecognised */
.status-pill.status-neutral  { background: #eff0f4 !important; color: #4b4b59 !important; }
/* Rejected · Cancelled · Void */
.status-pill.status-negative { background: #fdecec !important; color: #b91c1c !important; }

/* ----------------------------------------------------------------
   PROGRESS BARS
   ---------------------------------------------------------------- */
.progress {
  border-radius: 99px !important;
  background-color: #e2e8f0 !important;
  height: 8px !important;
  box-shadow: none !important;
}
.progress-bar {
  background-color: #24246D !important;
  border-radius: 99px !important;
  box-shadow: none !important;
}
.progress-bar-danger  { background-color: #DB2424 !important; }
.progress-bar-warning { background-color: #f59e0b !important; }
.progress-bar-info    { background-color: #0ea5e9 !important; }
.progress-bar-success { background-color: #16a34a !important; }

/* ----------------------------------------------------------------
   SELECT2
   ---------------------------------------------------------------- */
.select2-container .select2-choice,
.select2-container-multi .select2-choices {
  border: 1px solid #dde1ea !important;
  border-radius: 7px !important;
  background-color: #ffffff !important;
  background-image: none !important;
  box-shadow: inset 0 1px 2px rgba(0,0,0,0.04) !important;
  color: #1e293b !important;
}
/* Single-select: fixed height */
.select2-container .select2-choice {
  height: 34px !important;
  line-height: 32px !important;
  padding: 0 0 0 10px !important;
}
/* Multi-select: auto-grow to fit chosen chips */
.select2-container-multi .select2-choices {
  min-height: 34px !important;
  height: auto !important;
  padding: 3px 6px 3px 6px !important;
}
/* Placeholder / search input inside multi-select */
.select2-container-multi .select2-choices .select2-search-field input {
  font-size: 13px !important;
  color: #5f6b7a !important;
  height: 26px !important;
  line-height: 26px !important;
  padding: 0 4px !important;
  margin: 0 !important;
}
/* Selected chip / tag */
.select2-choices .select2-search-choice {
  background-color: #24246D !important;
  background-image: none !important;
  border: none !important;
  border-radius: 5px !important;
  color: #ffffff !important;
  font-size: 12px !important;
  padding: 3px 22px 3px 9px !important;
  margin: 2px 4px 2px 0 !important;
  line-height: 1.4 !important;
  box-shadow: none !important;
}
.select2-choices .select2-search-choice .select2-search-choice-close {
  /* The chip is navy #24246D and reserves 22px of padding on the right for this
     button. Two base-plugin problems left it broken: the multi-select rule pins
     the close to `left: 3px`, which wins over the reskin's `right: 5px` because an
     absolutely positioned element with a fixed width and both offsets set ignores
     `right` in LTR — so the button sat on the LEFT, cramped into the 9px left
     padding and overlapping the label. And its sprite glyph is dark, invisible on
     navy. Pin it to the right, drop the sprite, and draw a white x. */
  left: auto !important;
  right: 6px !important;
  top: 3px !important;
  width: 14px !important;
  height: 14px !important;
  background-image: none !important;
  color: rgba(255,255,255,0.7) !important;
  font-size: 15px !important;
  line-height: 13px !important;
  text-align: center !important;
}
.select2-choices .select2-search-choice .select2-search-choice-close::before {
  content: "\00d7" !important;
}
.select2-choices .select2-search-choice .select2-search-choice-close:hover {
  color: #ffffff !important;
  background-image: none !important;
}
.select2-choices .select2-search-choice-focus {
  background-color: #3a3a9c !important;
}
.select2-container .select2-choice:hover,
.select2-container-active .select2-choice {
  border-color: #24246D !important;
  box-shadow: 0 0 0 3px rgba(36,36,109,0.10) !important;
}
/* Dropdown arrow column */
.select2-container .select2-choice .select2-arrow {
  width: 28px !important;
  border-left: 1px solid #dde1ea !important;
  border-radius: 0 6px 6px 0 !important;
  background: #f1f5f9 !important;
  background-image: none !important;
}
/* The clear "x" on a Select2 that allows clearing.
   ----------------------------------------------------------------
   Select2 positions it at `right: 24px`, which clears its own 18px arrow with 6px to spare.
   The rule above widens the arrow to 28px, so the x ended up 4px *inside* the arrow, pressed
   against the chevron and hard to read as a separate control -- the same shape of bug as the
   sprite window below: a reskin changed the arrow's width and the things measured from it were
   not moved with it.

   Positioned from the arrow's width rather than from a number that happens to look right, so
   the two cannot drift apart again. Centred vertically too: `top: 8px` was written for
   Select2's own control height, not the reskin's. */
.select2-container .select2-choice abbr {
  right: 36px !important; /* 28px arrow + 8px gap */
  top: 50% !important;
  margin-top: -6px !important; /* half of its 12px height */
}

/* The arrow glyph. Select2 3.x paints it from a sprite strip (select2.png, or select2x2.png
   at 2x) through `b { width: 100%; height: 100% }` plus a background-position nudge, and that
   only lines up at Select2's own 18px arrow width. The rule above widens the arrow to 28px,
   so the 27px-wide b opened a window onto the NEXT glyph in the strip — that is the stray
   dark dot beside the chevron, and it appeared on every Select2 in the app. The nudge also
   left the glyph in the upper-left of a 32px-tall box instead of centred.

   One chevron drawn as an inline SVG has no strip to leak from, centres by definition at any
   arrow width, and stays crisp at any pixel density. Measured 2026-08-20 against Regular
   Payment, which had the same dot. */
.select2-container .select2-choice .select2-arrow b {
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='10' height='6' viewBox='0 0 10 6'%3E%3Cpath d='M1 1l4 4 4-4' fill='none' stroke='%2364748b' stroke-width='1.6' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E") !important;
  background-position: center center !important;
  background-size: 10px 6px !important;
  background-repeat: no-repeat !important;
}
/* Open state — flat top radius */
.select2-container.select2-dropdown-open .select2-choice {
  border-radius: 7px 7px 0 0 !important;
  border-bottom-color: transparent !important;
}
.select2-drop-active {
  border: 1px solid #24246D !important;
  border-top: none !important;
  border-radius: 0 0 7px 7px !important;
  box-shadow: 0 8px 16px rgba(0,0,0,0.08) !important;
}
.select2-results .select2-highlighted {
  background-color: #24246D !important;
  color: #ffffff !important;
}
.select2-results li {
  font-size: 13px !important;
  padding: 5px 10px !important;
}
/* Ensure selected/placeholder text is vertically centred and left-aligned */
.select2-container .select2-choice > .select2-chosen {
  display: block !important;
  line-height: 32px !important;
  text-align: left !important;
  overflow: hidden !important;
  text-overflow: ellipsis !important;
  white-space: nowrap !important;
}
/* Placeholder tone */
.select2-container .select2-choice > .select2-chosen:empty::before,
.select2-default > .select2-chosen {
  color: #5f6b7a !important;
}
/* Ensure container never exceeds form-control height */
.select2-container {
  line-height: normal !important;
}

/* ---- The double-border fix -------------------------------------------
   Select2 3.x copies the original <select>'s class list onto the container
   it generates, so `form-control` lands on BOTH the wrapper and, via our own
   rules, the inner .select2-choice. The result is two stacked borders, two
   focus rings, and a dropdown sized to the wrapper (334px) while the visible
   control is the choice (312px) — an 11px overhang on each side, which is
   the broken-looking edge on every select in the app.

   Strip the wrapper back to a plain, invisible box. .select2-choice is then
   the single control, and .select2-drop lines up with it exactly. */
.select2-container.form-control,
.select2-container-multi.form-control,
.select2-container.input-sm,
.select2-container-multi.input-sm {
  border: 0 !important;
  border-radius: 0 !important;
  background: transparent !important;
  background-image: none !important;
  box-shadow: none !important;
  padding: 0 !important;
  height: auto !important;
  min-height: 0 !important;
  line-height: normal !important;
}
/* ...and never let the wrapper draw a focus ring; the choice owns that. */
.select2-container.form-control:focus,
.select2-container.form-control.select2-container-active,
.select2-container-multi.form-control.select2-container-active {
  border: 0 !important;
  box-shadow: none !important;
  outline: none !important;
}
/* The drop is positioned against the container, which now matches the choice. */
.select2-drop {
  border-color: #24246D !important;
  box-shadow: 0 8px 24px rgba(36,36,109,0.12) !important;
}

/* ----------------------------------------------------------------
   FOOTER
   ---------------------------------------------------------------- */
.page-footer {
  background-color: #ffffff !important;
  border-top: 1px solid #e2e8f0 !important;
  color: #5f6b7a !important;
  font-size: 12px !important;
}

/* ----------------------------------------------------------------
   SCROLL-TO-TOP
   ---------------------------------------------------------------- */
.scroll-to-top {
  background-color: transparent !important;
  border: none !important;
  border-radius: 50% !important;
  box-shadow: none !important;
  opacity: 0.75 !important;
}
.scroll-to-top:hover {
  background-color: transparent !important;
  opacity: 1 !important;
  box-shadow: none !important;
}
.scroll-to-top > i { color: #24246D !important; }

/* ----------------------------------------------------------------
   SMALL / ACTION BUTTONS — unified design system
   Same visual language as full-size buttons, just smaller.
   Solid fill + white text + 7px radius + lift hover.
   ---------------------------------------------------------------- */

/* Base — xs action buttons: size and shape only.
   No colour here. This rule used to force `color: #fff !important`, on the
   assumption that every xs button is a solid fill. It is not: btn-default and
   btn-reject are ghosts, and btn-success/danger/info/warning are styled in this
   theme as coloured text on white. Because .btn.btn-xs is two classes it
   outranked .btn-default (one class), and it sits later in the file than
   .btn.btn-reject, so it beat that on order — every ghost xs button rendered
   white on white. The Reject on each approval tab was invisible, as were the
   xs buttons on the invoice tracker screens.
   Each variant already declares its own colour, so dropping it here is enough;
   there are no xs buttons without a variant class. */
.btn.btn-xs {
  font-size: 11.5px !important;
  font-weight: 500 !important;
  padding: 3px 9px !important;
  border-radius: 7px !important;
  line-height: 1.6 !important;
  letter-spacing: 0.01em !important;
  border: none !important;
  box-shadow: 0 1px 2px rgba(0,0,0,0.07) !important;
  transition: background 0.12s, box-shadow 0.12s, transform 0.08s !important;
}
.btn.btn-xs:active {
  transform: translateY(1px) !important;
  box-shadow: none !important;
}
/* input-sm — size only, no forced color (used by Reset/Back AND input-group btns)
   The comment above is why this must NOT set a border-radius. It did, at 7px on
   all four corners, and `.btn.input-sm` has the same specificity as
   `.input-group-btn > .btn` while sitting 1600 lines further down -- so it won
   and every input-sm button inside an input group rendered as a fully rounded
   pill floating inside the field instead of joining it. Every date picker in the
   app, measured on erp_travel_requests/new: button 7px/7px against an input that
   is 7px/0.
   Only `<button>` showed it: the group rule names `a.btn` as well, and that
   selector carries an element, which outranks `.btn.input-sm`. So the same
   trigger looked right as a link and wrong as a button, on the same screen.
   Dropping the line is the whole fix -- `.btn` above already sets 7px, so a
   Reset or Back button outside a group is unchanged. Verified in the browser:
   the group button went 7px/7px -> 0/7px, a loose .btn.input-sm stayed 7px/7px. */
.btn.input-sm {
  font-size: 11.5px !important;
  font-weight: 500 !important;
  padding: 3px 9px !important;
  line-height: 1.6 !important;
  transition: background 0.12s, box-shadow 0.12s, transform 0.08s !important;
}
/* Neutral ghost button — Back, Reset, Cancel links use .btn.default */
.btn.default {
  background-color: #ffffff !important;
  background-image: none !important;
  border: 1px solid #d0d7e2 !important;
  color: #374151 !important;
  box-shadow: 0 1px 2px rgba(0,0,0,0.04) !important;
}
.btn.default:hover,
.btn.default:focus {
  background-color: #f1f5f9 !important;
  border-color: #94a3b8 !important;
  color: #1e293b !important;
  transform: translateY(-1px) !important;
  box-shadow: 0 2px 8px rgba(0,0,0,0.08) !important;
}

/* ---- VIEW — sky blue (matches btn-info) ---- */
.btn.btn-xs.green-stripe,
.btn.default.btn-xs.green-stripe {
  background-color: #0ea5e9 !important;
  color: #ffffff !important;
}
.btn.btn-xs.green-stripe:hover,
.btn.default.btn-xs.green-stripe:hover {
  background-color: #0284c7 !important;
  box-shadow: 0 3px 10px rgba(14,165,233,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* ---- EDIT — indigo blue ---- */
.btn.btn-xs.blue-stripe,
.btn.default.btn-xs.blue-stripe {
  background-color: #3b82f6 !important;
  color: #ffffff !important;
}
.btn.btn-xs.blue-stripe:hover,
.btn.default.btn-xs.blue-stripe:hover {
  background-color: #2563eb !important;
  box-shadow: 0 3px 10px rgba(59,130,246,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* ---- DELETE / CANCEL — red (matches btn-danger) ---- */
.btn.btn-xs.red-stripe,
.btn.default.btn-xs.red-stripe {
  background-color: #ef4444 !important;
  color: #ffffff !important;
}
.btn.btn-xs.red-stripe:hover,
.btn.default.btn-xs.red-stripe:hover {
  background-color: #dc2626 !important;
  box-shadow: 0 3px 10px rgba(239,68,68,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* ---- APPROVE / SUBMIT — emerald (matches btn-success) ---- */
.btn.btn-xs.green-stripe.approve-alert,
.btn.default.btn-xs.green-stripe.approve-alert {
  background-color: #16a34a !important;
  color: #ffffff !important;
}
.btn.btn-xs.green-stripe.approve-alert:hover,
.btn.default.btn-xs.green-stripe.approve-alert:hover {
  background-color: #15803d !important;
  box-shadow: 0 3px 10px rgba(22,163,74,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* ---- PDF / DOWNLOAD — amber (matches btn-warning) ---- */
.btn.btn-xs.yellow-stripe,
.btn.default.btn-xs.yellow-stripe,
.btn.btn-xs.yellow-crusta,
.btn.default.btn-xs.yellow-crusta {
  background-color: #f59e0b !important;
  color: #ffffff !important;
}
.btn.btn-xs.yellow-stripe:hover,
.btn.default.btn-xs.yellow-stripe:hover,
.btn.btn-xs.yellow-crusta:hover,
.btn.default.btn-xs.yellow-crusta:hover {
  background-color: #d97706 !important;
  box-shadow: 0 3px 10px rgba(245,158,11,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* ---- OTHER — violet ---- */
.btn.btn-xs.purple-stripe,
.btn.default.btn-xs.purple-stripe {
  background-color: #8b5cf6 !important;
  color: #ffffff !important;
}
.btn.btn-xs.purple-stripe:hover,
.btn.default.btn-xs.purple-stripe:hover {
  background-color: #7c3aed !important;
  box-shadow: 0 3px 10px rgba(139,92,246,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}
.btn.btn-xs.purple-stripe.disabled,
.btn.default.btn-xs.purple-stripe.disabled {
  opacity: 0.45 !important;
  pointer-events: none !important;
}

/* ---- DARK — slate ---- */
.btn.btn-xs.blue-ebonyclay-stripe,
.btn.default.btn-xs.blue-ebonyclay-stripe {
  background-color: #475569 !important;
  color: #ffffff !important;
}
.btn.btn-xs.blue-ebonyclay-stripe:hover,
.btn.default.btn-xs.blue-ebonyclay-stripe:hover {
  background-color: #334155 !important;
  box-shadow: 0 3px 10px rgba(71,85,105,0.30) !important;
  transform: translateY(-1px) !important;
  color: #ffffff !important;
}

/* Bootstrap semantic xs buttons — inherit full-size colors at small scale */
.btn.btn-xs.btn-primary {
  background: linear-gradient(135deg, #24246D, #3a3a9c) !important;
  background-image: linear-gradient(135deg, #24246D, #3a3a9c) !important;
  color: #fff !important;
}
.btn.btn-xs.btn-primary:hover {
  background: linear-gradient(135deg, #1b1b55, #2e2e84) !important;
  box-shadow: 0 3px 10px rgba(36,36,109,0.30) !important;
  transform: translateY(-1px) !important;
}
.btn.btn-xs.btn-success {
  background-color: #16a34a !important;
  background-image: none !important;
  color: #fff !important;
}
.btn.btn-xs.btn-success:hover {
  background-color: #15803d !important;
  box-shadow: 0 3px 10px rgba(22,163,74,0.28) !important;
  transform: translateY(-1px) !important;
}
.btn.btn-xs.btn-warning {
  background-color: #f59e0b !important;
  background-image: none !important;
  color: #fff !important;
}
.btn.btn-xs.btn-warning:hover {
  background-color: #d97706 !important;
  box-shadow: 0 3px 10px rgba(245,158,11,0.28) !important;
  transform: translateY(-1px) !important;
}
.btn.btn-xs.btn-danger {
  background-color: #ef4444 !important;
  background-image: none !important;
  color: #fff !important;
}
.btn.btn-xs.btn-danger:hover {
  background-color: #dc2626 !important;
  box-shadow: 0 3px 10px rgba(239,68,68,0.28) !important;
  transform: translateY(-1px) !important;
}

/* ---- blue solid (non-stripe) ---- */
.btn.default.btn-xs.blue {
  background-color: #3b82f6 !important;
  color: #ffffff !important;
}

/* ---- Ghost variants at xs ----
   btn-default and btn-reject are the only xs variants that are not a solid
   fill, and they are the two that had no rule at this specificity. The base
   .btn.btn-xs strips the border for the solid variants, which also stripped
   theirs, so the outline is restored here rather than by weakening the base.
   Row-level Reject now matches the control panel's btn-sm Reject. */
.btn.btn-xs.btn-default {
  background-color: #ffffff !important;
  background-image: none !important;
  color: #374151 !important;
  border: 1px solid #d0d7e2 !important;
}
.btn.btn-xs.btn-default:hover,
.btn.btn-xs.btn-default:focus {
  background-color: #f1f5f9 !important;
  border-color: #94a3b8 !important;
  color: #1e293b !important;
  transform: translateY(-1px) !important;
}
/* The decision pair keeps its tints at btn-sm and btn-xs alike, so a row-level
   Approve/Reject reads the same as the one in the control panel. */
.btn.btn-xs.btn-approve {
  color: #196b40 !important;
  border: 1px solid #b0d8c3 !important;
  background-color: #ffffff !important;
}
.btn.btn-xs.btn-approve:hover,
.btn.btn-xs.btn-approve:focus {
  background-color: #effbf4 !important;
  border-color: #70c296 !important;
  color: #155b36 !important;
}
.btn.btn-xs.btn-reject {
  color: #b91c1c !important;
  border: 1px solid #e6c9c9 !important;
  background-color: #ffffff !important;
}
.btn.btn-xs.btn-reject:hover,
.btn.btn-xs.btn-reject:focus {
  background-color: #fdecec !important;
  border-color: #dda4a4 !important;
  color: #991b1b !important;
}

/* Spacing between action buttons in same table cell */
td .btn.btn-xs + .btn.btn-xs,
td .btn.input-sm + .btn.input-sm {
  margin-left: 4px !important;
}

/* ----------------------------------------------------------------
   MISC UTILITIES
   ---------------------------------------------------------------- */
.note {
  border-radius: 8px !important;
}
.portlet .portlet-title .tools > a.collapse i,
.portlet .portlet-title .tools > a.expand i {
  color: #5f6b7a !important;
}
/* Remove ugly default borders on list-group inside portlets */
.portlet .list-group-item {
  border-color: #f1f5f9 !important;
}


/***
Logo style adjustment
***/
.logo-default {
  height: 30px;
}

.padding-top-8 {
  padding-top: 8px
}

.pagination {
  float: right;
  margin: 0 !important;
}

.pagination span {
  position: relative;
  float: left;
  padding: 6px 12px;
  margin-left: -1px;
  line-height: 1.42857143;
  color: #24246d;
  text-decoration: none;
  background-color: #fff;
  border: thin solid #ddd;
}

.pagination span.disabled {
  background: #eee;
  border-color: #dddddd;
  color: #333;
}

.pagination a {
  position: relative;
  float: left;
  padding: 6px 12px;
  margin-left: -1px;
  line-height: 1.42857143;
  color: #24246d;
  text-decoration: none;
  background-color: #fff;
  border: thin solid #ddd;
}

.pagination em {
  position: relative;
  float: left;
  padding: 6px 12px;
  margin-left: -1px;
  line-height: 1.42857143;
  text-decoration: none;
  background: #eee;
  border-color: #dddddd;
  color: #333;
  border: thin solid #ddd;
  font-style: normal;
}

.min-height-28 {
  min-height: 28px !important;
}

.caption-filter {
  font-size: 12px !important;
  padding: 5px 0 5px 0 !important;
}

.tools-filter {
  padding: 6px 0 4px 0 !important;
}

.height-14 {
  height: 14px !important;
}

.w-1 {
  width: 8.33333333% !important;
}

.w-2 {
  width: 16.6666667% !important;
}

.w-3 {
  width: 25% !important;
}

.w-4 {
  width: 33.33333333% !important;
}

.w-5 {
  width: 41.6666667% !important;
}

.w-6 {
  width: 50% !important;
}

.w-7 {
  width: 58.33333333% !important;
}

.w-8 {
  width: 66.6666667% !important;
}

.w-9 {
  width: 75% !important;
}

.w-10 {
  width: 83.33333333% !important;
}

.w-11 {
  width: 91.6666667% !important;
}

.w-12 {
  width: 100% !important;
}

.margin-bottom-0 {
  margin-bottom: 0;
}

.margin-up {
  margin-top: -1px;
}

.overflow-x {
  overflow-x: auto !important;
}

.font-11 input {
  font-size: 10px;
}

table.table-bordered tbody th, table.table-bordered tbody td {
  border-bottom-width: thin !important;
}

.mask_currency {
  text-align: right
}


/*** Page toolbar: action buttons LEFT-aligned, stacking naturally ***/
.page-content .margin-bottom-20 .btn-group.pull-right,
.page-content .margin-bottom-20 .btn-group {
  float: left !important;
  margin-right: 4px !important;
  margin-bottom: 4px !important;
}
/* Clearfix for the button row so it takes real height */
.page-content .margin-bottom-20 {
  overflow: hidden;
}

/*** Filter portlet: tighter form-group spacing ***/
.portlet-title.min-height-28 ~ .portlet-body .form-group {
  margin-bottom: 8px !important;
}
.portlet-title.min-height-28 ~ .portlet-body .form-actions {
  padding: 10px 16px !important;
  margin-bottom: 0 !important;
}

/* ================================================================
   FILTER MODAL
   ================================================================ */

/* Filter trigger — a quiet control by default. Solid slate made it compete
   with the primary action for attention while saying nothing about state. */
.btn-filter-trigger {
  background-color: #ffffff !important;
  color: #475569 !important;
  border: 1px solid #d0d7e2 !important;
  border-radius: 7px !important;
  padding: 5px 13px !important;
  font-size: 13px !important;
  font-weight: 500 !important;
}
.btn-filter-trigger > i { color: #5f6b7a !important; margin-right: 5px !important; }
.btn-filter-trigger:hover,
.btn-filter-trigger:focus {
  background-color: #f1f5f9 !important;
  border-color: #94a3b8 !important;
  color: #1e293b !important;
}
.btn-filter-trigger:hover > i { color: #24246D !important; }
/* Filters applied — now it carries state, so it earns the brand colour. */
.btn-filter-trigger.has-active-filters,
.btn-filter-trigger.has-active-filters:hover {
  background-color: #eef0f8 !important;
  border-color: #c2c7e4 !important;
  color: #24246D !important;
}
.btn-filter-trigger.has-active-filters > i { color: #24246D !important; }
/* A count is information, not an error — navy, not red. */
.filter-badge {
  display: inline-block;
  margin-left: 7px;
  background: #24246D;
  color: #fff;
  font-size: 11px;
  font-weight: 600;
  border-radius: 10px;
  padding: 1px 7px;
  vertical-align: middle;
  line-height: 1.5;
  font-variant-numeric: tabular-nums;
}

/* Modal chrome — flat header, matching the cards and the control panel. The
   navy gradient bar here was the last survivor of the old portlet styling. */
/* ---- Confirmation modal ----
   Replaces the browser's confirm() slab. No header: the message is a question
   and it is the only thing worth reading, so it carries the dialog on its own.
   The buttons stay Yes / No because every data-confirm in this app is phrased
   as a question — naming them after the action instead would put "Cancel" next
   to "Cancel this timesheet?" and make the dismissal ambiguous. */
.shield-confirm .modal-dialog {
  margin-top: 12vh;
}
.shield-confirm-content {
  border-radius: 12px !important;
  border: none !important;
  box-shadow: 0 12px 40px rgba(15, 23, 42, 0.22) !important;
  overflow: hidden;
}
.shield-confirm-body {
  padding: 24px 24px 18px !important;
  text-align: center;
}
.shield-confirm-icon {
  display: block;
  font-size: 22px;
  margin-bottom: 12px;
  color: #5f6b7a;
}
.shield-confirm-icon.is-destructive {
  color: #b91c1c;
}
.shield-confirm-message {
  margin: 0 !important;
  font-size: 15px;
  font-weight: 500;
  line-height: 1.5;
  color: #1c1c26;
}
.shield-confirm-footer {
  padding: 12px 20px !important;
  border-top: 1px solid #eceff5 !important;
  background: #fbfcfe !important;
  text-align: center !important;
}
.shield-confirm-footer .btn {
  min-width: 84px;
}

.filter-modal-content {
  border-radius: 12px !important;
  overflow: hidden;
}
.filter-modal-header {
  background: #ffffff !important;
  background-image: none !important;
  padding: 13px 20px !important;
  border-bottom: 1px solid #eceff5 !important;
}
.filter-modal-header .modal-title {
  color: #1c1c26 !important;
  font-size: 15px !important;
  font-weight: 600 !important;
  letter-spacing: -0.01em !important;
}
.filter-modal-header .modal-title > i {
  color: #24246D !important;
  margin-right: 7px !important;
  font-size: 13px !important;
}
.filter-modal-header .close {
  color: #5f6b7a !important;
  opacity: 1 !important;
  text-shadow: none !important;
  font-size: 22px !important;
  font-weight: 400 !important;
}
.filter-modal-header .close:hover {
  color: #1e293b !important;
}
.filter-modal-body {
  padding: 20px 24px 8px !important;
  max-height: 68vh;
  overflow-y: auto;
}
/* Tighter form inside modal */
.filter-modal-body .form-group {
  margin-bottom: 10px !important;
}
/* Re-flow the grid. Filter partials were authored for the old inline portlet,
   which sat in a col-md-8 column — there `col-md-3` label + `col-md-4` field
   filled the row. Dropped into a modal-lg the same markup leaves ~40% of the
   dialog empty. Flex lets one rule cover every filter form, and a group that
   happens to hold two fields simply shares the remaining space instead of
   overflowing. */
.filter-modal-body .form-group {
  display: flex !important;
  align-items: center !important;
  flex-wrap: wrap !important;
  margin-left: 0 !important;
  margin-right: 0 !important;
}
.filter-modal-body .form-group > .control-label {
  flex: 0 0 26% !important;
  max-width: 26% !important;
  width: auto !important;
  float: none !important;
  padding-right: 14px !important;
  margin-bottom: 0 !important;
}
.filter-modal-body .form-group > div[class*="col-"] {
  flex: 1 1 0 !important;
  max-width: none !important;
  width: auto !important;
  float: none !important;
  padding-left: 0 !important;
}
@media (max-width: 700px) {
  .filter-modal-body .form-group > .control-label {
    flex-basis: 100% !important;
    max-width: 100% !important;
    text-align: left !important;
    padding-right: 0 !important;
    margin-bottom: 4px !important;
  }
}
.filter-modal-body .form-body {
  margin-bottom: 0 !important;
}
.filter-modal-footer {
  padding: 12px 20px !important;
  border-top: 1px solid #e2e8f0 !important;
  background: #f8fafc !important;
}
.filter-btn-reset {
  float: left !important;
  border-color: #cbd5e1 !important;
  color: #475569 !important;
}
.filter-btn-reset:hover {
  background-color: #fee2e2 !important;
  border-color: #fca5a5 !important;
  color: #dc2626 !important;
}
.filter-btn-apply {
  background-color: #24246D !important;
  border-color: #24246D !important;
}
.filter-btn-apply:hover {
  background-color: #1a1a52 !important;
}

/* Active filter chips */
.filter-chips-row {
  margin-bottom: 10px !important;
}
/* Keeps the grid gutter. Zeroing the padding pulled the chip row 15px left of
   the Filter button above it and the list card below it, so the one row that
   describes the table did not line up with anything. */
.filter-chips-container {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px;
}
.filter-chips-label {
  font-size: 12px;
  color: #475569;
  font-weight: 500;
  margin-right: 2px;
}
/* Facet chips — white with a hairline, brand navy for the field name. The old
   indigo (#e0e7ff / #6366f1) was the one colour on screen from outside the
   palette, so a row of them read as decoration rather than as state. */
.filter-chip {
  display: inline-flex;
  align-items: center;
  background: #ffffff;
  color: #33333f;
  border: 1px solid #d6dbe8;
  border-radius: 6px;
  padding: 2px 9px;
  font-size: 12px;
  font-weight: 400;
  white-space: nowrap;
}
.filter-chip .filter-chip-label {
  color: #24246D;
  margin-right: 4px;
  font-weight: 600;
}
.filter-chip strong { font-weight: 500; }
.filter-chip-remove {
  color: #5f6b7a;
  margin-left: 8px;
  font-size: 14px;
  line-height: 1;
  text-decoration: none !important;
  font-weight: 500;
}
.filter-chip-remove:hover {
  color: #b91c1c;
}
/* "Clear all" is a discard, so it keeps a red tint — but muted, and it sits
   last so it never competes with reading the facets themselves. */
.filter-chip-reset {
  background: #ffffff;
  color: #b91c1c;
  border-color: #e6c9c9;
  text-decoration: none !important;
}
.filter-chip-reset:hover {
  background: #fdecec;
  border-color: #dda4a4;
  color: #991b1b;
  text-decoration: none !important;
}

/*** Custom Style for Float-THead header ***/
table.floathead-cf thead {
    background-color: white;
    border: thin solid #ddd;
}

/* ==========================================================================
   Login — password reveal toggle
   ==========================================================================
   Metronic's .input-icon owns the left slot (the fa-lock), so the toggle is
   anchored to the right instead of reusing it.

   top/bottom 0 rather than a fixed height on purpose: login3.css sets the
   field height on this page, so anything hardcoded here would drift the
   moment that changes.
   ========================================================================== */

.input-icon.input-icon-reveal > .form-control {
  /* Without this the typed password runs underneath the button. */
  padding-right: 40px;
}

/* login3.css sets `padding: 10px 14px !important` on .login .content .form-control, which beats the
   rule above on !important alone. It already solves the same problem for the left-hand icon with
   `.login .content .input-icon .form-control { padding-left: 40px !important }`, so this mirrors
   that selector and its 40px rather than inventing a second convention. */
.login .content .input-icon.input-icon-reveal .form-control {
  padding-right: 40px !important;
}

.password-reveal {
  position: absolute;
  top: 0;
  bottom: 0;
  right: 0;
  width: 40px;
  padding: 0;
  border: 0;
  background: transparent;
  color: #999;
  line-height: 1;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
}

.password-reveal > i {
  font-size: 14px;
}

.password-reveal:hover {
  color: #24246D;
}

/* Keyboard focus must be visible — this control is reachable by Tab, and the
   browser default outline is clipped by the field's own border radius. */
.password-reveal:focus {
  color: #24246D;
  outline: 2px solid rgba(36, 36, 109, 0.35);
  outline-offset: -3px;
}

/* ==========================================================================
   Loading overlay (app/views/ui/_loading_overlay.html.erb)
   ==========================================================================
   Covers the viewport while a slow form renders. The same spinner image the
   existing erp_activity_requests / hr_timesheets overlays use, so a user
   moving between those screens and Travel Request sees one thing, not two.

   Those older copies carry these rules as a long inline style attribute
   repeated in four templates; this is the same appearance expressed once.
   ========================================================================== */

.loading-overlay {
  position: fixed;
  z-index: 99999;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background: url('/metro/assets/global/plugins/slider-layer-slider/skins/fullwidthdark/loading.gif') 50% 50% no-repeat rgba(0, 0, 0, 0.5);
}

/* ---- Field hint -------------------------------------------------------
   One line of guidance under a control, for things the user needs before
   they act rather than after. Introduced for the leave form, where the
   per-request cap was enforced server-side and never shown.

   #475569 is the established secondary tier, not a pale grey: the readability
   pass replaced eight greys with two readable tiers after a colleague reported
   the old ones were hard to read. A hint is still meant to be read.          */
.record-field__hint {
  margin-top: 6px !important;
  color: #475569 !important;
  font-size: 12px !important;
  line-height: 1.45 !important;
}

/* ---- Empty list -------------------------------------------------------
   A list whose collection is empty rendered its column headers and then
   nothing: the card stopped at the header with no body and no bottom edge,
   which reads as a page that failed to finish loading rather than as "there
   is nothing here". Reported on Training Request; measured across the app,
   ALL 36 list templates behave this way, so this belongs in the shared
   stylesheet rather than in 36 templates.

   The count line above the table already says "No requests" — the header row
   adds nothing once there are no rows to label, so it goes, and the card gets
   its bottom edge back.

   :has() is doing the work. Chrome 105+, Safari 15.4+, Firefox 121+ — all well
   below what this app's users run, and the failure mode if it were missing is
   simply the header staying visible, which is today's behaviour.            */
/* Two things this had to get right, both found by measuring in a browser rather than reasoning:

   * **`:empty` does not work here.** It requires no child nodes *at all*, and ERB leaves a newline
     inside `<tbody>` — one text node, so an empty list's tbody never matched.
   * **`:has()` cannot nest.** `table:has(tbody:not(:has(tr)))` is not a valid selector and the whole
     rule was dropped silently. `table:not(:has(tbody tr))` says the same thing with one level.
   * **floatThead rewraps the table**, moving the real one into `.floatThead-wrapper` and inserting
     a header-only clone beside it, so a child combinator from `.portlet-body` matches neither. The
     descendant selector covers both, and the clone matches too — it has no rows either. */
.portlet-body table:not(:has(tbody tr)) {
  display: none !important;
}
.portlet.box:not(:has(tbody tr)) .list-toolbar {
  border-bottom: 0 !important;
  border-radius: 0 0 4px 4px !important;
}

/* ==========================================================================
   Phone and tablet layout
   --------------------------------------------------------------------------
   Metronic's mobile defaults were written for its own dark, two-row phone
   header. SHIELD's header is one row and white, so below 992px several of
   those defaults describe a layout this app does not have. Each rule here
   turns one of them off; none of them is a new design.
   ========================================================================== */

@media (max-width: 991px) {
  /* The sidebar's collapse-to-rail control. On a phone the sidebar is a full-width
     panel that the hamburger opens and closes, so there is no rail to collapse to and
     the control does nothing -- it just sits at the top of the menu inviting a tap. */
  .page-sidebar .sidebar-toggler-wrapper { display: none !important; }

  /* Metronic unfixes the header below 992px and layout.css zeroes the
     container's margin to match:
       @media (max-width: 991px) { .page-container { margin-top: 0 !important } }
     The reskin's own `.page-header-fixed .page-container { margin-top: 56px
     !important }` carries no media query, and at (0,2,0) it out-specified that
     reset -- so the page went on reserving 56px for a header that is no longer
     fixed. That was most of the gap between the header and the menu. */
  .page-header-fixed .page-container { margin-top: 0 !important; }
}

@media (max-width: 480px) {
  /* Metronic gives the phone header a second row: `.top-menu { display: block;
     clear: both }` in layout.css drops the profile and notification menus
     below the header, and themes/default.css paints that row #3d3d3d. Against
     a white 56px header the result is a dark bar hanging underneath it. Keep
     the two menus on the header's own row, where the toggler already floats. */
  .page-header.navbar .top-menu {
    clear: none;
    float: right;
    background-color: transparent !important;
  }
  .page-header-fixed-mobile .page-header.navbar .top-menu {
    background-color: transparent !important;
  }

  /* Same rule set, applied to the user dropdown's own charcoal fills. */
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-user .dropdown-toggle,
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-user .dropdown-toggle:hover,
  .page-header-fixed-mobile .page-header.navbar .top-menu .navbar-nav > li.dropdown-user .dropdown-toggle {
    background-color: transparent !important;
  }
}

@media (max-width: 480px) {
  /* Why cancelling `clear` was not enough.
     The header's three pieces are floats, and the reskin pins the logo to a fixed
     `width: 235px !important`. A float that does not fit wraps to the next line no
     matter what `clear` says, so on a narrow phone the top menu still dropped below
     the header -- white now rather than black, but still below it.
     Measured: the three need 235 + 10 margin + 100 menu + 36 toggler = 381px inside
     the header's 20px padding, so they need a 401px viewport. At 414 they fitted with
     3px to spare; at 393 and 360 they do not fit and the menu wraps.
     The logo is the piece that should give way, and only when it has to. The width has to
     be a definite length, not `auto`: the logo is a float whose child image carries
     `max-width: 100%`, so `auto` shrink-wraps to an image that is itself sizing off the
     box -- measured at 360px the logo collapsed to 37px. `calc(100% - 150px)` reserves
     the menu and hamburger outright, and the 235px cap keeps today's size wherever there
     is room for it (anything above a 405px viewport). */
  .page-header.navbar .page-logo {
    width: calc(100% - 150px) !important;
    max-width: 235px !important;
  }
  /* The mark is `viewBox="0 0 210 58"` with no intrinsic width or height, so `width: auto`
     plus `height: auto` resolves to 0x0 -- measured, the logo vanished entirely. Width has
     to drive it and height follow the 210:58 ratio, with max-height standing in for the
     50px the desktop rule sets outright. Above a 405px viewport this renders 181x50, which
     is what it renders today; below it the mark shrinks in proportion instead of clipping. */
  .page-header.navbar .page-logo a img.logo-full {
    width: 100% !important;
    height: auto !important;
    max-height: 50px !important;
  }
}

@media (max-width: 767px) {
  /* The notification and inbox panels are `width: 255px` positioned against an ancestor that
     sits near the right edge of the header, so on a phone they hang off the screen: measured
     at a 393px viewport the panel ran from 222 to 477, 84px past the edge, and gave the whole
     page 84px of sideways scroll to chase it.

     Two things had to change. Dropping `position: relative` from the list item hands the
     absolutely positioned panel to `.page-header.navbar`, which is `position: relative` below
     992px and spans the viewport, so the offsets measure from the screen edges; `top` is left
     alone so the panel still drops from under its own icon. And the width is stated outright
     rather than derived from `left` + `right`, because the panel's contents were wide enough
     to push its minimum width past the space between them -- when that happens the browser
     drops `right` and the panel measured 563px inside a 393px screen anyway.

     `position: fixed` was tried first and is wrong here: inside the positioned header it
     ignored the right edge and resolved 563px wide at a static position 854px down the page. */
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-extended {
    position: static !important;
  }
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-extended > .dropdown-menu {
    left: 10px !important;
    right: auto !important;
    width: calc(100vw - 20px) !important;
    max-width: calc(100vw - 20px) !important;
  }
  /* The caret is placed `right: 9px` from the panel, which pointed at the icon back when the
     panel was 255px anchored beside it. A panel that spans the screen cannot point at
     anything with a fixed offset, and a caret aimed at empty header is worse than none.
     Metronic drops it the same way for its horizontal menu. */
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-extended > .dropdown-menu:before,
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-extended > .dropdown-menu:after {
    display: none !important;
  }

  /* The panel's own width no longer depends on its contents, but the contents can still
     overflow inside it -- the notification rows are a single long line each. */
  .page-header.navbar .top-menu .navbar-nav > li.dropdown-extended > .dropdown-menu .dropdown-menu-list {
    width: 100% !important;
    max-width: 100% !important;
  }
}

/* Notification panel height, at every width.
   ---------------------------------------------------------------------------
   The list was a slimScroll pane, and slimScroll needs a definite height: the
   markup carried `style="height: 250px"`, so the panel was 250px tall whether it
   held seventeen notifications or none. With none it was a blank 250px box.

   Native overflow sizes to the content and stops at the same 250px, so an empty
   panel is just its heading and a full one still scrolls. No height has to be
   computed, which is the point -- a row measures 95px at phone width and wraps
   taller inside the narrower desktop panel, so any number written here would be
   wrong at one of the two. */
.page-header.navbar .top-menu .navbar-nav > li.dropdown-extended .dropdown-menu .dropdown-menu-list {
  max-height: 250px;
  overflow-y: auto;
}
.page-header.navbar .top-menu .navbar-nav > li.dropdown-extended .dropdown-menu .dropdown-menu-empty {
  padding: 18px 15px;
  color: #6b7688;
  font-size: 13px;
  text-align: center;
}

/* ----------------------------------------------------------------
   STATUS LEGEND  (ui/_status_legend)
   A key for a status column. Each entry is the same pill the rows carry, so the
   two read as one thing. Replaces three `btn btn-xs` spans set inline at 10px,
   which looked like buttons, ran together on one line, and wrapped badly.
   ---------------------------------------------------------------- */
.status-legend {
  display: grid !important;
  grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)) !important;
  gap: 8px 20px !important;
  padding: 12px 14px !important;
  margin-bottom: 14px !important;
  background: #ffffff !important;
  border: 1px solid #e3e7ef !important;
  border-radius: 8px !important;
}
.status-legend-item {
  display: flex !important;
  align-items: baseline !important;
  gap: 9px !important;
  min-width: 0 !important;
}
/* The pill keeps its own size; only the explanation is set smaller than body text. */
.status-legend-item .status-pill { flex: none !important; }
.status-legend-text {
  font-size: 12px !important;
  line-height: 1.45 !important;
  color: #5b6472 !important;
  min-width: 0 !important;
}

@media (max-width: 767px) {
  /* One per line rather than a grid that would leave a 260px column half empty. */
  .status-legend { grid-template-columns: 1fr !important; gap: 10px !important; }
}

/* ----------------------------------------------------------------
   WIDE LINE-ITEM TABLES
   A table whose columns declare more width than the card can give them gets
   compressed, and the column with the longest content wins at everyone else's
   expense. `min-width` makes the declared widths hold and hands the overflow to
   the .table-scrollable wrapper, which already has overflow-x: auto.
   ---------------------------------------------------------------- */
.table-scrollable > .table.table-wide { min-width: 1180px !important; }

@media (min-width: 1200px) {
  .table-scrollable > .table.table-wide { min-width: 1400px !important; }
}
/* ----------------------------------------------------------------
   WIDE LINE-ITEM TABLES INSIDE A RECORD SHEET

   Bootstrap ships `.table { max-width: 100% }`, and that beats a table's own
   `width` however large it is — a stylesheet declaration against a used width,
   not a specificity contest an inline style can win. So the Purchase Order
   detail tables, which declare `width: 2000px` and sit in a `.record-lines-wrap`
   that scrolls horizontally, were being rendered at the container width and every
   column compressed to fit.

   Measured on the Guarantee Letter Meeting form at a 1440px viewport, reported
   2026-09-24 as "From Date and To Date are too narrow to read":

     as shipped        table 1440px   From Date cell 69px   23px for "23 Sep 2026"
     max-width lifted  table 2000px   From Date cell 86px   40px
     + 130px columns   table 2000px                         57px
     + table 2560px    table 2560px   From Date cell 130px  84px   <- fits (needs 74px)

   All three were needed. Widening the columns alone moved 23px to 57px and the
   date still did not fit, because the columns declared 2560px against a table
   declaring 2000px and were scaled down to suit. The tables now declare what
   their columns add up to, and this rule lets them have it.

   Scoped to `.table-wide`, which the 14 affected tables now carry, so nothing
   else starts overflowing. The wrapper already had `overflow-x: auto`.
   ---------------------------------------------------------------- */
.record-lines-wrap > .table.table-wide {
  max-width: none !important;
}

/* ----------------------------------------------------------------
   Title Case for navigation and screen titles (requested 2026-10-03).
   Every word of a sidebar entry, a screen title and a record sheet's
   title starts with a capital: "Monthly summaries" reads "Monthly
   Summaries". Done here rather than in the ~1,500 templates and the
   layout's 100-odd labels, so new screens get it without anyone
   remembering. `capitalize` only raises first letters -- document
   numbers (TR/DOM/2026/0001) and acronyms (TOIL, HR) are untouched --
   but it applies to whatever the title holds, a record's own name
   included. Section headings were already all caps.
   ---------------------------------------------------------------- */
.page-sidebar-menu > li > a > .title,
.page-sidebar-menu .sub-menu > li > a,
.control-panel .cp-title,
.record-sheet__title {
  text-transform: capitalize !important;
}

/* ----------------------------------------------------------------
   Sidebar menu search (shield-ui.js, "Sidebar menu search").

   The box sits at the top of the menu and stays there while the menu
   scrolls: sticky inside slimScroll on a desktop, and at the top of the
   screen on a phone, where the sidebar is the long panel the hamburger
   opens. On a phone the field is 44px tall and its text 16px, so iOS
   doesn't zoom the page when it takes focus.

   It belongs to the expanded menu only. On the collapsed icon rail it is
   hidden and nothing is filtered: the rail's sub-menus are hover flyouts,
   and a filter there would leave half-hidden flyouts. Expanding the
   sidebar brings the box, and any search in it, back.
   ---------------------------------------------------------------- */
.page-sidebar .page-sidebar-menu > li.sidebar-menu-search-wrapper {
  position: sticky !important;
  top: 0;
  z-index: 3;
  margin: 0 0 6px !important;
  padding: 10px 12px 8px !important;
  background: #24246D;
}
.theme-light .page-sidebar .page-sidebar-menu > li.sidebar-menu-search-wrapper {
  background: #ffffff;
  border-bottom: 1px solid #e9edf5 !important;
}
.page-sidebar-closed .page-sidebar .page-sidebar-menu > li.sidebar-menu-search-wrapper {
  display: none !important;
}

.sidebar-menu-search {
  position: relative;
}
.sidebar-menu-search__icon {
  position: absolute;
  top: 50%;
  left: 11px;
  transform: translateY(-50%);
  font-size: 13px;
  color: rgba(255,255,255,0.55);
  pointer-events: none;
}
.sidebar-menu-search__input {
  display: block;
  width: 100%;
  height: 36px;
  padding: 0 34px 0 32px;
  border: 1px solid rgba(255,255,255,0.18);
  border-radius: 8px;
  background: rgba(255,255,255,0.08);
  color: #ffffff;
  font-size: 13px;
  line-height: 34px;
  outline: none;
  box-shadow: none;
  transition: border-color 0.15s, box-shadow 0.15s, background-color 0.15s;
}
.sidebar-menu-search__input::placeholder { color: rgba(255,255,255,0.55); }
.sidebar-menu-search__input:focus {
  border-color: rgba(255,255,255,0.6);
  box-shadow: 0 0 0 3px rgba(255,255,255,0.15);
}
.sidebar-menu-search__clear {
  position: absolute;
  top: 50%;
  right: 4px;
  transform: translateY(-50%);
  width: 28px;
  height: 28px;
  padding: 0;
  border: 0;
  border-radius: 6px;
  background: transparent;
  color: rgba(255,255,255,0.7);
  line-height: 28px;
  text-align: center;
  cursor: pointer;
}
.sidebar-menu-search__clear[hidden] { display: none; }
.sidebar-menu-search__clear:hover,
.sidebar-menu-search__clear:focus-visible { background: rgba(255,255,255,0.12); color: #ffffff; outline: none; }
.sidebar-menu-search__status {
  margin: 6px 2px 0;
  font-size: 11.5px;
  line-height: 1.4;
  color: rgba(255,255,255,0.65);
}
.sidebar-menu-search__status:empty { display: none; }

.theme-light .sidebar-menu-search__icon { color: #7b8494; }
.theme-light .sidebar-menu-search__input {
  border-color: #dfe4ec;
  background: #f5f7fb;
  color: #2b3648;
}
.theme-light .sidebar-menu-search__input::placeholder { color: #8a93a3; }
.theme-light .sidebar-menu-search__input:focus {
  border-color: #24246D;
  background: #ffffff;
  box-shadow: 0 0 0 3px rgba(36,36,109,0.12);
}
.theme-light .sidebar-menu-search__clear { color: #6b7688; }
.theme-light .sidebar-menu-search__clear:hover,
.theme-light .sidebar-menu-search__clear:focus-visible { background: #eef1f6; color: #24246D; }
.theme-light .sidebar-menu-search__status { color: #6b7688; }

/* What a search hides and opens. Metronic's own `open` class and the inline
   display its slide animation leaves are not touched, so clearing the search
   puts the menu back as it was. */
.page-sidebar-menu.menu-search-active:not(.page-sidebar-menu-closed) li.menu-search-hidden {
  display: none !important;
}
.page-sidebar-menu.menu-search-active:not(.page-sidebar-menu-closed) li.menu-search-open > .sub-menu {
  display: block !important;
}
.page-sidebar-menu.menu-search-active:not(.page-sidebar-menu-closed) li.menu-search-open > a > .arrow:before {
  content: "\f107";
}

@media (max-width: 991px) {
  .sidebar-menu-search__input {
    height: 44px;
    font-size: 16px;
    line-height: 42px;
    padding-left: 36px;
    padding-right: 44px;
  }
  .sidebar-menu-search__icon { left: 13px; font-size: 15px; }
  .sidebar-menu-search__clear { width: 40px; height: 40px; line-height: 40px; right: 2px; }

  /* Bootstrap gives the open panel `overflow-y: auto`. It has no height limit here, so it never
     scrolls, but it still made itself the box the sticky search stuck to, and the search scrolled
     away with the menu. The collapse animation runs on .collapsing, which keeps its overflow. */
  .page-sidebar.navbar-collapse.in { overflow: visible !important; }
}
