/* =====================================================================================================
   Rengi web-admin — "The Pass" (WEB-UI-1)

   Every screen is a piece of the restaurant's own equipment: brushed-steel ground, white work surfaces,
   graphite ink, hairline rules instead of card shadows, rectangular controls, and one lamp colour that
   means "waiting for you". Green only ever means ready or fine, red only a fault or a destructive act.
   Every figure sits on tabular numerals. The kitchen board is the dark equipment panel. The Platform
   Console is the maker's service panel (graphite rail, cobalt mark); a restaurant's app is headed by
   its own name and logo.

   Shape: controls 6px, surfaces 8px, dialogs and touch tiles 12px, status marks 2px.
   Type: Fixel Text (UI), Fixel Display (large figures), both OFL (MacPaw, fonts/Fixel-OFL.txt); the tabular
   zero and seven are the plain ones (scripts/fonts/patch_fixel.py), so money in a column reads as money.
   Icons: Phosphor regular sprite (icons.svg, MIT). z-index: see --z-*.
   ===================================================================================================== */

@font-face { font-family: "Fixel Text"; src: url("fonts/FixelText-Regular.woff2?v=2") format("woff2"); font-weight: 400; font-style: normal; font-display: swap; }
@font-face { font-family: "Fixel Text"; src: url("fonts/FixelText-Medium.woff2?v=2") format("woff2"); font-weight: 500; font-style: normal; font-display: swap; }
@font-face { font-family: "Fixel Text"; src: url("fonts/FixelText-SemiBold.woff2?v=2") format("woff2"); font-weight: 600; font-style: normal; font-display: swap; }
@font-face { font-family: "Fixel Text"; src: url("fonts/FixelText-Bold.woff2?v=2") format("woff2"); font-weight: 700; font-style: normal; font-display: swap; }
@font-face { font-family: "Fixel Display"; src: url("fonts/FixelDisplay-SemiBold.woff2?v=2") format("woff2"); font-weight: 600; font-style: normal; font-display: swap; }
@font-face { font-family: "Fixel Display"; src: url("fonts/FixelDisplay-Bold.woff2?v=2") format("woff2"); font-weight: 700; font-style: normal; font-display: swap; }

/* ----------------------------------------------------------------------------------------- tokens */
:root {
    color-scheme: light;

    /* Steel: one warm-neutral grey family, from the work surface to graphite. */
    --steel-0: oklch(99.5% 0.0015 95);
    --steel-50: oklch(97.8% 0.002 95);
    --steel-100: oklch(95.6% 0.003 95);
    --steel-150: oklch(93.4% 0.0035 95);
    --steel-200: oklch(90.4% 0.004 95);
    --steel-300: oklch(84% 0.005 95);
    --steel-400: oklch(71% 0.006 95);
    --steel-500: oklch(52% 0.007 95);
    --steel-600: oklch(44% 0.008 95);
    --steel-700: oklch(35% 0.008 95);
    --steel-800: oklch(27% 0.008 95);
    --steel-900: oklch(21.5% 0.008 95);
    --steel-950: oklch(16.5% 0.007 95);

    /* Semantic surfaces and ink. */
    --canvas: var(--steel-50);
    --surface: var(--steel-0);
    --surface-raised: var(--steel-0);
    --surface-subtle: var(--steel-100);
    --surface-hover: var(--steel-50);
    --surface-accent: var(--steel-100);
    --rail: var(--steel-100);
    --rail-hover: var(--steel-150);
    --rail-ink: var(--steel-600);
    --ink: var(--steel-900);
    --navy: var(--steel-900);
    --muted: var(--steel-600);
    --subtle: var(--steel-500);
    --label: var(--steel-700);
    --border: var(--steel-200);
    --line-soft: oklch(93.6% 0.0035 95);
    --input-border: var(--steel-300);
    --hover-border: var(--steel-400);
    --neutral-soft: var(--steel-100);

    /* The action: graphite, like the keys on a piece of kitchen equipment. */
    --action: var(--steel-900);
    --action-hover: var(--steel-700);
    --on-action: var(--steel-0);

    /* The lamp: waiting for you. */
    --amber: oklch(50% 0.125 62);
    --amber-lamp: oklch(75% 0.155 70);
    --amber-soft: oklch(96% 0.035 82);
    --amber-line: oklch(85% 0.08 78);
    /* Ready, fine. */
    --green: oklch(47% 0.11 152);
    --green-lamp: oklch(62% 0.15 150);
    --green-soft: oklch(96% 0.03 152);
    --green-line: oklch(85% 0.07 152);
    /* A fault, or a step with no way back. */
    --red: oklch(50% 0.175 27);
    --red-lamp: oklch(60% 0.2 27);
    --red-soft: oklch(96% 0.022 27);
    --red-line: oklch(86% 0.06 27);
    /* Rengi itself: the console's mark and a support session inside a restaurant. */
    --cobalt: oklch(50% 0.17 264);
    --cobalt-strong: oklch(43% 0.17 264);
    --cobalt-soft: oklch(95.5% 0.025 264);
    /* Kept names: a note or an optional step (calm, never the lamp). */
    --blue: var(--steel-700);
    --blue-dark: var(--steel-900);
    --blue-soft: var(--steel-100);

    --focus: var(--steel-900);
    --focus-soft: oklch(21.5% 0.008 95 / .14);
    --selection: oklch(90% 0.07 82);

    /* Elevation: tinted to the ink, one light source above. */
    --shadow-1: 0 1px 0 oklch(21.5% 0.008 95 / .04), 0 1px 2px oklch(21.5% 0.008 95 / .05);
    --shadow-2: 0 2px 4px oklch(21.5% 0.008 95 / .04), 0 10px 28px -6px oklch(21.5% 0.008 95 / .16);
    --shadow-3: 0 4px 8px oklch(21.5% 0.008 95 / .06), 0 28px 64px -16px oklch(21.5% 0.008 95 / .32);
    --shadow: var(--shadow-1);

    /* Type. */
    --font-ui: "Fixel Text", "Segoe UI", system-ui, -apple-system, sans-serif;
    --font-figures: "Fixel Display", "Fixel Text", "Segoe UI", system-ui, sans-serif;
    --font-mono: ui-monospace, "Cascadia Mono", "Consolas", monospace;
    --text-2xs: 11px; --text-xs: 12px; --text-sm: 13px; --text-md: 14px; --text-lg: 16px;
    --text-xl: 18px; --text-2xl: 22px; --text-3xl: 26px;

    /* Space, shape, controls, layers, motion. */
    --space-1: 4px; --space-2: 8px; --space-3: 12px; --space-4: 16px; --space-5: 20px; --space-6: 24px; --space-8: 32px; --space-10: 40px;
    --radius-mark: 2px; --radius-control: 6px; --radius-surface: 8px; --radius-large: 12px;
    --control-sm: 32px; --control-md: 38px; --control-lg: 44px; --control-touch: 56px;
    --rail-width: 248px;
    --z-sticky: 10; --z-nav: 20; --z-popover: 30; --z-overlay: 100; --z-toast: 300; --z-support: 400;
    --ease-out: cubic-bezier(0.23, 1, 0.32, 1);
    --press: 120ms;

    font-family: var(--font-ui);
}

/* The dark theme; the kitchen board wears it too unless a cook chose light. */
:root[data-theme="dark"], :root:not([data-theme-preference="light"]) .kds-shell {
    color-scheme: dark;
    --canvas: oklch(17% 0.006 95);
    --surface: oklch(20.5% 0.007 95);
    --surface-raised: oklch(23.5% 0.008 95);
    --surface-subtle: oklch(23% 0.008 95);
    --surface-hover: oklch(24.5% 0.008 95);
    --surface-accent: oklch(24.5% 0.008 95);
    --rail: oklch(15% 0.006 95);
    --rail-hover: oklch(22% 0.007 95);
    --rail-ink: oklch(74% 0.006 95);
    --ink: oklch(94.5% 0.004 95);
    --navy: oklch(96% 0.004 95);
    --muted: oklch(74% 0.006 95);
    --subtle: oklch(64% 0.007 95);
    --label: oklch(84% 0.005 95);
    --border: oklch(31% 0.008 95);
    --line-soft: oklch(27% 0.008 95);
    --input-border: oklch(40% 0.009 95);
    --hover-border: oklch(52% 0.009 95);
    --neutral-soft: oklch(27% 0.008 95);
    --action: oklch(93% 0.004 95);
    --action-hover: oklch(84% 0.005 95);
    --on-action: oklch(17% 0.006 95);
    --amber: oklch(82% 0.13 78);
    --amber-lamp: oklch(78% 0.155 72);
    --amber-soft: oklch(30% 0.05 70);
    --amber-line: oklch(45% 0.08 70);
    --green: oklch(80% 0.13 150);
    --green-lamp: oklch(70% 0.15 150);
    --green-soft: oklch(28% 0.045 150);
    --green-line: oklch(42% 0.07 150);
    --red: oklch(76% 0.13 27);
    --red-lamp: oklch(66% 0.19 27);
    --red-soft: oklch(29% 0.06 27);
    --red-line: oklch(45% 0.1 27);
    --cobalt: oklch(70% 0.13 264);
    --cobalt-strong: oklch(58% 0.16 264);
    --cobalt-soft: oklch(28% 0.05 264);
    --blue: oklch(84% 0.005 95);
    --blue-dark: oklch(96% 0.004 95);
    --blue-soft: oklch(27% 0.008 95);
    --focus: oklch(94.5% 0.004 95);
    --focus-soft: oklch(94.5% 0.004 95 / .18);
    --selection: oklch(40% 0.07 75);
    --shadow-1: 0 1px 2px oklch(0% 0 0 / .35);
    --shadow-2: 0 10px 28px -6px oklch(0% 0 0 / .55);
    --shadow-3: 0 28px 64px -16px oklch(0% 0 0 / .7);
    --shadow: var(--shadow-1);
}

:root[data-density="compact"] { --control-md: 34px; }

/* ------------------------------------------------------------------------------------------- base */
* { box-sizing: border-box; }
html, body { min-height: 100%; }
html { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; }
body { margin: 0; color: var(--ink); background: var(--canvas); font-size: var(--text-md); line-height: 1.5; -webkit-font-smoothing: antialiased; text-rendering: optimizeLegibility; }
button, input, select, textarea { font: inherit; letter-spacing: inherit; }
/* A link is ink; in running text it carries an engraved underline. Links dressed as buttons, rows or
   cards style themselves. */
a { color: var(--ink); font-weight: inherit; text-decoration: none; text-decoration-thickness: 1px; text-underline-offset: 3px; }
a:not([class]):hover { color: var(--ink); text-decoration: underline; }
:is(p, li, dd, small, td, .alert, .hint, .field-hint, .muted, .section-heading) > a:not([class]) { text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 40%, transparent); }
:is(p, li, dd, small, td, .alert, .hint, .field-hint, .muted) > a:not([class]):hover { text-decoration-color: currentColor; }
h1, h2, h3, p { margin-top: 0; }
h1, h2, h3 { color: var(--navy); text-wrap: balance; }
h1 { margin-bottom: 6px; font-size: var(--text-3xl); font-weight: 600; line-height: 1.2; letter-spacing: -0.018em; }
h1[tabindex]:focus, h1[tabindex]:focus-visible { outline: none; }
h2 { margin-bottom: 4px; font-size: var(--text-lg); font-weight: 600; line-height: 1.3; letter-spacing: -0.008em; }
h3 { margin-bottom: 4px; font-size: var(--text-md); font-weight: 600; line-height: 1.35; }
p { color: var(--muted); text-wrap: pretty; }
small, .hint, .field-hint, .alert > span, .alert > strong, .entrance-door small, td { text-wrap: pretty; }
.entrance-door strong, .empty-state h2, .login-heading h1 { text-wrap: balance; }
strong, b { font-weight: 600; }
code { padding: 1px 5px; color: var(--ink); background: var(--neutral-soft); border: 1px solid var(--border); border-radius: var(--radius-mark); font-family: var(--font-mono); font-size: 12px; }
kbd { display: inline-flex; align-items: center; min-height: 22px; padding: 1px 6px; color: var(--muted); background: var(--surface); border: 1px solid var(--border); border-bottom-width: 2px; border-radius: 4px; font: 500 11px var(--font-mono); }
::selection { color: var(--ink); background: var(--selection); }
::placeholder { color: var(--subtle); opacity: 1; }
html { scrollbar-color: color-mix(in oklch, var(--ink) 22%, transparent) transparent; }
input, textarea { caret-color: var(--ink); }
table, .num, time, .tabular { font-variant-numeric: tabular-nums; }
.visually-hidden { position: absolute !important; width: 1px !important; height: 1px !important; padding: 0 !important; overflow: hidden !important; clip: rect(0,0,0,0) !important; white-space: nowrap !important; border: 0 !important; }
.skip-link { position: fixed; top: 8px; left: 8px; z-index: 1000; padding: 9px 13px; color: var(--on-action); background: var(--action); border-radius: var(--radius-control); text-decoration: none; transform: translateY(-150%); }
.skip-link:focus { color: var(--on-action); transform: none; }
.nowrap { white-space: nowrap; }
.muted { color: var(--muted); font-size: var(--text-xs); }
hr { height: 1px; margin: var(--space-5) 0; background: var(--border); border: 0; }

/* Keyboard focus: a graphite ring clear of the control, on every interactive element. */
button:focus-visible, a:focus-visible, input:focus-visible, select:focus-visible, textarea:focus-visible, summary:focus-visible, [tabindex]:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }

/* ------------------------------------------------------------------------------------------ icons */
.icon { display: inline-block; flex: none; width: 1.15em; height: 1.15em; vertical-align: -0.2em; fill: currentColor; }
.icon.lg { width: 1.4em; height: 1.4em; }
.button .icon { width: 17px; height: 17px; }

/* ------------------------------------------------------------------------------------------ shell
   A rail on the left, the work on the right. A restaurant's rail is brushed steel headed by its own
   name and logo; the console's rail is the maker's graphite panel with the cobalt mark. */
.app-shell { min-height: 100vh; display: grid; grid-template-columns: var(--rail-width) minmax(0, 1fr); }
.content-column { min-width: 0; display: flex; flex-direction: column; }
/* The rail is as tall as the window and scrolls on its own: with every section a cabinet has, the list
   is taller than a 768 px screen, and whatever sits below the fold would be out of reach. */
.sidebar { position: sticky; top: 0; height: 100vh; display: flex; flex-direction: column; gap: var(--space-3); padding: var(--space-4) var(--space-3) var(--space-3); color: var(--ink); background: var(--rail); border-right: 1px solid var(--border); overflow-y: auto; overscroll-behavior: contain; scrollbar-width: thin; }
/* The sections scroll inside the rail; the business's name above them and the account, language and theme
   below them stay in view on any screen (a cabinet's list is taller than a 900 px window). */
@media (min-width: 761px) {
    .sidebar { overflow: hidden; }
    .sidebar > .primary-nav { flex: 1 1 auto; min-height: 0; margin-inline: -4px; padding-inline: 4px; overflow-y: auto; overscroll-behavior: contain; scrollbar-width: thin; }
}
.rail-head { display: flex; align-items: center; gap: var(--space-2); }
.brand { flex: 1; min-width: 0; display: flex; align-items: center; gap: 10px; padding: 4px 6px 8px; color: var(--ink); text-decoration: none; border-radius: var(--radius-control); }
.brand:hover { color: var(--ink); }
.brand > span:last-child { min-width: 0; display: flex; flex-direction: column; }
/* A restaurant's name is what tells staff where they are: two lines before it is ever cut. */
.brand strong { display: -webkit-box; overflow: hidden; font-size: var(--text-md); font-weight: 600; line-height: 1.25; overflow-wrap: anywhere; -webkit-box-orient: vertical; -webkit-line-clamp: 2; }
.brand small { overflow: hidden; color: var(--muted); font-size: var(--text-xs); text-overflow: ellipsis; white-space: nowrap; }
/* The restaurant's mark: its logo when it has one, its initial on engraved steel until then. */
.brand-mark { position: relative; display: grid; place-items: center; flex: none; width: 36px; height: 36px; overflow: hidden; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); font-family: var(--font-figures); font-size: 16px; font-weight: 700; box-shadow: var(--shadow-1); }
.brand-mark img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: contain; }
/* Once the logo has loaded, the initial under it steps aside (a transparent logo must not show it);
   a logo that failed is hidden and the initial stays. The picture only marks itself (TenantMark). */
.brand-mark:has(> img[data-state="loaded"]) > span { visibility: hidden; }
.brand-mark > img[data-state="failed"] { display: none; }
.brand-mark.large { width: 52px; height: 52px; border-radius: var(--radius-large); font-size: 22px; }

.primary-nav { display: flex; flex-direction: column; gap: 1px; }
.nav-group { display: flex; flex-direction: column; gap: 1px; margin-top: var(--space-3); }
.nav-group-label { margin: 0 10px 4px; color: var(--subtle); font-size: var(--text-xs); font-weight: 600; letter-spacing: .01em; }
.primary-nav a { display: flex; align-items: center; gap: 10px; min-height: 36px; padding: 6px 10px; color: var(--rail-ink); border-radius: var(--radius-control); font-size: var(--text-md); font-weight: 500; line-height: 1.3; text-decoration: none; transition: background-color 120ms ease, color 120ms ease; }
.primary-nav a .icon { width: 18px; height: 18px; color: var(--subtle); transition: color 120ms ease; }
.primary-nav a > span:not(.icon) { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.primary-nav a:hover { color: var(--ink); background: var(--rail-hover); }
.primary-nav a:hover .icon { color: var(--ink); }
.primary-nav a.active { color: var(--ink); background: var(--surface); box-shadow: var(--shadow-1), inset 0 0 0 1px var(--border); font-weight: 600; }
.primary-nav a.active .icon { color: var(--ink); }
/* A surface the business has not bought: locked and visible, so an owner can decide to buy it. */
.primary-nav a.nav-locked, .primary-nav a.nav-locked:hover { color: var(--subtle); }
.nav-locked .icon { color: var(--subtle); }
/* The way back to another workspace (the queue's rail): a plain link with its arrow, first in the list. */
.nav-return { font-weight: 500; }
.nav-return + .nav-return { margin-top: 0; }
.nav-return-group { margin-bottom: var(--space-2); padding-bottom: var(--space-2); border-bottom: 1px solid var(--border); }

.sidebar-footer { margin-top: auto; display: grid; gap: var(--space-2); padding-top: var(--space-3); border-top: 1px solid var(--border); }
.connectivity { display: flex; align-items: center; gap: 8px; padding: 6px 8px; color: var(--muted); border-radius: var(--radius-control); font-size: var(--text-xs); text-decoration: none; }
.connectivity:hover { color: var(--ink); background: var(--rail-hover); }
.status-dot { display: inline-block; flex: none; width: 8px; height: 8px; background: var(--steel-400); border-radius: var(--radius-mark); }
.status-dot.online { background: var(--green-lamp); }
.status-dot.offline { background: var(--red-lamp); }
.status-dot.degraded { background: var(--amber-lamp); }
.connectivity.degraded { color: var(--amber); }
.user-card { min-width: 0; }
.user-card { display: flex; align-items: center; gap: 9px; padding: 6px 4px 6px 6px; }
.avatar { display: grid; place-items: center; flex: none; width: 30px; height: 30px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-control); font-size: var(--text-xs); font-weight: 600; }
.user-copy { min-width: 0; display: flex; flex: 1; flex-direction: column; line-height: 1.3; }
.user-copy strong { display: -webkit-box; overflow: hidden; color: var(--ink); font-size: var(--text-sm); font-weight: 600; overflow-wrap: anywhere; -webkit-box-orient: vertical; -webkit-line-clamp: 2; }
.user-copy small { color: var(--muted); font-size: var(--text-xs); overflow-wrap: anywhere; }
/* The language and the theme: a person's own settings, kept quietly at the foot of the rail. */
.rail-prefs { display: grid; grid-template-columns: 1fr 1fr; gap: 6px; }
.rail-prefs .selector-field span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); }
.rail-prefs select, .rail-prefs .shell-selector select { width: 100%; min-width: 0; min-height: 30px; padding: 3px 6px; background-color: transparent; border-color: var(--border); font-size: var(--text-xs); box-shadow: none; }

.icon-button { display: inline-grid; place-items: center; flex: none; width: 34px; height: 34px; padding: 0; color: var(--muted); background: transparent; border: 0; border-radius: var(--radius-control); cursor: pointer; font-size: 17px; line-height: 1; transition: background-color 120ms ease, color 120ms ease, transform var(--press) var(--ease-out); }
.icon-button .icon { width: 18px; height: 18px; }
.icon-button:hover { color: var(--ink); background: var(--rail-hover); }
.icon-button:active { transform: scale(.94); }
/* The menu key that folds the rail away exists only on a phone. */
.icon-button.rail-toggle { display: none; }

/* ------------------------------------------------------------------------------- cabinet navigation
   NAV-1. The cabinet in eight areas, not twenty-two screens: the rail names the areas, the strip above
   a page names the screens of the area being worked in, and a phone trades the rail for a bar under the
   thumb. One map draws all three (CabinetNavigation). */
.cabinet-shell .primary-nav > a { min-height: 40px; }
.cabinet-shell .primary-nav > .nav-group { margin-top: var(--space-4); padding-top: var(--space-3); border-top: 1px solid var(--border); }
/* The strip is navigation, not a filter: text links on the page's own rule, the screen in view underlined
   in ink. Filters are the bordered keys of .filter-bar and never look like this. */
.area-nav { display: flex; flex-wrap: wrap; gap: 0 var(--space-6); margin: -12px 0 var(--space-5); border-bottom: 1px solid var(--border); }
.area-nav a { position: relative; display: inline-flex; flex: none; align-items: center; gap: 6px; min-height: 44px; color: var(--muted); font-size: var(--text-md); font-weight: 500; text-decoration: none; white-space: nowrap; transition: color 120ms ease; }
.area-nav a::after { position: absolute; right: 0; bottom: -1px; left: 0; height: 2px; content: ""; background: transparent; transition: background-color 120ms ease; }
.area-nav a:hover { color: var(--ink); }
.area-nav a.active { color: var(--ink); font-weight: 600; }
.area-nav a.active::after { background: var(--ink); }
.area-nav a .icon { width: 14px; height: 14px; color: var(--subtle); }
.area-nav a.nav-locked, .area-nav a.nav-locked:hover { margin-left: auto; color: var(--subtle); }
/* The bar is a phone's; a wide screen has the rail. */
.tab-bar { display: none; }

/* A list of ways in — the «More» page, the work screens: a row a thumb can hit, with one line on what is
   behind it. */
