/* Шрифты (Montserrat + Fira Mono, самохост, OFL). Пути assets/fonts/ — для веба/кабинета. */
@font-face{font-family:'Fira Mono';font-style:normal;font-weight:400;font-display:swap;src:url('assets/fonts/firamono-400-cyrillic.woff2') format('woff2');unicode-range:U+0301, U+0400-045F, U+0490-0491, U+04B0-04B1, U+2116;}
@font-face{font-family:'Fira Mono';font-style:normal;font-weight:400;font-display:swap;src:url('assets/fonts/firamono-400-latin.woff2') format('woff2');unicode-range:U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;}
@font-face{font-family:'Montserrat';font-style:normal;font-weight:400;font-display:swap;src:url('assets/fonts/montserrat-400-cyrillic.woff2') format('woff2');unicode-range:U+0301, U+0400-045F, U+0490-0491, U+04B0-04B1, U+2116;}
@font-face{font-family:'Montserrat';font-style:normal;font-weight:400;font-display:swap;src:url('assets/fonts/montserrat-400-latin.woff2') format('woff2');unicode-range:U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;}
@font-face{font-family:'Montserrat';font-style:normal;font-weight:600;font-display:swap;src:url('assets/fonts/montserrat-600-cyrillic.woff2') format('woff2');unicode-range:U+0301, U+0400-045F, U+0490-0491, U+04B0-04B1, U+2116;}
@font-face{font-family:'Montserrat';font-style:normal;font-weight:600;font-display:swap;src:url('assets/fonts/montserrat-600-latin.woff2') format('woff2');unicode-range:U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;}
/* 700 — НАСТОЯЩЕЕ полужирное. До 03-08 возились только 400 и 600, а разметка просит 700/800/900
   в 38 местах (заголовки лендинга, справки, политики, 404) — браузер брал 600 и ЭМУЛИРОВАЛ жир,
   размазывая контуры: это самый крупный текст на странице, и выглядел он хуже всего остального.
   Вес 500 сняли этой же ночью как мёртвый (60 КБ), 700 стоит 30 КБ — суммарно страница даже легче,
   чем была, но заголовки рисуются настоящим начертанием. 800/900 матчатся на 700 по правилам CSS,
   поэтому разметку трогать не нужно. */
@font-face{font-family:'Montserrat';font-style:normal;font-weight:700;font-display:swap;src:url('assets/fonts/montserrat-700-cyrillic.woff2') format('woff2');unicode-range:U+0301, U+0400-045F, U+0490-0491, U+04B0-04B1, U+2116;}
@font-face{font-family:'Montserrat';font-style:normal;font-weight:700;font-display:swap;src:url('assets/fonts/montserrat-700-latin.woff2') format('woff2');unicode-range:U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;}

/* ============================================================================
   МАЯК VPN — ДИЗАЙН-СИСТЕМА (единая для админки, лендинга и кабинета).
   Токены и паттерны сняты с дизайн-системы Remnawave-панели (Mantine-тема, theme.ts):
   тёмная «GitHub-dark» палитра, шрифт Montserrat + Fira Mono, акцент cyan, радиус 8px.
   Полное описание паттернов и как применять — docs/DESIGN-SYSTEM.md.
   Подключать ПЕРВЫМ (до частных стилей страницы). Не редактировать точечно под одну страницу —
   правки токенов здесь распространяются на весь проект.
   ============================================================================ */

