/* ============================================================
   Оформление. Строгий деловой вид: спокойный цвет, много воздуха,
   акцент только там, где нужно действие или предупреждение.
   ============================================================ */

/* ============================================================
   Токены. Единственное место, где живут цвета, размеры и сетка:
   всё остальное ссылается сюда. Значения — из дизайн-системы
   «Учёт продаж»: тёмная и светлая темы описаны одинаково подробно.
   ============================================================ */

:root {
  color-scheme: light;

  /* Поверхности: страница, карточка, подложка внутри карточки */
  --page: #f5f7fa;
  --surface: #ffffff;
  --surface-raised: #eef1f6;
  --zebra: rgba(16, 27, 54, .022);
  --hover: rgba(16, 27, 54, .045);

  /* Текст. Нейтраль уведена в синеву: рядом с синим акцентом
     чистый серый выглядит грязным */
  --ink: #101b36;
  --ink-muted: #4a566d;
  --ink-faint: #5f6b7f;

  /* Линии */
  --border: #e3e7ee;
  --border-strong: #cdd4df;
  --field-border: #8793a6;   /* рамка полей: не бледнее 3:1 к фону (WCAG 1.4.11) */
  --grid: #eceff4;

  /* Акцент: одно действие на экране, активный раздел, ссылки */
  --accent: #123499;
  --accent-hover: #0a2472;
  --accent-press: #051650;
  --accent-soft: #e9edfa;
  --on-accent: #ffffff;
  --focus: #123499;

  /* Шкала выполнения плана. С акцентом не смешивается */
  --good: #0c8a3e;
  --warning: #c98207;
  --serious: #d1663a;
  --critical: #c2352f;

  /* Те же четыре ступени для текста. Цвет шкалы хорош для заливки и точки,
     но буквами на светлой подложке не дотягивал до нормы контраста 4,5
     (жёлтый — 2,8). Текстовые оттенки темнее: 4,6 и выше даже на
     насыщенной части плашки с прогрессом */
  --good-ink: #0a6e31;
  --warning-ink: #895905;
  --serious-ink: #9f4825;
  --critical-ink: #a92e29;
  /* Выходной в графике — сиреневый: не спутать с рабочей, отпуском и больничным */
  --off: #9148d6;
  --off-ink: #6c2bb0;

  /* Цвета категорий показателей: помогают различать группы колонок.
     Это не состояние — со шкалой плана они не пересекаются по смыслу */
  --cat-1: #4c6ef5;
  --cat-2: #0ca678;
  --cat-3: #e8590c;
  --cat-4: #7048e8;
  --cat-5: #0b7285;
  --cat-6: #c2255c;

  /* Данные на графиках */
  --series-1: #123499;
  --series-2: #d1663a;
  --weekend-ink: #b0431f;   /* выходные в шапках таблиц: 5:1 на белом */
  --axis: #c3c8d4;

  /* Шаг сетки — 4 пикселя */
  --space-1: 4px;
  --space-2: 8px;
  --space-3: 12px;
  --space-4: 16px;
  --space-5: 24px;
  --space-6: 32px;

  --radius-sm: 8px;
  --radius-md: 12px;
  --radius-lg: 16px;
  --radius-pill: 999px;

  /* Насыщенность заливки в плашках процентов */
  --pct-tint: 12%;
  --pct-tint-strong: 24%;

  --shadow-card: 0 1px 2px rgba(16, 27, 54, .04), 0 1px 3px rgba(16, 27, 54, .06);
  --shadow-pop: 0 8px 24px rgba(16, 27, 54, .12);

  /* Шрифт: Inter, если он есть локально или загрузился; иначе системный */
  --font: "Inter Local", Inter, system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;

  /* Типографика: один набор размеров на всё приложение */
  --fs-micro: 0.7188rem;
  --fs-xs: 0.7812rem;
  --fs-sm: 0.8125rem;
  --fs-base: 0.9062rem;
  --fs-body: 0.9375rem;
  --fs-lead: 0.9062rem;
  --fs-data: 0.875rem;
  --fs-h2: 1rem;
  --fs-h1: 1.4375rem;
  --fs-metric: 1.75rem;

  /* Сетка: контент не шире 1400, поля у шапки и страницы одинаковые */
  --content-max: 1400px;
  /* Высота поля и кнопки в строке фильтров */
  --control-h: 38px;
  --gutter: 40px;
  --header-h: 56px;

  /* Слои поверх страницы — одна шкала на всё. Внутри таблиц (липкие столбцы)
     свои местные значения 0–5, они выше 10 не поднимаются */
  --z-header: 30;
  --z-popover: 60;
  --z-status: 90;
  --z-toast: 100;
  --z-onb: 200;
}

/* Ниже 1480 контентный блок сужается вместе с окном, поля остаются 40,
   а на узких экранах сжимаются, чтобы не съедать саму таблицу */
@media (max-width: 900px) {
  :root { --gutter: 24px; }
}
@media (max-width: 600px) {
  :root { --gutter: 16px; }
}

/* Шрифт «Inter Local» (web/fonts/InterVariable.woff2) объявляет js/app.js,
   и только если файл на месте: объявление здесь заставляло браузер каждый
   раз просить отсутствующий файл. Нет файла — Inter приходит с Google */

/* Тёмная тема — равноправная: половина смен вечерние.
   Меняются только значения токенов, правила ниже одни и те же. */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    color-scheme: dark;

    --page: #0b1017;
    --surface: #171e2a;
    --surface-raised: #212a38;
    --zebra: rgba(255, 255, 255, .022);
    --hover: rgba(255, 255, 255, .055);

    --ink: #e8edf5;
    --ink-muted: #a7b2c2;
    --ink-faint: #929dae;

    --border: #2c3746;
    --border-strong: #44505f;
    --field-border: #7a8aa1;
    --grid: #28313d;

    --accent: #5b7ce8;
    --accent-hover: #7b96ee;
    /* Ссылки и активный раздел: accent на тёмной карточке давал 4,4 при норме 4,5 */
    --link: #7b96ee;
    --link-hover: #a3b6f4;
    --edge-shadow: rgba(0, 0, 0, .55);
    --accent-press: #486ada;
    --accent-soft: #1b2450;
    --on-accent: #0b1220;
    --focus: #8fa8f5;

    --good: #3fbf63;
    --warning: #e9b13c;
    --serious: #ef9367;
    --critical: #e8615f;

    /* На тёмном фоне текст шкалы, наоборот, чуть светлее заливки */
    --good-ink: #61cb7f;
    --warning-ink: #eab545;
    --serious-ink: #f1a37e;
    --critical-ink: #ee8d8c;
    --off: #b27cf0;
    --off-ink: #d4b3fa;

    --cat-1: #8da2ff;
    --cat-2: #38d9a9;
    --cat-3: #ffa94d;
    --cat-4: #b197fc;
    --cat-5: #4dd0e1;
    --cat-6: #f783ac;

    --series-1: #5b7ce8;
    --series-2: #ef9367;
    --weekend-ink: #ef9367;
    --axis: #3a424e;

    --pct-tint: 20%;
    --pct-tint-strong: 30%;

    --shadow-card: 0 1px 2px rgba(0, 0, 0, .35);
    --shadow-pop: 0 8px 24px rgba(0, 0, 0, .5);
  }
}

:root[data-theme="dark"] {
  color-scheme: dark;

  --page: #0b1017;
  --surface: #171e2a;
  --surface-raised: #212a38;
  --zebra: rgba(255, 255, 255, .022);
  --hover: rgba(255, 255, 255, .055);

  --ink: #e8edf5;
  --ink-muted: #a7b2c2;
  --ink-faint: #929dae;

  --border: #2c3746;
  --border-strong: #44505f;
  --field-border: #7a8aa1;
  --grid: #28313d;

  --accent: #5b7ce8;
  --accent-hover: #7b96ee;
  --link: #7b96ee;
  --link-hover: #a3b6f4;
  --edge-shadow: rgba(0, 0, 0, .55);
  --accent-press: #486ada;
  --accent-soft: #1b2450;
  --on-accent: #0b1220;
  --focus: #8fa8f5;

  --good: #3fbf63;
  --warning: #e9b13c;
  --serious: #ef9367;
  --critical: #e8615f;

  --good-ink: #61cb7f;
  --warning-ink: #eab545;
  --serious-ink: #f1a37e;
  --critical-ink: #ee8d8c;
  --off: #b27cf0;
  --off-ink: #d4b3fa;

  --cat-1: #8da2ff;
  --cat-2: #38d9a9;
  --cat-3: #ffa94d;
  --cat-4: #b197fc;
  --cat-5: #4dd0e1;
  --cat-6: #f783ac;

  --series-1: #5b7ce8;
  --series-2: #ef9367;
  --weekend-ink: #ef9367;
  --axis: #3a424e;

  --pct-tint: 20%;
  --pct-tint-strong: 30%;

  --shadow-card: 0 1px 2px rgba(0, 0, 0, .35);
  --shadow-pop: 0 8px 24px rgba(0, 0, 0, .5);
}

* { box-sizing: border-box; }

html, body {
  margin: 0;
  padding: 0;
  background: var(--page);
  color: var(--ink);
  font-family: var(--font);
  font-size: var(--fs-body);
  line-height: 1.5;
  -webkit-text-size-adjust: 100%;
  -webkit-font-smoothing: antialiased;
}

/* --link объявлен только в тёмной теме; в светлой берётся accent (9,9 : 1) */
a { color: var(--link, var(--accent)); text-underline-offset: 2px; }
a:hover { color: var(--link-hover, var(--accent-hover)); }

:focus-visible {
  outline: 2px solid var(--focus);
  outline-offset: 2px;
  border-radius: 4px;
}

/* ---------- каркас ---------- */

.app { min-height: 100vh; display: flex; flex-direction: column; }

header.top {
  position: sticky;
  top: 0;
  z-index: var(--z-header);
  background: var(--surface);
  border-bottom: 1px solid var(--border);
  padding: 0 var(--gutter);
}

.top-inner {
  max-width: var(--content-max);
  margin: 0 auto;
  display: flex;
  align-items: center;
  gap: 20px;
  min-height: var(--header-h);
  flex-wrap: wrap;
}

.brand {
  font-weight: 640;
  font-size: 0.9375rem;
  letter-spacing: -.011em;
  white-space: nowrap;
  display: flex;
  align-items: baseline;
  gap: 7px;
}
.brand span {
  color: var(--ink-faint);
  font-weight: 450;
  font-size: 0.8125rem;
  padding-left: 8px;
  border-left: 1px solid var(--border-strong);
}

nav.tabs {
  display: flex;
  gap: 1px;
  justify-content: flex-start;
  overflow-x: auto;
  flex: 1;
  scrollbar-width: none;
  margin: 0 -4px;
  padding: 0 4px;
}
nav.tabs::-webkit-scrollbar { display: none; }

/* Вкладок десять, и у каждой значок: в одну строку с названием и именем
   они не помещаются ни на одном разумном экране. Поэтому меню всегда
   занимает свою строку и стоит по центру, а не обрезается на краю */
nav.tabs { order: 3; flex: 1 0 100%; padding: 0 4px 8px; }
nav.tabs > a:first-child { margin-left: auto; }
nav.tabs > a:last-child { margin-right: auto; }
/* На ноутбуке значки у вкладок убираем: без них все десять разделов
   помещаются в строку, и листать меню не нужно */
@media (max-width: 1180px) {
  nav.tabs a .ic { display: none; }
}
/* Когда вкладки не влезают и так, края мягко гаснут — видно, что строка листается */
@media (max-width: 820px) {
  nav.tabs {
    -webkit-mask-image: linear-gradient(to right, transparent 0, #000 18px, #000 calc(100% - 18px), transparent 100%);
    mask-image: linear-gradient(to right, transparent 0, #000 18px, #000 calc(100% - 18px), transparent 100%);
  }
}

/* Каждый раздел — видимая кнопка с рамкой: без неё непонятно, где
   кончается зона нажатия (правка 26.09: «не понятна зона нажатия») */
nav.tabs { gap: 6px; }
nav.tabs a {
  min-height: 34px;
  padding: 0 12px;
  border: 1px solid var(--border);
  border-radius: var(--radius-sm);
  background: var(--surface);
  color: var(--ink-muted);
  text-decoration: none;
  white-space: nowrap;
  font-size: 0.875rem;
  font-weight: 460;
  transition: background .12s, color .12s, border-color .12s;
}
nav.tabs a:hover { background: var(--surface-raised); border-color: var(--border-strong); color: var(--ink); }
nav.tabs a:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
nav.tabs a.active {
  background: var(--accent-soft);
  border-color: color-mix(in srgb, var(--accent) 40%, transparent);
  color: var(--link, var(--accent));
  font-weight: 560;
}

/* Роль слева от имени: «куратор · Илья», «продавец · Саша» */
.who .role-tag {
  display: inline-flex;
  align-items: center;
  height: 22px;
  padding: 0 8px;
  border-radius: var(--radius-pill);
  background: var(--surface-raised);
  border: 1px solid var(--border);
  color: var(--ink-muted);
  font-size: 0.7188rem;
  font-weight: 600;
  letter-spacing: .02em;
  text-transform: uppercase;
}
.who .role-tag:empty { display: none; }

.who {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-left: auto;
  font-size: 0.8125rem;
  color: var(--ink-muted);
  white-space: nowrap;
}

main {
  flex: 1;
  width: 100%;
  max-width: var(--content-max);
  margin: 0 auto;
  padding: 26px var(--gutter) 72px;
}

h1 {
  font-size: var(--fs-h1);
  line-height: 28px;
  font-weight: 620;
  margin: 0 0 3px;
  letter-spacing: -.02em;
}
h2 { font-size: var(--fs-h2); line-height: 22px; font-weight: 600; margin: 30px 0 12px; letter-spacing: -.01em; }
.lead { color: var(--ink-muted); margin: 2px 0 20px; font-size: var(--fs-lead); }

/* ---------- карточки ---------- */

.card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-card);
  padding: 18px;
  margin-bottom: 16px;
}
.card > strong { font-size: 0.9375rem; font-weight: 600; letter-spacing: -.01em; }

