/*
 * Mirrorbot dashboard styles.
 *
 * Фирменная ТЁМНАЯ палитра витрины (faithful монолиту Latvia, коммит c02d548).
 * Дашборд ВСЕГДА тёмный и НЕ наследует Telegram-тему — трейдинг-витрина имеет
 * фиксированный фирменный вид (фон #0f1117, панели #1a1d27, янтарь #f59e0b).
 * Все компоненты используют var(--mb-*) токены ниже — не хардкодить цвета мимо них.
 */

:root {
  /* Базовые поверхности */
  --mb-bg: #0f1117; /* фон страницы */
  --mb-panel: #1a1d27; /* карточки/панели/инпуты */
  --mb-border: #2a2d3a; /* границы карточек и разделители */
  --mb-control-bg: #1e293b; /* неактивные контролы (таб/draw/ctab) */
  --mb-control-border: #334155; /* границы контролов */

  /* Текст */
  --mb-text: #e8eaf0; /* основной */
  --mb-hint: #94a3b8; /* приглушённый */
  --mb-muted: #6b7280; /* очень приглушённый (заголовки секций, th) */

  /* Акценты Telegram-совместимых токенов (фиксированы под тёмную тему) */
  --mb-link: #3b82f6; /* синий: buy / ссылки / фокус */
  --mb-button: #3b82f6; /* основная кнопка (buy / save) */
  --mb-button-text: #ffffff;
  --mb-destructive: #ef4444;

  /* Семантические токены P&L / направления / фирменный акцент. Одинаковы как в
     монолите: зелёный профит, красный убыток, янтарный active-акцент. */
  --mb-accent: #f59e0b; /* фирменный янтарь: active-табы/кнопки/режимы */
  --mb-pos: #22c55e;
  --mb-neg: #ef4444;
  --mb-warn: #f59e0b;

  /* Layout tokens */
  --mb-radius: 10px;
  --mb-pad: 12px;
  --mb-gap: 8px;
  --mb-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;
}

* {
  box-sizing: border-box;
}

html,
body {
  margin: 0;
  padding: 0;
  background: var(--mb-bg);
  color: var(--mb-text);
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial,
    sans-serif;
  font-size: 15px;
  line-height: 1.45;
  -webkit-font-smoothing: antialiased;
}

#app {
  display: block;
  max-width: 720px;
  margin: 0 auto;
  padding: var(--mb-pad);
}

/* Focus indicators — accessibility */
:focus-visible {
  outline: 2px solid var(--mb-link);
  outline-offset: 2px;
}

/* Header */
.hdr-row {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--mb-gap);
}

.hdr-name {
  margin: 0;
  font-size: 18px;
  font-weight: 600;
}

.hdr-stats {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--mb-gap);
  margin-top: var(--mb-gap);
}

.stat {
  background: var(--mb-panel);
  padding: var(--mb-pad);
  border-radius: var(--mb-radius);
  border: 1px solid var(--mb-border);
  display: flex;
  flex-direction: column;
  gap: 2px;
}

.stat-label {
  font-size: 12px;
  color: var(--mb-hint);
}

.stat-value {
  font-family: var(--mb-mono);
  font-size: 16px;
}

/* Icon button (back ‹ / refresh ↻). Flex-centred so the glyph sits dead-centre
 * — без этого кнопка была пустым квадратом (глиф добавлен в index.html). */
.btn-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  background: var(--mb-panel);
  color: var(--mb-text);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  width: 36px;
  height: 36px;
  font-size: 20px;
  line-height: 1;
  cursor: pointer;
}
.btn-icon:hover {
  border-color: var(--mb-accent, #3b82f6);
}
.btn-icon:active {
  transform: scale(0.94);
}
/* ⛔ `.btn-icon { display: inline-flex }` перебивает атрибут [hidden] (равная
   специфичность, авторское правило идёт после UA) → кнопка «‹»/«↻» оставалась
   видимой даже при back.hidden=true (app.js setHeader showBack:false на home).
   Owner-home — корень навигации, назад некуда → кнопка должна скрываться.
   Re-assert [hidden] с большей специфичностью (как .chart-*[hidden] ниже). */
.btn-icon[hidden] {
  display: none;
}

/* Tabs */
.tabs {
  display: flex;
  gap: 4px;
  margin: var(--mb-pad) 0;
  border-bottom: 1px solid var(--mb-border);
  overflow-x: auto;
}

.tab {
  appearance: none;
  background: transparent;
  border: 0;
  color: var(--mb-hint);
  padding: 10px 14px;
  font: inherit;
  font-weight: 500;
  cursor: pointer;
  border-bottom: 2px solid transparent;
  white-space: nowrap;
}

.tab[aria-selected="true"] {
  color: var(--mb-accent);
  border-bottom-color: var(--mb-accent);
}

/* Generic banner for errors / status messages */
.banner {
  background: var(--mb-panel);
  color: var(--mb-text);
  padding: var(--mb-pad);
  border-radius: var(--mb-radius);
  border: 1px solid var(--mb-border);
  margin-bottom: var(--mb-pad);
}

.banner.error {
  background: color-mix(in srgb, var(--mb-destructive) 18%, transparent);
  border-color: color-mix(in srgb, var(--mb-destructive) 35%, transparent);
  color: var(--mb-destructive);
}

/* View container */
.view {
  display: block;
}

/* Tables */
table.tbl {
  width: 100%;
  border-collapse: collapse;
  font-size: 14px;
}

.tbl th,
.tbl td {
  text-align: left;
  padding: 8px 6px;
  border-bottom: 1px solid var(--mb-border);
}

.tbl th {
  color: var(--mb-muted);
  font-weight: 500;
  font-size: 12px;
  text-transform: uppercase;
  letter-spacing: 0.04em;
}

.tbl td.num {
  font-family: var(--mb-mono);
  text-align: right;
}

/* Числовые заголовки выровнены вправо ВМЕСТЕ со значениями (Тикет/№/Лоты/Вход/
   P&L/Своп) — иначе подпись «висит» слева над правыми числами. Единый вид трёх
   таблиц master_home (запрос юзера 2026-06-08). */
.tbl th.num {
  text-align: right;
}

.side-buy {
  color: var(--mb-link);
  font-weight: 600;
}

.side-sell {
  color: var(--mb-destructive);
  font-weight: 600;
}

/* Hidden / redacted values from server */
.redacted {
  font-family: var(--mb-mono);
  color: var(--mb-hint);
  letter-spacing: 0.15em;
}

/* Events feed */
.event-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: var(--mb-gap);
}