.nav-rows { max-width: 720px; margin-bottom: var(--space-6); }
.nav-rows > h2 { margin: 0 0 var(--space-2); color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.nav-rows > ul { margin: 0; padding: 0; overflow: hidden; list-style: none; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.nav-rows > ul > li + li { border-top: 1px solid var(--line-soft); }
.nav-row { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: var(--space-3); min-height: 60px; padding: 10px var(--space-4); color: var(--ink); text-decoration: none; transition: background-color 120ms ease; -webkit-tap-highlight-color: transparent; }
.nav-row:hover { color: var(--ink); background: var(--surface-hover); }
.nav-row:focus-visible { outline-offset: -2px; }
.nav-row-mark { display: grid; place-items: center; width: 36px; height: 36px; color: var(--label); background: var(--surface-subtle); border-radius: var(--radius-control); }
.nav-row-mark .icon { width: 20px; height: 20px; }
.nav-row-copy { display: grid; gap: 1px; min-width: 0; }
.nav-row-copy strong { font-size: var(--text-md); font-weight: 600; line-height: 1.3; }
.nav-row-copy small { color: var(--muted); font-size: var(--text-sm); line-height: 1.35; text-wrap: pretty; }
.nav-row > .nav-row-go { width: 16px; height: 16px; color: var(--subtle); transition: color 120ms ease; }
.nav-row:hover > .nav-row-go { color: var(--ink); }
/* The account on the «More» page: the rail's foot with room for words. */
.account-panel { display: grid; gap: var(--space-4); padding: var(--space-4); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.account-panel .user-card { flex-wrap: wrap; gap: var(--space-3); padding: 0; }
.account-panel .user-copy { flex: 1 1 180px; }
.account-panel .rail-prefs { gap: var(--space-3); }
.account-panel .rail-prefs .selector-field span { position: static; width: auto; height: auto; overflow: visible; clip: auto; }
.account-panel .rail-prefs .shell-selector { display: grid; }
.account-panel .rail-prefs .shell-selector select { min-height: var(--control-lg); padding: 7px 10px; background-color: var(--surface); border-color: var(--input-border); font-size: var(--text-md); }

/* The console: the maker's service panel. */
.platform-shell .sidebar { --rail: var(--steel-950); --rail-hover: oklch(24% 0.008 95); --rail-ink: var(--steel-300); --subtle: var(--steel-400); color: var(--steel-100); background: var(--rail); border-right-color: oklch(10% 0.005 95); }
.platform-shell .brand, .platform-shell .brand:hover { color: var(--steel-50); }
.platform-shell .brand small, .platform-shell .nav-group-label, .platform-shell .connectivity, .platform-shell .user-copy small { color: var(--steel-400); }
/* The console's own name and what it is are read whole (cc-29): two short lines, never «…». */
.platform-shell .brand small { white-space: normal; text-wrap: balance; }
.platform-shell .brand-mark, .platform-login .brand-mark { color: #fff; background: var(--cobalt); border-color: transparent; box-shadow: none; }
.platform-shell .primary-nav a .icon { color: var(--steel-400); }
.platform-shell .primary-nav a:hover { color: #fff; }
.platform-shell .primary-nav a:hover .icon { color: #fff; }
.platform-shell .primary-nav a.active { color: #fff; background: oklch(26% 0.01 95); box-shadow: inset 2px 0 0 var(--cobalt); }
.platform-shell .primary-nav a.active .icon { color: oklch(78% 0.1 264); }
.platform-shell .sidebar-footer { border-top-color: oklch(26% 0.008 95); }
.platform-shell .user-copy strong { color: var(--steel-50); }
.platform-shell .avatar { color: var(--steel-50); background: oklch(24% 0.008 95); border-color: oklch(30% 0.008 95); }
.platform-shell .connectivity:hover, .platform-shell .icon-button:hover { color: #fff; background: var(--rail-hover); }
.platform-shell .sidebar .icon-button { color: var(--steel-300); }

/* The console's top bar: search, the command palette and a person's own settings. */
.shell-toolbar { position: sticky; top: 0; z-index: var(--z-nav); display: flex; align-items: center; gap: var(--space-2); min-height: 56px; padding: 9px clamp(20px, 3vw, 40px); background: color-mix(in oklch, var(--canvas) 94%, transparent); border-bottom: 1px solid var(--border); backdrop-filter: saturate(1.4) blur(10px); }
.global-search { position: relative; flex: 1; max-width: 560px; }
.shell-search { max-width: none; }
.shell-search kbd { margin-left: auto; }
.command-trigger { gap: 10px; color: var(--muted); }
.command-trigger kbd { font-size: 10px; }
.selector-field { display: grid; gap: 3px; color: var(--muted); font-size: var(--text-xs); font-weight: 500; }
.selector-field select { min-width: 150px; }
.shell-selector span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); }
.shell-selector select { min-width: 112px; min-height: 34px; font-size: var(--text-sm); }
.shell-toolbar .shell-selector select { min-width: 0; }
.command-trigger { margin-left: auto; }
.global-search .search-box { max-width: none; }
.help-trigger { border: 1px solid var(--border); }
.search-results { position: absolute; top: calc(100% + 6px); left: 0; right: 0; z-index: var(--z-popover); overflow: hidden; padding: 6px; background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius-surface); box-shadow: var(--shadow-2); }
.search-results > small { display: block; padding: 7px 9px 4px; color: var(--muted); }
.search-result { display: grid; grid-template-columns: 1fr auto; align-items: center; border-radius: var(--radius-control); }
.search-result.selected, .search-result:hover { background: var(--surface-accent); }
.search-result > button:first-child { min-width: 0; display: grid; gap: 2px; padding: 9px; color: var(--ink); background: transparent; border: 0; cursor: pointer; text-align: left; }
.search-result span { overflow: hidden; color: var(--muted); font-size: var(--text-xs); text-overflow: ellipsis; white-space: nowrap; }
.search-state { display: flex; align-items: center; justify-content: center; gap: 8px; min-height: 72px; padding: 12px; color: var(--muted); text-align: center; }
.search-state button { color: var(--ink); background: none; border: 0; cursor: pointer; text-decoration: underline; }
/* Under 1100 px the palette key keeps its icon and the search takes what is left; under 900 px language and
   theme leave the bar (they stay in Settings) rather than run off the screen. */
@media (max-width: 1100px) {
    .command-trigger > span:not(.icon), .command-trigger kbd { display: none; }
    .global-search { flex: 1 1 180px; min-width: 0; }
    .shell-toolbar .search-box { min-width: 0; }
}
@media (max-width: 900px) { .shell-toolbar .shell-selector { display: none; } }

.content { width: 100%; max-width: 1560px; min-width: 0; padding: 28px clamp(20px, 3vw, 40px) 72px; }

/* ------------------------------------------------------------------------------------ page header */
.page-header { display: flex; flex-wrap: wrap; align-items: flex-start; justify-content: space-between; gap: 16px 24px; margin-bottom: 24px; }
.page-header > div:first-child { flex: 1 1 420px; min-width: 0; }
/* The keys sit on the title's line (not on the subtitle's last line), so they stay put from page to page. */
.page-header .header-actions, .page-header .page-actions { flex: 0 1 auto; justify-content: flex-end; margin-top: -4px; margin-left: auto; }
.page-header h1 { margin-bottom: 4px; }
.page-header p { max-width: 72ch; margin-bottom: 0; font-size: var(--text-md); }
.page-actions, .header-actions { display: flex; align-items: center; gap: var(--space-2); flex-wrap: wrap; }
.tenant-heading { align-items: flex-start; }
.page-header .header-actions > .icon-button { width: var(--control-md); height: var(--control-md); color: var(--label); background: var(--surface); border: 1px solid var(--input-border); box-shadow: var(--shadow-1); }
.back-link { display: inline-flex; align-items: center; gap: 6px; margin-bottom: 14px; color: var(--muted); font-size: var(--text-sm); font-weight: 500; text-decoration: none; }
.back-link:hover { color: var(--ink); }
.title-line { display: flex; align-items: center; flex-wrap: wrap; gap: 8px 12px; }
.title-line h1, .title-line h2, .title-line h3 { margin-bottom: 0; }
.breadcrumbs { display: flex; align-items: center; flex-wrap: wrap; gap: 6px; margin-bottom: 12px; color: var(--muted); font-size: var(--text-sm); }
.breadcrumbs a { color: var(--muted); text-decoration: none; }
.breadcrumbs a:hover { color: var(--ink); text-decoration: underline; }
.refresh-note { color: var(--muted); font-size: var(--text-xs); }

/* --------------------------------------------------------------------------------------- controls
   Rectangular keys. A press settles like a hardware key (0.97, 120 ms); hover is a change of fill,
   never a lift. Graphite is the one action; the plain key is steel on white. */
.button { display: inline-flex; align-items: center; justify-content: center; gap: 7px; min-height: var(--control-md); padding: 0 14px; color: var(--ink); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-md); font-weight: 600; line-height: 1.2; text-align: center; text-decoration: none; white-space: nowrap; box-shadow: var(--shadow-1); transition: background-color 120ms ease, border-color 120ms ease, color 120ms ease, transform var(--press) var(--ease-out); -webkit-tap-highlight-color: transparent; touch-action: manipulation; }
.button:active:not(:disabled) { transform: scale(.97); }
/* Inside a table row or an inline action group a button is a control among controls, not a call to action. */
.button.small, td .button, .row-actions .button, .row-action { min-height: var(--control-sm); padding: 0 11px; font-size: var(--text-sm); }
td .button:not(.primary):not(.destructive), .row-actions .button:not(.primary):not(.destructive) { box-shadow: none; }
.button.primary { color: var(--on-action); background: var(--action); border-color: var(--action); }
.button.secondary { color: var(--ink); background: var(--surface); border-color: var(--input-border); }
.button.tertiary, .button.ghost { color: var(--ink); background: transparent; border-color: transparent; box-shadow: none; }
/* A quiet action with no plate of its own is marked the way a link is, so it never reads as a label. */
.button.tertiary:not(:has(.icon)) > span:only-child, .button.tertiary:not(:has(.icon, span)) { text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 35%, transparent); text-underline-offset: 3px; }
/* On a bar the key has its own plate, so it needs no underline. */
:is(.pos-bar, .kds-bar, .impersonation-bar) .button.tertiary, :is(.pos-bar, .kds-bar, .impersonation-bar) .button.tertiary > span { text-decoration: none; }
.button.full { width: 100%; }
.button.large { min-height: var(--control-lg); padding: 0 18px; font-size: var(--text-lg); }
.button:disabled, fieldset:disabled .button { opacity: .5; cursor: not-allowed; box-shadow: none; }
.button.destructive { color: var(--red); background: var(--red-soft); border-color: var(--red-line); }
.button.destructive.solid { color: white; background: var(--red); border-color: var(--red); }
:root[data-theme="dark"] .button.destructive.solid { color: var(--on-action); background: var(--red-lamp); border-color: var(--red-lamp); }
.button.danger-ghost { color: var(--red); background: transparent; border-color: transparent; box-shadow: none; }
.cabinet-dialog .form-actions > .button.danger-ghost { background: var(--red-soft); border-color: var(--red-line); }
@media (hover: hover) {
    .button:hover:not(:disabled) { color: var(--ink); background: var(--surface-hover); border-color: var(--hover-border); }
    .button.primary:hover:not(:disabled) { color: var(--on-action); background: var(--action-hover); border-color: var(--action-hover); }
    .button.tertiary:hover:not(:disabled), .button.ghost:hover:not(:disabled) { color: var(--ink); background: var(--surface-accent); border-color: transparent; }
    .button.destructive:hover:not(:disabled) { color: var(--red); background: color-mix(in oklch, var(--red-soft) 70%, var(--red-line)); border-color: var(--red); }
    .button.destructive.solid:hover:not(:disabled) { color: white; background: color-mix(in oklch, var(--red) 85%, black); border-color: color-mix(in oklch, var(--red) 85%, black); }
    .button.danger-ghost:hover:not(:disabled) { color: var(--red); background: var(--red-soft); border-color: transparent; }
    .cabinet-dialog .form-actions > .button.danger-ghost:hover:not(:disabled) { background: color-mix(in oklch, var(--red-soft) 70%, var(--red-line)); border-color: var(--red); }
    :root[data-theme="dark"] .button.destructive.solid:hover:not(:disabled) { color: var(--on-action); background: var(--red); border-color: var(--red); }
}
.link-button { padding: 0; color: inherit; background: none; border: 0; cursor: pointer; font: inherit; text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 40%, transparent); text-underline-offset: 3px; }
.link-button:hover { text-decoration-color: currentColor; }
.copy-inline { display: inline-block; max-width: min(240px, 100%); overflow: hidden; margin-block: -3px; padding: 3px 0; color: var(--muted); background: none; border: 0; cursor: pointer; font-family: var(--font-mono); font-size: .92em; text-align: left; text-overflow: ellipsis; vertical-align: bottom; white-space: nowrap; }
/* In a list of facts the id is whole: it wraps inside its own cell instead of running into the next one. */
dd > .copy-inline { max-width: 100%; white-space: normal; overflow-wrap: anywhere; font-size: var(--text-sm); }
.copy-inline:hover { color: var(--ink); text-decoration: underline; }
.sort-button { display: inline-flex; align-items: center; gap: 4px; padding: 0; color: inherit; background: none; border: 0; cursor: pointer; font: inherit; font-weight: inherit; letter-spacing: inherit; text-transform: inherit; }
.sort-button { min-height: 24px; margin-block: -3px; }
.sort-button .icon { width: 14px; height: 14px; }
.file-button { position: relative; overflow: hidden; cursor: pointer; }
.file-button input { position: absolute; width: 1px; height: 1px; opacity: 0; }

/* Fields: the label above, the help under it, the error under that. */
/* The field every text control starts from, at zero specificity: any component that draws its own (a search box,
   the till's note, a PIN) overrides it with a single class. */
:where(input[type="date"], input[type="time"], input[type="datetime-local"]) { height: var(--control-md); }
:where(select, input:not([type="checkbox"], [type="radio"], [type="range"], [type="color"]), textarea) { min-height: var(--control-md); padding: 7px 10px; color: var(--ink); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); outline: none; box-shadow: inset 0 1px 1px oklch(21.5% 0.008 95 / .03); transition: border-color 120ms ease, box-shadow 120ms ease; }
select { padding-right: 30px; appearance: none; background-image: linear-gradient(45deg, transparent 50%, var(--muted) 50%), linear-gradient(135deg, var(--muted) 50%, transparent 50%); background-position: calc(100% - 15px) 50%, calc(100% - 10px) 50%; background-size: 5px 5px, 5px 5px; background-repeat: no-repeat; cursor: pointer; }
select:focus, input:focus, textarea:focus { border-color: var(--ink); box-shadow: 0 0 0 3px var(--focus-soft); }
select:disabled, input:disabled, textarea:disabled { color: var(--muted); background-color: var(--surface-subtle); cursor: not-allowed; }
:is(input, select, textarea)[aria-invalid="true"], .invalid, select.invalid, input.invalid, textarea.invalid { border-color: var(--red); }
:is(input, select, textarea)[aria-invalid="true"]:focus { box-shadow: 0 0 0 3px color-mix(in oklch, var(--red) 22%, transparent); }
textarea { width: 100%; min-height: 84px; line-height: 1.45; resize: vertical; }
input[type="checkbox"], input[type="radio"] { width: 16px; height: 16px; accent-color: var(--action); cursor: pointer; }
input[type="color"] { width: 40px; height: 32px; padding: 2px; background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); }
input[type="search"]::-webkit-search-cancel-button { cursor: pointer; }
fieldset { min-width: 0; margin: 0; padding: 0; border: 0; }
.field { display: grid; grid-template-columns: minmax(0, 1fr); align-content: start; gap: 6px; min-width: 0; }
.field > input:not([type="checkbox"]):not([type="radio"]), .field > select, .field > textarea, .localized-field input, .localized-field textarea { width: 100%; min-width: 0; }
select { max-width: 100%; text-overflow: ellipsis; }
/* A list box shows its rows, not the dropdown chevron in the middle of them. */
select[multiple], select[size]:not([size="1"]) { padding-right: 10px; background-image: none; }
.field label { color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
.field-label { color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
.field small, .field-hint { color: var(--muted); font-size: var(--text-xs); line-height: 1.45; }
.field .validation-message, .validation-message { color: var(--red); font-size: var(--text-xs); font-weight: 500; }
/* A hint that is telling somebody something is wrong, not describing a field. */
.field small.warning-text { color: var(--amber); }
.required-mark { margin-left: 2px; color: var(--red); }
label .optional { margin-left: 6px; color: var(--muted); font-size: var(--text-xs); font-weight: 500; text-transform: lowercase; }
.compact-field { min-width: 220px; }
.align-end { align-self: end; }
.select-field { display: grid; gap: 6px; color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
/* The chosen value reads like every other field's, not like its 12 px label. */
.select-field select, .select-field input { color: var(--ink); font-size: var(--text-md); font-weight: 400; }
/* A label drawn as <label class="field"><span>…</span> looks like every other field label. */
label.field > span:first-child { color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
.select-field select { min-width: 150px; }
.search-box { min-width: 220px; max-width: 520px; display: flex; flex: 1; align-items: center; gap: 8px; height: var(--control-md); padding: 0 11px; color: var(--muted); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); transition: border-color 120ms ease, box-shadow 120ms ease; }
.search-box:focus-within { border-color: var(--ink); box-shadow: 0 0 0 3px var(--focus-soft); }
.search-box span { color: var(--subtle); font-size: 16px; }
.search-box input { align-self: stretch; width: 100%; min-height: 0; padding: 0; background: transparent; border: 0; outline: 0; box-shadow: none; }
.search-box input:focus { box-shadow: none; }
.inline-check { display: inline-flex; align-items: center; gap: 8px; color: var(--label); cursor: pointer; white-space: nowrap; }
.inline-check input { width: 16px; height: 16px; accent-color: var(--action); }
.toggle { display: inline-flex; align-items: flex-start; gap: 8px; color: var(--label); font-size: var(--text-sm); line-height: 1.4; cursor: pointer; }
.toggle > input[type="checkbox"] { margin-top: 1px; }
/* A checkbox inside a field reads as a choice, not as the field's label (the .field label rule made it 13 px bold). */
.field label:is(.toggle, .toggle-field, .switch, .inline-check) { color: var(--ink); font-size: var(--text-md); font-weight: 400; }
.field label.toggle-field small { font-weight: 400; }
.toggle input[type="checkbox"], .inline-check input[type="checkbox"] { flex: none; width: 16px; height: 16px; margin: 0; accent-color: var(--action); }
.toggle-field { display: flex; align-items: flex-start; gap: 10px; padding: 9px 0; cursor: pointer; }
.toggle-field input { flex: none; width: 18px; height: 18px; margin: 1px 0 0; accent-color: var(--action); }
.toggle-field span { display: grid; gap: 2px; }
.toggle-field small { color: var(--muted); font-size: var(--text-xs); }
/* A switch: a real checkbox drawn as the toggle on a panel. */
.switch { display: inline-flex; align-items: center; gap: 10px; color: var(--label); font-size: var(--text-sm); cursor: pointer; }
.switch input[type="checkbox"] { position: relative; flex: none; width: 34px; height: 20px; margin: 0; appearance: none; background: var(--steel-300); border-radius: 999px; transition: background-color 150ms ease; }
.switch input[type="checkbox"]::after { position: absolute; top: 2px; left: 2px; width: 16px; height: 16px; content: ""; background: var(--steel-0); border-radius: 50%; box-shadow: 0 1px 2px oklch(0% 0 0 / .25); transition: transform 150ms var(--ease-out); }
.switch input[type="checkbox"]:checked { background: var(--action); }
.switch input[type="checkbox"]:checked::after { transform: translateX(14px); }

/* Chips and presets: a quiet choice in a row. */
.chip-row { display: flex; flex-wrap: wrap; gap: 6px; margin: 12px 0; }
.chip { display: inline-flex; align-items: center; gap: 5px; padding: 2px 8px; color: var(--muted); background: var(--surface-subtle); border-radius: 4px; font-size: var(--text-xs); }
.chip.active { color: var(--ink); background: var(--surface); box-shadow: inset 0 0 0 1px var(--input-border); }

/* Tabs: an underline on the one in view, set on a hairline. */
.detail-tabs { position: sticky; top: 0; z-index: var(--z-sticky); display: flex; gap: 22px; margin-bottom: 22px; padding: 0 2px; overflow-x: auto; scrollbar-width: thin; background: var(--canvas); border-bottom: 1px solid var(--border); scrollbar-width: none; }
.detail-tabs a, .detail-tabs .tab { position: relative; padding: 11px 0 12px; color: var(--muted); font-size: var(--text-md); font-weight: 500; text-decoration: none; white-space: nowrap; }
.detail-tabs a:hover { color: var(--ink); }
.detail-tabs a.active { color: var(--ink); font-weight: 600; box-shadow: inset 0 -2px 0 var(--ink); }
.platform-shell .detail-tabs { top: 56px; }
/* CON-1: a group's sections stand one under another, each clear of the sticky strip when it is scrolled to. */
.tenant-section + .tenant-section { margin-top: var(--space-5); }
.tenant-section { scroll-margin-top: 120px; }
/* The brand screen's surface switch: its name, the one-choice plate, and the way back to the shared theme. */
.theme-surfaces { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2) var(--space-3); margin: 0 0 var(--space-5); }
.theme-surfaces-label { color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.theme-surfaces .filter-bar { margin: 0; }
@media (hover: hover) { .theme-surfaces .filter-bar .button[aria-pressed="true"]:hover:not(:disabled) { color: var(--ink); background: var(--surface); border-color: var(--border); } }
/* A filter of one choice: a segmented plate, the chosen segment raised. */
.filter-bar { display: inline-flex; flex-wrap: wrap; gap: 2px; max-width: 100%; margin-bottom: 18px; padding: 3px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.filter-bar .button { min-height: var(--control-sm); padding: 0 12px; color: var(--muted); background: transparent; border-color: transparent; box-shadow: none; font-size: var(--text-sm); font-weight: 500; }
@media (max-width: 1100px) { .filter-bar { flex-wrap: nowrap; overflow-x: auto; overscroll-behavior-x: contain; scrollbar-width: none; } .filter-bar .button { flex: none; } }
.filter-bar .button.primary, .filter-bar .button[aria-pressed="true"] { color: var(--ink); background: var(--surface); border-color: var(--border); box-shadow: var(--shadow-1); font-weight: 600; }
@media (hover: hover) { .filter-bar .button:hover:not(:disabled):not(.primary) { color: var(--ink); background: color-mix(in oklch, var(--surface) 55%, transparent); border-color: transparent; } .filter-bar .button.primary:hover { color: var(--ink); background: var(--surface); border-color: var(--border); } }
.pagination { display: flex; align-items: center; justify-content: space-between; gap: 12px; padding: 12px 16px; color: var(--muted); border-top: 1px solid var(--border); font-size: var(--text-sm); }
.pagination div { display: flex; align-items: center; gap: 10px; }

/* ---------------------------------------------------------------------------------------- feedback
   Status reads as a lamp and a word, never the colour alone. Quiet when all is well; the exceptions
   take a fill. */
.badge { display: inline-flex; align-items: center; gap: 6px; min-height: 22px; padding: 0 8px 0 7px; color: var(--label); background: var(--surface-subtle); border-radius: 4px; font-size: var(--text-xs); font-weight: 500; line-height: 1.2; white-space: nowrap; }
.badge::before { flex: none; width: 7px; height: 7px; content: ""; background: var(--steel-400); border-radius: var(--radius-mark); }
.badge.success { color: var(--label); background: var(--surface-subtle); }
.badge.success::before { background: var(--green-lamp); }
.badge.warning { color: var(--amber); background: var(--amber-soft); }
.badge.warning::before { background: var(--amber-lamp); }
.badge.danger { color: var(--red); background: var(--red-soft); }
.badge.danger::before { background: var(--red-lamp); }
/* Optional and not done: a todo in a calm voice, never the lamp (Task 5C). */
.badge.optional { color: var(--label); background: transparent; box-shadow: inset 0 0 0 1px var(--input-border); }
.badge.optional::before { background: transparent; box-shadow: inset 0 0 0 1.5px var(--steel-400); }
.badge.neutral { color: var(--label); background: var(--surface-subtle); }
.badge.info { color: var(--label); background: var(--surface-subtle); }
.badge.info::before { background: var(--steel-500); }
.badge .icon { width: 13px; height: 13px; margin-left: -1px; }
.badge.gift-line::before { display: none; }
/* In a table a state is one plate on one line (a two-line «Готове до / видачі» reads as two things);
   a column too narrow for it widens, and the table scrolls. */
td .badge { white-space: nowrap; }
.version { padding: 2px 7px; color: var(--muted); background: var(--surface-subtle); border-radius: 4px; font-family: var(--font-mono); font-size: 11px; }

.alert { display: grid; gap: 2px; margin-bottom: 18px; padding: 12px 14px; color: var(--ink); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); line-height: 1.45; }
.alert strong { display: block; font-weight: 600; }
/* A key inside an alert keeps its own width instead of stretching across the page. */
.alert > :is(a.button, button.button, .button) { justify-self: start; margin-top: 6px; }
.alert small { display: block; margin-top: 2px; color: var(--muted); }
.alert.error, .alert.danger { background: var(--red-soft); border-color: var(--red-line); }
.alert.error strong, .alert.danger strong { color: var(--red); }
.alert.success { background: var(--green-soft); border-color: var(--green-line); }
.alert.success strong { color: var(--green); }
.alert.warning { background: var(--amber-soft); border-color: var(--amber-line); }
.alert.warning strong { color: var(--amber); }
.alert.info { background: var(--surface-subtle); }
.alert.compact { padding: 8px 11px; font-size: var(--text-sm); }
.alert ul { margin: 4px 0 0; padding-left: 18px; }
/* One problem is a sentence, not a list of one. */
.alert ul:has(> li:only-child) { padding-left: 0; list-style: none; }
/* A page-level alert while a dialog is open: the backdrop dims the page, so the error rendered in
   normal flow would be invisible exactly when it matters most. */
.alert.floating { position: fixed; top: 18px; left: 50%; z-index: var(--z-toast); width: min(680px, calc(100vw - 40px)); transform: translateX(-50%); box-shadow: var(--shadow-2); }
.conflict-alert { grid-template-columns: auto 1fr; }
.alert-actions { grid-column: 2; display: flex; gap: 8px; margin-top: 8px; }
.error-panel .alert { margin-bottom: 0; }
.error-copy { color: var(--muted); font-size: var(--text-xs); }
.alert small code { display: inline-block; max-width: 100%; overflow-wrap: anywhere; vertical-align: bottom; user-select: all; }

.toast { position: fixed; right: 24px; bottom: 24px; z-index: var(--z-toast); max-width: min(440px, calc(100vw - 32px)); padding: 11px 16px; color: var(--steel-0); background: var(--steel-900); border-radius: var(--radius-surface); box-shadow: var(--shadow-2); font-weight: 500; transition: opacity 180ms ease, transform 180ms var(--ease-out); }
@starting-style { .toast { opacity: 0; transform: translateY(8px); } }
:root[data-theme="dark"] .toast { color: var(--steel-900); background: var(--steel-100); }
/* A copy the browser refused is said in the same place a successful one is, in the lamp's colour. */
.toast.warning { color: var(--amber); background: var(--amber-soft); border: 1px solid var(--amber-line); }

.loading-state { display: flex; align-items: center; justify-content: center; gap: 10px; min-height: 220px; color: var(--muted); }
.page-loading { min-height: 55vh; }
.spinner { flex: none; width: 16px; height: 16px; border: 2px solid color-mix(in oklch, currentColor 30%, transparent); border-top-color: currentColor; border-radius: 50%; animation: spin .7s linear infinite; }
.spinner.dark { color: var(--ink); }
@keyframes spin { to { transform: rotate(360deg); } }
.skeleton-card, .skeleton-panel, .skeleton-row { overflow: hidden; position: relative; }
.skeleton-panel { min-height: 260px; }
.skeleton-line { display: block; width: 100%; height: 12px; margin: 6px 0; background: linear-gradient(90deg, var(--surface-subtle) 25%, var(--border) 50%, var(--surface-subtle) 75%); background-size: 200% 100%; border-radius: 3px; animation: shimmer 1.4s ease-in-out infinite; }
.skeleton-line.short { width: 45%; }
.skeleton-line.title { width: 280px; height: 26px; margin-bottom: 22px; }
.skeleton-row td { height: 52px; }
@keyframes shimmer { to { background-position: -200% 0; } }
.empty-state { display: grid; justify-items: center; gap: 4px; padding: 72px 24px; text-align: center; }
.empty-state.compact { padding: 40px 20px; }
.empty-state h1, .empty-state h2 { margin-bottom: 4px; font-size: var(--text-xl); }
.empty-state p { max-width: 460px; margin-bottom: 8px; }
.empty-icon { display: grid; place-items: center; min-width: 44px; height: 44px; margin-bottom: 12px; padding: 0 10px; color: var(--muted); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-large); font-weight: 600; }
.empty-icon .icon { width: 22px; height: 22px; }
.success-icon { color: var(--green); background: var(--green-soft); border-color: var(--green-line); }
.success-screen { display: grid; justify-items: center; padding: 52px 24px; text-align: center; }
.success-mark { display: grid; place-items: center; width: 52px; height: 52px; margin-bottom: 15px; color: var(--steel-0); background: var(--green-lamp); border-radius: var(--radius-large); font-size: 24px; }
.success-mark .icon { width: 26px; height: 26px; }
.success-actions { display: flex; justify-content: center; gap: 8px; flex-wrap: wrap; margin-top: 12px; }
.dirty-indicator { display: inline-flex; align-items: center; gap: 6px; color: var(--amber); font-size: var(--text-xs); font-weight: 600; }
.dirty-indicator::before { width: 7px; height: 7px; content: ""; background: var(--amber-lamp); border-radius: var(--radius-mark); }
.rate-limit { margin: 0; color: var(--amber); font-size: var(--text-sm); text-align: center; }
.retry-button { margin-bottom: 14px; }

/* ---------------------------------------------------------------------------------------- surfaces
   A work surface is white on the steel ground, edged by a hairline. No shadow: a panel sits on the
   bench, it does not float over it. Inside a panel there are rules, never another card. */
.panel { margin-bottom: var(--space-5); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.toolbar-panel { padding: 16px 20px; }
.tenant-toolbar .select-field select { min-width: 128px; }
.tenant-toolbar > .button.tertiary { margin-left: auto; }
.toolbar-panel > .saved-view-picker { margin-top: var(--space-3); padding-top: var(--space-3); border-top: 1px solid var(--line-soft); }
.toolbar { display: flex; align-items: flex-end; gap: 10px; }
.tenant-toolbar { flex-wrap: wrap; }
.tenant-toolbar .search-box { flex-basis: 280px; }
.audit-toolbar { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)) auto; align-items: end; gap: 12px; }
.audit-toolbar > .field, .audit-toolbar > .select-field { min-width: 0; }
.audit-toolbar .select-field select { width: 100%; min-width: 0; }
.toolbar-actions { display: flex; gap: 8px; }
@media (max-width: 1280px) { .audit-toolbar { grid-template-columns: repeat(2, minmax(0, 1fr)); } .audit-toolbar > .toolbar-actions { grid-column: 1 / -1; } }
@media (width <= 760px) { .audit-toolbar { grid-template-columns: minmax(0, 1fr); } }
.filter-bar.audit-presets { flex-wrap: wrap; overflow-x: visible; margin-bottom: 12px; }
.code-subline { padding: 0; color: var(--muted); background: none; border: 0; font-size: 11px; }
.audit-table { min-width: 980px; }
.audit-table td > strong { white-space: nowrap; }
.page-size select { min-width: 78px; }
.toolbar-meta { display: flex; align-items: center; justify-content: space-between; gap: 18px; margin-top: 8px; color: var(--muted); font-size: var(--text-xs); }
.section-heading { display: flex; flex-wrap: wrap; align-items: flex-start; justify-content: space-between; gap: 12px 16px; padding: 16px 20px 12px; }
.section-heading > div { min-width: 0; }
/* A heading with no hint lines its actions up with the title's centre. */
.section-heading:not(:has(> div:first-child > p, > div:first-child > small)) { align-items: center; }
/* The title takes the row; its actions keep their size and, when there is no room beside it, go under it. */
.section-heading > div:first-child { flex: 1 1 240px; }
/* An action group never shrinks below its keys: without room it goes under the title (and wraps its keys). */
.section-heading > :not(:first-child) { flex: 0 0 auto; max-width: 100%; }
.section-heading > .row-actions, .section-heading > .page-actions { flex-wrap: wrap; align-items: center; justify-content: flex-end; }
.section-heading h2 { margin-bottom: 2px; }
.section-heading p { max-width: 72ch; margin-bottom: 0; font-size: var(--text-sm); }
.section-heading.padded { padding-bottom: 16px; }
.subsection { margin: 20px 20px 0; padding-top: 16px; border-top: 1px solid var(--border); }
.subsection .form-grid { padding: 0; }
/* An item a launch action scrolled to is outlined for a moment, so the eye lands where the fix is. */
.panel.focused { outline: 2px solid var(--ink); outline-offset: 2px; transition: outline-color 1.5s ease-in; }
.hint { color: var(--muted); font-size: var(--text-sm); }
/* Blocks placed straight in a panel keep the panel's 20 px inset like its headings and fields do. */
.panel > .alert, .panel.form-section > .alert { margin: 0 20px 16px; }
.panel > :is(.toggle-field, p.muted, p.hint):not(.padded-hint) { margin-inline: 20px; }
.padded-hint { margin-bottom: 0; padding: 10px 20px 0; }

/* ------------------------------------------------------------------------------------------ tables
   Fixed columns; a row restyles in place when its state changes. Headings are sentence-case plates. */
.table-panel { overflow: hidden; }
.table-scroll { overflow-x: auto; }
/* A table in a panel starts and ends on the panel's 20 px inset, in line with its heading. */
@media (min-width: 761px) {
    .panel > .table-scroll :is(th, td):first-child, .panel > table :is(th, td):first-child { padding-left: 20px; }
    .panel > .table-scroll :is(th, td):last-child, .panel > table :is(th, td):last-child { padding-right: 20px; }
}
/* A table wider than its panel says so, on every width: a soft edge on the side that has more, gone once scrolled to the end. */
.panel > .table-scroll { background: linear-gradient(to left, var(--surface) 40%, transparent) right / 28px 100% no-repeat local, linear-gradient(to left, oklch(21.5% 0.008 95 / .10), transparent) right / 14px 100% no-repeat scroll; }
table { width: 100%; border-collapse: collapse; }
th { position: sticky; top: 0; z-index: 1; padding: 9px 14px; color: var(--muted); background: var(--surface); border-bottom: 1px solid var(--border); font-size: var(--text-xs); font-weight: 600; text-align: left; white-space: nowrap; }
td { padding: 11px 14px; border-bottom: 1px solid var(--line-soft); vertical-align: middle; }
tbody tr:last-child td { border-bottom: 0; }
tbody tr { transition: background-color 120ms ease; }
tbody tr:hover td { background: var(--surface-hover); }
tr.selected td, tr.selected:hover td { background: var(--surface-accent); }
tr.faded td { opacity: .55; }
.tenant-name { color: var(--ink); font-weight: 600; }
/* An identifier in a row's second line is for copying, not reading: it may be cut short so the row keeps its width. */
.subline { display: block; max-width: 320px; margin-top: 2px; overflow: hidden; color: var(--muted); font-size: var(--text-xs); text-overflow: ellipsis; white-space: nowrap; }
.subline .copy-inline { max-width: 150px; }
.row-action { font-weight: 600; white-space: nowrap; }
a.row-action:not(.button) { text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 35%, transparent); text-underline-offset: 3px; }
a.row-action:not(.button):hover { text-decoration-color: currentColor; }
.summary-cell { max-width: 280px; color: var(--muted); }
.num { text-align: right !important; font-variant-numeric: tabular-nums; white-space: nowrap; }
.compact-table td { padding: 9px 10px; }
.compact-table th { padding: 8px 10px; }
.compact-table .subline { max-width: 230px; }
.compact-table .subline .copy-inline { max-width: 105px; }
.row-action-icon { padding-inline: 7px; font-size: 15px; line-height: 1; }
.row-actions { display: flex; gap: 8px; }
/* The actions column is as narrow as its keys and sits at the table's right edge. */
td.row-actions { display: table-cell; width: 1%; text-align: right; white-space: nowrap; }
td.row-actions > * + * { margin-left: 8px; }
/* A list wider than the screen keeps its actions in view: the last column pins to the right edge and the rest scrolls under it. */
.pinned-actions th:last-child, .pinned-actions td:last-child { position: sticky; right: 0; z-index: 1; background: var(--surface); box-shadow: -1px 0 0 var(--border); }
.pinned-actions th:last-child { z-index: 2; }
.pinned-actions tbody tr:hover td:last-child { background: var(--surface-hover); }
.tenant-table td.tenant-cell { min-width: 240px; }
.tenant-table td.launch-cell { min-width: 170px; }
/* Narrower than the whole list: the columns the tenant's own page carries (catalogue, manifest, last change) step back,
   so what an operator scans — who, whether it is on, how it pays, whether it can launch — stays whole beside its keys. */
@media (max-width: 1599px) { .tenant-table :is(th, td):is(.col-catalog, .col-manifest, .col-updated) { display: none; } .tenant-table td.tenant-cell { min-width: 220px; } }
@media (max-width: 1100px) {
    .tenant-table thead { display: none; }
    .tenant-table, .tenant-table tbody { display: block; }
    .tenant-table tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 6px 12px; padding: 12px 16px; border-bottom: 1px solid var(--line-soft); }
    .tenant-table td { display: block; padding: 0; border: 0; }
    .tenant-table td:not(.tenant-cell, .status-cell, .launch-cell, .actions-cell) { display: none; }
    .tenant-table td.tenant-cell { grid-column: 1; grid-row: 1; min-width: 0; }
    .tenant-table td.status-cell { grid-column: 1; grid-row: 2; }
    .tenant-table td.launch-cell { grid-column: 1; grid-row: 3; min-width: 0; }
    .tenant-table td.actions-cell { grid-column: 2; grid-row: 1 / span 3; align-self: center; position: static; background: transparent; box-shadow: none; }
    .panel > .table-scroll > .tenant-table td:is(:first-child, :last-child) { padding: 0; }
    .tenant-table tbody tr:hover :is(td, td:last-child) { background: none; }
    .tenant-table tbody tr:hover { background: var(--surface-hover); }
}
.table-toolbar { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 10px 12px; border-bottom: 1px solid var(--border); }
.table-toolbar input[type="search"] { max-width: 320px; }
.table-summary { margin: 0; padding: 10px 14px; color: var(--muted); font-size: var(--text-xs); border-top: 1px solid var(--border); }
.data-table td, .data-table th { padding-inline: 12px; }
.plain-list { margin: 0; padding: 0; list-style: none; }
:root[data-density="compact"] td { padding-block: 7px; }
:root[data-density="compact"] th { padding-block: 7px; }
:root[data-density="compact"] .metric { padding: 12px 14px; }

/* -------------------------------------------------------------------------------------- figures
   The quiet facts: one strip, divided by hairlines, figures on the grid. */
.metric-grid { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 0; margin-bottom: var(--space-5); overflow: hidden; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
/* The last figure is the launch state, a phrase rather than a number: its column takes what the phrase needs. */
@media (min-width: 1200px) { .metric-grid.five { grid-template-columns: repeat(4, minmax(0, 1fr)) minmax(max-content, 1.25fr); } .metric-grid.five > :last-child .badge { white-space: nowrap; } }
@media (max-width: 1100px) { .metric-grid.five { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
@media (min-width: 761px) and (max-width: 1199px) { .metric-grid.five:has(> :nth-child(5)) { grid-template-columns: repeat(6, minmax(0, 1fr)); } .metric-grid.five:has(> :nth-child(5)) > * { grid-column: span 2; } .metric-grid.five:has(> :nth-child(5)) > :nth-child(n+4) { grid-column: span 3; } }
@media (width <= 760px) { .metric-grid.five > :last-child:nth-child(odd) { grid-column: 1 / -1; } }
/* Every figure draws its own right and bottom rule; the panel's edge clips the ones on the outside. */
.metric { min-width: 0; container-type: inline-size; padding: 16px 18px; color: var(--ink); background: var(--surface); box-shadow: 1px 0 0 var(--line-soft), 0 1px 0 var(--line-soft); }
.metric span, .metric small { display: block; color: var(--muted); font-size: var(--text-xs); }
.metric strong { display: block; margin: 4px 0 2px; overflow: hidden; color: var(--ink); font-family: var(--font-figures); font-size: 24px; font-weight: 600; letter-spacing: -0.01em; line-height: 1.15; text-overflow: ellipsis; white-space: nowrap; font-variant-numeric: tabular-nums; }
.metric .badge { display: inline-flex; width: fit-content; max-width: 100%; white-space: normal; line-height: 1.3; text-align: left; }
a.metric { text-decoration: none; }
.metric-link { display: block; transition: background-color 120ms ease; }
.metric-link:hover { color: var(--ink); background: var(--surface-hover); }
.metric-grid.mini { grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); margin: 16px 0; }
.panel > .section-heading + .metric-grid.mini { margin-top: 0; }
.panel > .metric-grid.mini:last-child { margin-bottom: 0; border-bottom: 0; }
.metric strong.metric-na { color: var(--muted); font-family: var(--font-ui); font-size: var(--text-md); font-weight: 500; }
/* A state in a figure's place is a lamp and a word, set at body size (cc-07). */
.metric strong:has(> .badge) { overflow: visible; font-family: var(--font-ui); font-size: var(--text-md); font-weight: 500; white-space: normal; }
.metric-grid.three { grid-template-columns: repeat(3, minmax(0, 1fr)); }
/* A phone: the debt, which can be several currencies, gets the whole row; the two counts share the next. */
@media (width <= 760px) { .metric-grid.three { grid-template-columns: repeat(2, minmax(0, 1fr)); } .metric-grid.three > :first-child { grid-column: 1 / -1; } }
/* A figure per currency: the lines of one metric stack without the figure's own top gap. */
.metric strong + strong { margin-top: 0; }
@container (max-width: 240px) { .metric strong { font-size: clamp(17px, 10cqi, 24px); } }
/* Inside a panel the figures are a ruled strip across it, never a box in a box. */
.panel .metric-grid { border-width: 1px 0; border-radius: 0; }
.dashboard-metrics { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.dashboard-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-5); margin-bottom: var(--space-5); }
@media (max-width: 1100px) { .dashboard-grid { grid-template-columns: minmax(0, 1fr); } }
.dashboard-grid > .panel { margin-bottom: 0; }
div.detail-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-5); }
div.detail-grid > .panel { margin-bottom: 0; }
@media (max-width: 1279px) { div.detail-grid { grid-template-columns: minmax(0, 1fr); } .detail-tabs { gap: 18px; } }
@media (max-width: 900px) { .platform-shell .detail-tabs { position: static; } }
/* The facts of one record: the name, then its value, on two columns that line up. */
dl.detail-grid { display: grid; grid-template-columns: max-content minmax(0, 1fr); gap: 6px 18px; margin: 0 0 16px; }
dl.detail-grid dt { color: var(--muted); font-size: var(--text-sm); }
dl.detail-grid dd { margin: 0; min-width: 0; overflow-wrap: anywhere; }
.definition-list { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 24px; margin: 0; padding: 0 20px 16px; }
.definition-list div { min-width: 0; padding: 10px 0; border-bottom: 1px solid var(--line-soft); }
.definition-list dt { color: var(--muted); font-size: var(--text-xs); }
.definition-list dd { margin: 2px 0 0; overflow-wrap: anywhere; font-weight: 500; }
/* An unset value never reads like a value. */
.not-set { color: var(--subtle); font-weight: 400; }
#tenant-features > .flag-row { display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); gap: 0 24px; padding: 4px 20px 0; }
#tenant-features > .flag-row > .toggle { align-items: center; min-height: 40px; border-bottom: 1px solid var(--line-soft); }
#integration-readiness td:last-child { color: var(--muted); font-size: var(--text-sm); }
.launch-requirement { color: var(--muted); font-size: var(--text-xs); font-weight: 500; }
/* An inline editor's keys stand clear of its panel's edge; its fields stop at a readable width. */
.panel > form:last-child > fieldset:last-child > .form-actions:last-child { padding-bottom: 20px; }
.edit-panel .form-grid, .edit-panel .form-actions { max-width: 1040px; }
/* The JSON section opens like a section, with its own key. */
.form-actions + .json-details { margin: 16px 20px 20px; }
.json-details > summary { display: inline-flex; align-items: center; gap: 6px; list-style: none; }
.json-details > summary::-webkit-details-marker { display: none; }
.json-details > summary .icon { transition: transform 150ms var(--ease-out); }
.json-details[open] > summary .icon { transform: rotate(90deg); }
.json-details > .json-view { margin-top: 10px; }
/* Name and state stay close (columns of 260-370 px, as many as fit); the bottom row draws no rule of its own
   (the clip takes the last pixel of the box, so the space under it is a margin); a form section pads its own foot. */