/* Шапка экрана: заголовок и фильтры в одном ряду */
.page-head {
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  gap: var(--space-5);
  flex-wrap: wrap;
  margin-bottom: var(--space-5);
}
.page-head .titles { min-width: 0; }
.page-head h1 { margin: 0; }
.page-head .lead { margin: 2px 0 0; }
.page-head .filters {
  display: flex;
  align-items: flex-end;
  gap: var(--space-3);
  flex-wrap: wrap;
}
.page-head .filters .field { display: flex; flex-direction: column; gap: 3px; margin-bottom: 0; }
.page-head .filters label { margin-bottom: 0; }
.page-head .filters select,
.page-head .filters input { width: auto; height: var(--control-h); }
.page-head .filters button { height: var(--control-h); }
.page-head .filters label {
  font-size: var(--fs-micro);
  font-weight: 600;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--ink-faint);
}
.page-head .filters .row { gap: 6px; }
@media (max-width: 700px) {
  .page-head { gap: var(--space-4); }
  .page-head .filters { width: 100%; }
}

.row { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; }
.spacer { flex: 1; }

/* ---------- кнопки ---------- */

button, .btn {
  font: inherit;
  font-size: 0.875rem;
  font-weight: 500;
  line-height: 1.2;
  padding: 9px 16px;
  border-radius: var(--radius-sm);
  border: 1px solid var(--border-strong);
  /* Серая заливка: рядом с белым полем ввода кнопка должна читаться как кнопка */
  background: var(--surface-raised);
  color: var(--ink);
  cursor: pointer;
  white-space: nowrap;
  transition: background .15s, border-color .15s, color .15s, filter .12s, transform .08s;
}
button:hover:not(:disabled) { background: var(--hover); border-color: var(--ink-faint); }
button:active:not(:disabled) { transform: translateY(.5px); }
button:disabled { opacity: .5; cursor: default; }

button.primary {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--on-accent);
  font-weight: 560;
}
button.primary:hover:not(:disabled) { background: var(--accent-hover); border-color: var(--accent-hover); }
button.primary:active:not(:disabled) { background: var(--accent-press); border-color: var(--accent-press); }

button.ghost { background: transparent; border-color: transparent; color: var(--ink-muted); }
/* Кнопка-иконка: тема, шаг по дням */
button.icon {
  padding: 8px;
  width: 34px;
  height: 34px;
  display: inline-grid;
  place-items: center;
  line-height: 0;
}
button.icon svg { width: 17px; height: 17px; display: block; }
button.ghost:hover { background: var(--surface-raised); color: var(--ink); }

button.small { padding: 6px 12px; font-size: var(--fs-sm); }

/* ---------- поля ---------- */

input, select, textarea {
  font: inherit;
  min-height: var(--control-h);
  font-size: var(--fs-base);
  padding: 8px 11px;
  border-radius: var(--radius-sm);
  border: 1px solid var(--field-border);
  background: var(--surface);
  color: var(--ink);
  width: 100%;
  transition: border-color .12s, box-shadow .12s;
}
input:hover:not(:disabled), select:hover { border-color: var(--ink-faint); }
input:focus, select:focus, textarea:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px var(--accent-soft);
}
input:disabled, textarea:disabled { background: var(--surface-raised); color: var(--ink-faint); }

label {
  display: block;
  font-size: var(--fs-xs);
  font-weight: 500;
  color: var(--ink-muted);
  margin-bottom: 5px;
}
.field { margin-bottom: 15px; }
select { cursor: pointer; }

/* ---------- сообщения ---------- */

.msg {
  padding: 11px 13px;
  border-radius: var(--radius-sm);
  font-size: 0.875rem;
  margin-bottom: 14px;
  border: 1px solid transparent;
}
.msg.error {
  background: color-mix(in srgb, var(--critical) 9%, var(--surface));
  border-color: color-mix(in srgb, var(--critical) 26%, transparent);
  color: var(--critical-ink);
}
.msg.ok {
  background: color-mix(in srgb, var(--good) 9%, var(--surface));
  border-color: color-mix(in srgb, var(--good) 26%, transparent);
  color: var(--good-ink);
}
.msg.info { background: var(--surface-raised); color: var(--ink-muted); border-color: var(--border); }

.muted { color: var(--ink-faint); }
.small { font-size: 0.8125rem; }
.num { font-variant-numeric: tabular-nums; }

/* ---------- пустые состояния ---------- */

.empty {
  padding: 34px 20px;
  text-align: center;
  color: var(--ink-muted);
}
.empty .title { font-weight: 560; color: var(--ink); margin-bottom: 4px; }
.empty .hint { font-size: 0.8438rem; color: var(--ink-faint); max-width: 420px; margin: 0 auto; }

/* ---------- таблицы ---------- */

.table-wrap {
  overflow-x: auto;
  margin: 0 -18px;
  padding: 0;
  /* Тени по краям подсказывают, что таблица шире экрана */
  background:
    linear-gradient(to right, var(--surface) 40%, transparent) left center / 28px 100% no-repeat,
    linear-gradient(to left, var(--surface) 40%, transparent) right center / 28px 100% no-repeat,
    radial-gradient(farthest-side at 0 50%, var(--edge-shadow, rgba(16, 24, 40, .1)), transparent) left center / 9px 100% no-repeat,
    radial-gradient(farthest-side at 100% 50%, var(--edge-shadow, rgba(16, 24, 40, .1)), transparent) right center / 9px 100% no-repeat;
  background-attachment: local, local, scroll, scroll;
}

table { border-collapse: separate; border-spacing: 0; width: 100%; font-size: 0.875rem; }

th, td { padding: 10px 14px; text-align: right; white-space: nowrap; font-size: var(--fs-data); }
th:first-child, td:first-child { padding-left: 18px; }
th:last-child, td:last-child { padding-right: 18px; }

/* Липкую шапку не делаем: обёртка таблицы прокручивается вбок,
   и внутри неё шапка «зависает» поверх первой строки, пряча её */
thead th {
  background: var(--surface);
  font-size: 0.7188rem;
  font-weight: 600;
  color: var(--ink-faint);
  text-transform: uppercase;
  letter-spacing: .045em;
  border-bottom: 1px solid var(--border-strong);
  padding-top: 11px;
  padding-bottom: 8px;
}

tbody tr { --row-bg: transparent; }
tbody tr:nth-child(even) { --row-bg: var(--zebra); }
tbody tr:hover { --row-bg: var(--hover); }

tbody td {
  background: var(--row-bg);
  border-bottom: 1px solid var(--grid);
  font-variant-numeric: tabular-nums;
  transition: background .1s;
}

th:first-child, td:first-child { text-align: left; }

/* Таблица, в ячейках которой стоят поля и кнопки: всё по левому краю,
   чтобы подпись столбца начиналась ровно там же, где поле под ней */
.form-table th, .form-table td { text-align: left; }
.form-table td.num, .form-table th.num { text-align: right; }

/* Первая колонка не уезжает при горизонтальной прокрутке.
   Тонкая линия справа показывает, где она кончается. */
.sticky-col {
  position: sticky;
  left: 0;
  z-index: 1;
  background: var(--surface);
  background-image: linear-gradient(var(--row-bg), var(--row-bg));
  box-shadow: 1px 0 0 0 var(--border);
}
thead .sticky-col { z-index: 2; }

tr.group td {
  background: var(--surface-raised);
  padding-left: 0;
  font-size: 0.7188rem;
  font-weight: 650;
  color: var(--ink-muted);
  text-transform: uppercase;
  letter-spacing: .05em;
  padding-top: 7px;
  padding-bottom: 7px;
  border-bottom: 1px solid var(--border);
}

/* Название категории не уезжает вместе с горизонтальной прокруткой */
.sticky-label {
  position: sticky;
  left: 18px;
  display: inline-block;
  padding-left: 18px;
}

tr.total td {
  font-weight: 650;
  border-top: 2px solid var(--border-strong);
  background: var(--surface-raised);
  border-bottom: none;
}
tr.total .sticky-col { background: var(--surface-raised); }

/* Шапка с категориями над группой колонок */
.cat-th {
  text-align: center !important;
  border-left: 1px solid var(--border);
  color: var(--ink-muted);
  font-size: 0.6875rem;
}
/* Линия там, где начинается новая категория */
.group-start { border-left: 1px solid var(--border); }

/* ---------- светофор ---------- */

/* Процент выполнения — плашка с мягкой заливкой.
   Цвет несёт не восьмипиксельная точка, а сама ячейка: таблица на двенадцать
   точек читается одним взглядом. Число остаётся на месте, поэтому смысл
   не держится на одном цвете. */
.pct-pill {
  display: inline-flex;
  align-items: center;
  justify-content: flex-end;
  min-width: 56px;
  padding: 4px 9px;
  border-radius: var(--radius-sm);
  font-size: var(--fs-data);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
  letter-spacing: -.01em;
  color: var(--lv-ink, var(--lv));
  background: color-mix(in srgb, var(--lv) var(--pct-tint), transparent);
}
/* Там, где раньше под числом висела отдельная чёрточка, заливка сама
   показывает, сколько пройдено: левая часть плашки темнее правой */
.pct-pill[data-bar] {
  background: linear-gradient(
    to right,
    color-mix(in srgb, var(--lv) var(--pct-tint-strong), transparent) 0 var(--fill, 0%),
    color-mix(in srgb, var(--lv) 7%, transparent) var(--fill, 0%) 100%
  );
}
.pct-pill.lv-red { --lv: var(--critical); --lv-ink: var(--critical-ink); }
.pct-pill.lv-orange { --lv: var(--serious); --lv-ink: var(--serious-ink); }
.pct-pill.lv-amber { --lv: var(--warning); --lv-ink: var(--warning-ink); }
.pct-pill.lv-green { --lv: var(--good); --lv-ink: var(--good-ink); }
/* «Сегодня»: цифра за день в плашке светофора (доля от «нужно в день»); цвет не единственный признак — есть title и скрытый текст */
.pct-pill.day-pill { min-width: 0; justify-content: center; padding: 2px 8px; }
.sr-only { position: absolute; width: 1px; height: 1px; margin: -1px; padding: 0; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0; }
/* ВМП за месяц и стрелка к прошлому дню: рост — зелёный, падение — красный, текстом ↑/↓ */
.vmp-cell { display: inline-flex; align-items: baseline; gap: 6px; white-space: nowrap; }
.vmp-arrow { font-weight: 700; cursor: help; }
.vmp-arrow.up { color: var(--good-ink); }
.vmp-arrow.down { color: var(--critical-ink); }
.vmp-arrow.same { color: var(--ink-muted); }
.pct-pill.lv-none {
  color: var(--ink-faint);
  background: none;
  min-width: 0;
  padding: 4px 0;
  font-weight: 400;
}

.pct { display: inline-flex; align-items: center; gap: 7px; justify-content: flex-end; }
.dot { width: 8px; height: 8px; border-radius: 50%; flex: none; }
/* ---------- метки состояния ---------- */

.badge {
  display: inline-flex;
  align-items: center;
  padding: 3px 10px;
  border-radius: var(--radius-sm);
  font-size: var(--fs-sm);
  font-weight: 560;
  white-space: nowrap;
  border: 1px solid transparent;
}
.badge.ok {
  background: color-mix(in srgb, var(--good) 14%, transparent);
  border-color: color-mix(in srgb, var(--good) 34%, transparent);
  color: var(--good-ink);
}
/* День отмечен как пустой — это норма, а не тревога: нейтральный тон */
.badge.none {
  background: var(--surface-raised);
  border-color: var(--border);
  color: var(--ink-muted);
}
.badge.wait {
  background: color-mix(in srgb, var(--critical) 12%, transparent);
  border-color: color-mix(in srgb, var(--critical) 32%, transparent);
  color: var(--critical-ink);
}

/* ---------- плитки с цифрами ---------- */

.tiles {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(178px, 1fr));
  gap: 12px;
  margin-bottom: 18px;
}
.tile {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-card);
  padding: 16px 18px;
}
.tile .label {
  font-size: var(--fs-micro);
  font-weight: 600;
  color: var(--ink-faint);
  text-transform: uppercase;
  letter-spacing: .045em;
}
.tile .value {
  display: flex;
  align-items: center;
  gap: 6px;
  font-size: var(--fs-metric);
  line-height: 32px;
  font-weight: 640;
  letter-spacing: -.02em;
  margin-top: 4px;
  font-variant-numeric: tabular-nums;
}
.tile .note {
  font-size: var(--fs-sm);
  color: var(--ink-muted);
  margin-top: 4px;
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
}
/* Сравнение с прошлым месяцем: цифра важнее слов, поэтому она выделена */
.tile .delta { font-weight: 560; }
.tile .delta.up { color: var(--good-ink); }
.tile .delta.down { color: var(--critical-ink); }

/* ---------- ввод за день ---------- */

/* Список ввода. На широком экране — две колонки: семнадцать полей в один
   столбец заставляли крутить страницу, а справа при этом пустовала половина
   окна. Порядок обхода клавишами при этом привычный: слева направо, потом ниже. */
.entry-list { align-content: start; }
@media (min-width: 900px) {
  .entry-list {
    display: grid;
    grid-template-columns: 1fr 1fr;
    column-gap: var(--space-6);
  }
  .entry-list .cat-head { grid-column: 1 / -1; }
}