.event-list li {
  background: var(--mb-panel);
  padding: var(--mb-pad);
  border-radius: var(--mb-radius);
  border: 1px solid var(--mb-border);
}

.event-time {
  display: block;
  color: var(--mb-hint);
  font-size: 12px;
  margin-bottom: 4px;
}

.event-body {
  white-space: pre-wrap;
  word-break: break-word;
}

/* Settings */
.settings-form {
  display: flex;
  flex-direction: column;
  gap: var(--mb-pad);
}

.field {
  display: flex;
  flex-direction: column;
  gap: 4px;
}

.field label {
  font-size: 12px;
  color: var(--mb-hint);
}

.field input[type="number"] {
  background: var(--mb-panel);
  color: var(--mb-text);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 10px;
  font: inherit;
  font-family: var(--mb-mono);
}

.field input[type="number"]:focus {
  outline: none;
  border-color: var(--mb-link);
}

.btn-row {
  display: flex;
  gap: var(--mb-gap);
  flex-wrap: wrap;
}

.btn {
  appearance: none;
  background: var(--mb-button);
  color: var(--mb-button-text);
  border: 0;
  border-radius: var(--mb-radius);
  padding: 10px 16px;
  font: inherit;
  font-weight: 600;
  cursor: pointer;
}

.btn.secondary {
  background: var(--mb-control-bg);
  color: var(--mb-text);
  border: 1px solid var(--mb-control-border);
}

.btn[disabled] {
  opacity: 0.5;
  cursor: progress;
}

/* Chart container */
.chart-wrap {
  /* position:relative — якорь для canvas-overlay рисования (G1, .rect-overlay). */
  position: relative;
  margin-top: var(--mb-pad);
  background: var(--mb-panel);
  border-radius: var(--mb-radius);
  border: 1px solid var(--mb-border);
  padding: 8px;
}

#chart,
.chart {
  width: 100%;
  height: 240px;
}

/* Equity-график (G2): range-кнопки + canvas фиксированной высоты + строка статистики */
.equity-mount {
  display: flex;
  flex-direction: column;
  gap: 6px;
}

.eq-tf-btns {
  display: flex;
  gap: 6px;
}

.eq-tf-btn {
  flex: 1;
  padding: 4px 0;
  font-size: 12px;
  background: var(--mb-control-bg);
  color: var(--mb-hint);
  border: 1px solid var(--mb-control-border);
  border-radius: var(--mb-radius);
  cursor: pointer;
}

.eq-tf-btn.active {
  background: var(--mb-accent);
  color: #000;
  border-color: var(--mb-accent);
}

.eq-tf-btn:disabled {
  opacity: 0.4;
  cursor: default;
}

.eq-canvas-wrap {
  position: relative;
  width: 100%;
  height: 220px;
}

.eq-canvas {
  width: 100%;
  height: 100%;
  display: block;
}

.eq-stats {
  display: flex;
  justify-content: space-between;
  font-size: 12px;
  color: var(--mb-hint);
}

.eq-change {
  font-variant-numeric: tabular-nums;
}

/* Cards (Phase 15 single-user) */
.card {
  background: var(--mb-panel);
  padding: 14px;
  border-radius: 12px;
  border: 1px solid var(--mb-border);
  margin-top: var(--mb-pad);
}

.card h3 {
  margin: 0 0 8px 0;
  font-size: 16px;
  font-weight: 600;
}

.master-card {
  cursor: pointer;
}

/* Сводка мастер-счёта (Баланс + P&L) над таблицей «Позиции мастера».
   Цвет значений P&L — глобальные .pos/.neg; подписи — .muted. */
.master-acct-line {
  margin: 0 0 10px 0;
  font-size: 14px;
  font-variant-numeric: tabular-nums;
}