.flag-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(260px, 1fr)); gap: 0 32px; margin-bottom: 16px; padding: 0 20px; clip-path: inset(0 0 1px 0); }
.form-section > .flag-grid:last-child { margin-bottom: 0; }
.flag-grid div { display: grid; grid-template-columns: 8px minmax(0, 1fr) auto; align-items: center; gap: 8px; padding: 9px 0; border-bottom: 1px solid var(--line-soft); }
.flag-grid strong { color: var(--muted); font-size: var(--text-xs); font-weight: 500; }
.manifest-list, .review-list { padding: 0 20px 16px; }
.manifest-list div, .review-list div { display: flex; justify-content: space-between; gap: 16px; padding: 9px 0; border-bottom: 1px solid var(--line-soft); }
.manifest-list span, .review-list span { color: var(--muted); }
.manifest-list span { font-family: var(--font-mono); font-size: var(--text-sm); }
.policy { display: grid; gap: 2px; padding: 9px 0; border-top: 1px solid var(--line-soft); }
.policy span { color: var(--muted); font-size: var(--text-xs); }
/* Objects of the same kind side by side (branches). Inside a panel they are outlined, not raised. */
.card-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(270px, 1fr)); gap: 12px; padding: 0 20px 20px; }
.card-grid.bare { margin-bottom: var(--space-5); padding: 0; }
.branch-card { display: grid; align-content: start; gap: 12px; padding: 20px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
/* Inside a panel the branches are rows under hairlines, never cards in a card. */
.panel .card-grid { gap: 0 24px; }
.panel .branch-card { padding: 14px 0; background: transparent; border: 0; border-top: 1px solid var(--line-soft); border-radius: 0; }
.branch-card h2 { margin-bottom: 0; font-size: var(--text-lg); }
.branch-card p { margin: 0; }
.branch-card > small { color: var(--muted); }
.dense-cards .branch-card { min-height: 200px; }
/* A branch keeps one card size however many branches there are: empty tracks stay, cards are panels 20 px apart. */
.branch-grid { grid-template-columns: repeat(auto-fill, minmax(min(340px, 100%), 1fr)); gap: 20px; padding: 0; }
.branch-card > .row-actions { margin-top: 4px; }
/* The facts read as one row from the left, each as wide as its words (not two half-card columns); a narrow card wraps them. */
.branch-facts { display: flex; flex-wrap: wrap; gap: 8px 32px; margin: 0; }
.branch-facts dt { color: var(--muted); font-size: var(--text-xs); }
.branch-facts dd { margin: 0; font-size: var(--text-sm); font-weight: 600; }
/* NAV-1: what belongs to a branch, on its own card — rows on the card's hairlines, not a box in a box.
   Each opens the screen on this branch only. */
.branch-parts { margin: 0; padding: 0; list-style: none; border-top: 1px solid var(--line-soft); }
.branch-parts > li { border-bottom: 1px solid var(--line-soft); }
.branch-parts a { display: grid; grid-template-columns: auto minmax(0, 1fr) auto auto; align-items: center; gap: 10px; min-height: 44px; margin-inline: -8px; padding: 6px 8px; color: var(--ink); font-size: var(--text-md); font-weight: 500; text-decoration: none; border-radius: var(--radius-control); transition: background-color 120ms ease; -webkit-tap-highlight-color: transparent; }
.branch-parts a:hover { color: var(--ink); background: var(--surface-hover); }
.branch-parts a > .icon:first-child { width: 18px; height: 18px; color: var(--subtle); }
.branch-parts a > .nav-row-go { width: 14px; height: 14px; color: var(--subtle); }
.branch-parts small { color: var(--muted); font-size: var(--text-sm); font-variant-numeric: tabular-nums; text-align: right; }
/* The screen is showing one branch: which, the way back, and the way to all of them. */
.branch-scope { display: grid; gap: 2px; margin-bottom: var(--space-4); }
.branch-scope > .back-link { justify-self: start; margin-bottom: 6px; }
.scope-note { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 14px; margin: 0; padding: 8px 12px; color: var(--label); background: var(--surface-subtle); border-radius: var(--radius-control); font-size: var(--text-sm); }
.scope-note strong { color: var(--ink); font-weight: 600; }
.scope-note a { color: var(--ink); font-weight: 500; text-underline-offset: 3px; }
/* The branch editor: the coordinates are one pair with one hint under both; the switches are a grid of their own. */
.coordinate-pair { display: grid; align-content: start; gap: 6px; }
.cabinet-dialog .coordinate-pair > .form-grid { padding: 0; }
.branch-switches > .field > .toggle-field { padding-block: 0; }
.activity-list article { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; align-items: center; gap: 12px; padding: 12px 20px; border-top: 1px solid var(--line-soft); }
.activity-list article > div { min-width: 0; display: grid; }
.activity-list article > div span { color: var(--muted); font-size: var(--text-xs); }
.activity-list article > div strong { overflow-wrap: anywhere; }
.diagnostics-strip { display: grid; grid-template-columns: 1.4fr repeat(3, 1fr) auto; align-items: center; gap: 22px; padding: 16px 20px; }
.diagnostics-strip > div { min-width: 0; display: grid; }
.diagnostics-strip > div:first-child { grid-template-columns: auto minmax(0, 1fr); align-items: center; gap: 9px; }
.diagnostics-strip > div > div { display: grid; min-width: 0; }
.diagnostics-strip span, .diagnostics-strip small { overflow: hidden; color: var(--muted); font-size: var(--text-xs); text-overflow: ellipsis; white-space: nowrap; }
.connectivity-value.connected { color: var(--green); }
.connectivity-value.degraded { color: var(--amber); }
.connectivity-value.disconnected { color: var(--red); }

/* A note inside a panel: set on the steel, no second border. */
.notice-card { margin: 0 20px 16px; padding: 12px 14px; background: var(--surface-subtle); border-radius: var(--radius-control); }
.notice-card p { margin: 3px 0 0; }
.limitation-list { display: flex; gap: 8px; padding: 0 20px 20px; flex-wrap: wrap; }
/* What the manifest will never do: a fact of the product, not a fault (CD-16). */
.limitation-list span { display: inline-flex; align-items: center; gap: 6px; padding: 3px 8px; color: var(--label); background: var(--surface-subtle); border-radius: 4px; font-size: var(--text-xs); font-weight: 600; }
.limitation-list .icon { width: 13px; height: 13px; color: var(--muted); }
.panel-subhead { margin: 4px 20px 0; padding-bottom: 6px; color: var(--muted); font-size: var(--text-xs); font-weight: 600; border-bottom: 1px solid var(--line-soft); }
details { margin: 0 20px 20px; }
summary { color: var(--ink); cursor: pointer; font-weight: 600; }
summary:hover { text-decoration: underline; text-underline-offset: 3px; }
.json-view { max-height: 350px; overflow: auto; padding: 14px; color: var(--steel-100); background: var(--steel-950); border-radius: var(--radius-control); font-family: var(--font-mono); font-size: 11px; }
.technical-wrap { font-family: var(--font-mono); font-size: 11px; }
.version-note, .support-text { color: var(--muted); font-size: var(--text-xs); }

/* Platform diagnostics and a person's settings: facts in two columns of panels. */
.diagnostic-grid, .settings-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-5); margin-bottom: var(--space-5); }
.settings-grid > * { min-width: 0; }
.diagnostic-grid > .panel, .settings-grid > .panel { margin-bottom: 0; }
.diagnostic-card { padding: 18px 20px; }
.diagnostic-card h2 { margin-bottom: 12px; }
.diagnostic-card dl { display: grid; gap: 0; margin: 0; }
.diagnostic-card dl div { display: grid; grid-template-columns: 200px minmax(0, 1fr); gap: 12px; padding: 9px 0; border-top: 1px solid var(--line-soft); }
.diagnostic-card dt { color: var(--muted); }
.diagnostic-card dd { min-width: 0; margin: 0; overflow-wrap: anywhere; }
.diagnostic-card .status-dot { margin-right: 7px; }
.diagnostic-card dd code { display: inline-block; max-width: 100%; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; vertical-align: bottom; }
@media (max-width: 1280px) { .diagnostic-grid { grid-template-columns: minmax(0, 1fr); } }
@media (width <= 760px) { .diagnostic-card dl div { grid-template-columns: minmax(0, 1fr); gap: 2px; } }
.diagnostic-actions, .danger-zone { padding-bottom: 20px; }
.diagnostic-actions .form-actions { flex-wrap: wrap; padding-top: 4px; }
.sanitized-notice { display: flex; align-items: flex-start; gap: 10px; }
.sanitized-notice > .icon { margin-top: 2px; }
.settings-section { min-height: 145px; padding: 18px 20px; }
.settings-section h2 { margin-bottom: 14px; }
.settings-fields { display: grid; gap: 14px; max-width: 440px; }
.settings-fields .selector-field, .settings-fields .select-field { display: grid; gap: 5px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.settings-fields select { width: 100%; min-width: 0; }
.settings-fields .inline-check { color: var(--ink); font-size: var(--text-md); font-weight: 500; }
.settings-actions { display: flex; gap: 8px; padding: 0 20px; flex-wrap: wrap; }

/* First steps, for a console nobody has used yet. */
.onboarding-panel { overflow: hidden; }
.onboarding-count { margin: 0 20px 6px; color: var(--muted); font-size: var(--text-xs); font-variant-numeric: tabular-nums; }
.onboarding-progress { height: 6px; margin: 0 20px 12px; overflow: hidden; background: var(--line-soft); border-radius: 3px; }
.onboarding-progress span { display: block; height: 100%; background: var(--green-lamp); border-radius: inherit; }
.onboarding-list { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 24px; margin: 0; padding: 0 20px 16px; list-style: none; }
.onboarding-list li { display: grid; grid-template-columns: 1fr auto; align-items: center; min-height: 40px; padding: 4px 0; border-bottom: 1px solid var(--line-soft); }
.onboarding-list button { display: flex; align-items: center; gap: 8px; min-height: 32px; padding: 0; color: var(--ink); background: transparent; border: 0; cursor: pointer; text-align: left; }
.onboarding-list button .icon { color: var(--subtle); }
.onboarding-list li.complete button .icon { color: var(--green); }
.onboarding-list li.complete button { color: var(--muted); text-decoration: line-through; }

/* ----------------------------------------------------------------------------- the console's tools */
.modal-backdrop { position: fixed; inset: 0; z-index: var(--z-overlay); display: grid; align-items: start; justify-items: center; padding: min(7vh, 64px) 20px 20px; background: oklch(16.5% 0.007 95 / .55); transition: opacity 180ms ease; }
@starting-style { .modal-backdrop { opacity: 0; } }
.command-palette, .shortcut-dialog { width: min(100%, 640px); overflow: hidden; background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius-large); box-shadow: var(--shadow-3); }
.palette-input { display: flex; align-items: center; gap: 10px; padding: 12px 15px; border-bottom: 1px solid var(--border); }
.palette-input input { flex: 1; min-height: 32px; padding: 0; background: transparent; border: 0; box-shadow: none; }
.palette-input input:focus { box-shadow: none; }
.palette-results { max-height: 420px; overflow-y: auto; padding: 6px; }
.palette-command { width: 100%; display: flex; align-items: center; justify-content: space-between; padding: 9px 11px; color: var(--ink); background: transparent; border: 0; border-radius: var(--radius-control); cursor: pointer; text-align: left; }
.palette-command.selected, .palette-command:hover { background: var(--surface-accent); }
.shortcut-list { display: grid; margin: 0; padding: 0 20px 20px; }
.shortcut-list div { display: grid; grid-template-columns: 120px 1fr; align-items: center; padding: 9px 0; border-top: 1px solid var(--line-soft); }
.shortcut-list dd { margin: 0; color: var(--muted); }
.saved-view-picker { display: flex; align-items: end; gap: 8px; flex-wrap: wrap; }
.saved-view-picker .select-field select { min-width: 220px; }
.saved-view-editor { display: flex; align-items: end; gap: 8px; flex: 1 0 100%; padding-top: 8px; border-top: 1px solid var(--border); }
.saved-view-editor .field { min-width: min(320px, 100%); }
.drop-zone { display: grid; place-items: center; min-height: 120px; margin: 0 20px 18px; padding: 20px; color: var(--muted); background: var(--surface-subtle); border: 1px dashed var(--input-border); border-radius: var(--radius-surface); text-align: center; transition: background-color 150ms ease, border-color 150ms ease; }
.drop-zone.dragging { color: var(--ink); background: var(--surface-accent); border-color: var(--ink); }
.import-panel .import-actions { padding-top: 0; }
.print-summary { display: none; }

/* The audit trail: a row that opens its own detail underneath, the diff read left to right. */
.expand-button { display: grid; place-items: center; width: 28px; height: 28px; padding: 0; color: var(--label); background: var(--surface); border: 1px solid var(--border); border-radius: 4px; cursor: pointer; }
.expand-button:hover { color: var(--ink); border-color: var(--input-border); }
.expand-button .icon { width: 14px; height: 14px; transition: transform 160ms var(--ease-out); }
.expand-button[aria-expanded="true"] .icon { transform: rotate(90deg); }
.audit-detail-row td { padding: 0 18px 16px; background: var(--surface-subtle); }
.audit-detail-row:hover td { background: var(--surface-subtle); }
.audit-detail { padding: 14px 0 0; }
.audit-detail dl { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 10px 16px; margin: 0 0 12px; }
.audit-detail dl div { display: grid; }
.audit-detail dt { color: var(--muted); font-size: var(--text-xs); }
.audit-detail dd { margin: 2px 0 0; overflow-wrap: anywhere; }
.diff-list { padding: 0 20px; }
.diff-row { display: grid; grid-template-columns: 130px 1fr auto 1fr; align-items: center; gap: 10px; padding: 8px 0; border-bottom: 1px solid var(--line-soft); }
.diff-row .before { color: var(--muted); text-decoration: line-through; text-decoration-color: var(--red); }
.diff-row .after { color: var(--ink); font-weight: 600; }
.diff-arrow { display: inline-flex; color: var(--subtle); }
.compact-diff { padding: 0; }
.compact-diff .diff-row { grid-template-columns: 160px 1fr auto 1fr; }
.preview-box { margin: 0 20px 20px; padding-bottom: 16px; background: var(--surface-subtle); border-radius: var(--radius-surface); }
.creation-preview { margin: 0; }

/* ------------------------------------------------------------------------------------------ dialogs
   A dialog is a sheet laid on the bench: it settles in (scale .97 → 1, 200 ms), its blocks spaced by
   one gap, its action row kept in view while the form scrolls. */
.cabinet-dialog { width: min(680px, 100%); max-height: 86vh; overflow-y: auto; display: grid; align-content: start; gap: 18px; padding: 22px 0 0; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-large); box-shadow: var(--shadow-3); overscroll-behavior: contain; transition: opacity 200ms var(--ease-out), transform 200ms var(--ease-out); }
/* One column that never grows past the dialog: a wide table or a long word inside scrolls or wraps instead of
   widening the sheet past a phone's edge (the product editor was 450 px wide on a 390 px screen). */