.entry-row {
  display: grid;
  /* Название слева, поле справа у края своей колонки */
  grid-template-columns: minmax(180px, 1fr) 150px;
  gap: 14px;
  align-items: center;
  padding: 11px 12px;
  border-radius: var(--radius-sm);
}
.entry-row.derived .value { grid-column: 2; }
.entry-row:hover { background: var(--surface-raised); }
.entry-row .name { font-weight: 520; }
.entry-row .sub { font-size: 0.7812rem; color: var(--ink-faint); margin-top: 1px; }
.entry-row input { text-align: right; font-variant-numeric: tabular-nums; }
.entry-row input.saved { border-color: var(--good); box-shadow: 0 0 0 3px color-mix(in srgb, var(--good) 15%, transparent); }
.entry-row input.bad { border-color: var(--critical); box-shadow: 0 0 0 3px color-mix(in srgb, var(--critical) 15%, transparent); }
.entry-row.derived { opacity: .8; }
.entry-row.derived .value {
  text-align: right;
  font-variant-numeric: tabular-nums;
  font-weight: 560;
  padding-right: 12px;
}

.cat-head {
  font-size: 0.7188rem;
  font-weight: 650;
  color: var(--ink-faint);
  text-transform: uppercase;
  letter-spacing: .05em;
  padding: 18px 12px 7px;
}

/* ---------- месяц целиком ---------- */

.grid-table th, .grid-table td { padding: 4px 6px; font-size: 0.8125rem; }
.grid-table th:first-child, .grid-table td:first-child { min-width: 180px; }
.grid-table th.weekend { color: var(--weekend-ink); }
.grid-table input {
  padding: 4px 6px;
  font-size: 0.8125rem;
  min-width: 70px;
  text-align: right;
  font-variant-numeric: tabular-nums;
}
.grid-table input.saved { border-color: var(--good); }
.grid-table input.bad { border-color: var(--critical); }
.grid-table td.num { text-align: right; }

/* ---------- график смен ---------- */

.shift-grid td, .shift-grid th { padding: 4px 6px; text-align: center; font-size: 0.8125rem; }
.shift-grid td:first-child, .shift-grid th:first-child { text-align: left; min-width: 130px; }
/* Все семь дней одной ширины: и прошедшие (только чтение), и редактируемые (QA 04.10) */
.shift-grid { table-layout: fixed; width: 100%; min-width: 680px; }
.shift-grid th:first-child, .shift-grid td:first-child { width: 140px; }
.shift-grid input { padding: 4px 6px; text-align: center; font-size: 0.8125rem; width: 100%; min-width: 0; box-sizing: border-box; }
.shift-grid td.ro { height: 34px; }
.shift-grid th.weekend { color: var(--weekend-ink); }

/* ---------- график ---------- */

/* На всю ширину карточки (правка 30.09): рисунок строится под её ширину */
.chart { width: 100%; height: auto; display: block; }
.legend { display: flex; gap: 18px; font-size: 0.8125rem; color: var(--ink-muted); margin-top: 8px; }
.legend i { display: inline-block; width: 14px; height: 2px; vertical-align: middle; margin-right: 7px; }

/* ---------- вход ---------- */

.login-wrap { min-height: 100vh; display: grid; place-items: center; padding: 20px; }
.login-card { width: 100%; max-width: 360px; box-shadow: var(--shadow-pop); }
.login-card h1 { margin-bottom: 6px; }

/* ---------- всплывающее сообщение ---------- */

.toast {
  position: fixed;
  left: 50%;
  bottom: 28px;
  transform: translateX(-50%);
  display: inline-flex;
  align-items: center;
  gap: 12px;
  max-width: min(520px, calc(100vw - 2 * var(--gutter)));
  cursor: pointer;
  background: var(--ink);
  color: var(--surface);
  padding: 10px 18px;
  border-radius: 999px;
  font-size: 0.875rem;
  font-weight: 500;
  z-index: var(--z-toast);
  box-shadow: var(--shadow-pop);
  animation: toast-in .18s ease-out;
}
.toast .close {
  font-size: 1rem;
  line-height: 1;
  opacity: .6;
}
.toast:hover .close { opacity: 1; }
/* --on-accent: белый на светлой теме и тёмный на тёмной — там красный и зелёный
   светлее, и белые буквы на них читались плохо */
.toast.error { background: var(--critical); color: var(--on-accent); }
.toast.ok { background: var(--good); color: var(--on-accent); }
@keyframes toast-in {
  from { opacity: 0; transform: translate(-50%, 8px); }
  to { opacity: 1; transform: translate(-50%, 0); }
}

/* ---------- узкий экран ---------- */

@media (max-width: 720px) {
  main { padding: 18px 14px 64px; }
  .table-wrap { margin: 0 -14px; }
  th:first-child, td:first-child { padding-left: 14px; }
  th:last-child, td:last-child { padding-right: 14px; }
  .sticky-label { left: 14px; padding-left: 14px; }
  .card { padding: 14px; }
  .entry-row { grid-template-columns: 1fr 112px; padding: 10px 8px; gap: 10px; }
  .entry-row.derived .value { grid-column: auto; }
  h1 { font-size: 1.25rem; }
  .tile .value { font-size: 1.5rem; }
}

/* ---------- печать ---------- */