.slot-card {
  cursor: pointer;
}

.slot-body {
  margin-bottom: var(--mb-gap);
}

.slots-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  gap: var(--mb-gap);
  margin-top: var(--mb-pad);
}

@media (max-width: 480px) {
  .slots-grid {
    grid-template-columns: 1fr;
  }
}

/* Key-value pairs */
.kv {
  display: grid;
  grid-template-columns: max-content 1fr;
  gap: 4px 12px;
  margin: 0;
  font-size: 14px;
}

.kv dt {
  color: var(--mb-hint);
  font-size: 12px;
}

.kv dd {
  margin: 0;
  font-family: var(--mb-mono);
}

/* «Наш счёт» — карточка витрины Latvia 1:1: крупный баланс, ряды label↔value,
   разделители, цветной P&L с %-бейджем, P&L за периоды, блок ₽. Scoped на
   .account-card, чтобы не задеть остальные .card/.kv. */
.account-card h3 {
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: 0.8px;
  color: var(--mb-muted);
  font-weight: 600;
  margin: 0 0 10px 0;
}
.account-card .balance-row {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 12px;
  margin-bottom: 6px;
}
.account-card .balance-label {
  font-size: 13px;
  color: var(--mb-hint);
}
.account-card .balance-value {
  font-size: 20px;
  font-weight: 700;
  font-family: var(--mb-mono);
}
.account-card .amt {
  font-family: var(--mb-mono);
}
.account-card .divider {
  height: 1px;
  background: var(--mb-border);
  margin: 10px 0;
}
/* Светофор уровня маржи: .pos/.neg уже определены ниже (текстовый цвет),
   янтарную ступень добавляем здесь. */
.account-card .warn-hi {
  color: #d97706;
}

/* Процент доходности периода (Сегодня/Вчера/Неделя/Месяц) в скобках рядом с
   суммой — мельче суммы, цвет pos/neg наследуется от .pos/.neg. */
.account-card .period-pct {
  font-family: var(--mb-mono);
  font-size: 12px;
  opacity: 0.85;
}

/* Сводка «Мои ручные сделки» в стиле карточки «Наш счёт»: подпись слева,
   значение справа (а не в общей kv-сетке max-content 1fr). Месяц/Год по сумме,
   цвет pos/neg уже на span'ах (запрос юзера 2026-06-08). */
.manual-section .kv {
  grid-template-columns: 1fr auto;
  gap: 6px 12px;
}
.manual-section .kv dt {
  align-self: center;
  font-size: 13px;
}
.manual-section .kv dd {
  text-align: right;
  font-size: 15px;
}

/* %-бейдж рядом с плавающим P&L (порт .pct витрины Latvia). */
.pct {
  font-size: 13px;
  font-weight: 600;
  padding: 2px 8px;
  border-radius: 6px;
  white-space: nowrap;
}
.pct.pos {
  background: color-mix(in srgb, var(--mb-pos) 20%, transparent);
  color: var(--mb-pos);
}
.pct.neg {
  background: color-mix(in srgb, var(--mb-neg) 20%, transparent);
  color: var(--mb-neg);
}
.pct.warn-hi {
  background: rgba(217, 119, 6, 0.22);
  color: #d97706;
}
.pct.warn-lo {
  background: rgba(234, 179, 8, 0.2);
  color: #eab308;
}
.pct.neu {
  background: rgba(255, 255, 255, 0.1);
  color: var(--mb-hint);
}

/* Settings rows */
.field-row {
  display: flex;
  gap: var(--mb-gap);
  align-items: center;
  margin-bottom: var(--mb-gap);
  flex-wrap: wrap;
}

.field-row label {
  font-size: 12px;
  color: var(--mb-hint);
  min-width: 90px;
}

.field-row input[type="number"] {
  background: var(--mb-panel);
  color: var(--mb-text);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 8px 10px;
  font: inherit;
  font-family: var(--mb-mono);
  min-width: 100px;
  flex: 1;
}

.btn.danger {
  background: color-mix(in srgb, var(--mb-destructive) 88%, transparent);
  color: var(--mb-button-text);
}

.muted {
  color: var(--mb-hint);
  font-size: 13px;
}

/* Empty state */
.empty {
  color: var(--mb-hint);
  text-align: center;
  padding: 24px 12px;
}

/* Averaging ladder editor (порт avg-config-section с Latvia) */
.avg-table {
  width: 100%;
  border-collapse: collapse;
  margin-top: var(--mb-gap);
}

.avg-table th {
  font-size: 11px;
  text-transform: uppercase;
  color: var(--mb-muted);
  text-align: left;
  padding: 4px 6px;
  border-bottom: 1px solid var(--mb-border);
}

.avg-table td {
  font-size: 13px;
  padding: 7px 6px;
  border-bottom: 1px solid var(--mb-border);
}

.avg-table td.avg-rung {
  font-weight: 600;
}

.avg-table td.avg-label {
  color: var(--mb-hint);
  font-size: 11px;
}

.avg-input {
  width: 72px;
  background: var(--mb-panel);
  color: var(--mb-text);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 4px 8px;
  text-align: right;
  font-size: 14px;
}