:root {
  /* ---- ПАЛИТРА: тёмная «GitHub-dark» (Remnawave dark[0..9]) ---- */
  --dark-0:#c9d1d9; --dark-1:#b1bac4; --dark-2:#8b949e; --dark-3:#6e7681; --dark-4:#484f58;
  --dark-5:#30363d; --dark-6:#21262d; --dark-7:#161b22; --dark-8:#0d1117; --dark-9:#010409;

  /* ---- РОЛИ (семантика) ---- */
  --ds-bg:var(--dark-7);            /* фон страницы = body (Mantine --mantine-color-body=dark-7 #161b22, сверено с panel.demidov.info) */
  --ds-bg-deep:var(--dark-8);       /* dark-8 #0d1117 — старт градиента сайдбара / «глубокий» фон */
  --ds-surface:var(--dark-6);       /* сплошные контролы (инпуты, subtle-кнопки) */
  --ds-surface-2:var(--dark-8);     /* «утопленный» фон полей */
  --ds-border:var(--dark-5);        /* бордеры */
  --ds-border-soft:rgba(255,255,255,.08);
  --ds-text:var(--dark-0);          /* основной текст */
  --ds-dimmed:var(--dark-2);        /* приглушённый текст/подписи */

  /* ---- АКЦЕНТ: cyan (Mantine cyan, primaryShade 8) ---- */
  --cyan-4:#3bc9db; --cyan-5:#22b8cf; --cyan-6:#15aabf; --cyan-7:#1098ad; --cyan-8:#0c8599; --cyan-9:#0b7285;
  /* Заливка главной кнопки — cyan-9, а не унаследованный от Remnawave cyan-8: белый текст на cyan-8
     даёт 4.35 при пороге AA 4.5 (замер 02-08), на cyan-9 — 5.59. Ховер НЕ из шкалы: cyan-7 (3.43) и
     cyan-8 (4.35) оба проваливают порог, поэтому взят промежуточный тон 4.70 — кнопка при наведении
     по-прежнему светлеет, но текст на ней читается. Значение общее для кабинета, /tools/ip и панели
     (там зеркало в internal/admin/static/style.css) — менять только во всех сразу. */
  --ds-primary:var(--cyan-9); --ds-primary-hover:#0d7f92; --ds-primary-ink:#fff;

  /* ---- СТАТУСЫ (для нод/линий/бейджей): tailwind-оттенки как в Remnawave ---- */
  --st-alive:#2dd4bf;   /* бирюза — живо/онлайн */
  --st-error:#ef4444;   /* красный — ошибка/недоступно */
  --st-off:#6b7280;     /* серый — выключено/в пуле */
  --st-warn:#f59e0b;    /* янтарь — переходное */
  --ok:#40c057; --bad:#fa5252; --warn:#d29922;

  /* ---- ТИПОГРАФИКА ---- */
  --font:'Montserrat', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif;
  --font-mono:'Fira Mono', 'Fira Code', ui-monospace, SFMono-Regular, Menlo, monospace;
  --fs-xs:12px; --fs-sm:14px; --fs-md:16px; --fs-lg:18px; --fs-xl:20px;
  --lh:1.55; --fw-heading:600;

  /* ---- РАДИУСЫ (Mantine, default md) ---- */
  --r-xs:2px; --r-sm:4px; --r-md:8px; --r-lg:16px; --r-xl:32px; --r:var(--r-md);

  /* ---- ОТСТУПЫ (Mantine spacing) ---- */
  --sp-xs:10px; --sp-sm:12px; --sp-md:16px; --sp-lg:20px; --sp-xl:32px;

  /* ---- ТЕНИ ---- */
  --sh-sm:0 1px 3px rgba(0,0,0,.3); --sh-md:0 4px 12px rgba(0,0,0,.35); --sh-lg:0 8px 24px rgba(0,0,0,.4);
  --dur:.2s;
}

/* ============================ БАЗА ============================ */
.ds, body.ds { background:var(--ds-bg); color:var(--ds-text);
  font-family:var(--font); font-size:var(--fs-md); line-height:var(--lh); }
.ds h1,.ds h2,.ds h3,.ds h4 { font-weight:var(--fw-heading); color:var(--ds-text); }
.ds a { color:var(--cyan-5); text-decoration:none; }
.ds a:hover { text-decoration:underline; }
.ds .mono, .ds code, .ds kbd { font-family:var(--font-mono); }
.ds .dimmed { color:var(--ds-dimmed); }

/* ============================ КАРТОЧКА ============================ */
/* Паттерн Remnawave Card: полупрозрачная поверхность + мягкий бордер, радиус md, fade-in. */
.ds-card { background:rgba(255,255,255,.02); border:1px solid var(--ds-border-soft);
  border-radius:var(--r-md); padding:var(--sp-md); animation:ds-fade var(--dur) linear both; }
.ds-card--solid { background:var(--ds-surface); border-color:var(--ds-border); }
@keyframes ds-fade { from{opacity:0} to{opacity:1} }

/* ============================ БЕЙДЖ ============================ */
/* Дефолт Remnawave: radius md, variant outline. Плюс light-варианты по семантике. */
.ds-badge { display:inline-flex; align-items:center; gap:5px; padding:3px 9px; border-radius:var(--r-md);
  font-size:var(--fs-xs); font-weight:600; line-height:1.4; border:1px solid var(--ds-border); color:var(--ds-dimmed); }