@media print {
  header.top, .msg, button, select, textarea, nav.tabs { display: none !important; }
  .card { border: none; box-shadow: none; padding: 0; margin-bottom: 12px; }
  body { background: #fff; color: #000; }
  table { font-size: 0.75rem; }
}

/* --- экран настроек --- */
input.saved, select.saved {
  border-color: var(--good);
  box-shadow: 0 0 0 3px color-mix(in srgb, var(--good) 15%, transparent);
}
input.bad {
  border-color: var(--critical);
  box-shadow: 0 0 0 3px color-mix(in srgb, var(--critical) 15%, transparent);
}

button.danger {
  border-color: var(--critical);
  color: var(--critical-ink);
  font-weight: 600;
}

pre.log {
  margin: 0;
  padding: 12px 14px;
  max-height: 340px;
  overflow: auto;
  background: var(--surface-raised);
  border: 1px solid var(--border);
  border-radius: 8px;
  font-size: 0.75rem;
  line-height: 1.5;
  white-space: pre-wrap;
  word-break: break-word;
}

tr.muted td { opacity: 0.55; }
/* Кнопки действий («Вернуть», «Удалить») в приглушённой строке остаются яркими:
   иначе «Вернуть» выглядит заблокированной, хотя нажимается */
tr.muted td:last-child { opacity: 1; }

/* Второй закреплённый столбец: сдвиг слева проставляется из JS */
.sticky-col2 {
  position: sticky;
  z-index: 1;
  /* Тот же приём, что у первого столбца: сплошная подложка плюс цвет строки,
     иначе сквозь закреплённую ячейку просвечивают уезжающие под неё дни */
  background: var(--surface);
  background-image: linear-gradient(var(--row-bg), var(--row-bg));
  box-shadow: 1px 0 0 0 var(--border);
}
thead .sticky-col2 { z-index: 4; background: var(--surface); background-image: none; }
tr.total .sticky-col2 { background: var(--surface-raised); }
tr.group td { position: relative; z-index: 0; }

/* --- длинные и широкие таблицы --- */
/* Прокрутка живёт внутри обёртки, поэтому шапка может липнуть к её верху.
   Без своей прокрутки sticky прижималась бы к началу таблицы и налезала на строки. */
.table-wrap.scroll-y {
  max-height: min(70vh, 720px);
  overflow: auto;
  /* Докрутили таблицу до конца — дальше листается страница (правка 30.09) */
  overscroll-behavior: auto;
}
.table-wrap.scroll-y thead th {
  position: sticky;
  z-index: 3;
  background: var(--surface);
}
.table-wrap.scroll-y thead th.sticky-col {
  z-index: 5;
}
/* Без этой строки соседняя ячейка шапки перекрывает «Итого»:
   у правила выше приоритет выше, чем у общего thead .sticky-col2 */
.table-wrap.scroll-y thead th.sticky-col2 {
  z-index: 4;
}
.table-wrap.scroll-y tbody td.sticky-col {
  z-index: 2;
}
.table-wrap.scroll-y tbody tr.total td {
  position: sticky;
  bottom: 0;
  background: var(--surface-raised);
  z-index: 2;
  box-shadow: 0 -1px 0 0 var(--border);
}
/* Закреплённые столбцы — поверх соседних ячеек и в шапке, и в «Итого»
   (ревью 30.09: цифры наезжали на «Итого», подписи — на «Прогноз GI») */
.table-wrap.scroll-y tbody tr.total td.sticky-col,
.table-wrap.scroll-y tbody tr.total td.sticky-right { z-index: 3; }
.table-wrap.scroll-y thead th.sticky-right { z-index: 6; }
.table-wrap.scroll-y tbody td.sticky-right { z-index: 2; }
.table-wrap:focus-visible {
  outline: 2px solid var(--focus);
  outline-offset: 2px;
  border-radius: var(--radius-sm);
}

.scroll-note {
  font-size: 0.75rem;
  color: var(--ink-faint);
  padding: 0 0 7px;
  user-select: none;
}

/* --- ввод за день: полоса заполнения и подсказка по клавишам --- */
.progress {
  display: inline-block;
  width: 120px;
  height: 6px;
  border-radius: 3px;
  background: var(--grid);
  overflow: hidden;
  vertical-align: middle;
}
.progress i {
  display: block;
  height: 100%;
  width: 0;
  border-radius: 3px;
  background: var(--accent);
  transition: width .18s ease;
}

/* Заполненная строка помечается слева — видно, что осталось */
.entry-row { border-left: 2px solid transparent; }
.entry-row.done { border-left-color: var(--good); }
.entry-row.done .name { color: var(--ink-muted); }

.hint-keys { white-space: nowrap; }
@media (max-width: 720px) {
  .hint-keys { display: none; }
}


/* ---------- переключатель разделов ---------- */
/* Активный пункт выделяется белой плашкой, а не цветом: это навигация,
   а не действие, и синим он спорил с настоящими кнопками */
.seg {
  display: inline-flex;
  gap: 4px;
  padding: 4px;
  background: var(--surface-raised);
  border: 1px solid var(--border);
  border-radius: 10px;
  flex-wrap: wrap;
}
.seg button {
  background: transparent;
  border-color: transparent;
  color: var(--ink-muted);
  box-shadow: none;
}
.seg button:hover:not(.active) { background: var(--hover); border-color: transparent; }
.seg button.active {
  background: var(--surface);
  border-color: var(--border);
  color: var(--ink);
  font-weight: 560;
  box-shadow: var(--shadow-card);
}

/* ---------- форма в строку ---------- */
/* Поля с подписями и кнопка: кнопка выравнивается по нижнему краю полей */
.form-row {
  display: flex;
  gap: 14px;
  align-items: flex-end;
  flex-wrap: wrap;
}
.form-row > div { display: flex; flex-direction: column; }
/* Группа кнопок внутри формы остаётся строкой: в колонку её складывать нельзя */
.form-row > .row { flex-direction: row; align-items: center; }
.form-row label { margin-bottom: 5px; }

/* Заголовок карточки и пояснение под ним стоят плотнее */
.card > strong + p.muted { margin-top: 2px; }
.card-head { margin-bottom: 12px; }
.card-head .sub { color: var(--ink-faint); font-size: var(--fs-sm); margin-top: 2px; }


/* ---------- значки ---------- */
.ic { flex: none; display: block; }

/* Пункт меню со значком: значок приглушён, пока раздел не выбран */
nav.tabs a {
  display: inline-flex;
  align-items: center;
  gap: 7px;
}
nav.tabs a .ic { opacity: .65; transition: opacity .12s, transform .12s; }
nav.tabs a:hover .ic { opacity: 1; }
nav.tabs a.active .ic { opacity: 1; }

button .ic { margin-right: -2px; }
button { display: inline-flex; align-items: center; gap: 7px; justify-content: center; }

/* Статус со значком: цвет дублируется формой, а не заменяется ею */
.badge { gap: 5px; }
.badge .ic { width: 14px; height: 14px; }

/* Плитка: значок в углу, как в календаре-референсе — цветной чип */
.tile { position: relative; }
.tile .chip {
  position: absolute;
  top: 14px;
  right: 14px;
  width: 30px;
  height: 30px;
  display: grid;
  place-items: center;
  border-radius: var(--radius-sm);
  background: color-mix(in srgb, var(--chip, var(--accent)) 14%, transparent);
  color: var(--chip, var(--accent));
}
.tile .value { padding-right: 38px; }

/* Категория показателей: цветная метка у группы колонок и строк.
   Цвет только в метке, ячейки остаются чистыми — иначе таблица
   на двадцать колонок превращается в витраж */
.cat-chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.cat-chip::before {
  content: '';
  width: 7px;
  height: 7px;
  border-radius: 2px;
  background: var(--cat, var(--accent));
  flex: none;
}
th.cat-th .cat-chip { justify-content: center; }
tr.group td .cat-chip::before { width: 8px; height: 8px; }

/* Живой отклик: строки и карточки отзываются сразу, но без анимаций напоказ */
tbody tr:hover td { transition: background .1s; }
.tile { transition: border-color .12s, transform .12s; }
.tile:hover { border-color: var(--border-strong); }
/* ---------- права и внимание куратора ---------- */

/* Число у пункта меню: заявки на пароль, смены от сотрудников */
.nav-badge {
  display: inline-grid;
  place-items: center;
  min-width: 18px;
  height: 18px;
  padding: 0 5px;
  margin-left: 6px;
  border-radius: var(--radius-pill);
  background: var(--critical);
  /* Белый на светлом красном тёмной темы давал 3,3 : 1 — тёмный текст даёт 5,6 */
  color: var(--on-accent);
  font-size: 0.6875rem;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
  line-height: 1;
}

/* Смену поставил сотрудник — жёлтый уголок, пока куратор не посмотрит */
.shift-grid td.review { position: relative; }
.shift-grid td.review::after {
  content: '';
  position: absolute;
  top: 3px;
  right: 3px;
  border: 5px solid transparent;
  border-top-color: var(--warning);
  border-right-color: var(--warning);
  border-top-right-radius: 3px;
  pointer-events: none;
}
.review-card { border-left: 3px solid var(--warning); }
.review-list { display: grid; gap: 4px; font-size: var(--fs-sm); }
.review-row .by { font-weight: 600; }

/* Заявка «забыл пароль» в списке людей */
.form-table tr.reset-requested td { background: color-mix(in srgb, var(--warning) 9%, var(--row-bg, transparent)); }
.reset-card { border-left: 3px solid var(--warning); }

/* Поле пароля с кнопкой «показать» */
.password-field { position: relative; display: block; }
.password-field input { padding-right: 44px; }
.password-field .eye {
  position: absolute;
  top: 50%;
  right: 4px;
  transform: translateY(-50%);
  width: 34px;
  height: 34px;
  padding: 0;
  display: grid;
  place-items: center;
  border: 0;
  background: transparent;
  color: var(--ink-faint);
}
.password-field .eye:hover:not(:disabled) { background: var(--hover); color: var(--ink); }
.password-field .eye[aria-pressed="true"] { color: var(--accent); }

.link-button {
  border: 0;
  background: none;
  padding: 0;
  color: var(--link, var(--accent));
  font-size: var(--fs-sm);
  text-decoration: underline;
  text-underline-offset: 2px;
  cursor: pointer;
}
.link-button:hover:not(:disabled) { background: none; color: var(--link-hover, var(--accent-hover)); }

/* ---------- уведомление о сохранении ---------- */

/* Строка внизу экрана: «Сохраняю…» → «Внесено · GI · 5» или «Не сохранено».
   Цвет слева говорит состояние, текст — что именно записалось */
.save-status {
  position: fixed;
  left: 50%;
  bottom: 20px;
  z-index: var(--z-status);
  display: flex;
  align-items: center;
  gap: 10px;
  max-width: min(640px, calc(100vw - 2 * var(--gutter)));
  min-height: 44px;
  padding: 7px 8px 7px 14px;
  background: var(--surface);
  color: var(--ink);
  border: 1px solid var(--border-strong);
  border-left: 3px solid var(--st, var(--ink-faint));
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-pop);
  font-size: var(--fs-sm);
  opacity: 0;
  transform: translate(-50%, 12px);
  pointer-events: none;
  transition: opacity .18s ease-out, transform .18s ease-out;
}
.save-status.visible { opacity: 1; transform: translate(-50%, 0); pointer-events: auto; }
.save-status .mark { color: var(--st); display: grid; place-items: center; flex: none; }
.save-status .text { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.save-status.question .text, .save-status.fail .text { white-space: normal; }
.save-status .muted { color: var(--ink-muted); }
.save-status b { font-weight: 600; }
.save-status .time { color: var(--ink-faint); font-variant-numeric: tabular-nums; flex: none; padding-right: 6px; }
.save-status .count {
  flex: none;
  padding: 1px 7px;
  border-radius: var(--radius-pill);
  background: color-mix(in srgb, var(--good) 14%, transparent);
  color: var(--good-ink);
  font-weight: 600;
  font-variant-numeric: tabular-nums;
}
.save-status .close { width: 28px; height: 28px; padding: 0; font-size: 1.125rem; line-height: 1; flex: none; }
.save-status button.small { flex: none; }
.save-status.saving { --st: var(--ink-faint); }
.save-status.ok { --st: var(--good); }
.save-status.question { --st: var(--warning); }
.save-status.fail { --st: var(--critical); }
.save-status .spinner {
  width: 14px;
  height: 14px;
  border: 2px solid var(--border-strong);
  border-top-color: var(--accent);
  border-radius: 50%;
  animation: spin .8s linear infinite;
}
/* Обычные всплывающие сообщения поднимаются над строкой, а не прячутся под ней */
body.has-save-status .toast { bottom: 84px; }
@media (max-width: 600px) {
  .save-status { left: 16px; right: 16px; max-width: none; transform: translateY(12px); }
  .save-status .time { display: none; }
  .save-status.visible { transform: none; }
}
@media (prefers-reduced-motion: reduce) {
  .save-status .spinner { animation: none; }
}

/* ---------- полировка ---------- */

/* Флажки и переключатели не подчиняются общей высоте поля */
input[type="checkbox"], input[type="radio"] { min-height: 0; width: auto; }

/* Поля внутри таблиц живут по своей высоте. Общая высота 38 нужна строке
   фильтров и формам; в сетке месяца и графике смен она раздувала каждую
   строку с 39 до 47 пикселей, и таблица разъезжалась */
td input, td select { min-height: 0; }

/* Таблицы-формы (люди, точки, показатели) — плотнее: строка была 61 пиксель
   при поле 40, между строками гулял воздух */
.form-table td { padding-top: 6px; padding-bottom: 6px; }
.form-table td input, .form-table td select { padding: 6px 10px; }

/* Планы — та же плотность: сетка 12 × 17 полей */
.plan-table td { padding-top: 6px; padding-bottom: 6px; }
.plan-table td input { padding: 6px 10px; text-align: right; font-variant-numeric: tabular-nums; }

/* Таблица-справочник: колонки по содержимому, весь остаток ширины — последней
   колонке с кнопками. Иначе браузер раздаёт лишнюю ширину всем колонкам поровну,
   поля плавают посреди пустоты, а «В архив» уезжает к правому краю */
.form-table.compact th:last-child { width: 100%; }
.form-table.compact td:last-child { text-align: left; }

/* Переключатель разделов на экране настроек не должен прилипать к карточке */
.seg { margin-bottom: var(--space-4); }






/* Телефон. Шапка занимала треть экрана: название, строка с именем и меню
   на трёх этажах. Теперь название и кнопки в одну строку, меню — второй,
   и имя пользователя прячется: на своём телефоне его и так знаешь */
@media (max-width: 600px) {
  .top-inner { gap: 8px; min-height: 48px; }
  .brand { font-size: 0.875rem; }
  .who > .name { display: none; }
  .who .label { display: none; }
  nav.tabs { padding-bottom: 6px; }
  nav.tabs a { min-height: 32px; padding: 0 10px; font-size: 0.8438rem; }

  /* Плитки по две в ряд: четыре карточки друг под другом — это экран прокрутки
     до самой таблицы */
  .tiles { grid-template-columns: 1fr 1fr; gap: 8px; }
  .tile { padding: 12px 13px; }
  .tile .chip { display: none; }
  .tile .value { font-size: 1.3125rem; padding-right: 0; }
  .tile .label { font-size: 0.6562rem; }
  .tile .note { font-size: 0.75rem; }

  /* Фильтры: дата растягивается, кнопки шага рядом */
  .page-head .filters { gap: 8px; }
  .page-head .filters .field { flex: 1 1 140px; }
  .page-head .filters select,
  .page-head .filters input { width: 100%; }
}

@media (prefers-reduced-motion: reduce) {
  * { transition: none !important; }
}

/* Поле, которое сервер попросил подтвердить: не ошибка, а вопрос */
input.check {
  border-color: var(--warning);
  box-shadow: 0 0 0 3px color-mix(in srgb, var(--warning) 22%, transparent);
}

/* Пропущенные дни: строка-напоминание со ссылками на эти дни */
.gaps {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  padding: 11px 14px;
  margin-bottom: 16px;
  border-radius: var(--radius-sm);
  background: color-mix(in srgb, var(--warning) 10%, transparent);
  border: 1px solid color-mix(in srgb, var(--warning) 30%, transparent);
  font-size: var(--fs-sm);
  color: var(--ink);
}
.gaps .ic { color: var(--warning); }
.gaps button {
  padding: 2px 9px;
  font-size: var(--fs-sm);
  font-weight: 560;
  background: var(--surface);
  border-color: color-mix(in srgb, var(--warning) 45%, transparent);
}

/* ---------- движение ---------- */
/* Правило одно: двигаются прозрачность и сдвиг. Всё остальное —
   ширина, высота, положение в потоке — дёргает таблицы на двадцать колонок */

@keyframes spin { to { transform: rotate(360deg); } }
@keyframes card-in { from { opacity: 0; transform: translateY(4px); } to { opacity: 1; transform: none; } }
@keyframes sk-pulse { 0%, 100% { opacity: .55; } 50% { opacity: .9; } }

/* Кнопка во время запроса и сразу после успеха */
button.busy .ic { animation: spin .9s linear infinite; }
button.busy { cursor: progress; }
/* Пока идёт запрос и пока горит «Готово», кнопка недоступна, но не бледнеет:
   мигание прозрачности и было той самой «дёрганностью» при нажатии */
button.busy:disabled, button.ok:disabled { opacity: 1; }
button.busy .ic { transform-origin: 50% 50%; }
button.ok:not(.primary) { border-color: var(--good); color: var(--good-ink); }
button.primary.ok { background: var(--good); border-color: var(--good); }

/* Карточки появляются мягко — но только при первой отрисовке экрана */
main .card { animation: card-in .22s ease-out both; }

/* Плавный переход между разделами там, где браузер это умеет */
@view-transition { navigation: auto; }
::view-transition-old(root) { animation: none; opacity: 1; }
::view-transition-new(root) { animation: card-in .18s ease-out; }

/* Скелет: показываем форму будущей таблицы, чтобы страница не прыгала */
.skeleton { display: grid; gap: 10px; padding: 4px 0; }
.sk-row { display: grid; grid-template-columns: 1.4fr repeat(4, 1fr); gap: 12px; }
.sk-row span {
  height: 12px;
  border-radius: var(--radius-pill);
  background: var(--surface-raised);
  animation: sk-pulse 1.2s ease-in-out infinite;
}
.sk-row.sk-head span { height: 9px; background: var(--border); }
.sk-tile { display: grid; gap: 10px; }
.sk-line { height: 12px; border-radius: var(--radius-pill); background: var(--surface-raised);
           animation: sk-pulse 1.2s ease-in-out infinite; }
.sk-line.short { width: 45%; height: 9px; }
.sk-line.big { height: 26px; width: 70%; }

@media (prefers-reduced-motion: reduce) {
  main .card, .sk-row span, .sk-line, button.busy .ic { animation: none !important; }
  ::view-transition-old(root), ::view-transition-new(root) { animation: none !important; }
}


/* ---------- подмены: метки в строке и всплывающий выбор ---------- */
.subs-cell { display: flex; align-items: center; gap: 4px; flex-wrap: nowrap; }
.subs-cell .tag {
  display: inline-flex;
  align-items: center;
  height: 22px;
  padding: 0 7px;
  border-radius: var(--radius-pill);
  background: var(--accent-soft);
  color: var(--link, var(--accent));
  font-size: 0.75rem;
  font-weight: 560;
  white-space: nowrap;
}
.subs-cell .more { color: var(--ink-muted); font-size: 0.75rem; white-space: nowrap; }
.subs-cell .none { color: var(--ink-faint); }
.subs-cell button.small { padding: 3px 9px; margin-left: 4px; }

.popover {
  position: fixed;
  z-index: var(--z-popover);
  width: 320px;
  max-width: calc(100vw - 24px);
  padding: 14px;
  background: var(--surface);
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-md);
  box-shadow: var(--shadow-pop);
}
.popover .title { font-weight: 600; margin-bottom: 2px; }
.popover .hint { color: var(--ink-muted); font-size: var(--fs-sm); margin-bottom: 10px; }
.store-picker { display: grid; grid-template-columns: repeat(4, 1fr); gap: 6px; }
.store-picker button {
  min-height: 34px;
  padding: 0 4px;
  font-size: 0.8125rem;
  font-weight: 500;
  font-variant-numeric: tabular-nums;
  background: var(--surface);
  border: 1px solid var(--border-strong);
  color: var(--ink);
}
.store-picker button[aria-pressed="true"] {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--on-accent);
}
.store-picker button:disabled {
  background: var(--surface-raised);
  border-style: dashed;
  color: var(--ink-faint);
  opacity: 1;
}
.popover .actions { display: flex; gap: 8px; justify-content: flex-end; margin-top: 12px; }
.popover .actions .count { margin-right: auto; align-self: center; color: var(--ink-muted); font-size: var(--fs-sm); white-space: nowrap; }

/* ---------- люди: убрать и убранные ---------- */
button.danger-ghost { color: var(--critical-ink); }
button.danger-ghost:hover:not(:disabled) { background: color-mix(in srgb, var(--critical) 10%, transparent); color: var(--critical-ink); }






/* ---------- график: цвет по типу смены ---------- */
/* Рабочая — зелёная, выходной — серый, отпуск — жёлтый, больничный — красный,
   выход на другую точку — синий. Цвет дублируется буквой в ячейке и легендой */
.shift-grid td.k-work     { --k-bg: color-mix(in srgb, var(--good) 14%, var(--surface));     --k-ink: var(--good-ink); }
.shift-grid td.k-off      { --k-bg: color-mix(in srgb, var(--off) 14%, var(--surface));      --k-ink: var(--off-ink); }
.shift-grid td.k-vacation { --k-bg: color-mix(in srgb, var(--warning) 20%, var(--surface));  --k-ink: var(--warning-ink); }
.shift-grid td.k-sick     { --k-bg: color-mix(in srgb, var(--critical) 14%, var(--surface)); --k-ink: var(--critical-ink); }
.shift-grid td.k-away     { --k-bg: var(--accent-soft);                                        --k-ink: var(--accent); }
/* Плитка смены: и поле ввода, и подпись «только просмотр» выглядят одинаково.
   Рабочие смены насыщенные, выходные приглушены — взгляд цепляется за выходы на работу */