.avg-input:focus {
  outline: none;
  border-color: var(--mb-link);
}

.avg-input:disabled {
  opacity: 0.5;
}

.avg-actions {
  margin-top: var(--mb-pad);
  align-items: center;
}

.avg-status {
  font-size: 12px;
}

/* Instrument candlestick chart (порт UX витрины Latvia: выбор символа + ТФ) */
.chart-controls {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--mb-gap);
  margin-bottom: 8px;
}

.chart-controls label {
  font-size: 12px;
  color: var(--mb-hint);
}

.chart-symbol-select {
  background: var(--mb-panel);
  color: var(--mb-text);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 6px 8px;
  font: inherit;
  font-size: 14px;
}

.chart-symbol-select:focus {
  outline: none;
  border-color: var(--mb-link);
}

.chart-symbol-select:disabled {
  opacity: 0.5;
}

.tf-row {
  display: flex;
  gap: 4px;
  margin-left: auto;
}

.tf-btn {
  appearance: none;
  background: var(--mb-control-bg);
  color: var(--mb-hint);
  border: 1px solid var(--mb-control-border);
  border-radius: var(--mb-radius);
  padding: 4px 12px;
  font: inherit;
  font-size: 13px;
  cursor: pointer;
}

.tf-btn.active {
  background: var(--mb-accent);
  color: #000;
  border-color: var(--mb-accent);
}

/* Инструменты рисования (G1): тулбар над графиком + палитра прямоугольника. */
.draw-toolbar {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px;
  margin-bottom: 6px;
}

.draw-btn {
  appearance: none;
  background: var(--mb-control-bg);
  color: var(--mb-hint);
  border: 1px solid var(--mb-control-border);
  border-radius: var(--mb-radius);
  padding: 4px 9px;
  font-size: 13px;
  line-height: 1.2;
  min-width: 30px;
  cursor: pointer;
}

.draw-btn:hover:not(:disabled) {
  border-color: var(--mb-link);
}

/* Активный режим рисования — оранжевый, как .tf-btn.active (единый акцент). */
.draw-btn.active {
  background: var(--mb-accent);
  color: #000;
  border-color: var(--mb-accent);
}

.draw-btn:disabled {
  opacity: 0.4;
  cursor: default;
}

/* Палитра цвета прямоугольника — видима в режиме rect / при выделении. */
.rect-palette {
  display: inline-flex;
  gap: 4px;
  align-items: center;
}

.rect-color-btn {
  appearance: none;
  width: 18px;
  height: 18px;
  padding: 0;
  border: 2px solid transparent;
  border-radius: 50%;
  cursor: pointer;
}

.rect-color-btn.active {
  border-color: var(--mb-text);
}

.draw-hint {
  font-size: 10px;
  color: var(--mb-hint);
  margin-left: 4px;
}

/* Canvas-overlay прямоугольников — поверх свечей внутри .chart-wrap. pointer-
   events переключает JS: ловит мышь только в режиме rect (иначе pan графика).
   ⛔ Размер задаём ЯВНО (calc), НЕ width/height:auto: <canvas> — заменяемый
   элемент, при width:auto его дисплейный размер следует за intrinsic-атрибутом
   .width. renderRects пишет overlay.width = clientWidth × devicePixelRatio, и при
   dpr>1 (мобильный Telegram) это рождает обратную связь clientWidth→width→
   clientWidth → canvas лавинно растёт за лимит ~16384px → белый экран. Явный
   размер фиксирует clientWidth независимо от атрибута и рвёт цикл. */
.rect-overlay {
  position: absolute;
  top: 8px;
  left: 8px;
  width: calc(100% - 16px); /* 8px паддинг .chart-wrap слева+справа */
  height: calc(100% - 16px);
  /* ⛔ z-index ОБЯЗАТЕЛЕН: canvas'ы Lightweight Charts позиционированы с
     z-index:1/2, а overlay с z-index:auto уходит ПОД них (числовой z-index
     бьёт DOM-порядок). Тогда свечи и панятся вместо рисования (overlay не
     ловит drag), и уже нарисованные прямоугольники прячутся за свечами.
     Монолит Latvia держал z-index:5 — при cutover на модули потеряли. */
  z-index: 5;
}

.chart-status {
  margin-top: 6px;
  min-height: 1em;
}

/* Freshness-отметка «изм. ЧЧ:ММ:СС МСК» — момент реального изменения свежей
   свечи (см. slot.js). Тонкая приглушённая строка прямо под графиком. */
/* Заголовок графика = название валютной пары: жирный белый (запрос юзера
   2026-06-09). Селектор .card h3.chart-title перебивает .card h3 по специфичности. */
.card h3.chart-title {
  font-weight: 700;
  color: #fff;
  text-transform: none;
  letter-spacing: normal;
}