.ds-badge--primary { border-color:var(--cyan-7); color:var(--cyan-4); background:rgba(21,170,191,.10); }
.ds-badge--alive   { border-color:rgba(45,212,191,.4); color:#5eead4; background:rgba(45,212,191,.12); }
.ds-badge--error   { border-color:rgba(239,68,68,.4); color:#fca5a5; background:rgba(239,68,68,.12); }
.ds-badge--off     { border-color:var(--ds-border); color:var(--ds-dimmed); background:rgba(255,255,255,.05); }

/* ============================ КНОПКА ============================ */
/* Дефолт Remnawave: radius md, variant light, плавный transition. */
.ds-btn { display:inline-flex; align-items:center; justify-content:center; gap:6px; cursor:pointer;
  padding:8px 16px; border-radius:var(--r-md); font-family:var(--font); font-size:var(--fs-sm); font-weight:600;
  border:1px solid transparent; transition:all var(--dur) ease; text-decoration:none; }
.ds-btn--primary { background:var(--ds-primary); color:var(--ds-primary-ink); }
.ds-btn--primary:hover { background:var(--ds-primary-hover); }
.ds-btn--light { background:rgba(21,170,191,.12); color:var(--cyan-4); }
.ds-btn--light:hover { background:rgba(21,170,191,.20); }
.ds-btn--outline { background:transparent; border-color:var(--ds-border); color:var(--ds-text); }
.ds-btn--outline:hover { border-color:var(--cyan-7); }

/* ============================ ПОЛЕ ВВОДА ============================ */
.ds-input, .ds-select { width:100%; padding:9px 12px; border-radius:var(--r-md);
  background:var(--ds-surface-2); border:1px solid var(--ds-border); color:var(--ds-text);
  font-family:var(--font); font-size:var(--fs-sm); transition:border-color var(--dur); }
.ds-input:focus, .ds-select:focus { outline:none; border-color:var(--cyan-7); }
/* Было font-weight:500 — начертание 500 нигде в web/ и cabinet/ больше не используется (проверено
   03-08: ни .ds-label, ни .ds-table th не встречались в разметке ни разу), а его файлы (2×~30 КБ,
   latin+cyrillic) всё равно скачивались на каждый первый экран кабинета, потому что @font-face
   матчится по CSS независимо от того, применяется ли класс — и конкурировали за throttled-полосу
   с логотипом (LCP-элементом входа/регистрации): подмена ответа на 500-й вес логотипа замером
   PerformanceObserver дала LCP 2288мс против 1676мс без файлов веса 500 (throttled 1.6 Мбит/с,
   150мс, iPhone 13). 600 — не 400: это подпись/заголовок таблицы, ей нужен вес, а не «потише». */
.ds-label { display:block; font-size:var(--fs-xs); font-weight:600; color:var(--ds-dimmed); margin-bottom:4px; }

/* ============================ ТАБЛИЦА ============================ */
.ds-table { width:100%; border-collapse:collapse; font-size:var(--fs-sm); }
.ds-table th { text-align:left; padding:10px 12px; color:var(--ds-dimmed); font-weight:600;
  font-size:var(--fs-xs); text-transform:uppercase; letter-spacing:.03em; border-bottom:1px solid var(--ds-border); }
.ds-table td { padding:11px 12px; border-bottom:1px solid var(--ds-border-soft); }
.ds-table tbody tr:hover { background:rgba(255,255,255,.03); }

/* ============================ СТАТУС-ИНДИКАТОР ============================ */
/* Точка/иконка со свечением: 🟢 alive / 🔴 error / ⚪️ off. Для карточек нод/линий. */
.ds-dot { width:10px; height:10px; border-radius:50%; display:inline-block; background:var(--st-off); }
.ds-dot--alive { background:var(--st-alive); box-shadow:0 0 0 3px rgba(45,212,191,.18),0 0 10px 1px rgba(45,212,191,.5); }
.ds-dot--error { background:var(--st-error); box-shadow:0 0 0 3px rgba(239,68,68,.18),0 0 10px 1px rgba(239,68,68,.5); }

/* Карточка-строка со статус-подсветкой градиентом (паттерн Remnawave NodeCard). */
.ds-row { border-radius:var(--r-md); padding:12px 16px; border:1px solid var(--ds-border);
  background:linear-gradient(135deg, rgba(107,114,128,.10) 0%, var(--dark-7) 100%); transition:border-color var(--dur); }
.ds-row--alive { border-color:rgba(45,212,191,.30); background:linear-gradient(135deg, rgba(45,212,191,.15) 0%, var(--dark-7) 100%); }
.ds-row--error { border-color:rgba(239,68,68,.30); background:linear-gradient(135deg, rgba(239,68,68,.15) 0%, var(--dark-7) 100%); }
.ds-row--off   { border-color:rgba(107,114,128,.30); background:linear-gradient(135deg, rgba(107,114,128,.15) 0%, var(--dark-7) 100%); }
.ds-row:hover { border-color:var(--cyan-7); }

/* ============================ СКРОЛЛБАР ============================ */
.ds ::-webkit-scrollbar { width:8px; height:8px; }
.ds ::-webkit-scrollbar-thumb { background:var(--dark-5); border-radius:4px; }
.ds ::-webkit-scrollbar-track { background:transparent; }