.shift-grid td { padding: 3px; }
.shift-grid input, .shift-grid .cell {
  display: flex; align-items: center; justify-content: center;
  box-sizing: border-box;
  width: 100%; min-width: 0; height: 34px;
  padding: 0 6px;
  border: 1px solid transparent;
  border-radius: 8px;
  background: var(--k-bg, transparent);
  color: var(--k-ink, var(--ink-faint));
  font-size: 13px; font-weight: 600;
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}
.shift-grid td[class*="k-"] input, .shift-grid td[class*="k-"] .cell {
  border-color: color-mix(in srgb, var(--k-ink) 22%, transparent);
}
/* пустая ячейка: еле заметный пунктир только там, где можно писать */
.shift-grid input:placeholder-shown { border: 1px dashed var(--border); background: transparent; }
.shift-grid input:hover { border-color: var(--border-strong); }
.shift-grid input:focus { background: var(--surface); color: var(--ink); border-color: var(--accent); outline: none; box-shadow: 0 0 0 2px color-mix(in srgb, var(--accent) 25%, transparent); }
.shift-grid .cell { font-weight: 500; }
.shift-grid td.k-work .cell, .shift-grid td.k-work input { font-weight: 650; }
.shift-grid td.k-off { --k-bg: color-mix(in srgb, var(--off) 8%, transparent); --k-ink: color-mix(in srgb, var(--off-ink) 75%, var(--ink-faint)); }
.shift-grid td.k-off input, .shift-grid td.k-off .cell { border-color: transparent; font-weight: 500; }

.shift-legend { display: flex; flex-wrap: wrap; gap: 6px 16px; margin: 0 0 12px; font-size: var(--fs-sm); color: var(--ink-muted); }
.shift-legend span { display: inline-flex; align-items: center; gap: 6px; }
.shift-legend i {
  width: 14px; height: 14px; border-radius: 4px;
  background: var(--k-bg);
  border: 1px solid color-mix(in srgb, var(--k-ink) 35%, transparent);
}
.shift-legend .k-work     { --k-bg: color-mix(in srgb, var(--good) 14%, var(--surface));     --k-ink: var(--good-ink); }
.shift-legend .k-off      { --k-bg: color-mix(in srgb, var(--off) 14%, var(--surface));      --k-ink: var(--off-ink); }
.shift-legend .k-vacation { --k-bg: color-mix(in srgb, var(--warning) 20%, var(--surface));  --k-ink: var(--warning-ink); }
.shift-legend .k-sick     { --k-bg: color-mix(in srgb, var(--critical) 14%, var(--surface)); --k-ink: var(--critical-ink); }
.shift-legend .k-away     { --k-bg: var(--accent-soft);                                        --k-ink: var(--accent); }

/* ---------- выбор точки: кнопка и плитки ---------- */
.store-button {
  min-height: var(--control-h);
  min-width: 92px;
  padding: 0 10px 0 12px;
  justify-content: space-between;
  gap: 8px;
  background: var(--surface);
  border: 1px solid var(--border-strong);
  color: var(--ink);
  font-weight: 560;
  font-variant-numeric: tabular-nums;
}
.store-button .ic { color: var(--ink-muted); }
.store-button[aria-expanded="true"], .store-button:focus-visible { border-color: var(--accent); }
td .store-button { min-height: 32px; min-width: 84px; padding: 0 8px 0 10px; font-weight: 500; }
.store-fixed {
  display: inline-flex; align-items: center;
  min-height: var(--control-h); padding: 0 12px;
  border-radius: var(--radius-sm);
  background: var(--surface-raised);
  font-weight: 560;
}
.store-popover { width: 300px; padding: 10px; }
.store-picker button.none { color: var(--ink-muted); }

/* ---------- поле даты: набор цифрами + календарь ---------- */
.date-field {
  position: relative;
  display: inline-flex;
  align-items: center;
  min-height: var(--control-h);
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-sm);
  background: var(--surface);
  padding-right: 2px;
  transition: border-color .12s, box-shadow .12s;
}
.date-field:focus-within { border-color: var(--accent); box-shadow: 0 0 0 3px var(--accent-soft); }
.date-field.bad { border-color: var(--critical); box-shadow: 0 0 0 3px color-mix(in srgb, var(--critical) 15%, transparent); }
.date-field input.date-text {
  width: 104px;
  height: 34px;
  min-height: 0;
  border: 0;
  background: transparent;
  box-shadow: none !important;
  padding: 0 4px 0 12px;
  font-variant-numeric: tabular-nums;
}
.date-field .date-weekday { color: var(--ink-muted); font-size: var(--fs-sm); padding-right: 4px; min-width: 18px; }
.date-field button.date-calendar {
  width: 32px; height: 32px; padding: 0;
  display: inline-grid; place-items: center;
  border: 0; background: transparent; color: var(--ink-muted);
}
.date-field button.date-calendar:hover { background: var(--surface-raised); color: var(--ink); }

/* ---------- план выполнен ---------- */
/* Сплошная зелёная плашка с галочкой: отличается от «идёт хорошо» (светлая
   зелёная подложка) с первого взгляда, а не только числом больше 100 */
.pct-pill.closed {
  display: inline-flex; align-items: center; gap: 4px;
  background: var(--good-ink);
  color: var(--surface);
  font-weight: 650;
}
.pct-pill.closed .ic { width: 12px; height: 12px; }
tr.closed > td { background: color-mix(in srgb, var(--good) 7%, var(--row-bg, var(--surface))); }
tr.closed > td:first-child { box-shadow: inset 3px 0 0 var(--good-ink); }
.closed-mark { display: inline-flex; align-items: center; gap: 4px; color: var(--good-ink); font-weight: 600; font-size: var(--fs-sm); }

/* Пароль: метка и кнопки в столбик по сетке — «Сбросить» и «Убрать»
   стоят ровно друг под другом, какой бы длины ни была метка */
.pw-cell { display: grid; grid-template-columns: 158px auto auto; align-items: center; gap: 6px; }
.pw-cell > .badge { justify-self: start; }

/* ---------- свой календарь ---------- */
.calendar-popover { width: 296px; padding: 12px; }
.cal-head { display: flex; align-items: center; justify-content: space-between; gap: 4px; margin-bottom: 8px; }
.cal-title { font-weight: 600; flex: 1; text-align: center; }
button.cal-nav { width: 32px; height: 32px; padding: 0; font-size: 1.25rem; line-height: 1; background: transparent; border: 1px solid var(--border); }
button.cal-nav:hover:not(:disabled) { background: var(--surface-raised); }
.cal-week, .cal-grid { display: grid; grid-template-columns: repeat(7, 1fr); gap: 2px; }
.cal-week span { text-align: center; font-size: 0.6875rem; font-weight: 600; color: var(--ink-muted); padding: 4px 0; text-transform: uppercase; }
.cal-week span.weekend { color: var(--weekend-ink); }
button.cal-day {
  height: 36px; padding: 0;
  border: 1px solid transparent; background: transparent;
  color: var(--ink); font-weight: 500; font-variant-numeric: tabular-nums;
  border-radius: var(--radius-sm);
}
button.cal-day:hover:not(:disabled) { background: var(--surface-raised); }
button.cal-day.weekend { color: var(--weekend-ink); }
button.cal-day.other { color: var(--ink-faint); }
button.cal-day.today { border-color: var(--accent); font-weight: 650; }
button.cal-day.selected, button.cal-day.selected:hover { background: var(--accent); border-color: var(--accent); color: var(--on-accent); font-weight: 650; }
button.cal-day:disabled { color: var(--ink-faint); opacity: .45; background: transparent; }
button.cal-day:focus-visible { outline: 2px solid var(--accent); outline-offset: 1px; }
.cal-foot { display: flex; justify-content: flex-end; margin-top: 8px; }
@media (pointer: coarse) {
  button.cal-day { height: 40px; }
  .date-field input.date-text { cursor: pointer; }
}

/* ---------- памятка ---------- */
.brand-wrap { display: flex; align-items: center; gap: 6px; }

.help-dialog {
  width: min(640px, calc(100vw - 24px));
  max-height: calc(100vh - 48px);
  padding: 0;
  border: 1px solid var(--border-strong);
  border-radius: var(--radius-md);
  background: var(--surface);
  color: var(--ink);
  box-shadow: var(--shadow-pop);
  overflow: hidden;
}
.help-dialog[open] { display: flex; flex-direction: column; }
.help-dialog::backdrop { background: rgba(10, 16, 28, .45); }
.help-head { display: flex; align-items: center; justify-content: space-between; padding: 14px 16px 10px 20px; border-bottom: 1px solid var(--border); }
.help-head h2 { margin: 0; font-size: 1.125rem; }
.help-body { padding: 16px 20px 8px; overflow-y: auto; }
.help-foot { padding: 12px 20px 16px; border-top: 1px solid var(--border); display: flex; justify-content: flex-end; }
.help-step { margin-bottom: 16px; }
.help-step h3 { font-size: 0.9375rem; font-weight: 620; margin: 0 0 6px; }
.help-step p, .help-step li { font-size: 0.875rem; line-height: 1.5; color: var(--ink); margin: 0 0 4px; }
.help-step ul { margin: 0 0 4px; padding-left: 18px; }
.help-body kbd {
  display: inline-block; padding: 0 5px; min-width: 18px; text-align: center;
  border: 1px solid var(--border-strong); border-bottom-width: 2px; border-radius: 4px;
  background: var(--surface-raised); font: 600 12.5px/1.5 inherit; font-variant-numeric: tabular-nums;
}



.help-note { font-size: 0.8125rem; color: var(--ink-muted); margin: 8px 0 4px; }

@media (max-width: 600px) {
  .help-dialog { width: 100vw; max-width: 100vw; max-height: 100dvh; height: 100dvh; border-radius: 0; margin: 0; }
  .help-body { padding: 14px 16px 8px; }
}
@media (max-width: 600px) {

  }

/* ---------- телефон: пальцы, клавиатура, вырезы экрана ---------- */

/* iPhone приближает страницу, если в поле шрифт меньше 16px, и обратно
   сам не отдаляет — после ввода числа экран оставался увеличенным */
@media (pointer: coarse) {
  input, select, textarea { font-size: 1rem; }

  /* Кнопки не меньше 40 точек: в маленькие попадали соседние */
  button, .btn, nav.tabs a { min-height: 40px; }
  button.icon { width: 40px; height: 40px; min-width: 40px; }
  .page-head .filters input, .page-head .filters select, button.store-button { min-height: 40px; }
  /* Дата в рамке 40 точек, как соседние поля; шрифт 16px шире — поле тоже */
  .date-field input.date-text { width: 120px; height: 38px; min-height: 38px; }
  .date-field button.date-calendar { width: 38px; height: 38px; min-width: 38px; }
  .gaps button.small { min-width: 40px; }
  .save-status .close { width: 40px; height: 40px; }
}

/* Шапка на телефоне: название и кнопки справа в одну строку, меню — второй.
   Роль («куратор») не влезала и уводила кнопки на отдельную строку —
   шапка занимала 123 точки из 660 */
@media (max-width: 600px) {
  .who .role-tag { display: none; }
  .who { gap: 4px; }
  .top-inner { row-gap: 4px; }
}

/* Нижняя полоса iPhone: строка сохранения и сообщения не должны под неё уходить */
.save-status { bottom: calc(20px + env(safe-area-inset-bottom, 0px)); }
.toast { bottom: calc(28px + env(safe-area-inset-bottom, 0px)); }
body.has-save-status .toast { bottom: calc(84px + env(safe-area-inset-bottom, 0px)); }
main { padding-bottom: calc(72px + env(safe-area-inset-bottom, 0px)); }

/* ---------- старые браузеры без color-mix ---------- */
/* color-mix есть в Chrome/Android WebView с 111 и Safari с 16.2. На более
   старом телефоне правило с ним браузер просто пропускает, и плашки процентов,
   ячейки графика и сообщения остаются без заливки. Цвет текста живёт в своих
   токенах и не страдает, а заливку здесь заменяем цветной полосой слева */
@supports not (color: color-mix(in srgb, red 50%, blue)) {
  .pct-pill, .pct-pill[data-bar] {
    background: var(--surface-raised);
    box-shadow: inset 3px 0 0 var(--lv, var(--border-strong));
  }
  .pct-pill.closed { background: var(--good-ink); box-shadow: none; }
  .shift-grid td[class*="k-"], .shift-legend [class*="k-"] { --k-bg: var(--surface-raised); }
  .shift-grid td[class*="k-"] input, .shift-grid td[class*="k-"] .cell {
    border-color: var(--k-ink);
    box-shadow: inset 3px 0 0 var(--k-ink);
  }
  .msg.error { background: var(--surface-raised); border-color: var(--critical); }
  .msg.ok { background: var(--surface-raised); border-color: var(--good); }
  nav.tabs a.active { border-color: var(--accent); }
  .entry-row input.bad, .date-field.bad { box-shadow: none; border-width: 2px; }
  tr.closed > td { box-shadow: inset 0 0 0 9999px rgba(12, 138, 62, .07); }
}

/* ---------- ссылки-кнопки ---------- */
/* Переход на другой экран — это ссылка (открывается в новой вкладке,
   видна в адресе), но выглядит как кнопка */
a.btn { display: inline-flex; align-items: center; gap: 8px; text-decoration: none; color: var(--ink); }
a.btn:hover { color: var(--ink); background: var(--hover); border-color: var(--ink-faint); }
a.btn.primary { background: var(--accent); border-color: var(--accent); color: var(--on-accent); font-weight: 560; }
a.btn.primary:hover { background: var(--accent-hover); border-color: var(--accent-hover); color: var(--on-accent); }
a.btn:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }

/* Название слева вверху — ссылка на главную */
a.brand { color: var(--ink); text-decoration: none; }
a.brand:hover { color: var(--link, var(--accent)); }

/* ---------- 404 ---------- */
/* На весь экран, без шапки. Две колонки по вертикальному центру экрана:
   слева «404.», надпись и кнопка — по левому краю, справа рисунок —
   окно браузера с «уставшим» лицом (образцы из правок 27.09) */