.chart-updated {
  margin-top: 4px;
  font-size: 11px;
  color: var(--mb-hint, #6b7280);
}
.chart-updated[hidden] {
  display: none;
}

/* #4b: инфо-строка под графиком — N входов · лоты | ср.цена | P&L | пипсы.
   Порт chart-entry витрины Latvia. Спаны разделяем вертикальной чертой. */
.chart-entry {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 6px 10px;
  margin-top: 8px;
  font-size: 0.8rem;
  color: var(--mb-muted, #94a3b8);
}
.chart-entry[hidden] {
  display: none;
}
.chart-entry > span:not(:last-child)::after {
  content: "|";
  margin-left: 10px;
  opacity: 0.4;
}
.chart-entry .pos,
.chart-entry .neg {
  font-weight: 600;
}

/* #3: панель кнопок сделки под инфо-строкой (BUY/SELL в направлении мастера +
   «Ещё» + «Закрыть мои»). Порт chart-trade-bar витрины Latvia. */
.chart-trade-bar {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin-top: 8px;
}
.chart-trade-bar[hidden] {
  display: none;
}
.trade-btn {
  flex: 1 1 auto;
  min-width: 120px;
  padding: 10px 16px;
  border: none;
  border-radius: var(--mb-radius);
  font-size: 0.9rem;
  font-weight: 700;
  color: #fff;
  cursor: pointer;
}
.trade-btn:disabled {
  opacity: 0.55;
  cursor: default;
}
.trade-btn.btn-buy {
  background: var(--mb-pos, #22c55e);
}
.trade-btn.btn-sell {
  background: var(--mb-neg, #ef4444);
}
.trade-btn.btn-close-mine {
  background: var(--mb-border, #374151);
  color: var(--mb-text, #e2e8f0);
}
/* #3 Подсветка кнопки в сторону ТЕКУЩЕЙ сделки мастера («горит») */
.trade-btn.is-master-dir {
  outline: 2px solid #fbbf24;
  outline-offset: 1px;
  box-shadow: 0 0 10px 2px rgba(251, 191, 36, 0.7);
}
/* #3 Поле объёма лота (пусто = авто по балансу) */
.lot-input {
  flex: 0 0 84px;
  min-width: 64px;
  padding: 10px 8px;
  border: 1px solid var(--mb-border, #374151);
  border-radius: var(--mb-radius);
  background: var(--mb-bg, #0f172a);
  color: var(--mb-text, #e2e8f0);
  font-size: 0.9rem;
  text-align: center;
}
.lot-input::placeholder {
  color: var(--mb-muted, #94a3b8);
}
.lot-input:disabled {
  opacity: 0.55;
}

/* Currency grid — живые котировки мастера (B4, порт витрины Latvia) */
.currency-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(110px, 1fr));
  gap: var(--mb-gap);
}

.currency-grid .no-quotes {
  grid-column: 1 / -1;
}

.currency-card {
  background: var(--mb-panel);
  border-radius: var(--mb-radius);
  border: 1px solid var(--mb-border);
  padding: 10px;
  min-width: 0;
  overflow: hidden;
}

/* U2: кликабельная карточка валюты → открыть график инструмента. */
.currency-card.clickable {
  cursor: pointer;
}
.currency-card.clickable:hover {
  border-color: var(--mb-link);
}
.currency-card.clickable:focus-visible {
  outline: 2px solid var(--mb-link);
}

/* U5: процент к baseline в карточке P&L за периоды (серый, мельче — как витрина). */
.period-pnl-pct {
  color: var(--mb-hint);
  font-size: 0.85em;
}

/* U6: «обновлено HH:MM» в хедере — мелкий приглушённый текст справа от заголовка. */
.hdr-updated {
  font-size: 11px;
  color: var(--mb-hint);
  margin-left: auto;
}

.currency-name {
  font-size: 12px;
  font-weight: 700;
  color: var(--mb-text);
}

.currency-price {
  font-size: 13px;
  font-weight: 600;
  margin-top: 4px;
  font-family: var(--mb-mono);
  color: var(--mb-text);
}

.currency-meta {
  display: flex;
  justify-content: space-between;
  gap: 6px;
  margin-top: 6px;
  font-size: 10px;
  color: var(--mb-muted);
}

/* Currency-grid с позициями (G5, slot-view): активная карточка + pos-info/pos-line */
.currency-card.active {
  border-color: var(--mb-accent);
  background: #1f1a0f; /* тёмно-янтарный фон активной карточки (как монолит) */
}

.currency-card.active .currency-name {
  color: var(--mb-accent);
}

.currency-card .pos-info {
  display: flex;
  justify-content: space-between;
  gap: 6px;
  margin-top: 4px;
  font-size: 0.7rem;
  color: var(--mb-hint);
}

.currency-card.active .pos-info {
  border-top: 1px solid color-mix(in srgb, var(--mb-accent) 30%, transparent);
  padding-top: 4px;
}

.currency-card .pos-line {
  text-align: right;
  margin-top: 3px;
  font-size: 0.72rem;
  white-space: nowrap;
}

/* Волна 5: карточка позиции по паре ВНЕ прайс-фида (котировки нет вообще).
   ⚠️ Не путать с `.no-quotes` выше — то плашка «Нет котировок» на ВЕСЬ грид
   (ни фида, ни позиций), а это модификатор ОДНОЙ карточки.
   Сама карточка остаётся .active (позиция живая, деньги реальные), но на месте
   цены стоит текстовая пометка — гасим её до muted и снимаем моноширинный
   «цифровой» вид, чтобы её не читали как котировку. Двойное имя класса
   (.currency-card.no-quote) нужно, чтобы перебить .currency-price по
   специфичности. Кликабельной такая карточка не бывает — курсор/hover из
   .clickable к ней не применяются. */
.currency-card.no-quote .currency-price {
  color: var(--mb-muted);
  font-family: inherit;
  font-weight: 500;
  font-size: 12px;
}

.dir-dot,
.dir-arrow {
  flex: 0 0 auto;
}

.dir-buy {
  color: var(--mb-pos);
}

.dir-sell {
  color: var(--mb-neg);
}

.dir-mixed {
  color: var(--mb-warn);
}

.pos {
  color: var(--mb-pos);
}

.neg {
  color: var(--mb-neg);
}

.pos-pct {
  opacity: 0.8;
}

/* Closed trades — табы периодов + таблица (B3, порт closed-section Latvia) */
.closed-tabs {
  display: flex;
  gap: 4px;
  flex-wrap: wrap;
  margin-bottom: var(--mb-gap);
}

.ctab {
  appearance: none;
  background: var(--mb-control-bg);
  color: var(--mb-muted);
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 4px 12px;
  font: inherit;
  font-size: 13px;
  cursor: pointer;
}

.ctab:hover {
  color: var(--mb-text);
  border-color: #4b5563;
}

.ctab.ctab-active {
  background: #3b4261;
  color: var(--mb-text);
  border-color: #4b5563;
}

.closed-total td {
  font-weight: 600;
  border-top: 1px solid var(--mb-border);
}

/* Auth gate */
.gate {
  text-align: center;
  padding: 48px 16px;
  color: var(--mb-hint);
}

.gate h2 {
  color: var(--mb-text);
  margin-bottom: 8px;
}

/* Техническая строка с реальной ошибкой boot (чтобы «не загрузилось» не было
   немым — видно ЧТО упало; помогает диагностике без forged-auth). */
.gate-detail {
  margin-top: 10px;
  font-size: 12px;
  color: var(--mb-hint);
  opacity: 0.7;
  word-break: break-word;
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
}

/* Кнопка «Перезагрузить» на gate-экране (фолбэк ошибки boot, issue #2). */
.gate-retry {
  appearance: none;
  margin-top: 16px;
  background: var(--mb-control-bg);
  color: var(--mb-text);
  border: 1px solid var(--mb-control-border);
  border-radius: var(--mb-radius);
  padding: 8px 18px;
  font-size: 14px;
  cursor: pointer;
}

/* ── G6 popout ──────────────────────────────────────────────────────────────
   Кнопка ↗ в панели графика + раскладка отдельного окна popout.html. */
.chart-popout-btn {
  appearance: none;
  background: var(--mb-control-bg);
  color: var(--mb-hint);
  border: 1px solid var(--mb-control-border);
  border-radius: var(--mb-radius);
  padding: 4px 10px;
  font: inherit;
  font-size: 14px;
  line-height: 1;
  cursor: pointer;
}

.chart-popout-btn:hover {
  color: var(--mb-text);
  border-color: var(--mb-link);
}

/* Документ popout: ОДИН график инструмента на всё окно (charts.js сам ресайзит
   чарт по window resize, читая clientHeight — поэтому достаточно CSS-раскладки). */
.popout-body {
  margin: 0;
}

.popout-root {
  display: flex;
  flex-direction: column;
  min-height: 100vh;
  padding: var(--mb-pad);
  box-sizing: border-box;
}

.popout-chart {
  display: flex;
  flex: 1;
  min-height: 0; /* даёт вложенному flex-child право сжиматься (иначе overflow) */
}

.popout-chart .instrument-chart {
  display: flex;
  flex-direction: column;
  flex: 1;
  margin: 0;
  min-height: 0;
}

/* Карточка графика в popout тянется на всё окно (не фикс. 240px, как в слоте). */
.popout-chart .chart-wrap {
  flex: 1;
  min-height: 320px;
}

.popout-chart .chart {
  height: 100%;
}

.popout-gate {
  margin: auto;
  text-align: center;
  color: var(--mb-hint);
}

.popout-gate h2 {
  margin: 0 0 8px;
  color: var(--mb-text);
}

/* Модалка-overlay графика (master_home) удалена: клик по карточке валюты теперь
   открывает график ОТДЕЛЬНОЙ вкладкой браузера (popout.html), а не overlay’ем
   внутри дашборда. Раскладка вкладки — в блоке .popout-* выше. */

/* --------------------------------------------------------------------------
   Плашка «слот на паузе» (обзорный экран).

   Слот на паузе не зеркалит новые сделки, но внешне неотличим от слота, по
   которому просто нет сделок. Инцидент 28.07.2026: пауза, забытая на резервной
   ноде, прожила неделю незамеченной и выстрелила при failover. Поэтому статус
   вынесен из kv-списка в заметную плашку + янтарная рамка карточки.
   -------------------------------------------------------------------------- */
.paused-badge {
  margin: 6px 0 8px;
  padding: 6px 10px;
  border-radius: var(--mb-radius);
  /* Фолбэк первым: WebView старого Android (Chrome <111) не знает color-mix и
     отбросил бы всю декларацию — плашка осталась бы без заливки. */
  background: rgba(245, 158, 11, 0.18);
  background: color-mix(in srgb, var(--mb-warn) 18%, transparent);
  border: 1px solid var(--mb-warn);
  color: var(--mb-warn);
  font-size: 0.85rem;
  font-weight: 600;
  line-height: 1.3;
}

.card.slot-paused {
  border-color: var(--mb-warn);
}

/* --------------------------------------------------------------------------
   Панель «Ожидают входа» (confirm-mode, tech-spec-pending-entries §6.4).

   Карточка = группа сделок мастера (символ+направление), по которой EA ждёт
   решения оператора. Главное на ней — одна строка «лучше/хуже мастера»: она
   должна читаться с расстояния вытянутой руки, потому что решение принимается
   за секунды, пока цена не уехала. Отсюда крупный кегль и цвет по знаку.
   -------------------------------------------------------------------------- */
/* Сама секция: янтарная рамка как у «слот на паузе» — это единственный блок
   витрины, который требует ДЕЙСТВИЯ прямо сейчас (пока оператор не решил, зеркала
   не открываются), и он обязан выделяться среди соседних информационных карточек. */
.pending-section {
  border-color: var(--mb-accent);
}

.pending-card {
  border: 1px solid var(--mb-border);
  border-radius: var(--mb-radius);
  padding: var(--mb-pad);
  margin-bottom: var(--mb-gap);
  background: var(--mb-panel);
}

.pending-card:last-child {
  margin-bottom: 0;
}

.pending-head {
  margin: 0 0 6px;
  font-size: 1rem;
  font-family: var(--mb-mono);
  color: var(--mb-text);
}

.pending-card p {
  margin: 2px 0;
  font-size: 0.85rem;
  line-height: 1.35;
}

/* Главная строка решения — крупнее остальных, цвет по знаку разницы. */
.pending-delta {
  margin: 6px 0 !important;
  font-size: 0.95rem;
  font-weight: 600;
}

.pending-better {
  color: var(--mb-pos);
}

.pending-worse {
  color: var(--mb-neg);
}

/* «Войдём по 32 из 40 сделок мастера»: список тикетов урезан сервером до
   ENTRY_MAX_CMD_TICKETS, т.е. откроется ПОДМНОЖЕСТВО группы. Оговорка янтарём,
   как помеха: она правит главную денежную цифру карточки вниз, и пропустить её
   оператор не должен. Появляется только при усечении — обычная карточка
   выглядит ровно как раньше. */
.pending-scope {
  color: var(--mb-warn);
}

/* Помеха EA: подтверждение оператора НЕ обходит риск-лимиты — причина обязана
   быть заметной, иначе неактивная кнопка «Войти» выглядит как баг витрины. */
.pending-block {
  color: var(--mb-warn);
  font-weight: 600;
}

.pending-card.pending-blocked {
  border-color: var(--mb-warn);
}

/* Наблюдение на ПАУЗЕ (tech-spec §8c): карточка — витрина, а не пульт. Рамку и
   цвета НЕ трогаем (их уже задал `.pending-blocked` — пауза это помеха), и уж
   тем более не трогаем главную строку «лучше/хуже мастера на N пунктов ≈ ±$X»:
   ради неё панель на паузе и показывают. Приглушаем ровно блок действий —
   он мёртвый, и глазу не за что там цепляться.

   ⛔ Никакого `display` (и вообще ничего, что перебило бы `[hidden]`): «Не
   входить» на паузе не рисуется вовсе, а строка порога прячется через
   `.pending-defer-row[hidden]` — правило выше живо только потому, что рядом нет
   авторского display. Та же мина, что у `.btn-icon`. */
.pending-card.pending-paused .pending-actions {
  opacity: 0.6;
}

/* Глобальный `.btn[disabled]` ставит `cursor: progress` — он про «идёт отправка»
   (кнопки гаснут на время запроса). На паузе неактивность ПОСТОЯННА, и «часики»
   врали бы, что что-то грузится. */
.pending-card.pending-paused .pending-actions .btn[disabled] {
  cursor: not-allowed;
}

.pending-card.pending-deferred {
  /* Фолбэк первым: WebView старого Android (Chrome <111) не знает color-mix. */
  border-color: #334155;
  border-color: var(--mb-control-border);
  opacity: 0.85;
}

/* Отложенная карточка добралась до заданного порога — ради этого момента её и
   откладывали, поэтому подсветка янтарём и полная непрозрачность. */
.pending-card.pending-hit {
  border-color: var(--mb-accent);
  background: rgba(245, 158, 11, 0.1);
  background: color-mix(in srgb, var(--mb-accent) 10%, var(--mb-panel));
  opacity: 1;
}

.pending-actions {
  margin-top: var(--mb-gap);
}

.pending-defer-row {
  margin-top: 6px;
}

/* ⛔ Строка порога — это `.field-row`, а `.field-row { display: flex }` (авторское
   правило) перебивает UA-правило `[hidden] { display: none }`. Без re-assert поле
   порога и кнопка «Готово» торчали бы под КАЖДОЙ карточкой всегда, хотя JS честно
   ставит `deferRow.hidden = true`, — и случайный тап по «Готово» отправил бы
   `defer`, молча заблокировав вход, который никто не собирался откладывать.
   Тот же приём, что у `.btn-icon[hidden]` выше (см. комментарий там). */
.pending-defer-row[hidden] {
  display: none;
}

.pending-threshold {
  max-width: 260px;
}

/* Плашка панели (расхождение intent↔EA, протухший снимок, пауза) — заметная,
   как «слот на паузе»: молчаливое расхождение уже стоило недели невидимой
   рассинхронизации (инцидент 28.07.2026).

   Базовый класс держит ГЕОМЕТРИЮ (отступы, скругление, кегль); цвет тревоги — в
   модификаторе `.pending-warn` ниже. Без него плашка выглядела бы обычной
   строкой абзаца. */
.pending-banner {
  margin: 0 0 var(--mb-gap);
  padding: 6px 10px;
  border-radius: var(--mb-radius);
  background: rgba(148, 163, 184, 0.12);
  background: color-mix(in srgb, var(--mb-hint) 12%, transparent);
  border: 1px solid var(--mb-border);
  color: var(--mb-text);
  font-size: 0.85rem;
  font-weight: 600;
  line-height: 1.3;
}

/* Модификатор «это предупреждение» — янтарь тёмной темы, как у `.pending-block`
   и рамки `.pending-card.pending-blocked`. Его ставит `banner(text,
   "pending-warn")` на ВСЕ три тревожные плашки (расхождение intent↔EA,
   протухший снимок EA, пауза слота), и без правила они рисовались нейтрально —
   ровно те сообщения, которые обязаны бросаться в глаза.
   Одиночный класс, идёт ПОСЛЕ `.pending-banner` → перебивает базовые цвета при
   равной специфичности. */
.pending-warn {
  background: rgba(245, 158, 11, 0.18);
  background: color-mix(in srgb, var(--mb-warn) 18%, transparent);
  border-color: var(--mb-warn);
  color: var(--mb-warn);
}

/* Ответ EA на подтверждённый вход (tech-spec §8b) — строка ВНУТРИ карточки.
   Это то, ради чего оператор жал кнопку, поэтому заметнее обычных строк: до
   волны 2 карточка навсегда застывала на «ждём ответа EA», и реальный отказ EA
   (гонка с закрытием мастера, реквот, лимит на самом тике) был невидим.

   Селектор из ДВУХ классов намеренно: `.pending-card p` выше задаёт margin и
   font-size со специфичностью (0,1,1) и перебил бы одиночный класс (0,1,0) —
   ровно та мина, из-за которой соседней `.pending-delta` пришлось ставить
   `!important` на margin. Здесь она снимается специфичностью, без `!important`. */
.pending-card .pending-ack {
  margin: 6px 0;
  font-size: 0.9rem;
  font-weight: 600;
}

/* «Ждём ответа EA» — приглушённый (--mb-hint, как у обычных muted-строк), а не
   --mb-muted: это статус, который читают, а не подпись-заголовок. */
.pending-ack-pending {
  color: var(--mb-hint);
}

.pending-ack-ok {
  color: var(--mb-pos);
}

/* Отказ/таймаут — янтарём, как помеха: это НЕ «всё хорошо», но и не авария
   витрины; оператору нужно перечитать причину и решить заново. */
.pending-ack-fail {
  color: var(--mb-warn);
}

/* Эпилог ушедшей карточки: «мастер закрыл, пока вы думали» (tech-spec §8a).
   Приглушённый пунктирный блок — решения не требует, но и молча исчезнуть не
   должен: это единственное место, где видно, сколько стоило НЕ входить.
   Гаснет сам, когда сервер перестаёт отдавать его по TTL (фронт таймеров не
   заводит — вторая правда о TTL разъехалась бы с серверной).

   ⛔ `display` здесь НАМЕРЕННО не задан. Авторское правило `display:*` перебивает
   UA-правило `[hidden] { display: none }` (равная специфичность, автор идёт
   позже) — этой миной уже стреляли `.btn-icon` и `.pending-defer-row` выше.
   Если блоку когда-нибудь понадобится flex/grid — обязателен re-assert
   `.pending-departed[hidden] { display: none; }`. */
.pending-departed {
  border: 1px dashed var(--mb-border);
  border-radius: var(--mb-radius);
  padding: 8px var(--mb-pad);
  margin-bottom: var(--mb-gap);
  opacity: 0.75;
}

.pending-departed:last-child {
  margin-bottom: 0;
}

.pending-departed p {
  margin: 2px 0;
  font-size: 0.85rem;
  line-height: 1.35;
}

.pending-departed-head {
  font-family: var(--mb-mono);
  color: var(--mb-muted);
}

/* Сам итог — единственная строка эпилога, которую читают. */
.pending-departed-text {
  font-weight: 600;
  color: var(--mb-text);
}