.cabinet-dialog { grid-template-columns: minmax(0, 1fr); }
/* The close key centres on the title's line, not on the title and its hint together. */
.cabinet-dialog > .section-heading > .icon-button, .cabinet-dialog > form > .section-heading > .icon-button { margin-block: -6px; margin-right: -8px; }
@starting-style { .cabinet-dialog { opacity: 0; transform: scale(.97) translateY(6px); } }
.cabinet-dialog > form { display: grid; gap: 18px; }
.cabinet-dialog .form-grid, .cabinet-dialog .flag-row, .cabinet-dialog .settings-actions { padding-inline: 24px; }
.cabinet-dialog .form-section { display: grid; gap: 12px; padding-bottom: 0; }
.cabinet-dialog .form-section > .section-heading { padding-bottom: 0; }
/* A section of a dialog is headed like a section (16 px), so it never reads as one more field label. */
.cabinet-dialog .form-section > .section-heading h3 { margin: 0; font-size: var(--text-lg); font-weight: 600; }
.cabinet-dialog .form-section + .form-section { padding-top: 18px; border-top: 1px solid var(--line-soft); }
.cabinet-dialog .toggle { color: var(--ink); font-size: var(--text-md); }
.cabinet-dialog .flag-row { gap: 10px 18px; }
.cabinet-dialog .form-grid > p.muted { margin: 0; }
.cabinet-dialog > .form-actions:last-child, .cabinet-dialog > form > .form-actions:last-child { position: sticky; bottom: 0; z-index: 2; margin-top: 4px; padding: 14px 24px 16px; flex-wrap: wrap; justify-content: flex-end; background: var(--surface); border-top: 1px solid var(--border); border-radius: 0 0 var(--radius-large) var(--radius-large); }
.cabinet-dialog > :last-child:not(.form-actions) { padding-bottom: 22px; }
.cabinet-dialog.wide { width: min(920px, 100%); }
.cabinet-dialog .section-heading { padding: 0 24px; }
/* Anything else a dialog holds directly keeps the dialog's inset (a fieldset, a field, a note, a list of facts). */
.cabinet-dialog > :is(p, .field, fieldset:not(.dialog-group), .toggle-field, .notice-card) { margin-inline: 24px; }
.cabinet-dialog > p { margin-block: 0; }
.cabinet-dialog > .definition-list { padding-inline: 24px; }
.cabinet-dialog > .section-heading h2 { margin: 0; font-size: var(--text-xl); }
.cabinet-dialog table { width: 100%; }
.cabinet-dialog .server-side { display: grid; gap: 10px; margin: 0 24px; padding: 14px; border: 1px solid var(--border); border-radius: var(--radius-surface); background: var(--surface-subtle); }
.cabinet-dialog .server-side legend { display: flex; align-items: center; gap: 8px; padding: 0 6px; color: var(--label); font-size: var(--text-xs); font-weight: 600; }
.cabinet-dialog .server-side p { margin: 0; font-size: var(--text-sm); }
.cabinet-dialog .alert { margin: 0 24px; padding: 12px 16px; font-size: var(--text-sm); }
.cabinet-dialog .form-section > p.validation-message { margin: 6px 24px 0; }
@media (width <= 760px) { .cabinet-dialog .form-section > p.validation-message { margin-inline: 16px; } }
.cabinet-dialog .alert ul { margin: 0; padding-left: 18px; }
.cabinet-dialog .form-section > p.hint { margin: 0 24px; color: var(--muted); font-size: var(--text-sm); }
.cabinet-dialog .form-section > p.hint a, .cabinet-dialog .form-section > .alert a { margin-left: 6px; font-weight: 600; }
.cabinet-dialog .form-section > .alert.warning { margin: 0 24px; }
/* A table in a dialog keeps the dialog's gutter, its first and last columns in line with the fields above. */
.cabinet-dialog .table-scroll { margin-inline: 24px; }
.cabinet-dialog .table-scroll :is(th, td):first-child { padding-left: 0; }
.cabinet-dialog .table-scroll :is(th, td):last-child { padding-right: 0; }
/* The step with no way back stands apart from Save and Cancel: at the footer's other end. */
.cabinet-dialog .form-actions > :is(.danger-ghost, .button.destructive:not(.solid)) { order: -1; margin-right: auto; }
/* A question before a step with no way back: the facts between the question and the buttons. */
.confirm-dialog { width: min(520px, 100%); }
.confirm-dialog .confirm-facts { margin: 0 24px; }
.confirm-dialog .form-actions { justify-content: flex-end; }
/* POSTER-6: moving to another Poster account - the two accounts, then what moving does, then the one choice. */
.poster-account-change-facts { display: grid; gap: 10px; }
.poster-account-change-line { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 10px; margin: 0; overflow-wrap: anywhere; }
.poster-account-change-line small { color: var(--muted); font-size: var(--text-sm); }
.poster-account-change-effects { margin: 0; padding-left: 20px; color: var(--label); line-height: 1.5; }
.poster-account-change-effects li + li { margin-top: 4px; }
.poster-account-change-facts .hint { margin: 0; }
.poster-summary > span { display: block; margin-top: 2px; color: var(--label); font-size: var(--text-sm); font-weight: 400; }
/* A group of related controls in a dialog: the legend set as a field label, the rows under hairlines, the total last. */
.cabinet-dialog > fieldset.dialog-group { display: grid; gap: 0; margin: 0 24px; }
.dialog-group > legend { margin-bottom: 6px; padding: 0; color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
.plan-product { display: flex; align-items: center; justify-content: space-between; gap: 16px; min-height: calc(var(--control-md) + 12px); padding: 6px 0; border-bottom: 1px solid var(--line-soft); }
.plan-product .switch { color: var(--ink); font-size: var(--text-md); }
.money-input { display: inline-flex; align-items: center; gap: 8px; }
.money-input input { width: 120px; text-align: right; font-variant-numeric: tabular-nums; }
.money-input > span { min-width: 3ch; color: var(--muted); font-size: var(--text-sm); font-weight: 500; }
.dialog-total { display: flex; align-items: baseline; justify-content: space-between; gap: 12px; margin: 10px 0 0; color: var(--label); font-size: var(--text-sm); }
.dialog-total strong { color: var(--ink); font-size: var(--text-md); font-variant-numeric: tabular-nums; white-space: nowrap; }
/* The tenant takes the row; its three-letter currency sits beside it. */
.form-grid.tenant-currency { grid-template-columns: minmax(0, 1fr) 112px; }

/* ------------------------------------------------------------------------------------------- forms
   Label above, help under it, the error under that; sections divided by a rule, never boxed. */
.form-section { padding-bottom: 20px; }
.form-grid { display: grid; gap: 16px; padding: 0 20px; }
.form-grid.two { grid-template-columns: repeat(2, minmax(0, 1fr)); }
.form-grid.three { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.form-grid.four { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.form-grid > * { min-width: 0; }
/* A single column of fields in a wide panel stops at a readable width instead of running 1400 px. */
.panel .form-grid:not(.two, .three, .four) > .field { max-width: 720px; }
.span-two { grid-column: span 2; }
.span-three { grid-column: span 3; }
.field > small { line-height: 1.45; }
/* A switch that stands in a column of fields sits on the line of the controls beside it, not on the line of their labels. */
.form-grid.three > .field > .toggle:first-child, .form-grid.four > .field > .toggle:first-child { min-height: var(--control-md); margin-top: 22px; }
.form-grid.three > .field.span-three > .toggle:first-child, .form-grid.four > .field.span-three > .toggle:first-child { min-height: 0; margin-top: 0; }
.form-grid > .field > p.hint:only-child { max-width: 72ch; margin: var(--space-2) 0 calc(-1 * var(--space-2)); }
.field select { font: inherit; }
.form-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; padding: 20px 20px 0; }
/* Last in a panel, the keys stand clear of its edge. */
.panel:not(.form-section) > .form-actions:last-child, .panel:not(.form-section) > form:last-child > .form-actions:last-child, .panel:not(.form-section) > .section-body:last-child > .form-actions:last-child { padding-bottom: 20px; }
/* A quiet key that opens a row lines its word up with the text above it; its hover plate reaches out. */
:is(.settings-actions, .panel .form-actions, .form-section > .form-actions) > .button.tertiary:first-child { margin-left: -14px; }
/* On a phone these rows wrap, so a quiet key often starts a line of its own: its words line up with the edge, not its plate. */
@media (width <= 760px) { :is(.diagnostic-actions .form-actions, .saved-view-picker, .import-actions) > .button.tertiary { margin-left: -14px; } }
/* A panel that is saved on its own answers underneath its own button. */
.section-status { padding: 14px 20px 0; }
.section-status .alert { margin-bottom: 0; }
.section-status .alert + .alert { margin-top: 10px; }
.edit-panel { border-color: var(--input-border); }
.localized-field { display: grid; gap: 12px 16px; }
.localized-label { color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.localized-field .field label { color: var(--muted); font-size: var(--text-xs); font-weight: 500; }
.flag-row { display: flex; flex-wrap: wrap; gap: 10px 20px; padding: 0 20px; }
.reason-field { margin: 18px 20px 0; }
.confirmation-check { display: flex; align-items: flex-start; gap: 10px; margin: 14px 20px 0; padding: 12px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-control); cursor: pointer; }
.confirmation-check input { width: 18px; height: 18px; accent-color: var(--action); }
.validation-summary { grid-template-columns: auto 1fr; column-gap: var(--space-4); }
.validation-summary div { display: grid; gap: 4px; }
.validation-summary button { padding: 0; color: var(--red); background: none; border: 0; cursor: pointer; text-align: left; text-decoration: underline; text-underline-offset: 3px; }
.validation-summary button { min-height: 24px; }
@media (width <= 760px) { .alert.validation-summary { grid-template-columns: 1fr; } }

/* The creation wizard: numbered steps on one hairline; the current one in ink, a done one ticked. */
.wizard-steps { position: relative; display: flex; gap: 2px; margin-bottom: 18px; overflow-x: auto; border-bottom: 1px solid var(--border); scrollbar-width: thin; }
.wizard-steps > span { flex: 1; padding: 8px 10px; color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
.wizard-steps > span.active { color: var(--ink); box-shadow: inset 0 -2px 0 var(--ink); }
.wizard-steps button { display: flex; flex: 0 0 auto; align-items: center; gap: 8px; min-width: 0; padding: 10px 10px 11px; color: var(--muted); background: transparent; border: 0; cursor: pointer; font-size: var(--text-xs); font-weight: 600; white-space: nowrap; }
.wizard-steps button .step-key { display: grid; place-items: center; flex: none; width: 20px; height: 20px; padding: 0; color: var(--muted); background: var(--surface); border: 1px solid var(--input-border); border-radius: 4px; font-size: 11px; }
.wizard-steps button:hover:not(:disabled) { color: var(--ink); }
.wizard-steps button.active { color: var(--ink); box-shadow: inset 0 -2px 0 var(--ink); }
.wizard-steps button.active .step-key { color: var(--on-action); background: var(--action); border-color: var(--action); }
.wizard-steps button.complete { color: var(--label); }
.wizard-steps button.complete .step-key { color: var(--steel-0); background: var(--green-lamp); border-color: var(--green-lamp); }
.wizard-steps button:disabled { cursor: not-allowed; opacity: .6; }
@media (max-width: 1599px) { .wizard-steps button:not(.active) .step-name { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; } }
.step-number { display: inline-grid; place-items: center; float: left; width: 26px; height: 26px; margin-right: 10px; color: var(--ink); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: 4px; font-size: 11px; font-weight: 700; }
.wizard-footer { position: sticky; bottom: 12px; z-index: 3; display: flex; align-items: center; justify-content: space-between; gap: 14px; margin-top: 18px; padding: 12px 14px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); box-shadow: var(--shadow-2); }
.wizard-footer span { color: var(--muted); font-size: var(--text-xs); }
.template-bar { display: grid; grid-template-columns: auto minmax(160px, 240px) auto; justify-content: start; align-items: center; gap: 12px 16px; padding: 14px 20px; }
@media (max-width: 1100px) { .template-bar { grid-template-columns: minmax(0, 1fr) auto; } .template-bar > div { grid-column: 1 / -1; } }
.template-bar > div { display: grid; }
.template-bar span { color: var(--muted); font-size: var(--text-xs); }

/* The hours editor: one week, one row a day, the times on a grid. */
.schedule-grid { margin: 0 20px 20px; overflow: hidden; border: 1px solid var(--border); border-radius: var(--radius-surface); }
.schedule-head, .schedule-row { display: grid; grid-template-columns: minmax(120px, 1fr) 80px 150px 150px; align-items: center; gap: 12px; padding: 8px 12px; }
.schedule-head { color: var(--muted); background: var(--surface-subtle); font-size: var(--text-xs); font-weight: 600; }
.schedule-row { border-top: 1px solid var(--line-soft); }
.schedule-row input[type="checkbox"] { width: 18px; height: 18px; accent-color: var(--action); }

/* Launch readiness: the verdict first, then every check under its group, each marked with a symbol
   and a word, so a missing requirement never depends on its colour. */
.launch-verdict { display: flex; flex-wrap: wrap; align-items: center; gap: 8px 14px; margin: 0 20px 16px; padding: 12px 14px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.launch-verdict .badge { min-height: 26px; padding: 0 10px 0 9px; font-size: var(--text-sm); }
.launch-verdict p { flex: 1 1 260px; margin: 0; color: var(--ink); font-weight: 600; }
.launch-verdict small { color: var(--muted); }
.launch-verdict[data-launch-state="Blocked"] { background: var(--red-soft); border-color: var(--red-line); }
.launch-verdict[data-launch-state="Ready"] { background: var(--green-soft); border-color: var(--green-line); }
#launch-blockers { margin: 0 20px 16px; }
#launch-summary .badge { font-size: var(--text-xs); }
.launch-group { padding: 0 20px 8px; }
.launch-group h3 { margin: 12px 0 6px; color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
.launch-checks { display: grid; gap: 0; margin: 0; padding: 0; list-style: none; border-top: 1px solid var(--line-soft); }
.launch-check { display: grid; grid-template-columns: 26px 1fr; gap: 0 10px; padding: 10px 0; border-bottom: 1px solid var(--line-soft); }
.launch-check.neutral { opacity: .8; }
.launch-mark { display: inline-flex; align-items: center; justify-content: center; width: 22px; height: 22px; color: var(--muted); background: var(--surface-subtle); border-radius: 4px; font-size: 12px; font-weight: 700; }
.launch-mark .icon { width: 14px; height: 14px; }
.launch-check.danger .launch-mark { color: var(--steel-0); background: var(--red-lamp); }
.launch-check.warning .launch-mark { color: var(--steel-950); background: var(--amber-lamp); }
.launch-check.optional .launch-mark { color: var(--label); background: transparent; box-shadow: inset 0 0 0 1.5px var(--input-border); }
.launch-check.success .launch-mark { color: var(--steel-0); background: var(--green-lamp); }
.launch-check.info .launch-mark { color: var(--label); background: var(--surface-subtle); box-shadow: inset 0 0 0 1px var(--border); }
.launch-body { min-width: 0; }
.launch-body .title-line { display: flex; flex-wrap: wrap; align-items: center; gap: 6px 8px; }
.launch-message { margin: 4px 0 2px; }
.launch-meta { display: block; color: var(--muted); font-size: var(--text-xs); }
.launch-not-blocked { display: block; margin-bottom: 2px; color: var(--green); font-size: var(--text-xs); font-weight: 600; }
/* A platform override beside the published contact it replaces for customers (Task 5C). */
.contact-override { display: block; margin-top: 2px; color: var(--amber); font-size: var(--text-xs); font-weight: 600; }
.launch-body .row-action { display: inline-block; margin-top: 6px; }
/* A launch check's action is a button, not a link, because it may open a cabinet session. */
button.row-action.launch-action { padding: 0; color: var(--ink); background: none; border: 0; font-family: inherit; font-size: var(--text-sm); font-weight: 600; cursor: pointer; text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 35%, transparent); text-underline-offset: 3px; }
button.row-action.launch-action:disabled { color: var(--muted); cursor: default; text-decoration: none; }
.launch-unavailable { display: block; margin-top: 4px; color: var(--muted); font-size: var(--text-xs); }

/* Checkout money in the tenant wizard: the field beside its effective value. */
.checkout-money .effective-value { display: flex; flex-direction: column; justify-content: flex-end; gap: 4px; padding-bottom: 6px; }
.checkout-money .effective-value span { color: var(--muted); font-size: var(--text-xs); }
.checkout-money .effective-value strong { font-size: var(--text-lg); font-variant-numeric: tabular-nums; }
.checkout-summary { padding-bottom: 8px; }
.checkout-summary + .hint { padding: 0 20px 16px; color: var(--muted); }

/* The owner's invitation link, shown once: wide enough for the token to wrap, plain enough to copy by hand. */
.invitation-box { width: 100%; max-width: 720px; margin: 16px auto 4px; padding: 16px 18px; text-align: left; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.invitation-box h3 { margin: 0 0 6px; }
.invitation-box p { margin: 0 0 8px; }
.invitation-box .invitation-link code { display: block; padding: 10px 12px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-control); font-size: 12px; word-break: break-all; user-select: all; }
.invitation-box .form-actions { justify-content: flex-start; margin-top: 8px; padding: 0; }

/* The catalogue sheet and its photographs: issues first, the marks readable at a glance. */
.catalogue-import-actions { flex-wrap: wrap; gap: 10px; }
.catalogue-import .hint { margin: 6px 20px 0; }
.catalogue-report { margin: 14px 20px 0; }
.catalogue-problems, .catalogue-preview { width: calc(100% - 40px); margin: 14px 20px 0; font-size: var(--text-sm); }
.catalogue-problems td, .catalogue-preview td { vertical-align: top; }
.catalogue-problems tr.problem-error td:first-child { color: var(--red); font-weight: 600; }
.catalogue-problems tr.problem-warning td:first-child { color: var(--amber); font-weight: 600; }
.catalogue-images .metric-grid.mini { grid-template-columns: repeat(auto-fit, minmax(120px, 1fr)); margin: 14px 0; }
.catalogue-images .form-actions { justify-content: flex-start; flex-wrap: wrap; gap: 8px; padding-inline: 0; }
.catalogue-images-rows { display: grid; gap: 0; margin: 12px 0 4px; padding: 0; list-style: none; font-size: var(--text-sm); border-top: 1px solid var(--line-soft); }
.catalogue-images-rows li { display: flex; align-items: baseline; gap: 8px; padding: 7px 4px; border-bottom: 1px solid var(--line-soft); }
.catalogue-images-rows li code { font-size: 12px; word-break: break-all; }
.catalogue-images-rows li small { color: var(--muted); }
.catalogue-images-rows li[data-row-state="Missing"] .row-mark, .catalogue-images-rows li[data-row-state="Unused"] .row-mark { color: var(--amber); }
.catalogue-images-rows li[data-row-state="Ambiguous"] .row-mark, .catalogue-images-rows li[data-row-state="Invalid"] .row-mark, .catalogue-images-rows li[data-row-state="Failed"] .row-mark { color: var(--red); }
.catalogue-images-rows li[data-row-state="Ambiguous"], .catalogue-images-rows li[data-row-state="Invalid"], .catalogue-images-rows li[data-row-state="Failed"] { background: var(--red-soft); }
.catalogue-images-rows li[data-row-state="Missing"], .catalogue-images-rows li[data-row-state="Unused"] { background: var(--amber-soft); }
.catalogue-images-rows li[data-row-state="Uploaded"] .row-mark, .catalogue-images-rows li[data-row-state="Replaced"] .row-mark, .catalogue-images-rows li[data-row-state="AlreadyPresent"] .row-mark { color: var(--green); }
.row-mark { display: inline-block; min-width: 14px; font-weight: 700; text-align: center; }
.upload-progress { display: flex; align-items: center; flex-wrap: wrap; gap: 10px; margin: 12px 0; padding: 10px 12px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-control); font-size: var(--text-sm); }
.upload-progress .button { margin-left: auto; }

/* ------------------------------------------------------------------------------- cabinet editors */
/* A role is a choice about a person's day: a row with a sentence, the chosen one outlined in ink. */
.role-list { display: grid; grid-template-columns: repeat(auto-fit, minmax(240px, 1fr)); gap: 8px; padding: 0 24px; }
.role-card { display: flex; align-items: flex-start; gap: 10px; padding: 11px 13px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); cursor: pointer; transition: border-color 120ms ease, background-color 120ms ease; }
.role-card:hover { background: var(--surface-hover); border-color: var(--input-border); }
.role-card.chosen { background: var(--surface-subtle); border-color: var(--ink); box-shadow: inset 0 0 0 1px var(--ink); }
.role-card input[type="checkbox"] { flex: none; width: 16px; height: 16px; margin-top: 2px; accent-color: var(--action); }
/* minmax(0,1fr), not auto: a column sized to its content would make the sentence as wide as it likes. */
.role-copy { display: grid; grid-template-columns: minmax(0, 1fr); gap: 3px; min-width: 0; }
.role-copy strong { color: var(--ink); font-size: var(--text-md); font-weight: 600; }
.role-copy small { color: var(--muted); font-size: var(--text-xs); line-height: 1.45; white-space: normal; }
.role-summary { margin: 0 24px; padding: 12px 14px; background: var(--surface-subtle); border-radius: var(--radius-surface); }
.role-summary p { margin: 0; color: var(--ink); font-size: var(--text-sm); }
.role-summary p.muted { color: var(--muted); font-size: var(--text-xs); }
.role-summary ul { margin: 7px 0; padding-left: 18px; color: var(--muted); font-size: var(--text-xs); line-height: 1.55; }
.role-summary ul + p.muted { margin-top: 0; }
.role-scope { margin: 0; padding: 0 24px; line-height: 1.45; }
/* The people lists (staff, stations, couriers, promo codes). A name keeps its chip beside it, and a chip that is not a
   state carries no lamp. The e-mail under a name sets the floor of the name's column, up to 240 px (a longer address is
   cut, whole in its tooltip), so names stop breaking at every hyphen and the list still fits a laptop; the branches
   cell keeps a readable measure. An inner block's min and max widths count in the cell's own; the cell's would not. */
.name-line { display: inline-flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; }
.name-line > .badge::before { display: none; }
#staff-table .subline { max-width: 240px; }
.staff-branches { display: block; min-width: 100px; max-width: 300px; }
/* An expired code fades, but its pinned key stays solid: a see-through sticky cell would show the row scrolling under it. */
.promo-table tr.faded td:last-child { opacity: 1; }
.promo-expired { margin-left: 8px; }
/* The notice after making this browser a station: its key keeps its own width under the sentence. */
#station-enrolled > .button { justify-self: start; margin-top: 8px; }
/* A branch name that runs to two lines keeps its box on the first line, not between the two. */
.branch-flags .toggle { align-items: flex-start; }
.branch-flags .toggle > input[type="checkbox"] { margin-top: calc((1lh - 16px) / 2); }
.empty-state > .stations-pin-note { margin: 12px 0 0; }
/* KIOSK-1: an activation code is read off this screen and typed on a tablet across the room. */
.kiosk-code { margin: var(--space-4) 0; padding: var(--space-4); border: 1px dashed var(--border); border-radius: var(--radius-surface); background: var(--surface-subtle); color: var(--ink); font-family: var(--font-figures); font-size: calc(var(--text-xl) * 1.6); font-weight: 700; letter-spacing: 0.14em; text-align: center; user-select: all; }
@media (width <= 760px) {
    /* A phone: one card per row, each value under its heading, the row's keys across its foot. */
    .card-table thead { display: none; }
    .card-table, .card-table tbody { display: block; }
    .card-table tr { display: grid; grid-template-columns: minmax(0, 1fr); gap: 6px; padding: 12px 14px; border-bottom: 1px solid var(--line-soft); }
    .card-table tr:last-child { border-bottom: 0; }
    .card-table :is(td, td:last-child) { position: static; padding: 0; background: none; border: 0; box-shadow: none; }
    .card-table tbody tr:hover :is(td, td:last-child) { background: none; }
    .card-table tbody tr:hover { background: var(--surface-hover); }
    #staff-table .subline { max-width: none; }
    .card-table td[data-label]::before { display: block; margin-bottom: 2px; content: attr(data-label); color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
    .card-table td.row-actions { display: flex; flex-wrap: wrap; gap: 8px; width: auto; padding-top: 6px; white-space: normal; }
    .card-table td.row-actions > * + * { margin-left: 0; }
    .card-table td.row-actions .button { flex: 1 1 auto; min-height: var(--control-lg); }
    .card-table td:empty { display: none; }
}
/* Beside the rail on a tablet the columns no longer fit: each row is a card too — the name and its keys on the
   first line, then its facts side by side, each under its heading — instead of columns scrolling under the keys. */
@media (min-width: 761px) and (max-width: 1100px) {
    .card-table thead { display: none; }
    .card-table, .card-table tbody { display: block; }
    .card-table tr { display: flex; flex-wrap: wrap; align-items: flex-start; gap: 10px 28px; padding: 14px 20px; border-bottom: 1px solid var(--line-soft); }
    .card-table tr::after { order: 1; flex-basis: 100%; height: 0; content: ""; }
    .card-table tr:last-child { border-bottom: 0; }
    .card-table :is(td, td:last-child) { position: static; padding: 0; background: none; border: 0; box-shadow: none; }
    .card-table tbody tr:hover :is(td, td:last-child) { background: none; }
    .card-table tbody tr:hover { background: var(--surface-hover); }
    .card-table td:first-child { flex: 1 1 260px; min-width: 0; align-self: center; }
    .card-table td.row-actions { order: 1; display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 8px; width: auto; margin-left: auto; }
    .card-table td.row-actions > * + * { margin-left: 0; }
    .card-table td[data-label] { order: 2; flex: 0 1 auto; min-width: 96px; max-width: 320px; }
    .card-table td[data-label]::before { display: block; margin-bottom: 2px; content: attr(data-label); color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
    .card-table td:empty { display: none; }
    #staff-table .subline { max-width: none; }
    .panel > .table-scroll > .card-table td:is(:first-child, :last-child) { padding: 0; }
}

.modifier-group .section-heading { padding: 14px 20px 8px; }
.option-list { display: grid; gap: 0; margin: 0; padding: 0 20px 16px; list-style: none; }
.option-list li { display: flex; justify-content: space-between; gap: 12px; padding: 8px 2px; border-bottom: 1px solid var(--line-soft); font-size: var(--text-sm); }
.option-list li:last-child { border-bottom: 0; }
.option-list li.unavailable { color: var(--muted); text-decoration: line-through; }
.product-modifiers { display: flex; flex-direction: column; gap: 10px; }
.product-modifiers .section-heading, .cabinet-dialog .product-modifiers .section-heading { padding: 0; align-items: flex-start; }
.modifier-summary { padding: 12px 14px; background: var(--surface-subtle); border-radius: var(--radius-surface); }
.modifier-summary .option-list { padding: 8px 0 0; }
.modifier-summary .hint { margin: 2px 0 0; }
/* The groups of one product side by side, each as wide as a list of options reads (across the whole page an option
   and its surcharge sat 1,400 px apart); a surcharge is a figure that never breaks before its currency. */
.modifier-groups { display: grid; grid-template-columns: repeat(auto-fill, minmax(min(100%, 420px), 1fr)); gap: 20px; align-items: start; margin-bottom: var(--space-5); }
.modifier-groups > .panel { margin-bottom: 0; }
.option-list li > span:last-child { flex: none; font-variant-numeric: tabular-nums; white-space: nowrap; }
/* In a wide dialog a text kept in two languages sits side by side: one row per text, not one per language. The title
   stays in the first column so the columns nobody fills fold away. */
@media (min-width: 761px) {
    .cabinet-dialog.wide .form-grid > .localized-field { grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }
    .cabinet-dialog.wide .form-grid > .localized-field > .localized-label { grid-row: 1; grid-column: 1; }
    .cabinet-dialog.wide .form-grid > .localized-field:has(> .localized-label) > .field { grid-row: 2; }
}
/* The product editor's photographs and modifiers keep the dialog's inset like its fields; their titles are section titles. */
.cabinet-dialog .form-section > :is(.product-images, .product-modifiers) { padding-inline: 24px; }
.cabinet-dialog :is(.product-images, .product-modifiers) h3 { margin: 0; font-size: var(--text-lg); font-weight: 600; line-height: 1.3; }
/* The branches a dish is sold at: the switch centred under its heading, the price a figure under its own. */
.product-branches .branch-on-sale { width: 1%; text-align: center; }
.product-branches .branch-price { width: 1%; text-align: right; }
.product-branches .branch-price input { width: 132px; text-align: right; font-variant-numeric: tabular-nums; }
/* A modifier group's yes-or-no on a row of its own, then its two numbers, each as wide as a number. */
.cabinet-dialog > .modifier-required { padding-block: 0; }
.modifier-required input { margin-left: 0; }
.modifier-required strong { color: var(--ink); font-size: var(--text-md); font-weight: 600; }
.form-grid.modifier-limits { grid-template-columns: repeat(2, minmax(0, 200px)); }
.modifier-limits > .validation-message { grid-column: 1 / -1; margin-top: -8px; }
.cabinet-dialog .form-section > p.modifier-options-error { color: var(--red); font-size: var(--text-xs); font-weight: 500; }
/* The options of a group: a row each with every control on one line, a name box per language under its language. */
.option-table th.option-available, .option-table td.option-available { width: 1%; text-align: center; }
.option-table td.option-name input { width: 100%; min-width: 140px; }
.option-table .option-price { width: 132px; }
.option-table .option-price input { width: 100%; min-width: 96px; text-align: right; font-variant-numeric: tabular-nums; }
/* A: a dish's variants — the add-on options' table, and the per-branch prices folded under it. */
.variant-branches { margin-top: 12px; }
.variant-branches > summary { cursor: pointer; font-weight: 500; }
.variant-branches .branch-price { white-space: nowrap; }
.variant-branches .branch-price input[type="text"] { width: 96px; margin-inline-start: 8px; text-align: right; font-variant-numeric: tabular-nums; }

/* On a wide screen the column heading names each box; the label beside it speaks to a screen reader until the row is a card. */
.option-cell-label { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; }
@media (width <= 760px) {
    .cabinet-dialog .form-section > :is(.product-images, .product-modifiers, .product-variants) { padding-inline: 16px; }
    .cabinet-dialog > label.toggle-field.modifier-required { margin-inline: 16px; }
    .product-branches th { white-space: normal; }
    .product-branches .branch-price input { width: 96px; }
    /* A phone: an option per card, its names across the top, then its surcharge, whether it is on sale and its remove key. */
    .option-table thead { display: none; }
    .option-table table, .option-table tbody { display: block; }
    .option-table tr { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; align-items: end; gap: 10px 12px; padding: 12px 0; border-bottom: 1px solid var(--line-soft); }
    .option-table tbody tr:last-child { border-bottom: 0; }
    .option-table td, .option-table td.row-actions { display: grid; gap: 6px; width: auto; min-width: 0; padding: 0; border: 0; }
    .option-table td.row-actions { padding-bottom: 2px; }
    .option-table td.option-name { grid-column: 1 / -1; }
    .option-table td.option-name input { min-width: 0; }
    .option-table .option-price { width: auto; }
    .option-table td.option-available .toggle { align-items: center; min-height: var(--control-md); }
    .option-cell-label { position: static; width: auto; height: auto; overflow: visible; clip: auto; white-space: normal; color: var(--label); font-size: var(--text-xs); font-weight: 500; line-height: 1.3; }
    .option-table .toggle .option-cell-label { color: var(--ink); font-size: var(--text-md); font-weight: 400; }
}

/* The zones list: the zone's name keeps the width to be read; figure headings wrap over their right-aligned figures. */
.zones-table th { vertical-align: bottom; }
.zones-table th.num { white-space: normal; min-width: 88px; }
.zones-table td:first-child { min-width: 200px; }
.zones-table td:nth-child(2) { min-width: 160px; }
@media (max-width: 1100px) {
    .zones-table thead { display: none; }
    .zones-table, .zones-table tbody { display: block; }
    .zones-table tr { display: flex; flex-wrap: wrap; align-items: flex-start; gap: 10px 24px; padding: 14px 20px; border-bottom: 1px solid var(--line-soft); }
    .zones-table tr:last-child { border-bottom: 0; }
    .zones-table :is(td, td:first-child, td:nth-child(2), td:last-child) { position: static; min-width: 0; padding: 0; background: none; border: 0; box-shadow: none; text-align: left !important; }
    .zones-table tbody tr:hover :is(td, td:last-child) { background: none; }
    .zones-table tbody tr:hover { background: var(--surface-hover); }
    .panel > .table-scroll > .zones-table td:is(:first-child, :last-child) { padding: 0; }
    .zones-table td:first-child { flex: 1 1 calc(100% - 160px); align-self: center; }
    .zones-table td.row-actions { order: 1; width: auto; }
    .zones-table td[data-label] { order: 2; }
    .zones-table td[data-label]::before { display: block; margin-bottom: 2px; content: attr(data-label); color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
}
@media (width <= 760px) { .zones-table tr { padding: 12px 16px; gap: 8px 18px; } }
/* Delivery zones: the map, and the corners it is drawn from beside it, on the dialog's 24 px gutter. */
.zone-split { display: grid; grid-template-columns: minmax(0, 1fr) minmax(200px, 260px); gap: 16px; padding: 0 24px; }
/* Leaflet's panes and controls (z-index 200-1000) stay inside the map, under the dialog's sticky footer. */
.zone-map { position: relative; z-index: 0; isolation: isolate; height: 340px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
/* The count heads the list, the list takes what the map leaves, and the manual entry sits at the map's foot. */
.zone-points { display: grid; grid-template-rows: auto minmax(0, 1fr) auto; align-content: start; gap: 12px; }
.zone-points ol { max-height: 220px; overflow-y: auto; margin: 0; padding-left: 22px; color: var(--muted); font-size: var(--text-xs); font-variant-numeric: tabular-nums; }
.zone-points li { padding: 2px 0; }
/* Both levels are grid items: the field in the column, the row in the field; each may shrink. */
.zone-points > .field { min-width: 0; }
.zone-points .row-actions { gap: 8px; min-width: 0; }
.zone-vertex { width: 14px; height: 14px; border-radius: 50%; background: var(--steel-900); border: 2px solid white; box-shadow: 0 0 0 1px oklch(21.5% 0.008 95 / .45); cursor: grab; }
.leaflet-drag-target .zone-vertex, .zone-vertex:active { cursor: grabbing; }
.zone-points .row-actions input { min-width: 0; flex: 1 1 auto; }
.zone-points .row-actions .button { flex: 0 0 auto; }
@media (max-width: 1100px) { .zone-split { grid-template-columns: minmax(0, 1fr); } }
@media (width <= 760px) { .zone-split { padding-inline: 16px; } }

/* Order rules: four panels of short settings. A figure's field is not a paragraph wide, a switch's hint
   keeps a reading measure, and a toggle in a field is spaced by the field, not by its own padding. */
.order-rules-panel > .form-grid { max-width: 1040px; }
.order-rules-panel .form-grid > .field > .toggle-field { padding-block: 0; }
.order-rules-panel .toggle-field small { max-width: 64ch; }
.order-rules-panel .field > .flag-row { padding: 0; gap: 8px 24px; }
.order-rules-panel .field > p.muted { margin: 0; }
/* Each zone's own minimum: the name, and its amount at the end of a short line. */
.zone-minimums { display: grid; max-width: 480px; margin: 0; padding: 0; list-style: none; }
.zone-minimums li { display: flex; align-items: baseline; justify-content: space-between; gap: 16px; padding: 6px 0; border-bottom: 1px solid var(--line-soft); font-size: var(--text-sm); }
.zone-minimums li:first-child { padding-top: 0; }
.zone-minimums li:last-child { border-bottom: 0; }

/* Identity and branch inputs: optional marks read as such, the map is a picture of the stored numbers. */
.time-zone-field select { margin-top: 6px; font-size: var(--text-sm); }
.time-zone-field select option { padding: 4px 6px; }
.branch-location { margin: 16px 0 0; }
.panel > .branch-location { margin-top: 0; }
.panel > .branch-location .branch-map, .panel > .branch-location .location-status { margin-inline: 20px; }
.branch-location .section-heading { margin-bottom: 8px; }
.branch-map { position: relative; z-index: 0; isolation: isolate; height: 320px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.branch-location[data-map-state="unavailable"] .branch-map { display: none; }
.location-status { margin: 8px 0 4px; font-size: var(--text-sm); }
.location-status.is-unset { color: var(--amber); font-weight: 600; }
.location-status.is-set { color: var(--muted); }
.location-actions { display: flex; align-items: flex-end; }
.identity-summary { margin-bottom: 12px; }

/* CRM-1: the customers list — search above, dense rows, the name a link with the phone under it — and a customer's page. */
.customers-search { display: flex; flex-wrap: wrap; align-items: flex-end; gap: var(--space-2) var(--space-3); margin-bottom: var(--space-4); }
.customers-search > .field { flex: 1 1 320px; max-width: 520px; }
.customer-name { color: var(--ink); font-weight: 600; text-decoration: none; }
.customer-name:hover { text-decoration: underline; }
.customers-pager { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: var(--space-2); }
.customer-header .name-line { margin-top: 4px; color: var(--muted); }
.customer-columns { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-4); margin-bottom: var(--space-4); }
.customer-columns > .panel { margin: 0; }
.facts { display: grid; grid-template-columns: max-content minmax(0, 1fr); gap: 8px 16px; margin: 0; padding: 0 20px 20px; }
.facts dt { color: var(--muted); font-size: var(--text-sm); }
.facts dd { margin: 0; overflow-wrap: anywhere; }
.customer-addresses { display: grid; gap: 10px; margin: 0; padding: 0 20px 20px; list-style: none; }
.customer-addresses .subline { max-width: none; white-space: normal; }
@media (width <= 1100px) { .customer-columns { grid-template-columns: minmax(0, 1fr); } }
@media (width <= 760px) { .facts { grid-template-columns: minmax(0, 1fr); gap: 2px; } .facts dd + dt { margin-top: 8px; } }
/* The brand: colours as swatches beside their values, pictures at the shape the apps draw them. */
/* Presets fill the existing editor. Preview labels stay in the cabinet's own ink. */
.preset-editor { display: grid; gap: var(--space-3); padding: 0 20px; max-width: 880px; }
.preset-editor > .field { max-width: 440px; }
.preset-description { margin: 0; max-width: 72ch; color: var(--muted); font-size: var(--text-sm); }
.preset-previews { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-4); }
.preset-preview { min-width: 0; margin: 0; }
.preset-preview figcaption { margin-bottom: var(--space-2); color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.preset-canvas { padding: 16px; background: var(--preview-page, var(--canvas)); border: 1px solid var(--line-soft); border-radius: var(--radius-surface); }
.preset-sample-panel { display: grid; gap: 12px; padding: 14px; background: var(--preview-panel, var(--surface-subtle)); border-radius: var(--radius-surface); }
.preset-sample-title { color: var(--preview-ink, var(--ink)); font-size: var(--text-sm); font-weight: 600; }
.preset-sample-card { display: grid; gap: 8px; padding: 14px; color: var(--preview-ink, var(--ink)); background: var(--preview-card, var(--surface)); border-radius: var(--radius-surface); font-size: var(--text-sm); }
.preset-sample-caption { color: var(--preview-muted, var(--muted)); font-size: var(--text-xs); }
.preset-sample-action { justify-self: start; padding: 8px 12px; color: var(--preview-button-ink, var(--ink)); background: var(--preview-button, var(--surface-subtle)); border-radius: var(--radius-control); font-weight: 600; }
.preset-load-error > p { margin-top: 0; }
@media (width <= 600px) { .preset-previews { grid-template-columns: minmax(0, 1fr); } }
.brand-basics > .form-grid { max-width: 760px; }
.logo-field { display: grid; grid-template-columns: 52px minmax(0, 1fr); align-items: start; gap: var(--space-4); max-width: 760px; margin-bottom: var(--space-4); padding: 0 20px; }
/* Level with the address box: below the label's line (13 px × 1.3) and the field's 6 px gap. */
.logo-field > .brand-mark { margin-top: calc(var(--text-sm) * 1.3 + 6px); }
/* The palette in families, each under its own name; a hairline between families, never a card. */
.color-group, .badge-group { min-width: 0; margin: 0; padding: 0 20px; border: 0; }
.badge-group + .badge-group { margin-top: var(--space-5); padding-top: var(--space-4); border-top: 1px solid var(--line-soft); }
.color-group + .color-group { margin-top: var(--space-5); padding-top: var(--space-4); border-top: 1px solid var(--line-soft); }
.color-group > legend, .badge-group > legend { float: left; width: 100%; margin: 0 0 var(--space-3); padding: 0; color: var(--ink); font-size: var(--text-md); font-weight: 600; line-height: 1.3; }
.color-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(176px, 1fr)); gap: var(--space-3) var(--space-4); padding: 0 20px; }
.color-group > .color-grid { clear: both; padding: 0; }
.color-field label { overflow-wrap: anywhere; }
/* BRANDING-1: the browser's own picker is the swatch (a real control, Tab then Enter or Space), the hex code beside it, reset last. */
.color-control { display: flex; align-items: center; gap: var(--space-2); min-width: 0; }
.color-control > .color-hex { flex: 1 1 auto; width: 100%; min-width: 0; font-variant-numeric: tabular-nums; }
.color-pick { position: absolute; inset: 0; width: 100%; height: 100%; padding: 0; cursor: pointer; opacity: 0; }
.color-pick:disabled { cursor: not-allowed; }
.color-chip:focus-within { outline: 2px solid var(--focus); outline-offset: 2px; }
.color-reset { display: inline-grid; flex: none; place-items: center; width: var(--control-md); height: var(--control-md); padding: 0; color: var(--label); background: transparent; border: 1px solid transparent; border-radius: var(--radius-control); cursor: pointer; }
.color-reset:hover:not(:disabled) { color: var(--ink); background: var(--surface-subtle); }
/* Nothing to go back to: the key keeps its place, so the row does not shift as colours change. */
.color-reset:disabled { visibility: hidden; }
.color-field.is-invalid .color-hex { border-color: var(--red); }
.color-note { margin: 0; color: var(--muted); font-size: var(--text-xs); line-height: 1.45; }
/* The badges: the preview on the theme's card colour, its two colours, the contrast it reads at. */
/* Clears the floated legend, as .color-grid does: a grid beside a 100% float is pushed out of the panel sideways. */
.badge-rows { display: grid; clear: both; gap: var(--space-4); }
.badge-row { display: grid; grid-template-columns: 136px repeat(2, minmax(0, 1fr)) minmax(132px, 0.8fr); align-items: start; gap: var(--space-3) var(--space-4); }
.badge-sample { display: grid; place-items: center; min-height: 58px; padding: var(--space-2); background: var(--sample-bg, var(--surface)); border: 1px solid var(--line-soft); border-radius: var(--radius-surface); }
.product-badge { display: inline-flex; align-items: center; min-height: 22px; padding: 0 8px; color: var(--badge-ink, var(--ink)); background: var(--badge-bg, var(--surface-subtle)); border-radius: 4px; font-size: var(--text-xs); font-weight: 600; line-height: 1.2; white-space: nowrap; }
/* Level with the hex boxes: below the label's line (13 px x 1.3) and the field's 6 px gap. */
.badge-contrast { display: grid; gap: 2px; margin: calc(var(--text-sm) * 1.3 + 6px) 0 0; color: var(--muted); font-size: var(--text-xs); line-height: 1.45; font-variant-numeric: tabular-nums; }
.badge-contrast.is-low { color: var(--red); }
.badge-contrast-warning { display: inline-flex; align-items: center; gap: 4px; font-weight: 500; }
@media (width <= 1100px) { .badge-row { grid-template-columns: 120px repeat(2, minmax(0, 1fr)); } .badge-contrast { grid-column: 2 / -1; margin-top: 0; } }
@media (width <= 760px) { .badge-row { grid-template-columns: minmax(0, 1fr); } .badge-contrast { grid-column: auto; } }
/* The swatch paints over a transparency grid, so #FFFFFF shows as white and #00000029 as the faint veil it is. */
.color-chip { position: relative; flex: none; width: var(--control-md); height: var(--control-md); background: linear-gradient(var(--chip, transparent), var(--chip, transparent)), repeating-conic-gradient(var(--border) 0 25%, var(--surface) 0 50%) 0 0 / 10px 10px; border: 1px solid var(--input-border); border-radius: var(--radius-control); }
.palette-note { margin: 0; padding: 0 20px; color: var(--muted); font-size: var(--text-sm); }
/* Brand's Save rides the foot of the screen (the wizard's floating footer) with its answer beside it. */
.brand-save { margin-top: 0; }
/* FORM-1: the same bar under any whole-page form. Its answer wraps above the key rather than squeezing it. */
.save-bar { flex-wrap: wrap; }
.save-bar > .button { margin-left: auto; }
.brand-save-status { display: grid; flex: 1 1 auto; gap: var(--space-2); min-width: 0; }
.brand-save-status .alert { margin: 0; }
.brand-save-status .alert span { color: inherit; font-size: inherit; text-align: start; }
.brand-save-status .badge { color: var(--label); }
.form-grid.about-fields { max-width: 760px; }
.banner-thumb { width: 96px; height: 48px; object-fit: cover; background: var(--surface-subtle); border-radius: 4px; }
.image-upload { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); }
.image-upload .button { max-width: 100%; white-space: normal; }
/* A label drawn as a key: ".field label" would otherwise set it in the 13 px label type. */
.image-upload label.button { font-size: var(--text-md); line-height: 1.2; }
.image-upload input[type="file"] { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0,0,0,0); }
.upload-problem { color: var(--red); font-size: var(--text-xs); }
.upload-format { display: block; color: var(--muted); font-size: var(--text-xs); }
@media (width <= 760px) { .color-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
/* A strip rather than a grid: a dish has one picture, occasionally two. */
.product-images { display: flex; flex-direction: column; gap: 10px; }
.image-strip { display: flex; flex-wrap: wrap; gap: 10px; }
.image-tile { position: relative; width: 108px; height: 108px; margin: 0; overflow: hidden; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.image-tile img { display: block; width: 100%; height: 100%; object-fit: cover; }
.image-tile .icon-button { position: absolute; top: 4px; right: 4px; width: 26px; height: 26px; padding: 0; color: #fff; background: oklch(16.5% 0.007 95 / .72); border: none; border-radius: 4px; font-size: 14px; }
.image-tile .icon-button:hover:not(:disabled) { color: #fff; background: var(--red-lamp); }
/* The category picture keeps its square (the app crops it 1:1); the upload, its format and its help stand beside it,
   and go under it when a phone has no room for both. */
.category-image { display: flex; flex-wrap: wrap; align-items: flex-start; gap: 12px; }
.category-image-actions { display: flex; flex: 1 1 220px; flex-direction: column; align-items: flex-start; gap: 6px; max-width: 46ch; }
.image-tile.wide { display: grid; flex: none; place-items: center; width: 132px; height: 132px; }
.image-tile.wide > .icon { width: 32px; height: 32px; color: var(--subtle); }
.image-initial { color: var(--muted); font-family: var(--font-figures); font-size: 28px; font-weight: 600; }
/* The sign-in code read out to a customer: large enough to read across a counter, spaced into two fours. */
.assisted-code-value { margin: 6px 0; font-family: var(--font-figures); font-size: 34px; font-weight: 600; letter-spacing: .22em; font-variant-numeric: tabular-nums; }

/* ---------------------------------------------------------------------------------------- entrance
   A restaurant's door is headed by its own name and mark on steel; the console's door stands on the
   maker's graphite with the cobalt mark. A person's language and theme wait at the foot of the sheet. */
.login-shell { min-height: 100vh; min-height: 100dvh; display: grid; place-items: center; padding: 32px 16px; background: var(--canvas); }
.login-shell:has(.platform-login) { background: var(--steel-950); }
.login-shell:has(.platform-login)::before { position: fixed; top: 20px; left: 24px; content: "Rengi"; color: var(--steel-400); font-family: var(--font-figures); font-size: var(--text-lg); font-weight: 600; letter-spacing: -0.01em; }
.login-card { width: min(100%, 420px); padding: var(--space-8) var(--space-8) var(--space-6); color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-large); box-shadow: var(--shadow-2); }
.login-card.wide { width: min(100%, 540px); }
.login-shell:has(.platform-login) .login-card { border-color: oklch(30% 0.008 95); box-shadow: 0 30px 80px -20px oklch(0% 0 0 / .6); }
.login-brand { display: flex; align-items: center; gap: 12px; margin-bottom: var(--space-6); }
.login-brand > div { min-width: 0; display: grid; }
/* A business's name is how staff know they are at the right door: two lines (three on a phone) before
   it is cut, and the whole of it in the title. */
/* The business's name is who this sign-in is for: read whole, however long, never cut with «…». */
.login-brand strong { display: block; color: var(--ink); font-size: var(--text-lg); font-weight: 600; line-height: 1.25; overflow-wrap: anywhere; text-wrap: balance; }
.login-brand div span { color: var(--muted); font-size: var(--text-sm); }
.login-heading { margin-bottom: 20px; }
.login-heading h1 { margin-bottom: 4px; font-size: var(--text-2xl); }
.login-heading p { margin-bottom: 0; }
.login-card .alert { margin-bottom: var(--space-5); }
.login-card form { display: grid; gap: 16px; }
.login-card form .button.full { min-height: var(--control-lg); margin-top: 4px; font-size: var(--text-lg); }
/* The person's own settings, at the foot of the sheet: quiet, still one tab away. */
.login-toolbar { display: flex; gap: 8px; margin-top: var(--space-6); padding-top: var(--space-4); border-top: 1px solid var(--line-soft); }
.login-toolbar .selector-field { position: relative; flex: 1 1 0; min-width: 0; }
.login-toolbar .selector-field span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); }
/* Each picker says what it sets with its mark (the label is for screen readers), full height, and
   touch height where fingers choose: on the station's own page and on any coarse pointer. */
.login-toolbar .selector-field select { min-width: 0; min-height: var(--control-md); padding: 3px 28px 3px 9px; background-color: var(--surface); border-color: var(--input-border); box-shadow: none; font-size: var(--text-sm); font-weight: 400; }
.login-toolbar .selector-field .icon { position: absolute; top: 50%; left: 10px; width: 16px; height: 16px; color: var(--muted); transform: translateY(-50%); pointer-events: none; }
.login-toolbar .selector-field .icon + select { padding-left: 32px; }
#station-device .login-toolbar .selector-field select { min-height: var(--control-lg); }
@media (pointer: coarse) {
    .login-toolbar .selector-field select { min-height: var(--control-lg); }
}
.login-help { margin: var(--space-4) 0 0; color: var(--muted); font-size: var(--text-xs); text-align: center; }
.auth-state-card { display: grid; justify-items: center; gap: 14px; text-align: center; }
.auth-state-card h1, .auth-state-card p { margin: 0; }
.auth-state-card small { color: var(--muted); }
.auth-state-actions { display: flex; gap: 8px; justify-content: center; margin-top: 14px; }
.staff-sign-in-tenant { display: flex; flex-wrap: wrap; gap: 8px; align-items: baseline; margin: 0 0 16px; font-size: var(--text-sm); }
.entrance-back { margin: -12px 0 var(--space-5); font-size: var(--text-sm); }
.entrance-back a { display: inline-flex; align-items: center; gap: 6px; color: var(--muted); text-decoration: none; }
.entrance-back a:hover { color: var(--ink); text-decoration: underline; text-underline-offset: 3px; }
.staff-sign-in-other { margin: var(--space-4) 0 0; text-align: center; }
/* AUTH-UX-2: /login with no business known — where the sign-in is, nothing to fill in. */
.staff-entry-landing { display: grid; gap: var(--space-4); }
.staff-entry-landing p { margin: 0; color: var(--muted); }
/* The link's shape is an example in the sentence, not a field: an inline chip that moves whole to its own line. */
.staff-entry-shape { font-size: var(--text-sm); }
.staff-entry-shape code { display: inline-block; max-width: 100%; padding: 1px 5px; overflow-wrap: anywhere; font-size: var(--text-xs); user-select: all; }
.staff-entry-landing p.staff-entry-setup { color: var(--muted); font-size: var(--text-xs); }
/* The doors a signed-in account may open: a row each, its mark on a steel plate, the way in at the right. */
.entrance-doors { display: grid; gap: 8px; margin-top: 4px; }
.entrance-door { display: flex; align-items: center; gap: var(--space-3); min-height: 64px; padding: var(--space-3) var(--space-4); color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); text-decoration: none; transition: border-color 120ms ease, background-color 120ms ease, transform var(--press) var(--ease-out); }
.entrance-door:hover { color: var(--ink); background: var(--surface-hover); border-color: var(--input-border); }
.entrance-door:active { transform: scale(.985); }
.entrance-door > span:not(.entrance-icon) { flex: 1; min-width: 0; }
.entrance-door strong { display: block; font-size: var(--text-lg); font-weight: 600; }
.entrance-door small { display: block; color: var(--muted); font-size: var(--text-sm); }
.entrance-door .badge { margin-left: auto; }
.entrance-door::after { flex: none; width: 8px; height: 8px; margin-right: 4px; content: ""; border-top: 1.5px solid var(--subtle); border-right: 1.5px solid var(--subtle); transform: rotate(45deg); }
.entrance-icon { display: grid; place-items: center; flex: none; width: 40px; height: 40px; color: var(--ink); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); font-size: 20px; }
.entrance-icon .icon { width: 22px; height: 22px; }
.staff-launcher-sign-out { margin-top: 16px; text-align: center; }
/* A phone: the sheet and each door give their text the width (the shared phone block's .login-card
   padding is outranked here), and a long name may take a third line. */