.nf-screen {
  min-height: 100vh;
  min-height: 100dvh;
  display: flex;
  align-items: center;
  padding: 32px var(--gutter);
  background: var(--page);
  overflow: hidden;
}
.nf-layout {
  width: 100%;
  max-width: 1200px;
  margin: 0 auto;
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  align-items: center;
  gap: 32px;
}
.nf-inner { display: flex; flex-direction: column; align-items: flex-start; text-align: left; }
.nf-code {
  font-size: clamp(96px, 13vw, 180px);
  line-height: .85;
  font-weight: 800;
  letter-spacing: -.06em;
  font-variant-numeric: tabular-nums;
  color: var(--ink);
  margin-left: -.04em;   /* глаз видит левый край цифры, а не её поле */
}
.nf-title { font-size: clamp(28px, 3.4vw, 44px); line-height: 1.15; font-weight: 700; letter-spacing: -.03em; margin: 22px 0 0; }
.nf-title mark {
  background: var(--accent-soft);
  color: var(--link, var(--accent));
  padding: 0 10px;
  border-radius: var(--radius-sm);
  -webkit-box-decoration-break: clone;
  box-decoration-break: clone;
}
.nf-lead { max-width: 440px; color: var(--ink-muted); font-size: var(--fs-body); line-height: 1.5; margin: 14px 0 26px; }
.nf-home { padding: 11px 22px; }
.nf-art-wrap { display: flex; justify-content: center; pointer-events: none; }
.nf-art { width: 100%; max-width: 420px; height: auto; display: block; }
@media (max-width: 800px) {
  .nf-layout { grid-template-columns: 1fr; gap: 8px; }
  .nf-art-wrap { order: -1; justify-content: flex-start; }
  .nf-art { max-width: 180px; }
}
@media (max-width: 800px) and (max-height: 700px) {
  .nf-art-wrap { display: none; }
}

/* ---------- главная: дашборд ---------- */
/* Раскладка по эскизу из правки 30.09 — сетка в три колонки:
   ряд 1 — главная карточка GI и четыре плитки на две оставшиеся колонки;
   ряд 2 — «GI по дням» на две колонки и справа план полосой с памяткой.
   Все блоки — карточки системы: surface, рамка border, radius-lg */
.dash-head { margin-bottom: 18px; }
.dash-head h1 { font-size: 1.875rem; line-height: 1.15; letter-spacing: -.03em; font-weight: 700; margin: 0; }
.dash-head .lead { margin: 6px 0 0; }

.dash-grid {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  grid-template-areas:
    "main  tiles tiles"
    "chart chart side";
  gap: 14px;
  margin-bottom: 14px;
  align-items: stretch;
}
.dash-main { grid-area: main; }
.dash-tiles { grid-area: tiles; }
.dash-chart { grid-area: chart; }
.dash-side { grid-area: side; display: flex; flex-direction: column; gap: 14px; min-width: 0; }

.dash-card {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-card);
  padding: 18px;
  min-width: 0;
}
.dash-card-head { display: flex; align-items: flex-start; justify-content: space-between; gap: 12px; margin-bottom: 14px; flex-wrap: wrap; }
.dash-card-head h2 { margin: 0; font-size: 1.0625rem; line-height: 1.3; }
.dash-card-head p { margin: 3px 0 0; font-size: var(--fs-sm); }

.dash-label { font-size: var(--fs-sm); color: var(--ink-muted); }
.dash-main-top { display: flex; justify-content: space-between; align-items: center; gap: 8px; }
.dash-pill {
  display: inline-flex; align-items: center; gap: 6px;
  height: 28px; padding: 0 10px;
  border: 1px solid var(--border); border-radius: var(--radius-pill);
  font-size: var(--fs-xs); color: var(--ink-muted); white-space: nowrap;
}
.dash-big { font-size: 2.125rem; line-height: 1.1; font-weight: 700; letter-spacing: -.035em; font-variant-numeric: tabular-nums; margin-top: 8px; }
.dash-sub { display: flex; align-items: center; gap: 8px; margin-top: 6px; font-size: var(--fs-sm); flex-wrap: wrap; }
.dash-actions { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; margin-top: 16px; }
.dash-actions .btn { justify-content: center; border-radius: var(--radius-pill); padding: 10px 14px; }
.dash-actions .btn.primary { background: var(--ink); border-color: var(--ink); color: var(--surface); }
.dash-actions .btn.primary:hover { background: var(--accent); border-color: var(--accent); color: var(--on-accent); }

/* Процент — капсула цвета шкалы, как «↑ 5%» в образце */
.dash-chip {
  display: inline-flex; align-items: center;
  height: 22px; padding: 0 8px;
  border-radius: var(--radius-pill);
  font-size: 0.75rem; font-weight: 650; font-variant-numeric: tabular-nums;
  color: var(--lv-ink, var(--ink-muted));
  background: color-mix(in srgb, var(--lv, var(--ink-faint)) 14%, transparent);
  white-space: nowrap;
}
.dash-chip.lv-red { --lv: var(--critical); --lv-ink: var(--critical-ink); }
.dash-chip.lv-orange { --lv: var(--serious); --lv-ink: var(--serious-ink); }
.dash-chip.lv-amber { --lv: var(--warning); --lv-ink: var(--warning-ink); }
.dash-chip.lv-green { --lv: var(--good); --lv-ink: var(--good-ink); }

.dash-today { margin-top: 16px; padding: 12px; border-radius: var(--radius-md); background: var(--surface-raised); }
.dash-today-head { display: flex; justify-content: space-between; font-size: var(--fs-sm); font-weight: 600; margin-bottom: 10px; }
.dash-today-head .muted { font-weight: 400; }
.dash-minis { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 8px; }
.dash-mini { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-sm); padding: 10px; min-width: 0; }
.dash-mini-title { font-size: var(--fs-xs); color: var(--ink-muted); }
.dash-mini-value { font-size: 1rem; font-weight: 700; margin-top: 4px; font-variant-numeric: tabular-nums; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dash-mini-note { font-size: 0.7188rem; color: var(--ink-faint); margin-top: 2px; }
.dash-mini.ok .dash-mini-value { color: var(--good-ink); }
.dash-mini.wait .dash-mini-value { color: var(--warning-ink); }
.dash-bars .plan-hit { stroke: transparent; stroke-width: 12; cursor: help; }

/* Плитки 2 × 2 на две колонки сетки, по высоте — вровень с главной карточкой */
.dash-tiles { display: grid; grid-template-columns: 1fr 1fr; grid-auto-rows: 1fr; gap: 14px; }
.dash-tile {
  display: flex; flex-direction: column;
  padding: 14px;
  min-height: 132px;
  border-radius: var(--radius-lg);
  background: var(--surface);
  border: 1px solid var(--border);
  box-shadow: var(--shadow-card);
  color: var(--ink);
  text-decoration: none;
  min-width: 0;
  transition: border-color .12s, box-shadow .12s;
}
a.dash-tile:hover { border-color: var(--border-strong); box-shadow: var(--shadow-pop); color: var(--ink); }
.dash-tile-top { display: flex; justify-content: space-between; align-items: center; gap: 8px; font-size: var(--fs-sm); color: var(--ink-muted); }
.dash-tile-ic {
  width: 30px; height: 30px; flex: none;
  display: grid; place-items: center;
  line-height: 0;
  border-radius: 50%;
  border: 1px solid var(--border);
  color: var(--ink-muted);
}
/* Значок как блок: строчный svg садился на базовую линию и уезжал вниз */
.dash-tile-ic .ic, .dash-arrow .ic { display: block; }
.dash-tile-value { font-size: 1.75rem; font-weight: 700; letter-spacing: -.03em; margin-top: auto; padding-top: 12px; font-variant-numeric: tabular-nums; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dash-tile-note { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; font-size: var(--fs-xs); color: var(--ink-faint); margin-top: 6px; }
.dash-tile-note .up { color: var(--good-ink); }
.dash-tile-note .down { color: var(--critical-ink); }
/* График по дням */
.dash-legend { display: flex; gap: 12px; font-size: var(--fs-xs); color: var(--ink-muted); }
.dash-legend span { display: inline-flex; align-items: center; gap: 6px; }
.dash-legend .sw { display: inline-block; width: 10px; height: 10px; border-radius: 3px; }
.dash-legend .sw.fact { background: var(--accent); }
.dash-legend .sw.plan { width: 14px; height: 0; border-top: 2px dashed var(--ink-muted); border-radius: 0; }
.dash-chart { display: flex; flex-direction: column; }
.dash-chart-box { width: 100%; flex: 1; min-height: 210px; }
.dash-bars { width: 100%; height: auto; display: block; }
.dash-bars .bar { fill: var(--accent); }
.dash-bars .bar.today { fill: var(--accent); opacity: .45; }
.dash-bars .bar.future { fill: var(--border-strong); }
.dash-bars .bar:hover { fill: var(--accent-hover); opacity: 1; }

/* План полосой: пройденное — основным цветом, остаток — штриховкой, как в образце */
.dash-progress {
  height: 14px;
  border-radius: var(--radius-pill);
  background: repeating-linear-gradient(-45deg, var(--surface-raised) 0 6px, var(--border) 6px 8px);
  overflow: hidden;
}
.dash-progress i { display: block; height: 100%; background: var(--accent); border-radius: inherit; transition: width .45s ease-out; }
.dash-progress-foot { display: flex; justify-content: space-between; gap: 8px; margin-top: 8px; font-size: var(--fs-sm); flex-wrap: wrap; }
.dash-plan-need { margin: 10px 0 0; font-size: var(--fs-sm); color: var(--ink-muted); }

/* Памятка: карточки разделов листаются вбок, как карты в образце */
.dash-help-title { display: flex; align-items: center; gap: 10px; }
.dash-help .dash-card-head { align-items: center; }
.dash-help .dash-card-head button { border-radius: var(--radius-pill); display: inline-flex; align-items: center; gap: 6px; }

.dash-help-item {
  scroll-snap-align: start;
  display: flex; flex-direction: column; align-items: flex-start; gap: 6px;
  min-height: 128px;
  padding: 12px 14px;
  text-align: left;
  white-space: normal;
  border-radius: var(--radius-md);
  background: var(--surface-raised);
  border: 1px solid var(--border);
  color: var(--ink);
  font-weight: 400;
}
.dash-help-item:hover:not(:disabled) { border-color: var(--border-strong); }
.dash-help-item.accent { background: var(--accent); border-color: var(--accent); color: var(--on-accent); }
.dash-help-item.accent:hover:not(:disabled) { background: var(--accent-hover); color: var(--on-accent); }

.dash-help-item-title { font-size: 0.9375rem; font-weight: 650; margin-top: auto; }
.dash-help-item-text { font-size: var(--fs-xs); opacity: .8; line-height: 1.35; }

.dash-skel { display: flex; flex-direction: column; gap: 10px; }
.dash-skel span { height: 12px; border-radius: 6px; background: var(--surface-raised); animation: dash-pulse 1.2s ease-in-out infinite; }
@keyframes dash-pulse { 50% { opacity: .5; } }

/* Стрелка у числа: выросло — зелёная, упало — красная, не изменилось — нет */
.dash-big, .dash-tile-value { display: flex; align-items: center; gap: 6px; }
.dash-arrow { display: inline-grid; place-items: center; width: 26px; height: 26px; border-radius: 50%; flex: none; line-height: 0; }
.dash-arrow .ic { stroke-width: 2.4; }
.dash-arrow.up { color: var(--good-ink); background: color-mix(in srgb, var(--good) 14%, transparent); }
.dash-arrow.down { color: var(--critical-ink); background: color-mix(in srgb, var(--critical) 14%, transparent); }

/* Счётчик: каждая цифра — колонка 0…9 в окне высотой в строку,
   колонка уезжает вверх до нужной цифры */
.roll { display: inline-flex; align-items: flex-start; font-variant-numeric: tabular-nums; }
.roll-d { display: inline-block; height: 1.15em; line-height: 1.15em; overflow: hidden; }
.roll-col {
  display: flex; flex-direction: column;
  transform: translateY(0);
  transition: transform .9s cubic-bezier(.2, .8, .2, 1);
  will-change: transform;
}
.roll-col > span { height: 1.15em; }
.roll-s { display: inline-block; height: 1.15em; line-height: 1.15em; white-space: pre; }

@media (max-width: 1100px) {
  .dash-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
    grid-template-areas:
      "main  main"
      "tiles tiles"
      "chart chart"
      "side  side";
  }
  .dash-side { display: grid; grid-template-columns: 1fr 1fr; }
}
@media (max-width: 700px) {
  .dash-grid { grid-template-columns: minmax(0, 1fr); grid-template-areas: "main" "tiles" "chart" "side"; }
  .dash-side { display: flex; }
  .dash-head h1 { font-size: 1.5rem; }
  .dash-big { font-size: 1.75rem; }
  .dash-tile { min-height: 112px; }
  .dash-tile-value { font-size: 1.375rem; }

}

/* ---------- онбординг: подсветка памятки ---------- */
/* Затемнение — огромная тень у «окна» над блоком: светлым остаётся только
   он. Подсказка — белая карточка со стрелкой к блоку, кнопка «Хорошо» */
.onb-shield { position: fixed; inset: 0; z-index: var(--z-onb, 200); }
.onb-hole {
  position: fixed;
  z-index: var(--z-onb, 200);
  border-radius: calc(var(--radius-lg) + 4px);
  box-shadow: 0 0 0 9999px rgba(10, 16, 28, .62);
  pointer-events: none;
  transition: left .2s, top .2s, width .2s, height .2s;
}
.onb-tip {
  position: fixed;
  z-index: calc(var(--z-onb, 200) + 1);
  padding: 16px 18px 14px;
  border-radius: var(--radius-md);
  background: var(--surface);
  color: var(--ink);
  border: 1px solid var(--border);
  box-shadow: var(--shadow-pop);
  animation: onb-in .2s ease-out;
}
.onb-arrow {
  position: absolute;
  top: -8px;
  left: var(--arrow-x, 50%);
  width: 16px; height: 16px;
  margin-left: -8px;
  background: var(--surface);
  border-left: 1px solid var(--border);
  border-top: 1px solid var(--border);
  transform: rotate(45deg);
}
.onb-tip.above .onb-arrow { top: auto; bottom: -8px; transform: rotate(225deg); }
.onb-title { font-size: 1rem; font-weight: 700; letter-spacing: -.01em; }
.onb-text { margin: 6px 0 14px; font-size: var(--fs-body); line-height: 1.45; color: var(--ink-muted); }
.onb-foot { display: flex; justify-content: flex-end; }
.onb-ok {
  min-width: 96px;
  border-radius: var(--radius-pill);
  background: var(--ink);
  border-color: var(--ink);
  color: var(--surface);
  font-weight: 600;
}
.onb-ok:hover:not(:disabled) { background: var(--accent); border-color: var(--accent); color: var(--on-accent); }
@keyframes onb-in { from { opacity: 0; transform: translateY(4px); } to { opacity: 1; transform: none; } }
@media (prefers-reduced-motion: reduce) {
  .onb-hole { transition: none; }
  .onb-tip { animation: none; }
  .dash-skel span { animation: none; }
  .dash-progress i { transition: none; }
}

/* ---------- журнал правок: важность строк ---------- */
/* Смена и сброс паролей — красным, неудачные входы, 401 и сбои — жёлтым
   (правка 30.09): подложка строки, полоса слева и метка у действия */
tr.audit-critical > td { background: color-mix(in srgb, var(--critical) 9%, var(--row-bg, var(--surface))); }
tr.audit-warning > td { background: color-mix(in srgb, var(--warning) 11%, var(--row-bg, var(--surface))); }
tr.audit-critical > td:first-child { box-shadow: inset 3px 0 0 var(--critical); }
tr.audit-warning > td:first-child { box-shadow: inset 3px 0 0 var(--warning); }
.audit-tag {
  display: inline-flex; align-items: center;
  height: 22px; padding: 0 8px;
  border-radius: var(--radius-pill);
  font-size: 0.7812rem; font-weight: 600;
  white-space: nowrap;
}
.audit-tag.critical { color: var(--critical-ink); background: color-mix(in srgb, var(--critical) 16%, transparent); }
.audit-tag.warning { color: var(--warning-ink); background: color-mix(in srgb, var(--warning) 20%, transparent); }
@supports not (color: color-mix(in srgb, red 50%, blue)) {
  tr.audit-critical > td, tr.audit-warning > td { background: var(--surface-raised); }
  .audit-tag.critical, .audit-tag.warning { background: var(--surface-raised); }
}

/* ======================================================================
   Порция 12 (правка 30.09)
   ====================================================================== */

/* --- шапка: роль заметнее, без капса; «выйти» краснеет --- */
.who .role-tag {
  height: 26px;
  padding: 0 10px 0 8px;
  gap: 5px;
  text-transform: none;
  letter-spacing: 0;
  font-size: 0.7812rem;
  font-weight: 650;
  background: var(--accent-soft);
  border-color: color-mix(in srgb, var(--accent) 45%, transparent);
  color: var(--link, var(--accent));
}
.who .role-tag .ic { width: 14px; height: 14px; }
.who .role-tag.role-admin {
  background: color-mix(in srgb, var(--critical) 12%, var(--surface));
  border-color: color-mix(in srgb, var(--critical) 45%, transparent);
  color: var(--critical-ink);
}
.who .role-tag.role-manager, .who .role-tag.role-lead {
  background: color-mix(in srgb, var(--good) 12%, var(--surface));
  border-color: color-mix(in srgb, var(--good) 45%, transparent);
  color: var(--good-ink);
}
.who .name { color: var(--ink); font-weight: 560; }
button.logout:hover:not(:disabled) {
  background: color-mix(in srgb, var(--critical) 12%, transparent);
  color: var(--critical-ink);
}
/* Значок темы — ровно по центру кнопки */
button.icon { padding: 0; }
button.icon .ic { margin: 0; }

/* --- глаз в поле пароля не прыгает при нажатии --- */
.password-field .eye {
  top: 0; bottom: 0; margin: auto 0;
  transform: none;
  transition: background .15s, color .15s;
}
.password-field .eye:active:not(:disabled) { transform: none; }

/* --- метка категории: значок вместо квадратика --- */
.cat-chip::before { content: none; }
.cat-chip { color: var(--ink-muted); }
.cat-chip .ic { color: var(--link, var(--accent)); flex: none; }
.cat-head .cat-chip { gap: 7px; }

/* --- своя единственная точка — просто текст, не кнопка --- */
.store-fixed {
  background: transparent;
  padding: 0 2px;
  font-size: 0.9375rem;
  font-weight: 650;
  color: var(--ink);
}

/* --- ввод за день: поле ближе к названию, без пустоты посередине --- */
@media (min-width: 900px) {
  .entry-list { column-gap: var(--space-4, 16px); }
  .entry-row { grid-template-columns: minmax(0, 1fr) 140px; }
  .entry-list { max-width: none; }
}
/* Широкий экран — три колонки на всю ширину (правка 03.10, п. 5) */
@media (min-width: 1200px) {
  .entry-list { grid-template-columns: repeat(3, minmax(0, 1fr)); }
}

/* --- таблица «Точка»: компактнее, отстающие — красной полосой --- */
table.compact-table th, table.compact-table td { padding-top: 5px; padding-bottom: 5px; }
table.compact-table tr.group td { padding-top: 7px; padding-bottom: 5px; }
table.compact-table .pct-pill { min-height: 22px; }
tr.lagging > td { background: color-mix(in srgb, var(--critical) 6%, var(--row-bg, var(--surface))); }
tr.lagging > td:first-child { box-shadow: inset 3px 0 0 var(--critical); }

/* --- «Сектор»: столбцы вплотную, с разделителями --- */
table.matrix { border-collapse: collapse; }
table.matrix th, table.matrix td {
  padding: 5px 6px;
  border-right: 1px solid var(--grid, var(--border));
  text-align: center;
}
table.matrix th:last-child, table.matrix td:last-child { border-right: 0; }
table.matrix td.sticky-col, table.matrix th.sticky-col, table.matrix tr.group td { text-align: left; }
table.matrix .pct-pill { min-width: 46px; }
.missing-store { text-decoration: underline dotted; text-underline-offset: 3px; text-decoration-color: var(--ink-faint); cursor: help; }
.control-store { color: var(--critical-ink); text-decoration-color: currentColor !important; }
.msg.warn {
  background: color-mix(in srgb, var(--warning) 10%, var(--surface));
  border-color: color-mix(in srgb, var(--warning) 40%, transparent);
  color: var(--ink);
}

/* --- «Сегодня»: прогноз закреплён справа --- */
.sticky-right {
  position: sticky;
  right: 0;
  z-index: 1;
  background: var(--surface);
  background-image: linear-gradient(var(--row-bg), var(--row-bg));
  box-shadow: -1px 0 0 0 var(--border);
  min-width: 96px;
  text-align: center;
}
thead .sticky-right { z-index: 6; background: var(--surface); background-image: none; white-space: nowrap; vertical-align: middle; }
tr.total .sticky-right { background: var(--surface-raised); }

/* --- дни без цифр и незакрытые нули --- */
.gap-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 14px; margin-bottom: 14px; }
.gap-grid > .card { margin-bottom: 0; }
@media (max-width: 760px) { .gap-grid { grid-template-columns: 1fr; } }
.gap-card .row > .ic { color: var(--ink-muted); }
.gap-list { display: flex; flex-wrap: wrap; gap: 8px; }
.gap-row {
  display: inline-flex; align-items: center; gap: 8px;
  padding: 5px 6px 5px 10px;
  border: 1px solid var(--border);
  border-radius: var(--radius-pill);
}
.gap-count {
  display: inline-flex; align-items: center;
  height: 22px; padding: 0 9px;
  border-radius: var(--radius-pill);
  font-size: 0.7812rem; font-weight: 600;
  cursor: help;
}
.gap-count.bad { background: color-mix(in srgb, var(--critical) 12%, var(--surface)); color: var(--critical-ink); }
.gap-count.warn { background: color-mix(in srgb, var(--warning) 14%, var(--surface)); color: var(--warning-ink); }