@media (width <= 760px) {
    .login-shell .login-card { padding: var(--space-6) var(--space-5) var(--space-5); }
    .entrance-door { padding: var(--space-3); }
    .entrance-icon { width: 36px; height: 36px; }
    .entrance-icon .icon { width: 20px; height: 20px; }
    .entrance-door::after { margin-right: 0; }
}
/* A workspace the account may not open, said once over whatever is on screen. */
.staff-access-notice { position: fixed; top: 12px; left: 50%; z-index: var(--z-toast); display: flex; align-items: center; gap: 12px; width: max-content; max-width: min(560px, calc(100vw - 24px)); margin: 0; box-shadow: var(--shadow-2); transform: translateX(-50%); }
.my-pin { max-width: 560px; margin: 24px auto; }
.my-pin h1 { margin-top: 0; }

/* ------------------------------------------------------------------------------------ support mode
   Rengi inside a restaurant: the maker's cobalt, a band across the top and a frame round the whole
   screen for as long as it lasts. Nothing a restaurant's own staff ever sees looks like this. */
.impersonation-bar { position: sticky; top: 0; z-index: var(--z-support); display: flex; align-items: center; gap: 12px; min-height: 44px; padding: 7px 16px; color: #fff; background: var(--cobalt-strong); font-size: var(--text-sm); }
:root[data-theme="dark"] .impersonation-bar { background: oklch(40% 0.15 264); }
.impersonation-bar strong { font-weight: 600; }
.impersonation-bar .support-text { min-width: 0; color: #fff; font-size: var(--text-sm); }
.impersonation-bar .button { margin-left: auto; color: #fff; background: oklch(100% 0 0 / .14); border-color: oklch(100% 0 0 / .28); box-shadow: none; }
@media (hover: hover) { .impersonation-bar .button:hover:not(:disabled) { color: #fff; background: oklch(100% 0 0 / .26); border-color: oklch(100% 0 0 / .4); } }
.support-frame { position: fixed; inset: 0; z-index: calc(var(--z-support) - 1); pointer-events: none; border: 3px solid var(--cobalt-strong); }
/* Under the band the shell is as tall as the window minus the band (measured by the page; these are its first guesses). */
:root:has(#support-banner) { --support-band: 52px; }
:root:has(#support-banner) .app-shell { min-height: calc(100dvh - var(--support-band)); }
:root:has(#support-banner) .app-shell > .sidebar { top: var(--support-band); height: calc(100dvh - var(--support-band)); }
:root:has(#support-banner) .shell-toolbar { top: var(--support-band); }
:root:has(#support-banner) :is(.pos-shell, .kds-shell) { height: calc(100dvh - var(--support-band)); }
:root[data-theme="dark"] .support-frame { border-color: oklch(62% 0.16 264); }
.support-badge { display: inline-flex; align-items: center; gap: 6px; flex: none; padding: 2px 8px; color: var(--cobalt-strong); background: #fff; border-radius: 4px; font-size: var(--text-xs); font-weight: 700; }
.support-badge::before { width: 7px; height: 7px; content: ""; background: currentColor; border-radius: var(--radius-mark); }
.support-ended .support-badge { margin-bottom: 8px; color: var(--cobalt-strong); background: var(--cobalt-soft); }
/* Whose till or kitchen this is, beside the workspace's name. */
.shell-tenant { max-width: 28ch; margin-left: 10px; overflow: hidden; font-weight: 600; opacity: .8; text-overflow: ellipsis; white-space: nowrap; }

/* ----------------------------------------------------------------------------------------- cabinet
   The overview answers the first questions of a shift before anything else: is anything waiting on
   me, is a branch paused. The cell that needs the owner lifts (the lamp's fill); the rest stay quiet. */
.ops-band { display: grid; grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); margin-bottom: var(--space-5); overflow: hidden; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.ops-card { display: flex; flex-direction: column; align-items: flex-start; gap: 4px; min-width: 0; padding: 18px 20px 20px; color: var(--ink); background: var(--surface); box-shadow: 1px 0 0 var(--line-soft), 0 1px 0 var(--line-soft); }
.ops-card.attention { background: var(--amber-soft); }
.ops-card.paused { background: var(--red-soft); }
.ops-label { display: flex; align-items: center; gap: 8px; margin: 0 0 6px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.ops-label::before { flex: none; width: 8px; height: 8px; content: ""; background: var(--steel-400); border-radius: var(--radius-mark); }
.ops-card.attention .ops-label::before { background: var(--amber-lamp); box-shadow: 0 0 0 3px oklch(75% 0.155 70 / .22); }
.ops-card.paused .ops-label::before { background: var(--red-lamp); }
.ops-card.calm .ops-label::before { background: var(--green-lamp); }
.ops-reading { display: flex; align-items: baseline; flex-wrap: wrap; gap: 4px 12px; }
.ops-value { color: var(--ink); font-family: var(--font-figures); font-size: 40px; font-weight: 600; letter-spacing: -0.02em; line-height: 1; font-variant-numeric: tabular-nums; }
.ops-headline { color: var(--ink); font-size: var(--text-lg); font-weight: 600; }
.ops-headline.muted { color: var(--muted); font-weight: 500; }
.ops-card small { color: var(--muted); font-size: var(--text-sm); }
/* The key stands at the foot of the band, on one line with its neighbour's, 12 px clear of the words above it. */
.ops-card .button { margin-top: auto; }
.ops-card > :nth-last-child(2) { margin-bottom: 12px; }
.ops-card.paused .ops-headline { color: var(--red); }

/* TODAY-1: what is not in order, one row each, every row the way to where it is put right. The lamp
   says how much it matters: red is paper not coming out of the kitchen printer, amber is a note. */
.today-problems { margin-bottom: var(--space-5); overflow: hidden; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.today-problems h2 { margin: 0; padding: 14px 20px 10px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.today-problems ul { margin: 0; padding: 0; list-style: none; }
.today-problems li { border-top: 1px solid var(--line-soft); }
.today-problem { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: 12px; min-height: 60px; padding: 10px 20px; color: var(--ink); text-decoration: none; transition: background-color 120ms ease; }
.today-problem::before { width: 8px; height: 8px; content: ""; background: var(--amber-lamp); border-radius: var(--radius-mark); }
.today-problem.serious { background: var(--red-soft); }
.today-problem.serious::before { background: var(--red-lamp); }
.today-problem:hover { color: var(--ink); background: var(--surface-hover); }
.today-problem:focus-visible { outline-offset: -2px; }
.today-problem-copy { display: grid; gap: 1px; min-width: 0; }
.today-problem-copy strong { font-size: var(--text-md); font-weight: 600; line-height: 1.3; }
.today-problem-copy small { color: var(--muted); font-size: var(--text-sm); line-height: 1.35; text-wrap: pretty; }
.today-problem > .icon { width: 16px; height: 16px; color: var(--subtle); transition: color 120ms ease; }
.today-problem:hover > .icon { color: var(--ink); }
/* Nothing wrong is one quiet line under the band, not a box around good news. */
.today-calm { display: flex; align-items: center; gap: 8px; margin: calc(var(--space-3) - var(--space-5)) 0 var(--space-5); color: var(--muted); font-size: var(--text-sm); }
.today-calm::before { flex: none; width: 8px; height: 8px; content: ""; background: var(--green-lamp); border-radius: var(--radius-mark); }

/* The day's takings: the figures of the Reports screen, added up over the branches. */
.today-day { margin-bottom: var(--space-5); }
.today-day-heading { display: flex; align-items: center; justify-content: space-between; gap: 12px; min-height: 44px; }
.today-day-heading h2 { margin: 0; font-size: var(--text-lg); font-weight: 600; }
.today-day-more { display: inline-flex; align-items: center; gap: 4px; min-height: 44px; color: var(--label); font-size: var(--text-sm); font-weight: 600; text-decoration: none; }
.today-day-more:hover { color: var(--ink); }
.today-day-more .icon { width: 14px; height: 14px; }
.today-day .summary-strip { margin-bottom: 0; }
.today-day .summary-value { white-space: nowrap; }
.today-branches { margin: 8px 0 0; padding: 0; list-style: none; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.today-branches li { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; align-items: baseline; gap: 4px 16px; min-height: 44px; padding: 10px 18px; }
.today-branches li + li { border-top: 1px solid var(--line-soft); }
.today-branches span { overflow: hidden; font-weight: 500; text-overflow: ellipsis; white-space: nowrap; }
.today-branches small { color: var(--muted); font-size: var(--text-sm); white-space: nowrap; }
.today-branches strong { min-width: 9ch; font-family: var(--font-figures); font-weight: 600; font-variant-numeric: tabular-nums; text-align: right; white-space: nowrap; }
.today-day-note { display: block; margin-top: 8px; color: var(--muted); font-size: var(--text-sm); }

/* What the business has, in one strip of figures, each a way into its section. */
.summary-strip { display: grid; grid-template-columns: repeat(auto-fit, minmax(190px, 1fr)); margin-bottom: var(--space-5); overflow: hidden; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.summary-card { display: grid; align-content: start; gap: 2px; min-width: 0; padding: 16px 18px; color: var(--ink); background: var(--surface); box-shadow: 1px 0 0 var(--line-soft), 0 1px 0 var(--line-soft); text-decoration: none; transition: background-color 120ms ease; }
a.summary-card:hover { color: var(--ink); background: var(--surface-hover); }
.summary-card.static:hover { background: var(--surface); }
.summary-value { color: var(--ink); font-family: var(--font-figures); font-size: 28px; font-weight: 600; letter-spacing: -0.015em; line-height: 1.1; font-variant-numeric: tabular-nums; }
/* A tile that is a way into its section says so with a caret, which darkens under the pointer. */
a.summary-card { position: relative; padding-right: 44px; }
a.summary-card > .icon { position: absolute; top: 50%; right: 16px; width: 16px; height: 16px; color: var(--subtle); transform: translateY(-50%); transition: color 120ms ease; }
a.summary-card:hover > .icon { color: var(--ink); }
.summary-card strong { margin-top: 4px; font-weight: 600; }
.summary-card small { color: var(--muted); font-size: var(--text-xs); }
.owing { color: var(--red); font-size: var(--text-lg); font-variant-numeric: tabular-nums; white-space: nowrap; }
.owing-note { color: var(--red); }
#invite-administrator .form-actions { padding-bottom: 20px; }
.form-grid.narrow { max-width: 880px; }
.self-badge { margin-left: 8px; }
.billing-subscription .section-heading > .row-actions { align-items: center; }
.billing-invoices { table-layout: fixed; min-width: 900px; }
.billing-invoices th:nth-child(1) { width: 200px; }
.billing-invoices th:nth-child(2) { width: 130px; }
.billing-invoices th:nth-child(3) { width: 110px; }
.billing-invoices th:nth-child(4) { width: 140px; }
.billing-invoices th:last-child { width: 270px; }
.billing-invoices .note-cell { color: var(--muted); }
@media (min-width: 1366px) { .billing-subscription > .table-scroll :is(th, td):first-child { padding-left: 20px; } .billing-subscription > .table-scroll :is(th, td):last-child { padding-right: 20px; } }
/* Narrower than the five columns, their keys and a note: each invoice is two lines — when and how much, then its state and its keys. */
@media (max-width: 1365px) {
    .billing-invoices { table-layout: auto; min-width: 0; }
    .billing-invoices thead { display: none; }
    .billing-invoices, .billing-invoices tbody { display: block; }
    .billing-invoices tr { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: center; gap: 6px 14px; padding: 12px 20px; border-bottom: 1px solid var(--line-soft); }
    .billing-invoices tr:last-child { border-bottom: 0; }
    .billing-invoices :is(td, td:first-child, td:last-child) { position: static; padding: 0; background: none; border: 0; box-shadow: none; }
    .billing-invoices tbody tr:hover :is(td, td:last-child) { background: none; }
    .billing-invoices tbody tr:hover { background: var(--surface-hover); }
    .panel > .table-scroll > .billing-invoices td:is(:first-child, :last-child) { padding: 0; }
    .billing-invoices .period-cell { grid-column: 1 / 3; font-weight: 600; }
    .billing-invoices .amount-cell { grid-column: 3; }
    .billing-invoices .due-cell { grid-column: 1; color: var(--muted); font-size: var(--text-sm); }
    .billing-invoices .due-cell::before { content: attr(data-label) " "; }
    .billing-invoices .status-cell { grid-column: 2; justify-self: start; }
    .billing-invoices td.row-actions { grid-column: 3; width: auto; }
    .billing-invoices td.row-actions:empty { display: none; }
    .billing-invoices .note-cell { grid-column: 1 / -1; font-size: var(--text-sm); }
    .billing-invoices .note-cell:has(> .muted) { display: none; }
}
@media (width <= 560px) {
    .billing-invoices tr { grid-template-columns: minmax(0, 1fr) auto; padding: 12px 16px; }
    .billing-invoices .period-cell { grid-column: 1; }
    .billing-invoices .amount-cell { grid-column: 2; }
    .billing-invoices .due-cell { grid-column: 1; }
    .billing-invoices .status-cell { grid-column: 2; justify-self: end; }
    .billing-invoices td.row-actions { grid-column: 1 / -1; display: flex; gap: 8px; text-align: left; }
    .billing-invoices td.row-actions > * + * { margin-left: 0; }
    .billing-invoices td.row-actions .button { flex: 1 1 auto; }
}
.field-value { display: flex; align-items: center; min-height: var(--control-md); font-family: var(--font-figures); font-size: var(--text-lg); font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }

/* The menu: sections on the left as a list you work down, their dishes on the right. */
.menu-split { display: grid; grid-template-columns: minmax(220px, 300px) minmax(0, 1fr); gap: 16px; align-items: start; }
.menu-split > .panel { margin-bottom: 0; }
.menu-categories { display: grid; gap: 1px; padding: 6px; }
/* The name takes the row and the edit key keeps its size; the count and the state share the line under the name. */
.menu-category { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 4px; padding: 2px 4px; border-radius: var(--radius-control); transition: background-color 120ms ease; }
.menu-category:hover { background: var(--surface-hover); }
.menu-category.selected { background: var(--surface-accent); box-shadow: inset 0 0 0 1px var(--border); }
/* The chosen row's fill is the badge's own colour: the badge keeps a plate of its own. */
.menu-category.selected .badge { background: var(--surface); }
.menu-category > button:first-child { min-width: 0; display: grid; grid-template-columns: auto 1fr; align-items: center; gap: 10px; padding: 7px 4px; color: var(--ink); background: transparent; border: 0; cursor: pointer; text-align: left; }
.menu-category-text { min-width: 0; display: grid; gap: 3px; }
.menu-category-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 8px; }
/* A picture at the shape the app draws it (1:1), or the section's initial where one is missing: the rows stay
   aligned and a section with no photograph reads as one, not as a broken image. */
.menu-category-thumb { display: grid; flex: none; place-items: center; width: 32px; height: 32px; overflow: hidden; color: var(--muted); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: 4px; font-size: var(--text-sm); font-weight: 600; line-height: 1; }
.menu-category-thumb img { display: block; width: 100%; height: 100%; object-fit: cover; }
/* A long name wraps to a second line before it is cut; the whole name is the row's title. */
.menu-category strong { display: -webkit-box; overflow: hidden; font-size: var(--text-sm); font-weight: 600; line-height: 1.3; overflow-wrap: anywhere; -webkit-box-orient: vertical; -webkit-line-clamp: 2; }
.menu-category small { color: var(--muted); font-size: var(--text-xs); }
/* Stacked above the dishes, the sections fill the width in columns instead of one tall list. */
@media (max-width: 1100px) { .menu-split { grid-template-columns: minmax(0, 1fr); } .menu-categories { grid-template-columns: repeat(auto-fill, minmax(240px, 1fr)); } }
/* The dishes of the chosen section: the name keeps a readable width, the price a figure, the badges under the name. */
.menu-products td:first-child { min-width: 200px; }
.menu-products td.num { width: 1%; }
.menu-products .flag-row { margin-top: 4px; padding: 0; gap: 6px; }
@media (width <= 760px) {
    /* A phone: a card per dish, its name and edit key on the first line, its price, state and stop list under it. */
    .menu-products thead { display: none; }
    .menu-products, .menu-products tbody { display: block; }
    .menu-products tr { display: grid; grid-template-columns: auto auto minmax(0, 1fr) auto; grid-template-areas: "name name name edit" "price state stop stop"; align-items: center; gap: 8px 12px; padding: 12px 20px; border-bottom: 1px solid var(--line-soft); }
    .menu-products tbody tr:last-child { border-bottom: 0; }
    .menu-products td { display: block; min-width: 0; padding: 0; border: 0; }
    .menu-products td:first-child { grid-area: name; min-width: 0; }
    .menu-products td.num { grid-area: price; width: auto; text-align: left !important; }
    .menu-products td.menu-product-status { grid-area: state; }
    .menu-products td.menu-product-stop { grid-area: stop; color: var(--muted); font-size: var(--text-sm); }
    .menu-products td.menu-product-stop::before { content: attr(data-label) ": "; }
    .menu-products.pinned-actions td:last-child { grid-area: edit; width: auto; position: static; background: transparent; box-shadow: none; }
    .menu-products.pinned-actions td[colspan] { grid-area: auto / 1 / auto / -1; }
}

/* The allergen grid: the dish name stays put while the eye travels right. The name wraps inside a fixed column and its
   state sits under it, so the fourteen columns keep the room (inline, the badge made the column 670 px wide). */
.allergen-grid th[scope="row"] { position: sticky; left: 0; z-index: 1; width: 260px; min-width: 180px; max-width: 280px; background: var(--surface); color: var(--ink); font-size: var(--text-sm); font-weight: 500; line-height: 1.3; text-align: left; white-space: normal; overflow-wrap: anywhere; }
.allergen-grid th[scope="row"] .badge { display: flex; width: fit-content; margin: 4px 0 0; }
.allergen-grid td { padding: 2px 4px; text-align: center; }
/* Every column is named in words, set on its side so fourteen fit across; the headings stay over a long grid. */
.allergen-grid thead th { z-index: 2; padding: 8px 6px; color: var(--muted); font-size: var(--text-xs); white-space: nowrap; }
.allergen-grid thead th:not(:first-child) { height: 128px; padding: 8px 4px; text-align: center; vertical-align: bottom; }
.allergen-grid thead th:first-child { left: 0; z-index: 3; padding-inline: 14px; vertical-align: bottom; }
.allergen-head { display: inline-block; max-height: 112px; line-height: 1.2; text-align: left; white-space: normal; transform: rotate(180deg); writing-mode: vertical-rl; }
/* The whole cell is the target, not only its 16 px box; the row lights up to its name. */
.allergen-cell { display: grid; place-items: center; min-height: 36px; cursor: pointer; }
@media (hover: hover) { .allergen-grid tbody tr:hover th[scope="row"] { background: var(--surface-hover); } }
/* A long grid scrolls inside its panel, under its headings, and the page's Save stays in view. On a phone the page scrolls. */
@media (min-width: 761px) { .allergen-scroll { max-height: calc(100dvh - 240px); overflow: auto; } }
/* The filters on one line centred on the select, the count at the far end; a catalogue filter is as wide as its
   choices read, whatever the longest dish name is. */
.allergen-toolbar { flex-wrap: wrap; row-gap: 12px; }
.allergen-toolbar > .toggle { align-items: center; min-height: var(--control-md); white-space: nowrap; }
.allergen-toolbar > p.hint { display: flex; align-items: center; min-height: var(--control-md); margin: 0 0 0 auto; font-variant-numeric: tabular-nums; white-space: nowrap; }
.catalogue-filter select { width: clamp(220px, 28vw, 360px); max-width: 100%; }
@media (width <= 760px) {
    .allergen-grid th[scope="row"], .allergen-grid thead th:first-child { width: 40vw; min-width: 0; max-width: 150px; padding-inline: 10px; }
    .allergen-toolbar > p.hint { margin-left: 0; }
    .catalogue-filter select { width: 100%; }
}

/* The stop list: a row off sale reads as off sale from across a kitchen. The page stops at a width a
   row can be read across, so a dish is never 1250 px from its own switch. */
.stop-list-page { max-width: 1080px; }
/* The branches are a filter of one choice (the segmented plate); a long name wraps inside its segment
   instead of running past the screen, and a wrapped row of segments fills the plate. */
.filter-bar.branch-strip { flex-wrap: wrap; overflow-x: visible; }
.branch-strip .button { flex: 1 1 auto; justify-content: space-between; gap: 8px; min-width: 0; max-width: 100%; min-height: var(--control-md); padding-block: 6px; text-align: left; white-space: normal; }
.branch-strip-name { min-width: 0; overflow-wrap: anywhere; }
.branch-strip .badge { flex: none; }
/* The pause stands beside what it pauses, as a switch with a 44 px reach (the kitchen opens this on a touch screen). */
.branch-pause .section-heading { align-items: center; justify-content: flex-start; gap: var(--space-3) var(--space-6); }
.branch-pause .section-heading > div:first-child { flex: 0 1 auto; }
.branch-pause .switch, .stop-list-table .switch { min-height: var(--control-lg); padding-inline: var(--space-2); }
/* In a row the switch's reach overlaps the cell's padding rather than making every dish 20 px taller. */
.stop-list-table .switch { margin-block: -8px; }
.stop-list-page .table-toolbar { flex-wrap: wrap; }
.stop-list-page .search-box { flex: 1 1 220px; max-width: 320px; }
.stop-list-table td.num { width: 9rem; }
.stop-list-table th:last-child, .stop-list-table td:not([colspan]):last-child { width: 1%; text-align: right; white-space: nowrap; }
/* Off sale: struck through, greyed, and said in a word; its switch stays at full strength. */
tr.stopped td { color: var(--subtle); }
tr.stopped td strong { text-decoration: line-through; }
@media (max-width: 900px) {
    /* Narrow: a dish per row, its category and price under its name and its switch beside both, rather
       than four columns squeezed to five-line cells. */
    .stop-list-table thead { display: none; }
    .stop-list-table, .stop-list-table tbody { display: block; }
    .stop-list-table tr { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; grid-template-areas: "name name switch" "cat price switch"; align-items: center; gap: 2px var(--space-3); padding: var(--space-3) var(--space-4); border-bottom: 1px solid var(--line-soft); }
    .stop-list-table tbody tr:last-child { border-bottom: 0; }
    .stop-list-table td { padding: 0; border: 0; }
    .stop-list-table tbody tr:hover td { background: transparent; }
    .stop-list-table tbody tr:hover { background: var(--surface-hover); }
    .stop-list-table td:nth-child(1) { grid-area: name; }
    .stop-list-table td:nth-child(2) { grid-area: cat; color: var(--muted); font-size: var(--text-xs); }
    .stop-list-table td:nth-child(3) { grid-area: price; width: auto; font-size: var(--text-xs); }
    .stop-list-table td:nth-child(4) { grid-area: switch; }
    .stop-list-table td:not([colspan]):last-child { width: auto; }
    .stop-list-table td[colspan] { grid-column: 1 / -1; }
}
@media (width <= 760px) { .branch-strip .button { flex-basis: 100%; } }

/* APPS-1: the shelf of apps — what the cabinet can do. Two shelves by what the business has; an app is
   a row of the cabinet's own kind (a mark, a name, one line) with its state under it as a lamp and a
   word. One column under a thumb, a grid of the same rows on a wide screen. A connected app this
   account can open is the whole row; one it cannot, or one not connected, is the row without a way in. */
.app-shelf { margin-bottom: var(--space-6); }
.app-shelf > h2 { display: flex; align-items: baseline; gap: 8px; margin: 0 0 var(--space-2); font-size: var(--text-lg); font-weight: 600; }
.app-count { color: var(--muted); font-size: var(--text-sm); font-weight: 500; font-variant-numeric: tabular-nums; }
.app-shelf-how { max-width: 68ch; margin: 0 0 var(--space-3); color: var(--label); font-size: var(--text-md); line-height: 1.45; text-wrap: pretty; }
.app-list { display: grid; grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); margin: 0; padding: 0; overflow: hidden; list-style: none; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.app-list > li { display: grid; min-width: 0; box-shadow: 1px 0 0 var(--line-soft), 0 1px 0 var(--line-soft); }
.app-row { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; align-items: start; gap: var(--space-3); min-height: 72px; padding: 14px var(--space-4); color: var(--ink); text-decoration: none; }
a.app-row { transition: background-color 120ms ease; }
a.app-row:hover { color: var(--ink); background: var(--surface-hover); }
a.app-row:focus-visible { outline-offset: -2px; }
.app-row-copy { display: grid; justify-items: start; gap: 2px; min-width: 0; }
.app-row-copy strong { font-size: var(--text-md); font-weight: 600; line-height: 1.3; }
.app-row-copy small { color: var(--muted); font-size: var(--text-sm); line-height: 1.35; text-wrap: pretty; }
.app-row-copy .badge { margin-top: 6px; }
.app-row > .nav-row-go { align-self: center; width: 16px; height: 16px; color: var(--subtle); transition: color 120ms ease; }
a.app-row:hover > .nav-row-go { color: var(--ink); }
/* Not connected stays on the shelf, and quiet: the mark and the name step back, the line stays readable. */
.app-row.off .nav-row-mark { color: var(--subtle); }
/* POSTER-4: an app the owner connects themselves says so where the arrow alone would stand. */
.app-row-action { display: inline-flex; align-items: center; align-self: center; gap: 4px; color: var(--ink); font-size: var(--text-sm); font-weight: 600; white-space: nowrap; }
.app-row-action .icon { width: 14px; height: 14px; color: var(--subtle); transition: color 120ms ease; }
a.app-row:hover .app-row-action .icon { color: var(--ink); }
.app-row.off strong { color: var(--label); }

/* POSTER-1: the Poster app's own page. What the connection is, then three steps in the order they are
   done; each step's answer stands inside the step, beside the key that asked for it. */
.poster-state { padding: 16px 20px; }
.poster-state-line { display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 12px; }
.poster-state-line strong { font-size: var(--text-lg); font-weight: 600; overflow-wrap: anywhere; }
.poster-state-line small { color: var(--muted); font-size: var(--text-sm); overflow-wrap: anywhere; }
.poster-state p { max-width: 68ch; margin: 8px 0 0; color: var(--label); line-height: 1.45; text-wrap: pretty; }
.poster-step > :is(.poster-answer, .poster-preview, .poster-last, .poster-needs) { margin: 0 20px 16px; }
.poster-step .section-heading p { max-width: 68ch; text-wrap: pretty; }
.poster-ok { display: flex; align-items: baseline; gap: 8px; margin: 0; font-weight: 500; }
.poster-ok::before { flex: none; width: 8px; height: 8px; content: ""; background: var(--green-lamp); border-radius: var(--radius-mark); transform: translateY(-1px); }
.poster-answer > .alert { margin-top: 10px; }
.poster-needs { color: var(--muted); }
/* A branch and the Poster location it stands for: the name, the choice, the key, and the answer on its own line under them. */
.poster-branches { margin: 0 0 8px; padding: 0; list-style: none; border-top: 1px solid var(--line-soft); }
.poster-branches > li { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.2fr) auto; align-items: center; gap: 6px 12px; padding: 12px 20px; border-bottom: 1px solid var(--line-soft); }
.poster-branches > li:last-child { border-bottom: 0; }
.poster-branch-name { font-weight: 600; overflow-wrap: anywhere; }
.poster-branches select { width: 100%; min-width: 0; min-height: var(--control-md, 40px); }
.poster-branch-current { grid-column: 2 / -1; color: var(--label); }
.poster-row-status { grid-column: 1 / -1; min-height: 0; font-size: var(--text-sm); }
.poster-row-status:empty { display: none; }
.poster-row-problem { color: var(--red); }
.poster-row-hint { color: var(--muted); }
/* What a transfer would do: the totals in words, then the rows themselves. */
.poster-preview { padding-top: 4px; }
.poster-summary { margin: 0 0 6px; }
.poster-kinds { margin: 0 0 14px; padding: 0; color: var(--label); font-size: var(--text-sm); list-style: none; font-variant-numeric: tabular-nums; }
.poster-preview h3, .poster-last h3 { margin: 14px 0 6px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.poster-rows { max-height: 420px; margin: 0; padding: 0; overflow-y: auto; list-style: none; border: 1px solid var(--line-soft); border-radius: var(--radius-control); }
.poster-rows > li { display: grid; grid-template-columns: minmax(96px, auto) minmax(0, 1fr); align-items: baseline; gap: 4px 12px; padding: 9px 12px; }
.poster-rows > li + li { border-top: 1px solid var(--line-soft); }
.poster-rows > li > .badge { justify-self: start; }
.poster-rows > li > .poster-row-copy:only-child { grid-column: 1 / -1; }
.poster-row-copy { display: grid; gap: 1px; min-width: 0; }
.poster-row-copy strong { font-weight: 600; overflow-wrap: anywhere; }
.poster-row-copy small { color: var(--muted); font-size: var(--text-sm); }
.poster-preview > .form-actions { padding: 14px 0 0; }
.poster-last { padding-top: 12px; border-top: 1px solid var(--line-soft); }
.poster-last h3 { margin-top: 0; }
.poster-last p { max-width: 68ch; margin: 0; color: var(--label); font-variant-numeric: tabular-nums; }
/* POSTER-2: the fourth step says on a line of its own whether orders go to Poster, then the last day and what did not get there. */
.poster-step > .poster-ok { margin: 0 20px 16px; }
.poster-last > h3 ~ h3 { margin-top: 14px; }
.poster-last > .hint { margin-top: 8px; color: var(--muted); }
/* POSTER-3: the refresh switch and the photo note are blocks of the menu step, so their button and their warning start at the block's own edge. */
.poster-last > .form-actions { padding: 12px 0 0; }
.poster-last > .alert { margin: 10px 0 0; }
/* POSTER-4: the owner's own key. Where to find it as three numbered lines, one field, one key;
   on the connected screen the same form waits behind «Replace the key» in a quiet last block. */
.poster-key-steps { max-width: 68ch; margin: 0 20px 16px; padding-left: 22px; color: var(--label); line-height: 1.5; }
.poster-key-steps li + li { margin-top: 4px; }
.poster-key-form { display: grid; gap: 12px; max-width: 560px; padding: 0 20px; }
.poster-key-form > .form-actions { padding: 0; }
.poster-key-form > .alert { margin: 0; }
.poster-key-line { max-width: 68ch; margin: 0 20px 12px; color: var(--label); overflow-wrap: anywhere; }
.poster-key-block > .form-actions { padding-top: 0; }
.poster-key-block > .poster-key-form { margin-top: 4px; }
/* POSTER-5: the way through Poster — one key and the one line that says what happens next — and the
   key's own form folded under it as the second way. */
.poster-sign-in { display: grid; justify-items: start; gap: 10px; padding: 0 20px 18px; }
.poster-sign-in > p { max-width: 68ch; margin: 0; color: var(--label); line-height: 1.5; }
.poster-key-details > p { max-width: 68ch; margin: 10px 0 0; color: var(--label); line-height: 1.5; }
.poster-key-details > .poster-key-steps { margin: 10px 0 16px; }
.poster-key-details > .poster-key-form { padding: 0; }
.poster-key-details { margin-bottom: 0; }
.poster-connect > .poster-key-line { margin-top: 14px; margin-bottom: 0; }
.poster-key-details > summary { padding: 8px 0; }
/* POSTER-5b: the last page of the tab that went to Poster for a support session — the sign-in's sheet,
   holding one outcome: a lamp and a heading (green when it connected, amber when the person has to act),
   the sentence, and under a rule where to go next. */
.poster-return h1 { display: flex; align-items: baseline; gap: 10px; margin-bottom: 10px; font-size: var(--text-2xl); }
.poster-return h1::before { flex: none; width: 9px; height: 9px; content: ""; background: var(--amber-lamp); border-radius: var(--radius-mark); transform: translateY(-2px); }
.poster-return[data-outcome="connected"] h1::before { background: var(--green-lamp); }
.poster-return p { margin-bottom: 0; color: var(--label); line-height: 1.5; overflow-wrap: anywhere; }
.poster-return .poster-return-lead { color: var(--ink); }
.poster-return .poster-return-next { margin-top: var(--space-4); padding-top: var(--space-4); border-top: 1px solid var(--line-soft); color: var(--muted); font-size: var(--text-sm); }
/* The console: a derived field of an integration is a fact to read, never a box to type in. */
.integration-fact { display: block; min-height: var(--control-md, 40px); padding: 9px 0 0; color: var(--ink); font-weight: 500; overflow-wrap: anywhere; }
.integration-fact.unknown { color: var(--muted); font-weight: 400; }
.integration-about { max-width: 72ch; margin: 0 20px 12px; color: var(--label); line-height: 1.45; }

/* The business's settings: the shop's name takes the widest share of a wide row; the currency, set once,
   reads as a value beside the fields; the languages are four choices, not a run of marks and words. */
@media (width > 1100px) { .form-grid.three.settings-basics { grid-template-columns: minmax(0, 2fr) repeat(2, minmax(0, 1fr)); } }
.readonly-value { display: flex; align-items: center; min-height: var(--control-md); color: var(--ink); font-size: var(--text-md); font-weight: 600; font-variant-numeric: tabular-nums; }
.flag-row.locale-choices { gap: 8px 20px; }
@media (width <= 900px) { .form-grid.two.settings-contacts { grid-template-columns: minmax(0, 1fr); } }
/* The phone list lines up with the fields above it: its words and its rules on the panel's inset (a
   dialog's), each field as wide as its column. Under 900 px each number is a card, its switch named. */
.phone-list { padding-inline: 20px; }
.cabinet-dialog .phone-list { padding-inline: 24px; }
.phone-list table { table-layout: fixed; max-width: 880px; }
.phone-list th:first-child, .phone-list td:first-child { padding-left: 0; }
.phone-list th:last-child, .phone-list td:last-child { padding-right: 0; }
.phone-list th:first-child { width: 36%; }
.phone-list th:nth-child(3) { width: 150px; }
.phone-list th:last-child { width: 48px; }
.phone-list td input:not([type="radio"]) { width: 100%; min-width: 0; }
.phone-list .toggle input[type="radio"] { flex: none; width: 16px; height: 16px; margin: 0; accent-color: var(--action); }
.phone-list tbody tr:last-child td { border-bottom: 0; }
.form-section > .phones-section { padding-bottom: 0; }
@media (width > 900px) { .phone-primary-text { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; } }
@media (width <= 900px) {
    .phone-list thead { display: none; }
    .phone-list table, .phone-list tbody { display: block; }
    .phone-list tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 8px 12px; align-items: center; padding: 12px 0; border-bottom: 1px solid var(--line-soft); }
    .phone-list tbody tr:last-child { border-bottom: 0; }
    .phone-list td { display: block; padding: 0; border: 0; }
    .phone-list td:first-child, .phone-list td:nth-child(2) { grid-column: 1 / -1; }
}
@media (width <= 760px) { .cabinet-dialog .phone-list { padding-inline: 16px; } }
/* FFR-1: the social links read like the phone list above them: the network, the address (the widest),
   the caption, the switch, the remove key. Under 900 px each link is a card, its switch named. */
.social-list { padding-inline: 20px; }
.social-list table { table-layout: fixed; max-width: 980px; }
.social-list th:first-child, .social-list td:first-child { padding-left: 0; }
.social-list th:last-child, .social-list td:last-child { padding-right: 0; }
.social-list th:first-child { width: 150px; }
.social-list th:nth-child(3) { width: 24%; }
.social-list th:nth-child(4) { width: 120px; }
.social-list th:last-child { width: 48px; }
.social-list td input:not([type="checkbox"]), .social-list td select { width: 100%; min-width: 0; }
.social-list tbody tr:last-child td { border-bottom: 0; }
.settings-apps { padding-top: 0; }
@media (width > 900px) { .social-visible-text { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; } }
@media (width <= 900px) {
    .social-list thead { display: none; }
    .social-list table, .social-list tbody { display: block; }
    .social-list tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 8px 12px; align-items: center; padding: 12px 0; border-bottom: 1px solid var(--line-soft); }
    .social-list tbody tr:last-child { border-bottom: 0; }
    .social-list td { display: block; padding: 0; border: 0; }
    .social-list td:nth-child(-n+3) { grid-column: 1 / -1; }
}
/* SEO-1/SEO-2: a search result as Google draws it, the count under each SEO text, and the SEO
   section of an editor, folded until it is opened. */
.seo-snippet { display: grid; gap: 2px; max-width: 600px; margin: 0; padding: 14px 16px; background: var(--surface-subtle); border-radius: var(--radius-control); overflow-wrap: anywhere; }
.seo-snippet-caption { margin-bottom: 6px; color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
.seo-snippet-url { color: var(--label); font-size: var(--text-sm); }
.seo-snippet-title { color: var(--ink); font-size: var(--text-lg); font-weight: 600; line-height: 1.35; }
.seo-snippet-description { margin: 0; color: var(--label); font-size: var(--text-sm); line-height: 1.5; }
.counted-field .char-count { justify-self: end; font-variant-numeric: tabular-nums; }
.counted-field .char-count.over { color: var(--red); font-weight: 600; }
.seo-section-toggle { display: inline-flex; align-items: center; gap: 8px; min-height: var(--control-md); padding: 0; color: var(--ink); background: none; border: 0; font: inherit; font-weight: 600; cursor: pointer; text-align: left; }
.seo-section-toggle .icon { width: 16px; height: 16px; color: var(--muted); }
.seo-section-body { display: grid; gap: 16px; }
.image-tile.og { display: grid; flex: none; place-items: center; width: 228px; max-width: 100%; height: 120px; }
/* SEO-1/SEO-5: lists edited in place — the verification codes, the redirects. A row of fields on a
   wide screen; under 900 px each row is a card, its fields named, the remove key at its corner. */
.edit-list { padding-inline: 20px; }
.edit-list table { table-layout: fixed; max-width: 980px; }
.edit-list th:first-child, .edit-list td:first-child { padding-left: 0; }
.edit-list th:last-child, .edit-list td:last-child { width: 48px; padding-right: 0; }
.edit-list td input, .edit-list td select { width: 100%; min-width: 0; }
.edit-list tbody tr:last-child td { border-bottom: 0; }
.verification-list table { max-width: 760px; }
.verification-list th:first-child { width: 180px; }
/* P1-5: wide enough for «302 — тимчасово» and the chevron, so the kind reads without opening it. */
.redirect-list th:nth-child(3) { width: 200px; }
.redirect-list td { vertical-align: top; }
.redirect-problem { display: block; margin-top: 4px; overflow-wrap: anywhere; }
@media (width <= 900px) {
    .edit-list thead { display: none; }
    .edit-list table, .edit-list tbody { display: block; }
    .edit-list tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 8px 12px; align-items: end; padding: 12px 0; border-bottom: 1px solid var(--line-soft); }
    .edit-list tbody tr:last-child { border-bottom: 0; }
    .edit-list td { display: block; width: auto; padding: 0; border: 0; }
    .edit-list td:not(:last-child) { grid-column: 1; }
    .edit-list td:last-child { grid-column: 2; grid-row: 1; width: auto; }
    .edit-list td[data-label]::before { display: block; margin-bottom: 4px; content: attr(data-label); color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
}
/* SEO-4: the site's pages and the blocks a page is built from. A block is a card with its type and
   its keys on top; a hidden one recedes; one the save refused is outlined. */
.site-page-path { font-family: var(--font-mono); font-size: var(--text-sm); overflow-wrap: anywhere; }
.site-blocks { display: grid; gap: 12px; padding: 0 20px; }
.site-blocks-empty { margin: 0 20px; }
.site-block { min-width: 0; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.site-block.hidden-block { background: var(--surface-subtle); }
.site-block.invalid { border-color: var(--red); }
.site-block-head { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 8px 12px; padding: 10px 16px; border-bottom: 1px solid var(--line-soft); }
.site-block-name { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; min-width: 0; font-weight: 600; }
.site-block-keys { display: flex; flex-wrap: wrap; gap: 6px; }
.site-block-body { display: grid; gap: 16px; padding: 16px; }
.site-block-body .form-grid { padding: 0; }
.site-block-body .alert { margin: 0; }
/* P2-9: an empty block says so in amber, under its type's hint; the save still takes it. */
.site-block-body .block-empty-hint { margin: 0; color: var(--amber); }
.site-block-items { display: grid; gap: 10px; }
.site-block-item { display: grid; gap: 12px; padding: 12px; background: var(--surface-subtle); border-radius: var(--radius-control); }
.site-block-item-head { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 8px; font-size: var(--text-sm); font-weight: 600; }
.site-block-add { display: flex; flex-wrap: wrap; align-items: end; gap: 8px; padding: 16px 20px 20px; }
.site-block-add .field { flex: 1 1 220px; max-width: 320px; }
.site-product-picker { display: grid; gap: 4px; max-height: 260px; overflow-y: auto; padding: 8px 12px; border: 1px solid var(--border); border-radius: var(--radius-control); }
.site-page-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 8px 16px; padding: 0 20px; }
.page-conflict { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 12px; }
@media (width <= 760px) {
    .site-blocks { padding: 0 16px; }
    .site-block-body { padding: 12px; }
    .site-block-add { padding-inline: 16px; }
}
/* Site analytics: the two consent switches belong together; the fields they unlock stand a step below. */
.toggle-stack { display: grid; padding: 0 20px; }
.toggle-stack + .form-grid { margin-top: 16px; }
.consent-note { margin: 0; }
/* Sign-in without SMS: the caution stands above the form with its mark; the form's panel keeps its inset. */
.assisted-caution { grid-template-columns: auto minmax(0, 1fr); align-items: start; column-gap: 10px; }
.assisted-caution > .icon { width: 18px; height: 18px; margin-top: 1px; color: var(--label); }
.assisted-form { padding-top: 20px; }
.assisted-form > .form-actions:last-child { padding-bottom: 0; }
/* The change log: the time never breaks, a record's id is set as an identifier and recedes, and on a
   phone each change is a card (who and when, then what and where) rather than a table cut off at its edge. */
.audit-id { color: var(--muted); font-family: var(--font-mono); font-size: var(--text-xs); white-space: nowrap; }
@media (width <= 760px) {
    .audit-log thead { display: none; }
    .audit-log, .audit-log tbody { display: block; }
    .audit-log tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 2px 12px; padding: 12px 16px; border-bottom: 1px solid var(--line-soft); }
    .audit-log tbody tr:last-child { border-bottom: 0; }
    .audit-log td { padding: 0; border: 0; }
    .audit-log td:first-child { grid-column: 2; grid-row: 1; color: var(--muted); font-size: var(--text-xs); }
    .audit-log td:nth-child(2) { grid-column: 1; grid-row: 1; font-weight: 600; }
    .audit-log td:nth-child(3), .audit-log td:nth-child(4) { grid-column: 1 / -1; }
}

/* Billing history: what a tenant was invoiced under, kept, and quieter than a live subscription. */
.billing-history { background: var(--surface-subtle); }
.billing-history .section-heading h2 { font-size: var(--text-lg); }
.billing-history th { background: var(--surface-subtle); }
.billing-history > .table-scroll { background: none; }
.billing-history td { color: var(--muted); }
.billing-history td:first-child { color: var(--ink); }
.billing-history tbody tr:hover td { background: transparent; }

/* A courier on an order: the name and the way to reach them, and once, the link to hand on. */
.courier-row { display: flex; flex-wrap: wrap; align-items: center; gap: 9px; margin: 0 0 14px; padding: 10px 12px; background: var(--surface-subtle); border-radius: var(--radius-control); font-size: var(--text-sm); }
.courier-label { color: var(--muted); font-size: var(--text-xs); font-weight: 600; }
.courier-link { display: flex; flex-wrap: wrap; align-items: center; gap: 9px; margin: -6px 0 14px; padding: 10px 12px; background: var(--surface-subtle); border-radius: var(--radius-control); font-size: var(--text-sm); }
.courier-link code { flex: 1 1 320px; overflow-wrap: anywhere; font-size: 12px; }
.courier-link small { flex: 1 1 100%; }

/* ---------------------------------------------------------------------------------- the order queue
   Scanned, not read: the number, how long it has waited and the next step lead every row. The
   columns never move; a row restyles in place as its order moves on. */
.queue-panel { overflow: hidden; }
.queue-table td { padding-block: 12px; }
.queue-number { font-family: var(--font-figures); font-size: 21px; font-weight: 600; letter-spacing: -0.01em; font-variant-numeric: tabular-nums; }
/* The number is the way into the order: it carries the engraved underline even where nothing hovers. */
.queue-table .link-button { text-decoration: none; }
.queue-table .link-button .queue-number { text-decoration: underline; text-decoration-thickness: 1px; text-decoration-color: color-mix(in oklch, currentColor 30%, transparent); text-underline-offset: 5px; }
.queue-table .link-button:hover .queue-number { text-decoration-color: currentColor; }
.queue-table th:first-child { width: 5rem; }
/* How long it has waited on the first line; the clock and the chips share the second (one line at
   desktop widths, so the cell never grows a third). */
.queue-age { display: block; color: var(--ink); font-family: var(--font-figures); font-size: var(--text-lg); font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.queue-when { white-space: nowrap; }
.queue-placed { display: inline; margin-right: var(--space-2); color: var(--muted); font-size: var(--text-xs); }
.queue-placed .branch-time { font-size: inherit; }
.queue-meta { display: inline-flex; flex-wrap: wrap; gap: 4px; vertical-align: middle; }
/* The keys keep to their content at the panel's right edge; the first key has one width whatever its
   word (the longest, «Передать курьеру», is 153 px), so Reject stands at the same place on every row. */
.queue-table td.row-actions { width: 1%; }
.queue-table td.row-actions .button { min-height: var(--control-md); padding: 0 14px; font-size: var(--text-md); }
.queue-table td.row-actions .button.primary { min-width: 10rem; }
.queue-table tr.waiting .queue-age { color: var(--amber); }
.queue-customer small { display: block; color: var(--muted); font-size: var(--text-xs); }
.table-summary.queue-total { border-top: 1px solid var(--border); }
/* The status plate scrolls sideways under the shared rule; here its scrollbar stays, so a mouse can reach the rest. */
@media (max-width: 1100px) { .queue-filter { scrollbar-width: thin; } }
/* Up to 1100 px the rail still takes 224 px, and six columns that cannot shrink put the keys past the
   panel's edge: a card per order instead. The number, its state, how it leaves and how long it has
   waited on the first line, the customer under them, the keys last; every card keeps the same columns. */
@media (max-width: 1100px) {
    .queue-table thead { display: none; }
    .queue-table, .queue-table tbody { display: block; }
    .queue-table tr { display: grid; align-items: baseline; gap: var(--space-2) var(--space-4); padding: var(--space-3) var(--space-4); border-bottom: 1px solid var(--line-soft); }
    .queue-table tbody tr:last-child { border-bottom: 0; }
    .queue-table td { padding: 0; border: 0; }
    .queue-table tbody tr:hover td, .queue-table tbody tr.selected td { background: transparent; }
    .queue-table tbody tr:hover { background: var(--surface-hover); }
    .queue-table tbody tr.selected { background: var(--surface-accent); }
    .queue-now tr { grid-template-columns: 3.5rem 9rem minmax(0, 1fr) 9.5rem; grid-template-areas: "num status fulfil when" "num cust cust when" "act act act act"; }
    .queue-later tr { grid-template-columns: 3.5rem minmax(0, 1fr) minmax(0, 1fr); grid-template-areas: "num when status" "num fulfil cust"; }
    .queue-table td:first-child { grid-area: num; }
    .queue-now td:nth-child(2), .queue-later td:nth-child(3) { grid-area: status; }
    .queue-now td:nth-child(3), .queue-later td:nth-child(4) { grid-area: fulfil; }
    .queue-now td:nth-child(4), .queue-later td:nth-child(5) { grid-area: cust; }
    .queue-now td:nth-child(5), .queue-later td:nth-child(2) { grid-area: when; }
    .queue-when { white-space: normal; }
    .queue-table td.row-actions { grid-area: act; display: flex; flex-wrap: wrap; justify-content: flex-end; gap: var(--space-2); width: auto; white-space: normal; }
    .queue-table td.row-actions > * + * { margin-left: 0; }
    /* An order waiting for the customer's money has no key to press: no empty row under it. */
    .queue-table td.row-actions:empty { display: none; }
}
@media (width <= 760px) {
    /* A phone: the number with its state at the right edge, the customer, then the time with how it leaves;
       the two keys share the card's width equally whatever their words. */
    .queue-table tr { gap: var(--space-1) var(--space-3); padding: var(--space-3) 14px; }
    .queue-now tr { grid-template-columns: minmax(0, 1fr) auto; grid-template-areas: "num status" "cust cust" "when fulfil" "act act"; }
    .queue-later tr { grid-template-columns: minmax(0, 1fr) auto; grid-template-areas: "num status" "when when" "cust fulfil"; }
    .queue-now td:nth-child(2), .queue-now td:nth-child(3), .queue-later td:nth-child(3), .queue-later td:nth-child(4) { justify-self: end; }
    .queue-table td.row-actions { display: grid; grid-auto-flow: column; grid-auto-columns: minmax(0, 1fr); padding-top: var(--space-2); }
    .queue-table td.row-actions .button, .queue-table td.row-actions .button.primary { min-width: 0; min-height: var(--control-lg); }
}
/* The reject question: the number set as in the queue, the phone under the name. */
.reject-facts { align-items: baseline; }
.reject-facts small { display: block; color: var(--muted); font-size: var(--text-xs); }
.queue-auto-refresh { min-height: var(--control-md); padding-inline: var(--space-1); }
.order-source { margin-left: 6px; }
/* Times on the operator screens are the branch's own; the zone is named only when it matters. */
.branch-time { white-space: nowrap; }
.branch-time .zone { margin-left: 4px; color: var(--muted); font-weight: 500; }
.order-timing { gap: 4px; }
.order-timing .zone { color: inherit; opacity: .8; }

/* Cancellation requests sit above the queue: work the operator must answer before it goes stale. */
.cancellation-requests { margin: 0 0 var(--space-5); overflow: hidden; background: var(--surface); border: 1px solid var(--amber-line); border-radius: var(--radius-surface); }
.cancellation-requests h2 { display: flex; align-items: center; gap: 8px; margin: 0; padding: 12px 16px; font-size: var(--text-md); background: var(--amber-soft); border-bottom: 1px solid var(--amber-line); }
.cancellation-requests h2::before { width: 8px; height: 8px; content: ""; background: var(--amber-lamp); border-radius: var(--radius-mark); }

/* The open order: what was ordered first, then the paperwork. */
.order-detail { margin-top: var(--space-5); padding: 16px 20px 20px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.order-detail > header { display: flex; align-items: center; justify-content: space-between; gap: 16px; margin-bottom: 14px; padding-bottom: 12px; border-bottom: 1px solid var(--line-soft); }
.order-detail > header h2 { margin: 0; font-size: var(--text-xl); font-variant-numeric: tabular-nums; }
.order-detail .form-section { padding: 16px 0 0; margin-top: 16px; border-top: 1px solid var(--line-soft); }
.order-detail .form-section .section-heading, .order-detail .form-section .form-grid { padding-inline: 0; }
.order-detail .form-section .section-heading { padding-top: 0; }
.detail-items { width: 100%; margin-bottom: 4px; border-collapse: collapse; }
.detail-items td { padding: 8px 0; border-bottom: 1px solid var(--line-soft); vertical-align: top; }
.detail-items tbody tr:hover td { background: transparent; }
.detail-items .quantity { width: 3.5rem; color: var(--muted); font-variant-numeric: tabular-nums; white-space: nowrap; }
/* Amounts line up when the digits do. */
.detail-items .amount { text-align: right; white-space: nowrap; font-variant-numeric: tabular-nums; }
.detail-items small { color: var(--muted); }
.detail-items tfoot td { padding-top: 10px; border-bottom: none; }
.detail-items tfoot .total td { border-top: 1px solid var(--border); font-size: var(--text-lg); }
.detail-items tr.cash-change td { color: var(--amber); font-weight: 600; }
/* The kitchen ticket of the open order: its state beside the title, the one button under it. */
.operator-kitchen-ticket .section-heading { flex-wrap: wrap; }
.operator-kitchen-ticket-body { display: flex; flex-direction: column; align-items: flex-start; gap: 8px; padding: 0 20px; }
.order-detail .operator-kitchen-ticket-body { padding-inline: 0; }
.operator-kitchen-ticket-body p { margin: 0; }
/* POSTER-2: the order's line about the Poster register — the word and the sentence, and under them what a person here has to do. */
.operator-poster .section-heading p { max-width: 68ch; margin: 4px 0 0; color: var(--label); overflow-wrap: anywhere; }
.operator-poster > .alert { margin: 10px 20px 0; }
.operator-poster-actions { display: flex; flex-wrap: wrap; gap: 8px; padding: 10px 20px 0; }
.operator-poster > .pos-print-error { margin: 8px 20px 0; font-size: var(--text-sm); }
.order-detail .operator-poster > :is(.alert, .pos-print-error) { margin-inline: 0; }
.order-detail .operator-poster-actions { padding-inline: 0; }

/* --------------------------------------------------------------------------------- station bars
   The till and the kitchen share one strip of chrome: a graphite band holding where this is, who is
   on it, and the way to hand it on. Everything else belongs to the work under it. */
.pos-shell, .kds-shell { display: flex; flex-direction: column; height: 100vh; height: 100dvh; color: var(--ink); background: var(--canvas); }
.pos-bar, .kds-bar { --bar-ink: var(--steel-100); --bar-muted: var(--steel-400); --bar-line: oklch(100% 0 0 / .14); --bar-hover: oklch(100% 0 0 / .08); display: flex; align-items: center; gap: 8px; flex: none; min-height: 52px; padding: 4px 16px; color: var(--bar-ink); background: var(--steel-900); border-bottom: 1px solid var(--steel-950); }
.pos-mark { display: grid; place-items: center; flex: none; width: 32px; height: 32px; color: var(--steel-900); background: var(--steel-100); border-radius: var(--radius-control); font-size: 16px; font-weight: 700; }
.pos-mark .icon { width: 19px; height: 19px; }
.pos-title, .kds-title { flex: none; color: #fff; font-size: var(--text-lg); font-weight: 600; white-space: nowrap; }
/* When the strip runs short the names give way, never the keys or the selectors: the business first,
   then the station, then the person, each ending in an ellipsis rather than a clipped letter. */
.pos-bar .shell-tenant, .kds-bar .shell-tenant { flex: 0 3 auto; min-width: 0; max-width: 48ch; margin-left: 2px; color: var(--bar-muted); font-weight: 500; opacity: 1; }
.pos-bar-spacer, .kds-bar-spacer { flex: 1; }
.pos-station, .kds-station { flex: 0 1 auto; min-width: calc(6ch + 20px); max-width: 24ch; overflow: hidden; padding: 3px 9px; color: var(--bar-ink); border: 1px solid var(--bar-line); border-radius: 4px; font-size: var(--text-xs); font-weight: 600; text-overflow: ellipsis; white-space: nowrap; }
.pos-cashier, .kds-cook { display: inline-flex; align-items: center; gap: 6px; flex: 0 1 auto; min-width: 0; max-width: 28ch; color: var(--bar-ink); font-size: var(--text-sm); font-weight: 500; white-space: nowrap; }
:is(.pos-cashier, .kds-cook) > span { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
:is(.pos-cashier, .kds-cook) > .icon { flex: none; }
:is(.pos-bar, .kds-bar) .shell-selector { flex: none; }
:is(.pos-bar, .kds-bar) .button { flex: none; min-height: 36px; color: var(--bar-ink); background: transparent; border-color: var(--bar-line); box-shadow: none; }
@media (hover: hover) { :is(.pos-bar, .kds-bar) .button:hover:not(:disabled) { color: #fff; background: var(--bar-hover); border-color: oklch(100% 0 0 / .24); } }
/* Handing the station on is the one action the bar exists for: the light key on the dark strip. */
:is(.pos-bar, .kds-bar) .button.pos-switch, :is(.pos-bar, .kds-bar) .button.kds-switch { min-height: var(--control-lg); padding-inline: 16px; color: var(--steel-900); background: var(--steel-100); border-color: var(--steel-100); font-weight: 600; }
@media (hover: hover) { :is(.pos-bar, .kds-bar) .button.pos-switch:hover:not(:disabled), :is(.pos-bar, .kds-bar) .button.kds-switch:hover:not(:disabled) { color: var(--steel-900); background: #fff; border-color: #fff; } }
:is(.pos-bar, .kds-bar) .icon-button { width: var(--control-lg); height: var(--control-lg); color: var(--bar-ink); }
:is(.pos-bar, .kds-bar) .icon-button:hover { color: #fff; background: var(--bar-hover); }
:is(.pos-bar, .kds-bar) .shell-selector select { min-width: 0; min-height: 36px; color: var(--bar-ink); background-color: transparent; border-color: var(--bar-line); box-shadow: none; background-image: linear-gradient(45deg, transparent 50%, var(--bar-muted) 50%), linear-gradient(135deg, var(--bar-muted) 50%, transparent 50%); }
:is(.pos-bar, .kds-bar) .shell-selector select option { color: var(--ink); background: var(--surface); }
:is(.pos-bar, .kds-bar) :focus-visible { outline-color: var(--steel-100); }
.pos-main, .kds-main { flex: 1; min-height: 0; overflow: hidden; }
.pos-switch-refused { display: flex; align-items: center; justify-content: space-between; gap: 12px; margin: 0; border-width: 0 0 1px; border-radius: 0; }
.station-overlay { z-index: calc(var(--z-support) + 1); }
/* The overlay's one sentence is its heading: set on the dialog's inset like every other dialog's content. */
.station-overlay .cabinet-dialog > h2 { margin: 0 24px; font-size: var(--text-xl); }
@media (max-width: 1180px) {
    /* A counter or pass screen of 1024–1180: the other workspaces stay one tap away as icons, each still
       named by its hidden label, and the business keeps a shorter place instead of leaving the strip. */
    :is(.pos-bar, .kds-bar) .shell-tenant { max-width: 20ch; }
    :is(.pos-bar, .kds-bar) .button.tertiary { width: 36px; padding: 0; }
    :is(.pos-bar, .kds-bar) .button.tertiary > span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; }
}
@media (max-width: 1023px) {
    :is(.pos-bar, .kds-bar) .shell-tenant { display: none; }
}
@media (width <= 760px) {
    /* A phone: the mark says which workspace this is, so its word and the switch key's label step back
       (still read aloud), and the station and the person keep the room. */
    :is(.pos-title, .kds-title), :is(.pos-bar, .kds-bar) :is(.button.pos-switch, .button.kds-switch) > span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; }
    :is(.pos-bar, .kds-bar) :is(.button.pos-switch, .button.kds-switch) { width: var(--control-lg); padding: 0; }
    .station-overlay .cabinet-dialog > h2 { margin-inline: 16px; }
}

/* --------------------------------------------------------------------------- station chooser (PIN)
   The people who may work here, by name only; one tap, then six digits on keys big enough for a thumb. */
/* One top inset for every state (names, keypad, loading), grown with the screen's height: the heading
   never jumps between states, a wall monitor is not top-heavy, and 1366×768 keeps the foot in view. */
.station-chooser { display: flex; flex-direction: column; align-items: center; gap: 20px; height: 100%; padding: clamp(32px, 20vh - 100px, 128px) 16px 20px; overflow-y: auto; }
.station-chooser-head { display: grid; justify-items: center; gap: 6px; text-align: center; }
.station-chooser-head h1 { margin: 0; font-size: var(--text-3xl); }
.station-chooser-head p { margin: 0; color: var(--muted); font-size: var(--text-lg); }
/* Which station this is: a meta line under the heading, never a label above it. */
.station-chooser-name { display: inline-flex; align-items: center; gap: 6px; color: var(--muted); font-size: var(--text-md); font-weight: 500; }
.station-chooser-name .icon { width: 16px; height: 16px; }
.station-notice { display: flex; align-items: center; justify-content: space-between; gap: 12px; width: min(640px, 100%); }
/* The people sit centred under the heading, as many to a row as fit (three at most), and a
   two-word name stays on one line. */
.station-roster { display: grid; grid-template-columns: repeat(auto-fit, minmax(240px, 280px)); justify-content: center; gap: 12px; width: min(880px, 100%); }
.station-person { display: flex; align-items: center; gap: 12px; min-height: 76px; padding: 12px 16px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-large); cursor: pointer; font-size: var(--text-xl); font-weight: 600; text-align: left; touch-action: manipulation; transition: border-color 120ms ease, background-color 120ms ease, transform var(--press) var(--ease-out); }
.station-person > span:last-child { min-width: 0; overflow-wrap: anywhere; }
.station-person:hover:not(:disabled) { background: var(--surface-hover); border-color: var(--input-border); }
.station-person:active:not(:disabled) { transform: scale(.97); }
.station-person:disabled { opacity: .5; cursor: not-allowed; }
.station-person-mark { display: grid; place-items: center; flex: none; width: 44px; height: 44px; color: var(--ink); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); font-family: var(--font-figures); font-size: var(--text-xl); }
.station-roster-empty { max-width: 520px; text-align: center; }
.station-keypad { display: grid; justify-items: center; gap: 12px; width: min(340px, 100%); }
.station-pin-for { margin: 0; color: var(--ink); font-size: var(--text-xl); font-weight: 600; text-align: center; }
/* One field shows the progress: the keyboard types into it and its six marks are what it shows. */
.station-pin-field { display: grid; width: 100%; }
.station-pin-field > * { grid-area: 1 / 1; }
.station-pin-input, .station-pin-input:disabled { width: 100%; height: 56px; min-height: 56px; color: transparent; caret-color: transparent; font-size: 22px; text-align: center; }
.station-pin-dots { display: flex; gap: 14px; place-self: center; pointer-events: none; }
.station-pin-dots span { width: 12px; height: 12px; border: 2px solid var(--subtle); border-radius: var(--radius-mark); transition: background-color 90ms ease, border-color 90ms ease; }
.station-pin-dots span.filled { background: var(--ink); border-color: var(--ink); }
/* A wrong PIN is said in a line kept for it: the keys under the finger never move. */
.station-pin-status { width: 100%; min-height: 24px; }
.station-pin-error { display: flex; align-items: center; justify-content: center; gap: 8px; margin: 0; color: var(--red); font-weight: 600; text-align: center; text-wrap: balance; }
.station-pin-error::before { flex: none; width: 8px; height: 8px; content: ""; background: var(--red-lamp); border-radius: var(--radius-mark); }
.station-keys { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; width: 100%; }
.station-key { min-height: 68px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-bottom-width: 2px; border-radius: var(--radius-large); cursor: pointer; font-family: var(--font-figures); font-size: 28px; font-weight: 600; touch-action: manipulation; -webkit-tap-highlight-color: transparent; transition: background-color 90ms ease, transform var(--press) var(--ease-out); }
.station-key:hover:not(:disabled) { background: var(--surface-hover); }
.station-key:active:not(:disabled) { background: var(--surface-accent); transform: scale(.96); }
.station-key-soft { color: var(--muted); font-family: var(--font-ui); font-size: var(--text-md); font-weight: 600; }
.station-key-soft .icon { width: 24px; height: 24px; }
/* The way back is a full-width touch key under the keypad; the busy spinner sits inside its left end. */
.station-keypad .form-actions { position: relative; justify-content: center; width: 100%; padding: 0; }
.station-keypad .form-actions .button { flex: 1; min-height: var(--control-lg); font-size: var(--text-lg); }
.station-keypad .form-actions .spinner { position: absolute; top: 50%; left: 16px; z-index: 1; margin-top: -8px; }
.station-chooser-foot { margin-top: auto; }
@media (width <= 760px) {
    .station-roster { grid-template-columns: minmax(0, 1fr); }
}

/* ------------------------------------------------------------------------------------------ the till
   Worked standing, at arm's length, with a queue waiting: the menu keys on the left, the ticket on
   the right with its total and the one button that matters pinned at its foot. */
.pos-grid { display: grid; grid-template-columns: minmax(0, 1fr) 400px; height: 100%; }
/* The search, the drawer and the categories stay put; only the keys scroll under them. */
.pos-menu { display: flex; flex-direction: column; min-width: 0; min-height: 0; padding: 14px 16px 0; overflow: hidden; }
.pos-menu-bar { display: flex; gap: 8px; flex: none; margin-bottom: 12px; }
.pos-branch, .pos-search { min-height: var(--control-lg); height: var(--control-lg); padding: 0 12px; font-size: var(--text-lg); }
/* A long branch name ends in an ellipsis instead of pushing the search off the row. */
.pos-branch { flex: 0 1 auto; min-width: 120px; max-width: min(360px, 45%); padding-right: 34px; font-weight: 600; }
.pos-search { flex: 1 1 200px; min-width: 0; }
.pos-branch-name { display: block; flex: 0 1 auto; min-width: 0; max-width: min(360px, 45%); height: var(--control-lg); overflow: hidden; padding: 0 14px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-control); font-size: var(--text-lg); font-weight: 600; line-height: calc(var(--control-lg) - 2px); text-overflow: ellipsis; white-space: nowrap; }
/* Every category in view: the keys wrap onto a second row rather than hiding off the edge. */
.pos-categories { display: flex; flex-wrap: wrap; gap: 8px; flex: none; margin-bottom: 12px; }
.pos-chip { flex: none; max-width: 240px; overflow: hidden; min-height: var(--control-lg); padding: 0 16px; text-overflow: ellipsis; color: var(--label); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-md); font-weight: 600; white-space: nowrap; touch-action: manipulation; transition: background-color 90ms ease, border-color 90ms ease, transform var(--press) var(--ease-out); }
.pos-chip:hover { border-color: var(--input-border); }
.pos-chip:active { transform: scale(.97); }
.pos-chip.chosen { color: var(--on-action); background: var(--action); border-color: var(--action); }
/* The keys: one size, a name of up to three lines, the price on one line along the row. The 2px inset
   keeps a key's hover edge and press from being clipped by the scroller. */
.pos-products { display: grid; flex: 1 1 auto; grid-template-columns: repeat(auto-fill, minmax(176px, 1fr)); gap: 8px; align-content: start; min-height: 0; margin-inline: -2px; padding: 2px 2px 16px; overflow-y: auto; overscroll-behavior: contain; scrollbar-width: thin; }
.pos-product { display: grid; grid-template-rows: auto 1fr auto; align-content: start; gap: 6px; min-height: 108px; padding: 12px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); cursor: pointer; text-align: left; touch-action: manipulation; -webkit-tap-highlight-color: transparent; transition: border-color 90ms ease, background-color 90ms ease, transform var(--press) var(--ease-out); }
.pos-product:not(:has(img)) { grid-template-rows: 1fr auto; }
.pos-product:hover:not(:disabled) { border-color: var(--input-border); }
.pos-product:active:not(:disabled) { background: var(--surface-accent); transform: scale(.97); }
.pos-product img { width: 100%; height: 84px; object-fit: cover; border-radius: 4px; }
.pos-product-name { display: -webkit-box; overflow: hidden; font-size: var(--text-md); font-weight: 600; line-height: 1.3; overflow-wrap: anywhere; -webkit-box-orient: vertical; -webkit-line-clamp: 3; }
.pos-product-price { color: var(--label); font-size: var(--text-md); font-weight: 500; font-variant-numeric: tabular-nums; }
/* Off the menu for now: the key keeps its row and its price keeps the line of its neighbours' prices;
   beside the price, a lamp and a word, not fault red. */
.pos-product.off { grid-template-columns: minmax(0, 1fr) auto; background: var(--surface-subtle); cursor: not-allowed; }
.pos-product.off :is(img, .pos-product-name) { grid-column: 1 / -1; }
.pos-product.off :is(.pos-product-name, .pos-product-price) { color: var(--muted); }
.pos-product.off .pos-product-name { text-decoration: line-through; text-decoration-color: var(--muted); }
.pos-product-off { grid-row: -2; grid-column: 2; align-self: end; }

.pos-ticket { display: flex; flex-direction: column; min-width: 0; min-height: 0; padding: 14px 16px 16px; overflow-y: auto; background: var(--surface); border-left: 1px solid var(--border); }
.pos-ticket-heading { display: flex; align-items: baseline; justify-content: space-between; margin: 0 0 6px; font-size: var(--text-lg); }
/* Empty or full, the ticket keeps its total and the place key at its foot: the hand finds them in one place. */
.pos-ticket-empty { flex: 1 1 auto; margin: 0 0 12px; padding: 18px 0; color: var(--muted); border-top: 1px solid var(--line-soft); font-size: var(--text-md); }
.pos-lines { display: grid; flex: 1 1 auto; align-content: start; gap: 0; min-height: 96px; margin: 0 0 8px; padding: 0; overflow-y: auto; list-style: none; border-top: 1px solid var(--line-soft); }
.pos-line { display: grid; gap: 4px; padding: 8px 0; border-bottom: 1px solid var(--line-soft); }
.pos-line-head { display: flex; justify-content: space-between; gap: 10px; font-size: var(--text-md); }
.pos-line-head strong { overflow-wrap: anywhere; }
.pos-line-total { font-weight: 600; font-variant-numeric: tabular-nums; white-space: nowrap; }
.pos-line-option { color: var(--muted); font-size: var(--text-xs); font-variant-numeric: tabular-nums; }
/* One row per line: the quantity keys, the note for the kitchen, and the remove key. */
.pos-line-actions { display: grid; grid-template-columns: auto auto auto minmax(0, 1fr) auto; align-items: center; gap: 8px; margin-top: 4px; }
.pos-step { display: grid; place-items: center; width: 44px; height: 40px; padding: 0; color: var(--ink); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); cursor: pointer; font-size: 20px; line-height: 1; touch-action: manipulation; transition: background-color 90ms ease, transform var(--press) var(--ease-out); }
.pos-step:hover:not(:disabled) { border-color: var(--ink); }
.pos-step:active:not(:disabled) { background: var(--surface-accent); transform: scale(.94); }
.pos-qty { min-width: 30px; font-family: var(--font-figures); font-size: var(--text-lg); font-weight: 600; text-align: center; font-variant-numeric: tabular-nums; }
.pos-remove { display: grid; place-items: center; width: 40px; height: 40px; padding: 0; color: var(--muted); background: transparent; border: 0; border-radius: var(--radius-control); cursor: pointer; font-size: 18px; touch-action: manipulation; }
.pos-remove:hover:not(:disabled) { color: var(--red); background: var(--red-soft); }
.pos-note { width: 100%; min-width: 0; min-height: 40px; height: 40px; padding: 0 10px; font-size: var(--text-sm); box-shadow: none; }
.pos-sum { display: flex; justify-content: space-between; align-items: baseline; flex: none; padding-top: 10px; border-top: 1px solid var(--border); font-size: var(--text-md); font-weight: 600; }
.pos-sum strong { font-family: var(--font-figures); font-size: 30px; font-weight: 600; letter-spacing: -0.015em; font-variant-numeric: tabular-nums; }
.pos-sum-note { flex: none; margin: 2px 0 10px; }
.pos-payment { display: grid; grid-auto-columns: minmax(0, 1fr); grid-auto-flow: column; gap: 6px; flex: none; margin-bottom: 10px; }
.pos-pay { display: inline-flex; align-items: center; justify-content: center; gap: 8px; min-height: 52px; color: var(--label); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-lg); font-weight: 600; touch-action: manipulation; transition: background-color 90ms ease, border-color 90ms ease, transform var(--press) var(--ease-out); }
.pos-pay:active:not(:disabled) { transform: scale(.97); }
.pos-pay.chosen { color: var(--ink); background: var(--surface-accent); border-color: var(--ink); box-shadow: inset 0 0 0 1px var(--ink); }
.pos-pay.chosen::before { width: 8px; height: 8px; content: ""; background: var(--ink); border-radius: var(--radius-mark); }
.pos-payment-choose, .pos-payment-none { flex: none; margin: 0 0 10px; }
.pos-shift-required { flex: none; gap: 10px; margin-bottom: 10px; }
.pos-shift-required .button { justify-self: start; }
.pos-shift-required-note { flex: none; margin: 0 0 10px; font-size: var(--text-sm); }
#pos-place { flex: none; min-height: var(--control-touch); font-size: var(--text-xl); }

/* A dish with choices: its options as keys, the chosen one outlined in ink. */
.pos-dialog { width: min(640px, 100%); }
.pos-options { display: grid; grid-template-columns: repeat(auto-fit, minmax(160px, 1fr)); gap: 8px; padding: 0 24px; }
.pos-option { display: flex; flex-wrap: wrap; justify-content: space-between; align-items: center; gap: 2px 8px; min-height: 52px; padding: 10px 12px; color: var(--ink); background: var(--surface); border: 1px solid var(--input-border); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-md); text-align: left; touch-action: manipulation; transition: transform var(--press) var(--ease-out); }
.pos-option:active:not(:disabled) { transform: scale(.97); }
.pos-option.chosen { background: var(--surface-accent); border-color: var(--ink); box-shadow: inset 0 0 0 1px var(--ink); font-weight: 600; }
.pos-option:disabled { opacity: .5; cursor: not-allowed; }
.pos-option > span:first-child { min-width: 0; overflow-wrap: anywhere; }
.pos-option-price { color: var(--muted); font-variant-numeric: tabular-nums; white-space: nowrap; }

/* Orders ready to hand over: a bounded strip above the ticket; one quiet line when there are none. */
.pos-ready { display: grid; flex: none; gap: 8px; margin: -2px 0 14px; padding: 10px 0 12px; border-bottom: 1px solid var(--border); }
.pos-ready.empty { padding-block: 2px 10px; }
.pos-ready-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; }
.pos-ready-head h2 { display: flex; align-items: center; gap: 8px; margin: 0; font-size: var(--text-md); }
.pos-ready-head h2::before { width: 8px; height: 8px; content: ""; background: var(--green-lamp); border-radius: var(--radius-mark); }
.pos-ready.empty .pos-ready-head h2 { color: var(--muted); font-weight: 500; }
.pos-ready.empty .pos-ready-head h2::before { background: var(--steel-400); }
/* The count is a figure beside the lamp, not a second lamp. */
.pos-ready-head .badge { min-width: 28px; justify-content: center; font-size: var(--text-sm); font-weight: 600; font-variant-numeric: tabular-nums; }
.pos-ready-head .badge::before { display: none; }
.pos-ready-list { display: grid; gap: 6px; max-height: min(34vh, 300px); margin: 0; padding: 0; overflow-y: auto; overscroll-behavior: contain; list-style: none; }
.pos-ready-card { display: grid; grid-template-columns: minmax(0, 1fr) auto; grid-template-areas: "head button" "lines button"; align-items: center; gap: 2px 10px; padding: 8px 8px 8px 12px; background: var(--green-soft); border: 1px solid var(--green-line); border-radius: var(--radius-surface); }
.pos-ready-card-head { grid-area: head; display: flex; align-items: baseline; gap: 8px; }
.pos-ready-number { font-family: var(--font-figures); font-size: var(--text-xl); font-variant-numeric: tabular-nums; }
.pos-ready-waiting { color: var(--muted); font-size: var(--text-xs); font-variant-numeric: tabular-nums; white-space: nowrap; }
.pos-ready-lines { grid-area: lines; min-width: 0; margin: 0; padding: 0; color: var(--label); font-size: var(--text-sm); list-style: none; }
.pos-ready-lines li { overflow-wrap: anywhere; }
.pos-ready-handover { grid-area: button; justify-content: center; min-width: 104px; min-height: var(--control-lg); }
.pos-ready-stale, .pos-ready-notice, .pos-ready-problem { margin: 0; font-size: var(--text-xs); }
.pos-ready-stale { color: var(--amber); }
.pos-ready.stale .pos-ready-card { opacity: .6; }
.pos-ready-notice { color: var(--muted); }
.pos-ready-problem { color: var(--red); }
.pos-done-ready { width: min(460px, 100%); }
.pos-done-ready .pos-ready { margin: 0; padding: 12px 14px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); }

/* A sale rung up: the number the customer is given, the facts, the next sale one key away. */
.pos-done { display: grid; place-items: center; align-content: safe center; gap: 14px; height: 100%; padding: 20px; overflow-y: auto; }
.pos-done-card { display: grid; justify-items: center; gap: 10px; width: min(460px, 100%); padding: 28px 24px 22px; text-align: center; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-large); transition: opacity 200ms var(--ease-out), transform 200ms var(--ease-out); }
@starting-style { .pos-done-card { opacity: 0; transform: scale(.97); } }
.pos-done-mark { display: grid; place-items: center; width: 48px; height: 48px; color: #fff; background: var(--green-lamp); border-radius: var(--radius-large); font-size: 24px; }
.pos-done-mark .icon { width: 26px; height: 26px; }
.pos-done-card h1 { margin: 0; font-size: var(--text-xl); }
.pos-done-number { margin: 0; color: var(--muted); font-size: var(--text-md); }
.pos-done-number strong { display: block; color: var(--ink); font-family: var(--font-figures); font-size: 44px; font-weight: 600; letter-spacing: -0.02em; line-height: 1.1; font-variant-numeric: tabular-nums; }
.pos-done-facts { display: grid; gap: 0; width: 100%; margin: 6px 0; border-top: 1px solid var(--line-soft); }
.pos-done-facts > div { display: flex; justify-content: space-between; gap: 12px; padding: 7px 0; border-bottom: 1px solid var(--line-soft); font-size: var(--text-sm); }
.pos-done-facts dt { color: var(--muted); }
.pos-done-facts dd { margin: 0; font-weight: 600; font-variant-numeric: tabular-nums; }
/* The total is the figure the customer is told. */
.pos-done-facts > div:first-child { align-items: baseline; }
.pos-done-facts > div:first-child dd { font-family: var(--font-figures); font-size: var(--text-xl); }
/* The next sale is the widest key on the card, at touch height; the rest share its row, so the
   strip of orders to hand over stays in view under the card on a 1366×768 till. */
.pos-done-actions { display: flex; flex-wrap: wrap; justify-content: center; gap: 8px; width: 100%; margin-top: 4px; }
#pos-new-order { flex: 2 1 0; min-height: var(--control-touch); }
.pos-done-actions .button:not(#pos-new-order) { flex: 1 1 0; min-height: var(--control-lg); }
.pos-done-note { margin: 2px 0 0; }

/* The drawer's state: one row above the menu, glanced at between customers. */
.pos-shift { display: flex; flex: none; flex-wrap: wrap; align-items: center; gap: 8px 14px; margin-bottom: 12px; padding: 8px 8px 8px 12px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); font-size: var(--text-sm); }
.pos-shift.none { background: var(--amber-soft); border-color: var(--amber-line); }
.pos-shift .button { min-height: var(--control-md); }
.pos-shift-state { display: inline-flex; align-items: center; gap: 8px; font-weight: 600; white-space: nowrap; }
.pos-shift-state.none { color: var(--amber); }
.pos-shift-state.none::before { width: 8px; height: 8px; content: ""; background: var(--amber-lamp); border-radius: var(--radius-mark); }
.pos-shift-dot { width: 8px; height: 8px; background: var(--green-lamp); border-radius: var(--radius-mark); }
.pos-shift-expected { color: var(--label); white-space: nowrap; }
.pos-shift-expected strong { color: var(--ink); font-size: var(--text-lg); font-variant-numeric: tabular-nums; }
.pos-shift-hint { flex: 1 1 200px; min-width: 0; font-size: var(--text-xs); }
.pos-shift-spacer { flex: 1; }

/* What the till's printer did with a sale. */
.pos-print { display: grid; gap: 8px; width: 100%; padding: 10px 0 4px; border-top: 1px solid var(--line-soft); text-align: left; }
.pos-print-row { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; font-size: var(--text-sm); }
.pos-print-label { color: var(--muted); }
.pos-print-actions { margin-left: auto; }
.pos-print-actions .button { min-height: var(--control-lg); }

@media (max-width: 1180px) {
    /* A 1024 counter screen keeps the ticket beside the menu, a little narrower. */
    .pos-grid { grid-template-columns: minmax(0, 1fr) 360px; }
}
@media (max-width: 1023px) {
    /* A phone behind the counter: the ticket under the menu rather than a column that leaves neither usable. */
    .pos-grid { grid-template-columns: 1fr; grid-template-rows: minmax(0, 1fr) auto; }
    .pos-ticket { max-height: 52vh; border-top: 1px solid var(--border); border-left: 0; }
    .pos-ready-list { max-height: 22vh; }
    .pos-products { grid-template-columns: repeat(auto-fill, minmax(132px, 1fr)); }
    /* Stacked, the categories are one row that scrolls sideways and fades where it goes on. */
    .pos-categories { flex-wrap: nowrap; padding-bottom: 2px; overflow-x: auto; scrollbar-width: thin; mask-image: linear-gradient(to right, #000 calc(100% - 32px), transparent); }
    .station-chooser { padding-top: 18px; }
    .pos-shift-hint { display: none; }
}
@media (width <= 760px) {
    /* A phone: the till is one page that scrolls, the menu then the ticket, with the place key held at
       the foot of the screen once the ticket is in view, not two cramped scrollers. */
    .pos-shell { height: auto; min-height: 100dvh; }
    .pos-main { overflow: visible; }
    .pos-grid { height: auto; grid-template-rows: auto auto; }
    .pos-menu, .pos-products, .pos-lines { overflow: visible; }
    .pos-ticket { max-height: none; overflow: visible; }
    #pos-place { position: sticky; bottom: 8px; }
    .pos-menu-bar { flex-wrap: wrap; }
    .pos-branch, .pos-branch-name { flex: 1 1 100%; max-width: none; }
    .pos-options { grid-template-columns: minmax(0, 1fr); padding-inline: 16px; }
}

/* ---------------------------------------------------------------------------------- the kitchen board
   The dark equipment panel at the pass (dark unless a cook chose light). Read from 1.5 to 3 m by
   somebody with their hands full: the number and the minutes are the loudest things on it, then what
   to make, then one key. New work carries the lamp; the ticket next to start stands forward. */
.kds-main { display: flex; flex-direction: column; padding: 12px 16px 16px; }
.kds-head { display: flex; flex: none; align-items: center; gap: 12px; margin-bottom: 12px; }
/* A branch that can be switched is a select with its chevron; the one branch there is is a name, not a control. */
.kds-branch { min-width: 0; min-height: var(--control-lg); height: var(--control-lg); padding: 0 34px 0 14px; color: var(--ink); background-color: var(--surface); background-position: calc(100% - 19px) 50%, calc(100% - 14px) 50%; border: 1px solid var(--border); border-radius: var(--radius-control); font-size: var(--text-lg); font-weight: 700; }
.kds-branch-name { min-width: 0; overflow: hidden; color: var(--ink); font-size: var(--text-xl); font-weight: 700; text-overflow: ellipsis; white-space: nowrap; }
.kds-count { color: var(--label); font-size: var(--text-lg); font-weight: 600; font-variant-numeric: tabular-nums; }
.kds-clock { color: var(--ink); font-family: var(--font-figures); font-size: 30px; font-weight: 600; letter-spacing: -0.01em; font-variant-numeric: tabular-nums; }
.kds-sound { display: inline-flex; flex: none; align-items: center; gap: 8px; min-height: var(--control-lg); padding: 0 14px; color: var(--label); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-sm); font-weight: 600; }
.kds-sound.on { color: var(--ink); border-color: var(--green-line); }

/* The exceptions: said across the pass, never a dialog; the board under them keeps working. */
.kds-cancelled, .kds-stale, .kds-print-alert { display: flex; flex: none; flex-wrap: wrap; align-items: baseline; gap: 4px 14px; margin-bottom: 8px; padding: 12px 16px; border-radius: var(--radius-surface); overflow-wrap: anywhere; }
.kds-cancelled { justify-content: space-between; align-items: center; color: #fff; background: var(--red-lamp); font-size: var(--text-xl); }
.kds-dismiss { display: grid; place-items: center; width: 44px; height: 44px; padding: 0; color: #fff; background: transparent; border: 1px solid oklch(100% 0 0 / .5); border-radius: var(--radius-control); cursor: pointer; font-size: 20px; }
.kds-dismiss:hover { background: oklch(100% 0 0 / .12); }
.kds-notice { flex: none; margin: 0 0 8px; padding: 10px 14px; color: var(--label); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); font-size: var(--text-md); }
.kds-print-alert { color: var(--ink); background: var(--amber-soft); border: 1px solid var(--amber-line); }
.kds-print-alert strong, .kds-stale strong { display: inline-flex; align-items: center; gap: 10px; font-size: var(--text-xl); }
.kds-print-alert strong { color: var(--amber); }
.kds-print-alert strong::before, .kds-stale strong::before { flex: none; width: 10px; height: 10px; content: ""; border-radius: var(--radius-mark); }
.kds-print-alert strong::before { background: var(--amber-lamp); }
.kds-print-alert span, .kds-stale span { color: var(--label); font-size: var(--text-lg); }
.kds-print-alert.failed { background: var(--red-soft); border-color: var(--red-line); }
.kds-print-alert.failed strong { color: var(--red); }
.kds-print-alert.failed strong::before { background: var(--red-lamp); }
/* The board can no longer be confirmed: louder than a printer, since it is the orders themselves. */
.kds-stale { color: var(--ink); background: var(--red-soft); border: 2px solid var(--red-lamp); }
.kds-stale strong { color: var(--red); }
.kds-stale strong::before { background: var(--red-lamp); }
.kds-stale .kds-stale-since, .kds-stale .kds-stale-checking { color: var(--muted); font-size: var(--text-md); }
.kds-print-recovered, .kds-restored { display: flex; flex: none; align-items: center; gap: 10px; margin: 0 0 8px; padding: 8px 14px; color: var(--green); background: var(--surface); border: 1px solid var(--green-line); border-radius: var(--radius-surface); font-size: var(--text-md); font-weight: 600; }
.kds-print-recovered::before, .kds-restored::before { width: 8px; height: 8px; content: ""; background: var(--green-lamp); border-radius: var(--radius-mark); }

/* Three fixed stages; each scrolls on its own. */
.kds-columns { display: grid; flex: 1; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 12px; min-height: 0; }
.kds-column { display: flex; flex-direction: column; gap: 12px; min-height: 0; padding: 12px; overflow-y: auto; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); scrollbar-width: thin; }
.kds-column-title { display: flex; flex: none; align-items: center; gap: 10px; margin: 2px 2px 0; color: var(--ink); font-size: var(--text-xl); font-weight: 600; }
.kds-column-title::before { width: 10px; height: 10px; content: ""; background: var(--steel-500); border-radius: var(--radius-mark); }
.kds-new .kds-column-title::before { background: var(--amber-lamp); }
.kds-ready .kds-column-title::before { background: var(--green-lamp); }
.kds-column-count { min-width: 34px; margin-left: auto; padding: 1px 8px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: 4px; font-family: var(--font-figures); font-size: var(--text-lg); text-align: center; font-variant-numeric: tabular-nums; }
/* A quiet stage says so in the middle of itself, big enough to read from the pass: a quiet kitchen,
   not a board that has not loaded. */
.kds-empty { margin: auto; padding: 24px 0; color: var(--subtle); font-size: var(--text-xl); text-align: center; }

/* One track no wider than the card, and words that break anywhere: a pasted name, a phone number in
   a note or a modifier with no spaces wraps inside the ticket instead of pushing out of the stage. */
.kds-ticket { display: grid; flex: none; grid-template-columns: minmax(0, 1fr); gap: 8px; padding: 12px 16px 16px; color: var(--ink); background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-surface); overflow-wrap: anywhere; transition: border-color 200ms ease, box-shadow 200ms ease; }
.kds-new .kds-ticket { border-color: var(--amber-line); }
.kds-ready .kds-ticket { border-color: var(--green-line); }
/* The oldest new ticket is the next one to start: it stands forward. */
.kds-new .kds-ticket:first-of-type { border-color: var(--amber-lamp); box-shadow: inset 0 0 0 1px var(--amber-lamp); }
.kds-ticket-head { display: flex; align-items: baseline; justify-content: space-between; gap: 10px; padding-bottom: 8px; border-bottom: 1px solid var(--line-soft); }
.kds-number { font-family: var(--font-figures); font-size: 34px; font-weight: 600; letter-spacing: -0.02em; line-height: 1; font-variant-numeric: tabular-nums; }
.kds-age { color: var(--ink); font-family: var(--font-figures); font-size: 28px; font-weight: 600; font-variant-numeric: tabular-nums; }
.kds-new .kds-age { color: var(--amber); }
.kds-booked { color: var(--amber); font-size: var(--text-xl); font-weight: 700; }
.kds-tags { display: flex; flex-wrap: wrap; gap: 6px; }
/* Pickup or delivery changes how the order is packed: readable from the pass, still under the lines. */
.kds-tag { padding: 4px 8px; color: var(--label); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: 4px; font-size: var(--text-lg); font-weight: 600; line-height: 1.2; }
.kds-lines { display: grid; gap: 8px; margin: 0; padding: 0; list-style: none; }
.kds-lines li { display: grid; gap: 2px; }
.kds-line { font-size: 20px; font-weight: 500; line-height: 1.3; }
.kds-line b { font-family: var(--font-figures); font-size: 22px; font-weight: 700; font-variant-numeric: tabular-nums; }
.kds-modifier { padding-left: 24px; color: var(--label); font-size: 17px; }
.kds-line-note { justify-self: start; margin-left: 24px; padding: 2px 8px; color: var(--amber); background: var(--amber-soft); border-radius: 4px; font-size: var(--text-lg); font-weight: 600; }
.kds-note { margin: 0; padding: 8px 10px; color: var(--ink); background: var(--amber-soft); border: 1px solid var(--amber-line); border-radius: var(--radius-control); font-size: 17px; }
.kds-action { display: inline-flex; align-items: center; justify-content: center; gap: 10px; min-height: 60px; color: var(--on-action); background: var(--action); border: 0; border-radius: var(--radius-surface); cursor: pointer; font-size: 21px; font-weight: 700; touch-action: manipulation; -webkit-tap-highlight-color: transparent; transition: filter 90ms ease, transform var(--press) var(--ease-out); }
.kds-action:active:not(:disabled) { transform: scale(.98); }
.kds-action.ready { color: var(--steel-950); background: var(--green-lamp); }
.kds-action:disabled { opacity: .55; cursor: progress; }
@media (hover: hover) { .kds-action:hover:not(:disabled) { filter: brightness(1.06); } }
.kds-waiting { margin: 0; color: var(--label); font-size: var(--text-lg); }

@media (max-width: 1023px) {
    /* A portrait tablet keeps the three stages side by side; only the bar and the top row get tighter. */
    .kds-head { flex-wrap: wrap; }
    .kds-clock { font-size: 22px; }
}
@media (max-width: 767px) {
    /* A phone at the pass: one stage under another, New first, each as tall as its tickets, and the page
       the one thing that scrolls. Squeezed into the screen's height, a stage's row came out shorter than
       its tickets and they were drawn over the next stage. */
    .kds-main { overflow-y: auto; }
    .kds-columns { flex: none; grid-template-columns: minmax(0, 1fr); }
    .kds-column { min-height: auto; overflow: visible; }
    /* The top row wraps one way for every board: the branch on its own row, then the count, the sound
       key and the clock, flush right. */
    .kds-head .kds-bar-spacer { display: none; }
    .kds-branch, .kds-branch-name { flex: 1 1 100%; }
    .kds-sound { margin-left: auto; }
}

/* ------------------------------------------------------------------------- the cash shift and its X/Z
   A plain two-column ledger that prints as it reads on screen. Operational, not fiscal. */
.shift-dialog { width: min(620px, 100%); }
.shift-dialog .form-section { gap: 10px; }
.shift-dialog-problem { padding: 0 24px; }
.shift-field { display: grid; gap: 6px; padding: 0 24px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.shift-field input { min-height: var(--control-lg); height: var(--control-lg); padding: 0 12px; font-family: var(--font-figures); font-size: var(--text-xl); font-variant-numeric: tabular-nums; }
.shift-dialog .form-section > .alert { margin: 0 24px; }
.shift-toggle { display: flex; gap: 8px; padding: 0 24px; }
.shift-expected-line, .shift-confirm { margin: 0; padding: 0 24px; color: var(--ink); font-size: var(--text-lg); }
.shift-expected-line strong { font-family: var(--font-figures); font-size: var(--text-2xl); font-variant-numeric: tabular-nums; }
.shift-dialog-report { padding: 0 24px; }
@media (width <= 760px) {
    /* On a phone the dialog's inset is 16px: the fields line up with its title and help again. */
    .shift-field, .shift-toggle, .shift-expected-line, .shift-confirm, .shift-dialog-report, .shift-dialog-problem { padding-inline: 16px; }
    .shift-dialog .form-section > .alert { margin-inline: 16px; }
}
.shift-report { display: grid; gap: 14px; color: var(--ink); }
.shift-report-head h2 { margin: 0 0 6px; font-size: var(--text-lg); }
/* The kind is a line of the sheet under its name; in a dialog, whose title already says it, only paper shows it. */
.shift-report-kind { margin: 0 0 6px; color: var(--label); font-size: var(--text-xs); font-weight: 700; }
.shift-dialog .shift-report-kind { display: none; }
.shift-report-when { display: grid; gap: 3px; margin: 0; font-size: var(--text-sm); }
.shift-report-when > div { display: flex; gap: 8px; }
.shift-report-when dt { min-width: 92px; color: var(--muted); }
.shift-report-when dd { margin: 0; font-variant-numeric: tabular-nums; }
.shift-report-figures th, .shift-report-figures td { position: static; padding: 7px 4px; color: var(--ink); background: none; border-bottom: 1px solid var(--line-soft); font-size: var(--text-md); font-weight: 400; text-align: left; white-space: normal; }
.shift-report-figures td { text-align: right; font-variant-numeric: tabular-nums; white-space: nowrap; }
.shift-report-figures tr.sub th { padding-left: 18px; color: var(--label); font-size: var(--text-sm); }
.shift-report-figures tr.sub td { color: var(--label); font-size: var(--text-sm); }
.shift-report-figures tr.sub.split th { padding-left: 32px; font-size: var(--text-xs); }
.shift-report-figures tr.sub.split td { font-size: var(--text-xs); }
.shift-report-figures tr.strong th, .shift-report-figures tr.strong td { font-weight: 600; }
.shift-report-figures tr.total th, .shift-report-figures tr.total td { font-size: var(--text-lg); font-weight: 700; border-bottom: 2px solid var(--ink); }
.shift-report-figures tbody tr:hover td { background: none; }
/* The sheet's last line is the total, and it ends without a rule either side. */
.shift-report-figures tbody tr:last-child th, .shift-report-figures tbody tr:last-child td { border-bottom: 0; }
.variance.short, td.variance.short { color: var(--red) !important; }
.variance.over, td.variance.over { color: var(--amber) !important; }
.variance.balanced, td.variance.balanced { color: var(--green) !important; }
.shift-report-figures tr.variance small { margin-left: 6px; font-size: var(--text-2xs); font-weight: 600; }
.shift-report-note { margin: 0; font-size: var(--text-sm); }
.shift-report-section h3, .shift-report-section summary { margin: 0 0 6px; font-size: var(--text-md); font-weight: 600; cursor: default; }
.shift-report-section summary { cursor: pointer; }
/* The orders fold is a part of the sheet, not a panel's fold: it keeps the sheet's edges, so its totals end under the figures. */
details.shift-report-section { margin: 0; }
.shift-report-section[open] summary, .shift-report-section summary { color: var(--ink); }
.shift-report-list { display: grid; gap: 0; margin: 0; padding: 0; list-style: none; font-size: var(--text-sm); font-variant-numeric: tabular-nums; }
.shift-report-list li { display: flex; flex-wrap: wrap; gap: 4px 10px; padding: 6px 0; border-bottom: 1px solid var(--line-soft); }
.shift-report-list li.cancelled { color: var(--muted); text-decoration: line-through; }
.shift-report-reason { flex: 1; min-width: 120px; }
/* The money in both lists stands in one column, as in the figures above: an order's total flush right (on its
   own line too, when the row wraps), a movement's amount right-aligned after a type of one width. */
.shift-report-orders li > strong { min-width: 4.5em; }
.shift-report-orders li > :last-child { margin-left: auto; white-space: nowrap; text-align: right; }
.shift-report-movements li > strong { min-width: 6.5em; }
.shift-report-movements li > :nth-child(3) { min-width: 8em; text-align: right; white-space: nowrap; }
.shift-report-disclaimer { margin: 0; padding-top: 8px; color: var(--muted); border-top: 1px solid var(--border); font-size: var(--text-xs); }
@media (width <= 760px) {
    .shift-dialog-report { padding-inline: 16px; }
}
@media print {
    .shift-dialog .shift-report-kind { display: block; }
}

/* ------------------------------------------------------------------------------------------ reports
   A window of days, its figures on the grid, and the export beside the controls that chose it. */
/* The day's filters and the export's range are two groups: the export anchored at the right of the row, and
   under 1100 px a row of its own that starts at the content edge under a rule. */
.reports-controls { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: end; gap: 12px 24px; margin-bottom: 20px; }
.reports-filters { display: flex; flex-wrap: wrap; align-items: flex-end; gap: 12px; min-width: 0; }
.reports-control { display: grid; gap: 6px; color: var(--label); font-size: var(--text-sm); font-weight: 600; }
.reports-control select, .reports-control input { min-width: 200px; font-size: var(--text-md); font-weight: 400; }
.reports-control select { max-width: 100%; }
/* Every date on the row is the same control at the same size, and as tall as the select and the key beside it. */
.reports-control input[type="date"] { width: 160px; min-width: 0; height: var(--control-md); }
.reports-control strong { display: inline-flex; align-items: center; height: var(--control-md); color: var(--ink); font-size: var(--text-md); }
.reports-export { display: flex; flex-wrap: wrap; align-items: flex-end; gap: 12px; padding-left: 16px; border-left: 1px solid var(--border); }
.reports-export-error { margin-bottom: 16px; }
.reports-panel .section-heading { padding: 16px 20px 0; }
.reports-panel > .alert { margin: 12px 20px 0; }
/* Six headline tiles: three across, six on a wide screen, two on a narrow one; never a hole in the grid. */
.metric-grid.reports-metrics { grid-template-columns: repeat(3, minmax(0, 1fr)); margin: 16px 0; }
.reports-metrics .metric { container-type: inline-size; padding: 16px 20px; background: var(--surface); }
/* A report shows its numbers whole: a long total shrinks to fit its tile rather than losing its end. */
.reports-metrics .metric strong { font-size: min(24px, 11.5cqi); }
/* The split tables stand side by side only while each keeps 300 px; narrower, they stack instead of overprinting.
   Each keeps its own height, so a short table's rows are not stretched out of line with its neighbour's. */
.reports-splits { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 300px), 1fr)); align-items: start; gap: 16px 24px; padding: 0 20px 20px; }
.reports-split th, .reports-split td { padding: 8px 12px; }
.reports-split th:first-child, .reports-split td:first-child { padding-left: 0; }
.reports-split th:last-child, .reports-split td:last-child { padding-right: 0; }
.reports-current { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 12px; padding: 12px 20px 20px; }
.reports-current-facts { display: flex; flex-wrap: wrap; gap: 8px 32px; margin: 0; }
.reports-current-facts dt { color: var(--muted); font-size: var(--text-xs); }
.reports-current-facts dd { margin: 2px 0 0; font-size: var(--text-md); font-variant-numeric: tabular-nums; }
/* A panel with nothing in it yet says so in body type, not as a footnote. */
.reports-none { margin: 0 20px; padding: 8px 0 20px; font-size: var(--text-md); }
@media (min-width: 1800px) {
    .metric-grid.reports-metrics { grid-template-columns: repeat(6, minmax(0, 1fr)); }
}
@media (max-width: 1100px) {
    .reports-controls { grid-template-columns: minmax(0, 1fr); }
    .reports-export { padding: 12px 0 0; border-left: 0; border-top: 1px solid var(--border); }
}
@media (max-width: 900px) {
    .metric-grid.reports-metrics { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (width <= 760px) {
    .reports-metrics .metric strong { font-size: min(20px, 11.5cqi); }
    .reports-filters { display: grid; }
    /* The export's range reads as one: from and to side by side, the key under both. */
    .reports-export { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .reports-export > .button { grid-column: 1 / -1; }
    .reports-control select, .reports-control input, .reports-control input[type="date"] { width: 100%; min-width: 0; }
}

/* ----------------------------------------------------------------------------------------- printing */
.printing-fiscal { color: var(--label); background: var(--surface-subtle); border-color: var(--border); }
.printing-credential { border-color: var(--input-border); }
.printing-token-row { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; padding: 0 20px; }
.printing-token { flex: 1 1 320px; min-width: 0; padding: 10px 12px; font-size: var(--text-sm); word-break: break-all; user-select: all; }
.printing-credential > .alert, .printing-credential > p.muted { margin: 10px 20px 0; }
.printing-config { margin: 14px 20px 0; }
.printing-config p { margin: 8px 0; }
.printing-config pre { max-width: 100%; margin: 0; padding: 12px; overflow: auto; color: var(--steel-100); background: var(--steel-950); border-radius: var(--radius-control); font-family: var(--font-mono); font-size: 12px; line-height: 1.5; }
/* The markup pairs each switch with its key; two rows flowed by column keep the switches side by side above the keys. */
.printing-settings .form-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); grid-template-rows: auto auto; grid-auto-flow: column; }
/* A switch whose words run to two lines keeps its box on the first line. */
.printing-settings .form-grid > .field > .toggle { display: flex; align-items: flex-start; gap: 8px; min-height: 24px; }
.printing-settings .form-grid > .field > .toggle > input[type="checkbox"] { margin-top: calc((1lh - 16px) / 2); }
/* The branch switcher is labelled like the other small selectors, and reads as a control, not as its label. */
.printing-branch-field { min-width: 0; }
.printing-branch-field select { max-width: 420px; font-size: var(--text-md); font-weight: 400; }
.printing-target-hint { margin: 12px 20px 0; }
.printing-actions { display: flex; flex-wrap: wrap; align-items: center; justify-content: flex-end; gap: 8px; }
/* The description keeps a readable width; the two test keys go under it together rather than into a stepped pile. */
.printing-agents > .section-heading > div:first-child, .printing-jobs-heading > div:first-child { flex: 1 1 360px; }
.printing-agents > .alert, .printing-agents > p.muted { margin: 0 20px 14px; }
.printing-agent-list { display: grid; gap: 0; margin: 0; padding: 0 20px 8px; list-style: none; border-top: 1px solid var(--line-soft); }
.printing-agent { display: grid; gap: 10px; padding: 14px 0; border-bottom: 1px solid var(--line-soft); }
.printing-agent:last-child { border-bottom: 0; }
.printing-agent.revoked { opacity: .6; }
.printing-agent-head { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; }
.printing-agent-facts { display: flex; flex-wrap: wrap; gap: 6px 24px; margin: 0; font-size: var(--text-sm); }
.printing-agent-facts dt { color: var(--muted); font-size: var(--text-xs); }
.printing-agent-facts dd { margin: 2px 0 0; }
.printing-printers { display: grid; gap: 6px; margin: 0; padding: 0; list-style: none; font-size: var(--text-sm); }
.printing-printers li { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; }
.printing-agent .row-actions { display: flex; flex-wrap: wrap; gap: 8px; }
.printing-new-agent { display: flex; flex-wrap: wrap; align-items: flex-end; gap: 10px; padding: 14px 20px 20px; border-top: 1px solid var(--border); }
.printing-new-agent .field { flex: 1 1 240px; }
/* The empty job list reads as the list's content, under the rule a table's headings would draw. */
.printing-empty { margin: 0; padding: 16px 20px 20px; color: var(--muted); font-size: var(--text-sm); border-top: 1px solid var(--line-soft); }
@media (width <= 760px) {
    /* One column: each switch is followed by its own key, the second pair a step apart. */
    .printing-settings .form-grid { grid-template-rows: none; grid-auto-flow: row; }
    .printing-settings .form-grid > :nth-child(3) { margin-top: 8px; }
    .printing-branch-field { flex: 1 1 auto; }
    .printing-branch-field select { width: 100%; max-width: none; }
    .printing-agent .row-actions > .button { flex: 1 1 auto; }
}
.printing-job-table td { vertical-align: top; }
.printing-job-table td > small { display: block; margin-top: 3px; }
.printing-job-table .badge + .badge { margin-left: 6px; }
.printing-reason { display: block; margin-top: 3px; }
.printing-error, .pos-print-error { display: block; color: var(--red); font-size: var(--text-xs); overflow-wrap: anywhere; }

/* ------------------------------------------------------------------------------------------ courier
   Read on a phone, one-handed, often outdoors: one column, large type, targets that need no aim. */
.courier-shell { min-height: 100vh; min-height: 100dvh; padding: 16px; background: var(--canvas); }
.courier-card { width: min(100%, 560px); margin: 0 auto; padding: 20px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-large); font-size: var(--text-lg); }
.courier-card h1 { margin: 0; font-size: var(--text-3xl); }
.courier-head { display: flex; align-items: flex-start; justify-content: space-between; gap: 12px; margin-bottom: 16px; }
.courier-head p { margin: 4px 0 0; }
.courier-gone { text-align: center; }
.courier-gone .empty-icon { display: grid; margin: 0 auto 10px; font-size: 30px; }
.courier-done { margin: 0 0 14px; padding: 11px 13px; background: var(--green-soft); border: 1px solid var(--green-line); border-radius: var(--radius-surface); }
.courier-facts { display: grid; gap: 14px; margin: 0 0 18px; }
.courier-facts dt { color: var(--muted); font-size: var(--text-sm); font-weight: 600; }
.courier-facts dd { display: grid; gap: 4px; margin: 4px 0 0; }
.courier-facts strong { font-size: var(--text-xl); }
.courier-call, .courier-address, .courier-branch { display: inline-block; padding: 10px 0; font-size: var(--text-xl); font-weight: 600; text-decoration: underline; text-decoration-color: color-mix(in oklch, currentColor 35%, transparent); text-underline-offset: 4px; }
.courier-doorway { font-size: var(--text-xl); }
.courier-total { font-family: var(--font-figures); font-size: 26px; font-variant-numeric: tabular-nums; }
.courier-change { color: var(--amber); font-weight: 600; }
.courier-items { display: grid; gap: 10px; margin: 0 0 20px; padding: 14px 0 0; list-style: none; border-top: 1px solid var(--line-soft); }
.courier-items li { display: flex; gap: 12px; }
.courier-quantity { min-width: 32px; font-weight: 700; font-variant-numeric: tabular-nums; }
.courier-items small { display: block; }
.courier-actions .button { min-height: var(--control-touch); font-size: var(--text-xl); }
.courier-branch { display: block; margin-top: 18px; text-align: center; }

/* --------------------------------------------------------------------------------------- responsive */
@media (max-width: 1100px) {
    :root { --rail-width: 224px; }
    .sidebar { padding-inline: 10px; }
    .metric-grid { grid-template-columns: repeat(2, 1fr); }
    .form-grid.three, .form-grid.four { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .form-grid.three > .span-three, .form-grid.four > .span-three { grid-column: 1 / -1; }
    .metric-grid.dashboard-metrics { grid-template-columns: repeat(4, minmax(0, 1fr)); }
    .diagnostics-strip { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .diagnostics-strip .button { justify-self: start; }
    .diagnostics-strip .button.tertiary { margin-left: -14px; }
}

@media (max-width: 900px) {
    .diagnostic-grid, .settings-grid { grid-template-columns: 1fr; }
    .metric-grid.dashboard-metrics { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .onboarding-list { grid-template-columns: 1fr; }
}

@media (max-width: 760px) {
    /* A phone: the rail folds into a header row with the restaurant's mark and a menu key. */
    .app-shell { display: block; }
    .sidebar { position: sticky; top: 0; z-index: var(--z-nav); width: auto; height: auto; max-height: 100dvh; padding: 8px 12px; overflow-x: hidden; border-right: 0; border-bottom: 1px solid var(--border); }
    .icon-button.rail-toggle { display: inline-grid; }
    .brand { padding-block: 4px; }
    .sidebar:not(.open) .primary-nav, .sidebar:not(.open) .sidebar-footer { display: none; }
    .sidebar.open { overflow-y: auto; }
    .sidebar-footer { margin-top: 10px; }
    .content { padding: 22px 16px 48px; }
    .page-header, .toolbar, .pagination { align-items: stretch; flex-direction: column; }
    /* Stacked, the search box keeps its own height instead of growing to fill the column. */
    .toolbar .search-box { flex: 0 0 auto; max-width: none; }
    .page-header > div:first-child { flex: 0 0 auto; }
    .page-header .header-actions, .page-header .page-actions { justify-content: flex-start; margin-top: 0; margin-left: 0; }
    h1 { font-size: var(--text-2xl); }
    .modal-backdrop { padding: 10px; }
    .cabinet-dialog, .cabinet-dialog.wide { width: 100%; max-height: calc(100dvh - 20px); gap: 16px; }
    .cabinet-dialog .form-grid, .cabinet-dialog .flag-row, .cabinet-dialog .section-heading { padding-inline: 16px; }
    .role-list, .role-scope { padding-inline: 16px; }
    .role-summary { margin-inline: 16px; }
    .role-list { grid-template-columns: 1fr; }
    .cabinet-dialog .alert, .cabinet-dialog .server-side, .cabinet-dialog .form-section > p.hint { margin-inline: 16px; }
    .cabinet-dialog > :is(p, .field, fieldset:not(.dialog-group), .toggle-field, .notice-card) { margin-inline: 16px; }
    .cabinet-dialog > .definition-list { padding-inline: 16px; }
    .cabinet-dialog .table-scroll { margin-inline: 16px; }
    /* On a phone the footer's keys share the row evenly instead of wrapping raggedly. */
    .cabinet-dialog > .form-actions:last-child > .button, .cabinet-dialog > form > .form-actions:last-child > .button { flex: 1 1 auto; }
    .cabinet-dialog > fieldset.dialog-group { margin-inline: 16px; }
    .cabinet-dialog > .form-actions:last-child, .cabinet-dialog > form > .form-actions:last-child { padding-inline: 16px; }
    .form-grid.two, .form-grid.three, .form-grid.four { grid-template-columns: 1fr; }
    .form-grid.three > .field > .toggle:first-child, .form-grid.four > .field > .toggle:first-child { min-height: 0; margin-top: 0; }
    /* A toolbar with nothing left in it (the cabinet and the operator hide their selectors here) is not a blank bar. */
    .shell-toolbar:not(:has(.global-search > *)) { display: none; }
    .header-actions { align-items: stretch; }
    .page-header :is(.header-actions, .page-actions) > .button { flex: 1 1 auto; }
    div.detail-grid, .form-grid.three, .form-grid.four { grid-template-columns: 1fr; }
    .span-two, .span-three { grid-column: auto; }
    .metric-grid, .metric-grid.five { grid-template-columns: 1fr 1fr; }
    .definition-list, .flag-grid { grid-template-columns: 1fr; }
    .diff-row { grid-template-columns: 1fr; }
    .pagination div { justify-content: space-between; }
    .dashboard-grid { grid-template-columns: 1fr; }
    .dashboard-metrics { grid-template-columns: 1fr 1fr; }
    .diagnostics-strip { grid-template-columns: 1fr; }
    .ops-band { grid-template-columns: 1fr; }
    .summary-strip { grid-template-columns: 1fr 1fr; }
    .ops-value { font-size: 34px; }
    /* The takings get the whole width of a phone; the two counts share the row under them. */
    .today-day .summary-card.wide { grid-column: 1 / -1; }
    .today-day .summary-card:not(.wide) .summary-value { font-size: 22px; }
    .today-problem { padding-inline: var(--space-4); }
    .today-problems h2 { padding-inline: var(--space-4); }
    .today-branches li { grid-template-columns: minmax(0, 1fr) auto; padding-inline: var(--space-4); }
    .today-branches small { grid-column: 1; grid-row: 2; }
    .today-branches strong { grid-column: 2; grid-row: 1 / span 2; align-self: center; }
    .toolbar-meta { align-items: flex-start; flex-direction: column; }
    .template-bar { grid-template-columns: 1fr; }
    .schedule-grid { overflow-x: auto; }
    .schedule-head, .schedule-row { min-width: 620px; }
    .wizard-footer { display: grid; grid-template-columns: auto minmax(0, 1fr); gap: 6px 12px; padding: 10px 12px; }
    .wizard-footer span { grid-column: 1 / -1; grid-row: 1; text-align: left; }
    .wizard-footer .button.primary { justify-self: stretch; white-space: normal; line-height: 1.2; }
    /* P1-2: a save bar's answer takes the room left of Save and wraps in it; it never widens its column
       past the screen and pushes Save off. A refusal, which is sentences, gets the whole row, and Save
       the row under it. */
    :is(.save-bar, .brand-save) { grid-template-columns: minmax(0, 1fr) auto; }
    :is(.save-bar, .brand-save) > .brand-save-status { grid-column: 1; grid-row: 1; overflow-wrap: anywhere; }
    :is(.save-bar, .brand-save) > .button { grid-column: 2; grid-row: 1; margin-left: 0; }
    :is(.save-bar, .brand-save) > .brand-save-status:has(.alert) { grid-column: 1 / -1; }
    :is(.save-bar, .brand-save) > .brand-save-status:has(.alert) + .button { grid-column: 1 / -1; grid-row: 2; }
    .audit-detail dl { grid-template-columns: 1fr 1fr; }
    .shell-toolbar { flex-wrap: wrap; padding: 10px 14px; }
    .global-search { flex-basis: 100%; max-width: none; }
    .command-trigger span, .shell-selector { display: none; }
    .login-card { padding: 22px 18px 16px; }
    .entrance-door { min-height: 60px; }
    .pos-shift .button { flex: 1 1 auto; }
    .pos-shift-spacer { display: none; }
    .printing-settings .form-grid { grid-template-columns: 1fr; }
    .printing-actions { width: 100%; justify-content: flex-start; }
    .printing-actions > :is(.button, select) { flex: 1 1 auto; }
    .printing-new-agent .button { width: 100%; }
    /* A phone: the badge and the way out on one row, the sentence under them, small. */
    .impersonation-bar { display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 4px 10px; min-height: 0; padding: 8px 12px; }
    .impersonation-bar .support-badge { grid-row: 1; justify-self: start; }
    .impersonation-bar .button { grid-row: 1; grid-column: 2; min-height: var(--control-sm); margin-left: 0; padding: 0 11px; font-size: var(--text-sm); }
    .impersonation-bar .support-text { grid-column: 1 / -1; font-size: var(--text-xs); line-height: 1.35; }
    :root:has(#support-banner) { --support-band: 96px; }
    :root:has(#support-banner) .app-shell > .sidebar { height: auto; max-height: calc(100dvh - var(--support-band)); }
    .toast { right: 16px; bottom: 16px; left: 16px; max-width: none; }
}

/* NAV-1, a phone. The business's name is the page's first line and scrolls away with it; the areas are a
   bar fixed under the thumb, and every page leaves room for it. (Written as a range so the block above
   stays the first of its spelling.) */
@media (width <= 760px) {
    .cabinet-shell > .sidebar { position: static; padding: 6px 12px; }
    .cabinet-shell > .sidebar .brand { padding-block: 4px; }
    .cabinet-shell .content { padding-bottom: calc(96px + env(safe-area-inset-bottom)); }
    .cabinet-shell > .tab-bar { position: fixed; right: 0; bottom: 0; left: 0; z-index: var(--z-nav); display: grid; grid-auto-columns: minmax(0, 1fr); grid-auto-flow: column; gap: 2px; padding: 6px 6px calc(6px + env(safe-area-inset-bottom)); background: var(--rail); border-top: 1px solid var(--border); }
    .tab-bar a { display: grid; align-content: center; justify-items: center; gap: 3px; min-width: 0; min-height: 52px; color: var(--rail-ink); font-size: var(--text-2xs); font-weight: 500; line-height: 1.2; text-decoration: none; border-radius: var(--radius-control); -webkit-tap-highlight-color: transparent; }
    .tab-bar a > span:last-child { max-width: 100%; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
    .tab-mark { display: grid; place-items: center; width: 48px; height: 28px; border-radius: var(--radius-control); transition: background-color 120ms ease, transform var(--press) var(--ease-out); }
    .tab-mark .icon { width: 22px; height: 22px; }
    .tab-bar a.active { color: var(--ink); font-weight: 600; }
    .tab-bar a.active .tab-mark { background: var(--surface); box-shadow: var(--shadow-1), inset 0 0 0 1px var(--border); }
    .tab-bar a:active .tab-mark { transform: scale(.94); }
    /* The strip runs edge to edge and slides sideways when an area has more screens than fit. */
    .area-nav { flex-wrap: nowrap; gap: 0 22px; margin: -10px -16px 18px; padding-inline: 16px; overflow-x: auto; overscroll-behavior-x: contain; scrollbar-width: none; }
    .area-nav::-webkit-scrollbar { display: none; }
    .area-nav a { min-height: 48px; font-size: 15px; }
    .area-nav a.nav-locked { margin-left: 0; }
    .nav-row { min-height: 64px; }
    .branch-parts a { min-height: 48px; font-size: 15px; }
    .app-list { grid-template-columns: minmax(0, 1fr); }
    /* A phone stacks a branch's row: its name, the choice at full width, the key under it. Every key is a thumb's height. */
    .poster-branches > li { grid-template-columns: minmax(0, 1fr); }
    .poster-branches > li > .button { justify-self: start; }
    .poster-branch-current { grid-column: auto; }
    .poster-step .button, .poster-branches select { min-height: var(--control-lg); }
    .poster-step .section-heading > .button { width: 100%; justify-content: center; }
    .poster-preview > .form-actions > .button { width: 100%; justify-content: center; }
    .poster-rows { max-height: 360px; }
    .poster-rows > li { grid-template-columns: minmax(0, 1fr); }
    .poster-key-form .button, .poster-key-block .button, .poster-key-form input { min-height: var(--control-lg); }
    .poster-key-form > .form-actions > .button, .poster-key-block > .form-actions > .button { flex: 1 1 100%; justify-content: center; }
    .poster-sign-in { justify-items: stretch; }
    .poster-sign-in > .button { min-height: var(--control-lg); justify-content: center; }
    .poster-key-details > summary { padding: 12px 0; }
    .operator-poster-actions > .button { width: 100%; min-height: var(--control-lg); justify-content: center; }
    .app-row-copy strong { font-size: var(--text-lg); }
    .back-link { min-height: 44px; margin-bottom: 2px; font-size: var(--text-md); }
    .nav-row-copy strong { font-size: var(--text-lg); }
    .account-panel .user-card > .button { flex: 1 1 100%; min-height: var(--control-lg); }
    .account-panel .rail-prefs { grid-template-columns: minmax(0, 1fr); }
    .cabinet-shell .toast { bottom: calc(80px + env(safe-area-inset-bottom)); }
    /* A save bar that travels with the screen stops above the bottom bar, not behind it. */
    .cabinet-shell .wizard-footer { bottom: calc(72px + env(safe-area-inset-bottom)); }
}

/* ------------------------------------------------------------------------ motion, contrast, paper */
@media (hover: none) {
    tbody tr:hover td { background: transparent; }
    tr.selected td { background: var(--surface-accent); }
}

@media (prefers-reduced-motion: reduce) {
    *, *::before, *::after { scroll-behavior: auto !important; animation-duration: .01ms !important; animation-iteration-count: 1 !important; transition-duration: .01ms !important; }
    .button:active:not(:disabled), .pos-product:active:not(:disabled), .pos-chip:active, .pos-step:active:not(:disabled), .pos-pay:active:not(:disabled), .pos-option:active:not(:disabled), .station-key:active:not(:disabled), .station-person:active:not(:disabled), .kds-action:active:not(:disabled), .entrance-door:active, .icon-button:active { transform: none; }
}

@media (forced-colors: active) {
    .status-dot, .badge, .button, input, select, textarea { forced-color-adjust: none; border: 1px solid CanvasText; }
    .status-dot, .badge::before, .ops-label::before, .kds-column-title::before { background: CanvasText; }
    .primary-nav a.active, .pos-chip.chosen, .pos-pay.chosen, .pos-option.chosen, .role-card.chosen { outline: 2px solid Highlight; }
    .support-frame { border-color: Highlight; }
}

@page { size: A4; margin: 14mm; }
@media print {
    :root { color-scheme: light; --canvas: #fff; --surface: #fff; --surface-subtle: #fff; --ink: #000; --navy: #000; --muted: #333; --label: #222; --border: #bbb; --line-soft: #ddd; }
    .sidebar, .shell-toolbar, .breadcrumbs, .header-actions, .page-actions, .detail-tabs, .toast, .skip-link, .no-print, .onboarding-panel, .impersonation-bar, .support-frame { display: none !important; }
    .app-shell { display: block; }
    .content { max-width: none; padding: 0; }
    .panel, .metric { box-shadow: none; break-inside: avoid; }
    .print-summary { display: block; }
    .screen-tenant-detail { display: none !important; }
    a { color: #000; text-decoration: none; }
    /* The slip: the confirmation card alone, no chrome. */
    .pos-bar, .pos-done-actions, .pos-grid, .pos-done-ready, .pos-print { display: none !important; }
    .pos-shell, .pos-main, .pos-done { display: block; height: auto; }
    .pos-done-card { width: 100%; border: 0; box-shadow: none; }
    /* A report being looked at prints alone: the sheet, on paper, as on screen. */
    body:has(.shift-print) * { visibility: hidden; }
    body:has(.shift-print) .shift-print, body:has(.shift-print) .shift-print * { visibility: visible; }
    body:has(.shift-print) .pos-shell, body:has(.shift-print) .pos-main, body:has(.shift-print) .pos-grid,
    body:has(.shift-print) .pos-menu, body:has(.shift-print) .app-shell, body:has(.shift-print) .content-column,
    body:has(.shift-print) .content { display: block; height: auto; overflow: visible; }
    body:has(.shift-print) .modal-backdrop { position: absolute; inset: 0; display: block; padding: 0; background: none; }
    body:has(.shift-print) .shift-print { position: absolute; top: 0; left: 0; width: 100%; max-height: none; overflow: visible; border: 0; box-shadow: none; }
    .shift-print .no-print { display: none !important; }
    .shift-report-section[open] summary, .shift-report-section summary { list-style: none; }
}

/* ---- The dealership: the stock, its photographs, the buyers' leads and conversations. ---- */
.mono { font-family: var(--font-mono); letter-spacing: .02em; }
.segmented { display: inline-flex; flex-wrap: wrap; gap: 2px; margin-bottom: var(--space-4); padding: 2px; background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-control); }
.segmented > button { display: inline-flex; align-items: center; gap: var(--space-2); min-height: 32px; padding: 0 12px; color: var(--label); background: transparent; border: 0; border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-sm); font-weight: 600; }
.segmented > button.active { color: var(--ink); background: var(--surface); box-shadow: var(--shadow-1); }
.segmented > button:disabled { cursor: default; opacity: .6; }
.toolbar > .segmented { margin-bottom: 0; }
.listing-row { display: flex; align-items: center; gap: var(--space-3); color: var(--ink); text-decoration: none; }
.listing-thumb { flex: none; width: 96px; height: 72px; object-fit: cover; background: var(--surface-subtle); border-radius: var(--radius-control); }
.listing-thumb.small { width: 64px; height: 48px; }
.listing-thumb.empty { display: grid; place-items: center; color: var(--muted); }
.split-view { display: grid; gap: var(--space-4); align-items: start; }
.split-view.has-detail { grid-template-columns: minmax(280px, 2fr) minmax(0, 3fr); }
.split-view > .panel { margin-bottom: 0; }
.split-list .nav-rows, .split-list > .nav-rows { max-width: none; margin: 0; }
.split-list .nav-row.active { background: var(--surface-hover); }
.split-detail { padding: var(--space-4) var(--space-5); }
.lead-message { margin: var(--space-4) 0; padding: var(--space-3) var(--space-4); background: var(--surface-subtle); border-left: 3px solid var(--border); border-radius: var(--radius-control); white-space: pre-wrap; }
.lead-car { display: flex; gap: var(--space-3); align-items: flex-start; margin: var(--space-4) 0; }
.lead-car > div { display: grid; gap: 2px; }
.conversation-meta { display: grid; justify-items: end; gap: 4px; font-size: var(--text-xs); color: var(--muted); }
.chat-thread { display: grid; gap: var(--space-4); }
.chat-messages { display: grid; gap: var(--space-2); max-height: 60vh; margin: 0; padding: 0; overflow-y: auto; list-style: none; }
.chat-message { display: grid; gap: 2px; max-width: 80%; padding: var(--space-2) var(--space-3); background: var(--surface-subtle); border-radius: var(--radius-surface); }
.chat-message.mine { justify-self: end; background: var(--surface-hover); }
.chat-message > p { margin: 0; white-space: pre-wrap; overflow-wrap: anywhere; }
.chat-message > time, .chat-author { color: var(--muted); font-size: var(--text-xs); }
.chat-author { font-weight: 600; }
.chat-reply textarea { width: 100%; }
.photo-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(200px, 1fr)); gap: var(--space-3); margin: 0 0 var(--space-4); padding: 0; list-style: none; }
.photo-tile { position: relative; display: grid; gap: var(--space-2); padding: var(--space-2); background: var(--surface-subtle); border: 1px solid var(--border); border-radius: var(--radius-surface); }
.photo-tile > img { width: 100%; height: auto; aspect-ratio: 4 / 3; object-fit: cover; border-radius: var(--radius-control); }
.photo-tile > .badge { position: absolute; top: var(--space-3); left: var(--space-3); }
.photo-pending { display: grid; place-items: center; aspect-ratio: 4 / 3; color: var(--muted); font-size: var(--text-sm); }
.equipment-flags { display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); gap: var(--space-2) var(--space-4); }
.hours-grid { display: grid; gap: var(--space-2); }
.hours-day { display: grid; grid-template-columns: 160px minmax(0, 1fr); align-items: center; gap: var(--space-3); }
.hours-intervals { display: flex; flex-wrap: wrap; align-items: center; gap: var(--space-2); }
.hours-interval { display: inline-flex; align-items: center; gap: var(--space-1); }
.site-service { padding-top: var(--space-3); border-top: 1px solid var(--border); }
.import-rules { margin: 0 0 var(--space-4); padding-left: var(--space-5); }
.sticky-actions { position: sticky; bottom: 0; z-index: 2; padding: var(--space-3) 0; background: var(--canvas); border-top: 1px solid var(--border); }
@media (max-width: 900px) {
    .split-view.has-detail { grid-template-columns: minmax(0, 1fr); }
    .split-view.has-detail > .split-list { display: none; }
    .hours-day { grid-template-columns: minmax(0, 1fr); }
}

/* Agro: a segmented choice made of real radios (the console's «what the business sells»), and
   a fieldset that reads as one field of a form grid (a machine's attribute with several options). */
.segmented > label { position: relative; display: inline-flex; align-items: center; min-height: 32px; padding: 0 12px; color: var(--label); border-radius: var(--radius-control); cursor: pointer; font-size: var(--text-sm); font-weight: 600; }
.segmented > label.active { color: var(--ink); background: var(--surface); box-shadow: var(--shadow-1); }
.segmented > label > input { position: absolute; inset: 0; margin: 0; opacity: 0; cursor: pointer; }
.segmented > label:has(input:focus-visible) { outline: 2px solid var(--focus); outline-offset: 2px; }
fieldset.field { min-width: 0; margin: 0; padding: 0; border: 0; }
fieldset.field > legend { margin-bottom: 6px; padding: 0; color: var(--label); font-size: var(--text-sm); font-weight: 600; line-height: 1.3; }