/* --- подсказка по наведению --- */
.tip-trigger:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
.hover-tip {
  position: absolute;
  z-index: var(--z-popover);
  max-width: min(320px, calc(100vw - 16px));
  padding: 9px 11px;
  background: var(--surface);
  border: 1px solid var(--border-strong, var(--border));
  border-radius: var(--radius-sm);
  box-shadow: 0 8px 24px rgba(0, 0, 0, .14);
  font-size: 0.8125rem;
  line-height: 1.4;
  color: var(--ink);
}
.hover-tip .tip-days { margin-top: 4px; font-variant-numeric: tabular-nums; }
.hover-tip .tip-list { margin: 4px 0 0; padding-left: 18px; }

/* --- «Месяц»: пустые дни красным, компактнее --- */
.grid-table th, .grid-table td { padding: 2px 3px; font-size: 0.7812rem; }
.grid-table input { min-width: 52px; width: 56px; padding: 3px 5px; height: 26px; font-size: 0.7812rem; }
.grid-table th:first-child, .grid-table td:first-child { min-width: 150px; }
.grid-table th.day-empty { color: var(--critical-ink); box-shadow: inset 0 -2px 0 var(--critical); }
.grid-table td.day-empty { background: color-mix(in srgb, var(--critical) 6%, transparent); }
.grid-table th.flash { animation: day-flash 1.2s ease-out; }
@keyframes day-flash { from { background: color-mix(in srgb, var(--critical) 30%, var(--surface)); } }

/* --- планы одной точки столбцом --- */
.plan-list .entry-row { grid-template-columns: minmax(0, 1fr) 150px; }
.plan-input { text-align: right; font-variant-numeric: tabular-nums; }
.plan-table .plan-input { min-width: 92px; padding: 5px 8px; }

/* --- журнал: фильтр сверху --- */
.role-fixed { color: var(--ink-muted); }

/* --- несохранённые правки: плашка внизу --- */
.unsaved-bar {
  position: fixed;
  left: 50%;
  bottom: 18px;
  transform: translateX(-50%);
  z-index: var(--z-status);
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  max-width: min(720px, calc(100vw - 24px));
  padding: 10px 12px 10px 14px;
  background: var(--surface);
  border: 1px solid color-mix(in srgb, var(--warning) 55%, transparent);
  border-left: 4px solid var(--warning);
  border-radius: var(--radius-sm);
  box-shadow: 0 10px 30px rgba(0, 0, 0, .18);
  font-size: 0.8438rem;
}
.unsaved-bar > .ic { color: var(--warning-ink); }
.unsaved-bar > span { flex: 1 1 220px; }
.unsaved-bar.shake { animation: bar-shake .4s ease-in-out; }
@keyframes bar-shake {
  20%, 60% { transform: translateX(calc(-50% - 6px)); }
  40%, 80% { transform: translateX(calc(-50% + 6px)); }
}

/* --- главная: уведомления справа от приветствия --- */
.dash-head {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(280px, 400px);
  gap: 14px;
  align-items: start;
}
@media (max-width: 860px) { .dash-head { grid-template-columns: 1fr; } }
.dash-notices { padding: 14px 16px; }
.dash-notices .dash-card-head { margin-bottom: 6px; align-items: center; }
.dash-notices h2 { display: inline-flex; align-items: center; gap: 8px; font-size: 1rem; margin: 0; }
.dash-notice-count {
  min-width: 20px; height: 20px; padding: 0 6px;
  display: inline-grid; place-items: center;
  border-radius: var(--radius-pill);
  background: var(--critical); color: #fff;
  font-size: 0.7188rem; font-weight: 700;
}
.dash-notice-count.none { display: none; }
.dash-notice-list { display: grid; gap: 2px; max-height: 190px; overflow: auto; overscroll-behavior: auto; }
.dash-notice-head {
  width: 100%;
  justify-content: flex-start;
  gap: 8px;
  padding: 6px 8px;
  border: 0;
  background: transparent;
  text-align: left;
  font-weight: 500;
  color: var(--ink-muted);
}
.dash-notice-head .ic { flex: none; }
.dash-notice-title { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.dash-notice.unread .dash-notice-head { color: var(--ink); font-weight: 650; }
.dash-notice.unread .dash-notice-head::after {
  content: ''; width: 7px; height: 7px; border-radius: 50%; background: var(--critical); flex: none;
}
.dash-notice-text { padding: 0 8px 8px 31px; font-size: 0.8125rem; white-space: pre-line; color: var(--ink); }
.dash-notice-empty { margin: 4px 0 0; }
.dash-notice-form { display: grid; gap: 8px; margin: 4px 0 10px; }

/* --- памятка: четыре карточки сеткой --- */
.dash-help-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 8px; }
.dash-help-grid .dash-help-item { min-height: 0; padding: 10px 12px; gap: 3px; justify-content: flex-start; }
.dash-help-grid .dash-help-item-title { margin-top: 0; font-size: 0.875rem; display: inline-flex; align-items: center; gap: 6px; }
.dash-help-grid .dash-help-item-text { font-size: 0.75rem; }

/* --- график: даты правок нажимаются --- */
.date-chip {
  height: 24px; min-height: 24px; padding: 0 8px; margin: 2px 3px 2px 0;
  border-radius: var(--radius-pill);
  font-size: 0.7812rem; font-weight: 600;
  background: var(--surface-raised);
}
.review-row { line-height: 30px; }
.review-list .review-row { display: flex; flex-wrap: wrap; align-items: center; gap: 0 4px; }

.dash-notice-head { display: flex; overflow: hidden; }
.dash-notice-head > .muted { flex: none; white-space: nowrap; }
/* На телефоне роль — значком, без подписи: место в шапке на вес золота */
@media (max-width: 640px) {
  .who .role-tag { display: inline-flex; padding: 0 6px; }
  .who .role-tag .role-text { display: none; }
}
/* Плашка «несохранено» внизу — всплывающее сообщение поднимается над ней */
body.has-unsaved .toast { bottom: calc(96px + env(safe-area-inset-bottom)); }

/* --- ревью 02.10: кнопка «день сдан» в шапке, компактная шапка на телефоне --- */
.confirm-slot { display: flex; align-items: flex-end; }
.confirm-slot:empty { display: none; }
.confirm-note { margin: 0 0 10px; font-size: var(--fs-sm, 13px); color: var(--ink-muted); }
.confirm-note .muted { color: inherit; }
@media (max-width: 600px) {
  .confirm-slot { width: 100%; }
  .confirm-slot .confirm-day { width: 100%; justify-content: center; }
  header.top { padding: 0 12px; }
  .top-inner { min-height: 0; gap: 4px 12px; padding-top: 6px; }
  .brand { font-size: 0.875rem; }
  .brand span { display: none; }
  nav.tabs { padding-bottom: 4px; }
}


/* ---- Доступность (QA 03.10) ---- */
/* Текст на акцентной плитке памятки не бледнеет: в тёмной теме было 3,8:1 */
.dash-help-item.accent .dash-help-item-text { opacity: 1; }
/* Счётчик уведомлений: в тёмной теме белое на светло-красном было 3,3:1 */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .dash-notice-count { color: #0b1220; }
}
:root[data-theme="dark"] .dash-notice-count { color: #0b1220; }
/* Цели касания: ссылки-коды точек и мелкие кнопки не меньше 24 px */
a.small, .gaps button.small {
  display: inline-flex; align-items: center; min-height: 24px; min-width: 24px; justify-content: center; padding-block: 3px;
}
.brand { display: inline-flex; align-items: center; min-height: 24px; }
/* Ссылка «К содержимому» для клавиатуры */
.skip-link {
  position: absolute; left: 8px; top: -48px; z-index: 1000;
  padding: 8px 14px; border-radius: var(--radius-sm);
  background: var(--ink); color: var(--surface); text-decoration: none;
}
.skip-link:focus { top: 8px; }
/* Узкий экран (320 px): кнопки переносят текст, строки не растягивают страницу */
@media (max-width: 380px) {
  button, .btn { white-space: normal; max-width: 100%; }
  .dash-actions { grid-template-columns: 1fr; }
  .row { flex-wrap: wrap; }
}

.shift-legend .rv i {
  display: inline-block; width: 0; height: 0; margin-right: 6px; vertical-align: middle;
  border: 5px solid transparent; border-top-color: var(--warning); border-right-color: var(--warning);
  border-top-right-radius: 3px;
}

/* Легенда цветов под таблицами «Точка» и «Сектор» (QA 03.10, 5-4) */
.color-legend { display: flex; flex-wrap: wrap; gap: 6px 16px; margin-top: 10px; align-items: center; }
.color-legend-item { display: inline-flex; align-items: center; gap: 6px; }
.color-legend-dot { width: 10px; height: 10px; border-radius: 50%; display: inline-block; }

/* «Сдать день» на телефоне закреплена внизу экрана (QA 03.10, 5-6) */
@media (max-width: 600px) {
  .confirm-slot:not(:empty) {
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 40;
    padding: 10px 12px calc(10px + env(safe-area-inset-bottom));
    background: var(--surface, #fff); border-top: 1px solid var(--border, #ddd);
  }
  body:has(.confirm-slot:not(:empty)) main { padding-bottom: 88px; }
  body.has-unsaved .confirm-slot { bottom: 76px; }
  /* «Сдать день» остаётся внизу, а плашка «Внесено / Не сохранено» всплывает над ней,
     а не перекрывает её. Плашка бывает в две строки, поэтому запас с избытком */
  body:has(.confirm-slot:not(:empty)) .save-status { bottom: calc(86px + env(safe-area-inset-bottom, 0px)); }
  body:has(.confirm-slot:not(:empty)).has-save-status .toast { bottom: calc(160px + env(safe-area-inset-bottom, 0px)); }
}

/* Длинные слова без пробелов не растягивают страницу (QA 3-11) */
.card, .dash-card, .msg, .toast, .dash-notice, .help-body, .notice-text, h1, h2, h3, p, label,
td.text, .name-cell, .comment {
  overflow-wrap: anywhere;
}

/* Меню админа: одиннадцать вкладок помещаются на 1024 px (QA 8-10) */
@media (min-width: 821px) and (max-width: 1180px) {
  nav.tabs { gap: 3px; }
  nav.tabs a { padding: 0 8px; font-size: 0.8125rem; gap: 5px; }
}

/* «Особый контроль» на «Сегодня» заметнее обычного «не сдали» (QA 5-9) */
.badge.wait.control { background: var(--critical); border-color: var(--critical); color: #fff; font-weight: 600; }

/* «Месяц» на телефоне: закреплённые колонки не съедают две трети ширины (QA 8-11) */
@media (max-width: 600px) {
  .grid-table th:first-child, .grid-table td:first-child { min-width: 112px; max-width: 128px; }
  .grid-table th, .grid-table td { padding: 4px 4px; }
}

/* Цели касания на телефоне — не меньше 44 px (QA 6-6) */
@media (max-width: 600px) {
  button, .btn, select, input:not([type="checkbox"]):not([type="radio"]), nav.tabs a { min-height: 44px; }
  .grid-table input { min-height: 40px; }
  button.icon, .icon-btn { min-width: 44px; }
}
@media (max-width: 600px) {
  button.store-button, button.store-button.small, td select, .row select, label + select { min-height: 44px; }
}

/* ---- Повторный прогон 03.10: мелочи на телефоне и в тёмной теме ---- */
/* F-05: «особый контроль» в тёмной теме — тёмный текст на светлой плашке */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .badge.wait.control { color: #0b1220; }
}
:root[data-theme="dark"] .badge.wait.control { color: #0b1220; }

@media (max-width: 600px) {
  /* F-02/F-03: цели касания */
  select, header.top button, header.top .icon, .dash-card a.small, td > a, .gap-row a, button.small, .small.icon,
  input[type="date"] { min-height: 44px; }
  header.top button, header.top .icon, button.icon, button.small.icon, .who button { min-width: 44px; }
  td > a, .gap-row a, .notice a { display: inline-flex; align-items: center; min-height: 44px; min-width: 44px; justify-content: center; }
  /* F-07: сообщение не прячет закреплённую «Сдать день» */
  body:has(.confirm-slot:not(:empty)) .toast { bottom: calc(76px + env(safe-area-inset-bottom)); }
}
/* F-06: на телефоне «Прогноз» не закрепляем справа — иначе он закрывает «Статус» */
@media (max-width: 600px) {
  .sticky-right, thead .sticky-right, .table-wrap.scroll-y tbody td.sticky-right, .table-wrap.scroll-y thead th.sticky-right {
    position: static; box-shadow: none;
  }
}

/* Дожим 44 px на телефоне: правила выше по файлу имели большую специфичность */
@media (max-width: 600px) {
  .page-head .filters input, .page-head .filters select, .page-head select, button.store-button,
  .filters select, form select, .card select { min-height: 44px; }
  button.icon, header.top button.icon { width: 44px; height: 44px; min-width: 44px; }
  .date-field button.date-calendar { width: 44px; height: 44px; min-width: 44px; }
  .save-status .close { width: 44px; height: 44px; }
  .gap-row a, .gap-row button { display: inline-flex; align-items: center; justify-content: center; min-height: 44px; min-width: 44px; }
  td a.store-link, td > a:only-child { padding: 10px 6px; }
}
@media (max-width: 600px) {
  main button, main select, main .gap-row a, main td > a { min-height: 44px !important; }
  main button { min-width: 44px !important; }
  main .gap-row a, main td > a { min-width: 44px; display: inline-flex; align-items: center; justify-content: center; }
}
@media (max-width: 600px) {
  main a.small, main td a { min-height: 44px; min-width: 44px; display: inline-flex; align-items: center; justify-content: center; }
}

/* F-08: вкладки меню админа помещаются и на 1280 px */
@media (min-width: 1181px) and (max-width: 1320px) {
  nav.tabs { gap: 3px; }
  nav.tabs a { padding: 0 9px; gap: 5px; }
}

/* Логотип в шапке на телефоне — цель касания 44 px (QA 6-10) */
@media (max-width: 600px) {
  a.brand { display: inline-flex; align-items: center; min-height: 44px; }
}

/* ---------- список выбора в виде плиток (месяц, показатель, роль) ---------- */
.choice-popover { min-width: 160px; padding: 10px; }
.choice-list button { text-align: left; padding: 0 12px; white-space: nowrap; }
.choice-button:disabled { opacity: 0.6; cursor: not-allowed; }

/* Стрелка у числа стоит по центру самих цифр, а не коробки: у разных шрифтов
   цифры в строке сидят чуть ниже середины, и стрелка «съезжала» вверх
   (правка 03.10, п. 6). Оба — от верха строки, стрелка опущена на em-долю */
.dash-big, .dash-tile-value, .tile .value { align-items: flex-start; }
.dash-big .dash-arrow, .dash-tile-value .dash-arrow, .tile .value .dash-arrow {
  margin-top: calc(0.55em - 13px);
}
.dash-big .roll, .dash-tile-value .roll, .tile .value .roll { line-height: 1.15em; }

/* Люди (QA 04.10): кнопки роли одной ширины по самой длинной подписи; в форме добавления выбор тянется на всю ячейку, пустот нет */
td .role-button { width: 232px; box-sizing: border-box; max-width: 100%; justify-content: space-between; }
.add-pick .store-button, .add-pick .choice-button { width: 100%; justify-content: space-between; }
td .store-button { width: 104px; justify-content: space-between; }
/* Дата рождения без дня недели: поле уже, чем у даты на экранах ввода; в форме добавления — по содержимому */
.birth-field input.date-text { width: 120px; }
.add-birth .date-field { display: flex; }
.add-birth .date-field input.date-text { flex: 1 1 auto; }

/* «Люди» на телефоне: каждая строка таблицы — карточка из двух колонок, а не
   семь колонок с прокруткой вбок (где роль, точка и пароль прятались за краем) */
@media (max-width: 600px) {
  .people-wrap, .people-wrap.scroll-y { overflow: visible; max-height: none; margin: 0; background: none; }
  .people-table, .people-table tbody { display: block; width: 100%; min-width: 0; }
  .people-table thead { display: none; }
  .people-table tr { display: block; }
  .people-table tr:not(.group) {
    display: grid; grid-template-columns: 1fr 1fr; gap: 6px 10px;
    padding: 10px 0; border-bottom: 1px solid var(--border);
  }
  .people-table td { display: block; padding: 0; border: 0; min-width: 0; text-align: left; position: static; background: transparent !important; }
  .people-table tr.reset-requested { background: color-mix(in srgb, var(--warning) 9%, transparent); }
  .people-table td[data-label]::before {
    content: attr(data-label); display: block; margin-bottom: 1px;
    font-size: 0.6875rem; line-height: 1.2; color: var(--ink-muted);
  }
  .people-table td.sticky-col { grid-column: 1 / -1; font-weight: 600; background: transparent; }
  .people-table td input, .people-table td select, .people-table td .store-button, .people-table td button.select {
    width: 100% !important; max-width: 100%; box-sizing: border-box;
    min-height: 40px; padding-top: 6px; padding-bottom: 6px;
  }
  /* Дата рождения: поле даты тянется на ширину колонки карточки, а не на 100% внутри себя */
  .people-table td .date-field { display: flex; width: 100%; box-sizing: border-box; }
  .people-table td .date-field input.date-text { flex: 1 1 auto; width: auto !important; min-width: 0; min-height: 38px; height: 38px; padding-top: 0; padding-bottom: 0; }
  /* Пароль: бейдж и кнопки «Выдать»/«Убрать» переносятся, а не растягивают страницу вбок */
  .people-table .pw-cell { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; }
  .people-table .pw-cell > button { width: auto !important; flex: 0 0 auto; height: auto; min-height: 36px; }
}

/* Фокус по Tab прокручивает страницу так, чтобы поле не оказывалось под плашкой сохранения
   (и под закреплённой кнопкой «Сдать день») */
html { scroll-padding-bottom: 8px; }
@media (max-width: 600px) {
  html:has(body.has-save-status) { scroll-padding-bottom: 150px; }
  html:has(.confirm-slot:not(:empty)) { scroll-padding-bottom: 100px; }
  html:has(.confirm-slot:not(:empty)):has(body.has-save-status) { scroll-padding-bottom: 170px; }
}

/* ---------- окно «Загрузить книгу Excel» ---------- */
.book-pick { display: flex; flex-direction: column; gap: 6px; margin: 8px 0; }
.book-pick input[type="file"] { max-width: 100%; }
.book-prefs { margin: 10px 0; padding: 10px 12px; border: 1px solid var(--border); border-radius: var(--radius-md); background: var(--surface-raised); }
.book-prefs[hidden] { display: none; }
.book-pref-row { display: flex; align-items: center; gap: 10px; margin: 6px 0; }
.book-pref-row label { flex: 0 0 110px; font-size: 0.875rem; }
.book-pref-row select { flex: 1; min-width: 0; }
.book-summary { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 2px 16px; margin: 8px 0; font-size: 0.875rem; }
.book-summary dt { color: var(--ink-muted); }
.book-summary dd { margin: 0; text-align: right; font-variant-numeric: tabular-nums; }
@media (max-width: 600px) {
  .book-pref-row { flex-direction: column; align-items: stretch; gap: 4px; }
  .book-pref-row label { flex: none; }
  .book-summary { grid-template-columns: 1fr; }
  .book-summary dd { text-align: left; font-weight: 600; margin-bottom: 4px; }
}
