@import url('https://fonts.googleapis.com/css2?family=Cinzel:wght@600;700&family=EB+Garamond:wght@400;500;600;700&family=Pirata+One&family=UnifrakturMaguntia&family=IM+Fell+English:ital@0;1&display=swap');
  /* =====================================================================
     СЛОВАРЬ  —  этап 0 приведения визуала к единообразию.

     Два слоя, и путать их нельзя.

     1) ПАЛИТРА  --c-*
        Сырьё: имена для красок, которые встречаются в игре не по одному
        разу. Значения здесь НИКОГДА не переопределяются. --c-gold-bright
        золотой на любом экране, в любой панели, всегда.

     2) РОЛИ  --text-* / --surface-* / --fill-* / --border*
        Кто чем работает на КОНКРЕТНОЙ поверхности. Роли ссылаются на
        палитру и МОГУТ переопределяться внутри поверхности. Именно так
        устроен .pm-card: он подменяет у себя --text-primary на золото,
        и всё содержимое, которое обращается по роли, перекрашивается
        само, без единой правки.

     🔴 Правило, из которого весь этот словарь вырос.
        Цвет, вписанный в разметку числом (style="color:#3a2410"), мимо
        ролей НЕ перекрашивается. Ровно поэтому таблица лидеров осталась
        пергаментной, когда карточка попапа стала тёмным стеклом: ник
        игрока получил контраст 1.18:1 к своему фону. А таблица
        Statistics в 08-campaign.js написана на var(--text-muted) и
        перекрасилась сама.

        Вывод для любой будущей правки: инлайновый #hex в разметке —
        технический долг, а не решение. Новый цвет заводится здесь.

     Что сюда СОЗНАТЕЛЬНО не попало: шкала кеглей шрифта. Размеры на
     боевом экране заданы в координатах холста 1700x760 и будут заново
     выведены по «линейке холста» через режим ?layout=1. Заводить шкалу
     сейчас — значит делать эту работу дважды.
     ===================================================================== */
  :root{
    /* ---------- 1. ПАЛИТРА ---------- */

    /* золото и пергаментный текст — язык нового тёмного стекла */
    --c-gold-bright:#f3e2bd;   /* основной светлый текст на тёмном */
    --c-gold:#d9b45c;          /* рамки, заголовки таблиц, акцент */
    --c-gold-hot:#ffd54a;      /* самое яркое: FIGHT, статус, награды */
    --c-gold-dim:#c9b795;      /* подписи и второстепенное на тёмном */
    --c-gold-deep:#c98a2e;     /* выделение зоны, предупреждение */

    /* дерево и кожа — тёмные тёплые поверхности */
    --c-wood-900:#0a0806;      /* фон боевого HUD */
    --c-wood-800:#221507;      /* низ градиента плашек */
    --c-wood-700:#241708;      /* низ градиента панели управления */
    --c-wood-600:#3a2410;      /* верх градиента плашек; тёмный текст */
    --c-wood-550:#3a2a16;      /* верх градиента панели управления */
    --c-wood-500:#3a2a14;      /* рамка пергаментной карточки */
    --c-ink:#060504;           /* затемнение сцены боя */

    /* пергамент — светлые поверхности старого языка (My Warrior, .screen) */
    --c-parch-050:#faf7f0;
    --c-parch-100:#efeadd;
    --c-parch-200:#ecdcb0;
    --c-parch-300:#e6d4a8;
    --c-parch-400:#e0cd9c;
    --c-parch-500:#d8c088;
    --c-parch-line:#d8d2c0;    /* разделители на светлом */

    /* геральдика — цвета действий и состояний */
    --c-blood:#7a3030;         /* главное действие, акцент бренда */
    --c-blood-lit:#8a3030;     /* тот же красный, чуть светлее */
    --c-blood-700:#5a1c1c;
    --c-blood-800:#4a1c1c;
    --c-blood-900:#3a1010;
    --c-danger:#c23b3b;
    --c-danger-text:#b33030;
    --c-danger-lit:#e0716f;    /* красный, читаемый на тёмном стекле (5.5:1) */
    --c-success:#4c8c4c;
    --c-success-text:#3f7a3f;
    --c-success-lit:#7fbf5f;   /* зелёный, читаемый на тёмном стекле (7.8:1) */

    /* нейтральные */
    --c-white:#ffffff;
    --c-ash:#8a8578;           /* приглушённый текст на светлом */
    --c-slate:#5f5a4e;         /* вторичный текст на светлом */
    --c-graphite:#221f1a;      /* основной текст на светлом */
    --c-blush:#f1dede;         /* светлая подложка акцента */

    /* ---------- 2. РОЛИ (светлая поверхность — состояние по умолчанию) ----------
       Переопределяются внутри .pm-card и других тёмных поверхностей. */
    --surface-0:var(--c-parch-100);
    --surface-1:var(--c-parch-050);
    --text-primary:var(--c-graphite);
    --text-secondary:var(--c-slate);
    --text-muted:var(--c-ash);
    --border:var(--c-parch-line);
    --border-accent:var(--c-blood);
    --bg-accent:var(--c-blush);
    --text-accent:var(--c-blood);
    --fill-accent:var(--c-blood);
    --on-accent:var(--c-white);
    --fill-success:var(--c-success);
    --fill-warning:var(--c-gold-deep);
    --fill-danger:var(--c-danger);
    --text-danger:var(--c-danger-text);
    --text-success:var(--c-success-text);

    /* ---------- 3. СТЕКЛО ----------
       Прозрачности тёмного стекла собраны в одном месте: сейчас их в коде
       четыре разных (0.26 / 0.5 / 0.62 / 0.86), и самая прозрачная стоит
       под самым важным текстом — именем бойца и полосой здоровья.
       Менять эти числа — этап 2, здесь они только названы. */
    --glass-thin:rgba(10,8,6,0.26);    /* .nh-card — карточка бойца */
    --glass:rgba(10,8,6,0.5);          /* панели DEF и ударов */
    --glass-card:rgba(10,8,6,0.62);    /* попапы .pm-card */
    --glass-solid:rgba(10,8,6,0.86);   /* пост-боевая панель */
    --glass-line:rgba(217,180,92,0.32);  /* золотая рамка стекла */
    --glass-line-lit:rgba(217,180,92,0.45);
    --glass-btn:rgba(0,0,0,0.35);        /* фон кнопки на стекле */
    --glass-btn-hover:rgba(217,180,92,0.18);
    --glass-field:rgba(0,0,0,0.3);       /* фон поля ввода на стекле */

    /* затемнение под попапами. Сейчас в коде 4 значения (0.4/0.5/0.55/0.6) —
       сведение к одному это этап 3, здесь только имена. */
    --scrim:rgba(0,0,0,0.4);
    --scrim-strong:rgba(0,0,0,0.55);

    /* ---------- 4. ГЕОМЕТРИЯ ----------
       Ступени выбраны так, чтобы совпасть с уже существующими значениями:
       подстановка ничего не двигает. Всё, что осталось после этого этапа
       написано числом (8.5px, 11.3px, 7.5px) — выброс, который ждёт
       решения на этапе 3, и виден именно тем, что он не назван. */
    --r-xs:3px;
    --r-sm:5px;
    --r-md:6px;
    --r-lg:8px;
    --r-xl:10px;
    --r-pill:20px;
    --r-round:50%;

    --sp-1:4px;
    --sp-2:6px;
    --sp-3:8px;
    --sp-4:10px;
    --sp-5:14px;
    --sp-6:20px;

    /* ---------- 5. ШРИФТЫ ---------- */
    --font-sans: 'EB Garamond', Georgia, 'Times New Roman', serif;
    --font-display: 'Cinzel', Georgia, serif;
    --font-title: 'Pirata One', 'Cinzel', serif;
  }
  .top-sticky-bar{ width:100%; }
  @media (max-width: 800px){
    .top-sticky-bar{ }
  }
  body{ margin:0; padding:1.2rem; background:var(--surface-0); color:var(--text-primary);
        font-family:var(--font-sans); display:flex; flex-wrap:wrap; justify-content:center; }
  .wrap{ width:100%; max-width:860px; }
  @media (min-width:900px){ .wrap{ max-width:min(94vw, 1180px); } }
  @media (min-height:700px) and (min-width:900px){ .wrap{ max-width:min(90vw, 1100px); } }
  button{ font-family:var(--font-sans); background:var(--surface-1); color:var(--text-primary);
          border:0.5px solid var(--border); border-radius:var(--r-sm); cursor:pointer; }
  input, select, textarea{ font-family:var(--font-sans); }
  button:hover{ background:var(--surface-0); }
  button:disabled{ opacity:0.4; cursor:default; }
  .screen{ background:
      radial-gradient(ellipse at 25% 10%, rgba(255,250,230,0.45) 0%, rgba(255,250,230,0) 45%),
      radial-gradient(ellipse at 85% 95%, rgba(120,80,30,0.22) 0%, rgba(120,80,30,0) 50%),
      linear-gradient(135deg, var(--c-parch-200) 0%, var(--c-parch-400) 42%, var(--c-parch-500) 65%, var(--c-parch-300) 100%);
      border:0.5px solid var(--border); border-radius:14px;
           padding:14px; display:flex; align-items:flex-start; gap:14px; position:relative; overflow:hidden; }
  .control-panel{
    background:linear-gradient(180deg,var(--c-wood-550),var(--c-wood-700)); border:1px solid #1a1006;
    border-radius:var(--r-xl); padding:10px;
    box-shadow:0 2px 10px rgba(0,0,0,0.35), inset 0 0 0 1px rgba(255,245,210,0.08);
  }
  .fighter-name-plate{
    background:rgba(20,14,8,0.42); border-radius:var(--r-sm); padding:2px 8px;
    text-shadow:0 1px 2px rgba(0,0,0,0.8);
  }
  .fighter-name-plate #p1NameLabel, .fighter-name-plate #p2NameLabel{ color:var(--c-gold-bright); }
  .fighter-name-plate span[id$="AtkLabel"]{ color:#d8c9a0 !important; }

  @media (max-width: 800px){
    .fighter-name-plate{
      max-width:47% !important;
      flex-wrap:wrap !important; white-space:normal !important; gap:2px !important;
      font-size:10px !important; padding:2px 5px !important; justify-content:center !important;
    }
    #p1NameBtn.fighter-name-plate{ left:6px !important; }
    #p2NameBtn.fighter-name-plate{ right:6px !important; }
    .fighter-name-plate span[id$="NameLabel"]{
      max-width:100%; min-width:0; flex:0 1 auto;
      overflow:hidden; text-overflow:ellipsis; white-space:nowrap;
    }
  }
  .choice-row button{
    width:38px !important; height:38px !important;
    background-size:cover; background-position:center; background-repeat:no-repeat;
    border-radius:var(--r-round); border:2px solid rgba(216,210,192,0.9); background-color:var(--surface-1);
    transition:border-color .15s ease, box-shadow .15s ease, transform .1s ease;
  }
  .choice-row{ gap:8px !important; }
  .choice-row button svg{ display:none; }
  .choice-row button[data-zone="head"]{ background-image:url('../img/zone_head.png'); }
  .choice-row button[data-zone="body"]{ background-image:url('../img/zone_body.png'); }
  .choice-row button[data-zone="legs"]{ background-image:url('../img/zone_legs.png'); }
  .choice-row button.zone-btn-selected{
    border-color:var(--c-gold-deep); box-shadow:0 0 0 2px rgba(201,138,46,0.45), 0 0 8px rgba(201,138,46,0.7);
    transform:scale(1.08);
  }
  .log-icon-img{ width:19px; height:19px; border-radius:var(--r-round); object-fit:cover; display:block; }
  .ab-row{ flex-direction:column; }
  .hp-frame{
    position:relative; width:100%; aspect-ratio:640/80;
    background:url('../img/hp_frame.png') center/100% 100% no-repeat;
  }
  .hp-frame-inner{
    position:absolute; left:5.3%; right:6%; top:22%; bottom:20%;
    border-radius:2px; overflow:hidden; background:rgba(20,14,8,0.55);
  }
  .hp-frame-fill{ height:100%; transition:width .3s ease; }
  .hp-frame-label{
    position:absolute; inset:0; display:flex; align-items:center; justify-content:center;
    font-size:11px; font-weight:700; color:#fff; text-shadow:0 1px 3px rgba(0,0,0,0.9);
    pointer-events:none;
  }

  #logMine, #logTheirs{ scrollbar-width:thin; scrollbar-color:var(--border) transparent; }
  #logMine::-webkit-scrollbar, #logTheirs::-webkit-scrollbar{ width:5px; }
  #logMine::-webkit-scrollbar-thumb, #logTheirs::-webkit-scrollbar-thumb{ background:var(--border); border-radius:var(--r-xs); }
  #logMine::-webkit-scrollbar-track, #logTheirs::-webkit-scrollbar-track{ background:transparent; }

  /* Компактная раскладка для узких мобильных экранов (в т.ч. телефон в горизонтальной ориентации) */
  @media (max-width: 800px){
    body{ padding:0.6rem; }
    .screen{ padding:8px; gap:8px; }
    #battleSceneBox{ width:320px !important; height:146px !important; }
    #turnTimerBox{ font-size:38px !important; }
    #perkBannerText{ font-size:19px !important; padding:6px 10px !important; }
    #logColMine, #logColTheirs{ height:146px !important; }
    #logColMine, #logColTheirs{ flex:0 0 76px !important; }
    .choice-row button{ width:30px !important; height:30px !important; }
    .choice-row{ gap:5px !important; }
  }

  #rotateHint{ display:none; position:fixed; inset:0; background:var(--surface-0); z-index:200;
               align-items:center; justify-content:center; text-align:center; padding:24px; box-sizing:border-box; }
  .equip-slot{ border:1px dashed var(--border); border-radius:var(--r-lg); padding:8px 4px;
               display:flex; flex-direction:column; align-items:center; gap:4px;
               color:var(--text-muted); font-size:10px; }

  /* ===== Общий стиль всплывающих окон (попапов) — тёмное стекло + золотая рамка,
     как у боевой панели ударов/блоков (.nh-panel/.control-panel). Семантические
     токены (--text-*, --border, --surface-*) переопределены только внутри .pm-card,
     поэтому весь вложенный контент, использующий var(--text-secondary) и т.п.
     в инлайн-стилях, автоматически подхватывает тёмную золотую тему. ===== */
  .pm-card{
    position:relative; box-sizing:border-box;
    font-family:'EB Garamond',serif; color:var(--c-gold-bright);
    background:var(--glass-card);
    border-radius:var(--r-xl); border:none;
    backdrop-filter:blur(10px) saturate(0.9);
    -webkit-backdrop-filter:blur(10px) saturate(0.9);
    box-shadow:0 8px 32px rgba(0,0,0,0.55), inset 0 0 30px rgba(0,0,0,0.35);
    --text-primary:var(--c-gold-bright); --text-secondary:rgba(243,226,189,0.75);
    --text-muted:rgba(243,226,189,0.65); --border:var(--glass-line);
    --surface-0:rgba(0,0,0,0.28); --surface-1:rgba(0,0,0,0.18);
    /* роли состояний: на светлой карточке это были тёмно-красный и тёмно-зелёный,
       на стекле они не читаются — подменяем на светлые варианты той же семьи */
    --text-accent:var(--c-gold); --bg-accent:rgba(217,180,92,0.14);
    --text-danger:var(--c-danger-lit); --text-success:var(--c-success-lit);
  }
  .pm-card::before{
    content:''; position:absolute; inset:0; pointer-events:none; z-index:2;
    border:14px solid transparent;
    border-image:url('../img/ui/frame_ornate.png') 100 fill stretch;
  }
  .pm-card > p:first-child, .pm-card .pm-title{
    font-family:'Cinzel',serif; font-weight:700; color:var(--c-gold-bright); letter-spacing:0.02em;
  }
  .pm-card b, .pm-card strong{ font-family:'Cinzel',serif; }
  /* Кнопки внутри окон рисует единый набор «КНОПКИ: ЕДИНАЯ СХЕМА» ниже —
     здесь для них правил нет нарочно, чтобы не было второго языка. */
  .pm-card input{
    font-family:'EB Garamond',serif; background:var(--glass-field) !important;
    border:1px solid rgba(217,180,92,0.35) !important; color:var(--c-gold-bright) !important; border-radius:var(--r-md);
  }
  .pm-card input::placeholder{ color:rgba(243,226,189,0.45); }
  .pm-card table{ color:var(--c-gold-bright); }
  .pm-card table th{ color:var(--c-gold); }
  .pm-card table tr{ border-top:1px dashed rgba(217,180,92,0.28) !important; }
  .pm-card ::-webkit-scrollbar{ width:8px; }
  .pm-card ::-webkit-scrollbar-thumb{ background:rgba(217,180,92,0.35); border-radius:4px; }

  /* ===== ПЛИТА ИТОГОВ БОЯ (V33, 11.09.2026) =====
     Была коричневая заливка с золотой рамкой по периметру. Andy 11.09.2026:
     «немного выпадает из стиля, нужно и её оформить в нашем стиле» — и то же
     про ту, что переезжает в правую сторону боевого экрана. Теперь это та же
     тёмная стеклянная плита с вязью, что у окон (.pm-card) и панелей боя:
     один язык на всю игру, а не третий. Середина у frame_ornate.png
     прозрачная, поэтому рамка лежит поверх содержимого и ничего не закрывает. */
  .res-plate{
    position:relative; box-sizing:border-box;
    background:var(--glass-card);
    border:none; border-radius:var(--r-lg);
    box-shadow:0 6px 22px rgba(0,0,0,0.5), inset 0 0 24px rgba(0,0,0,0.35);
  }
  .res-plate::before{
    content:''; position:absolute; inset:0; pointer-events:none; z-index:2;
    border:12px solid transparent;
    border-image:url('../img/ui/frame_ornate.png') 100 fill stretch;
  }
  /* Внутренние карточки итогов — без вязи, чтобы рамка не спорила с рамкой:
     тонкая золотая линия по стеклу, как у полей ввода в окнах. */
  .res-box{
    background:rgba(0,0,0,0.26);
    border:1px solid rgba(217,180,92,0.30);
    border-radius:var(--r-md);
  }

  .crest-btn{
    background:none; border:none; padding:0; cursor:pointer;
    height:clamp(220px, 56vh, 440px); display:flex; align-items:flex-end;
    transition:transform 0.15s ease, filter 0.15s ease;
    filter:drop-shadow(0 6px 14px rgba(0,0,0,0.6));
  }
  .crest-btn:hover{ background:none; transform:translateY(-4px) scale(1.03); filter:drop-shadow(0 10px 20px rgba(0,0,0,0.7)) brightness(1.08); }
  .crest-btn:active{ transform:translateY(0) scale(0.99); }
  .crest-img{ height:100%; width:auto; display:block; pointer-events:none; }
  #topExitBtn:hover{ transform:scale(1.08); }
  #topExitBtn:active{ transform:scale(0.96); }
  /* =====================================================================
     КНОПКИ: ЕДИНАЯ СХЕМА (решение Andy 09.09.2026). Правила пользования —
     docs/паспорт/02-контент.md, раздел «Кнопки: единая схема».

     Один материал на всю игру: колотая каменная плита из образцов Andy
     (img/ui/btn/slab.webp, с рунами; slab_plain.webp — без). При наведении
     мышкой, нажатии пальцем и выборе с клавиатуры она загорается
     (slab_fire.webp / slab_plain_fire.webp). Все четыре картинки делает
     tools/build_ui_buttons.py из двух JPEG на Drive; какую пару берёт
     кнопка, задают переменные --btn-stone и --btn-fire.

     Как устроено. Сама кнопка прозрачна и без рамки; плиту рисуют два слоя
     под текстом: ::before — камень, ::after — огонь, скрытый и проявляющийся
     плавно. Плита нарезана на девять кусков (border-image): углы не
     растягиваются, края и середина тянутся, поэтому одна картинка годится
     кнопке любой ширины и высоты. Свечение выходит за край кнопки (outset),
     зона нажатия — сама плита.

     Числа картинки: окно 1000×303, поле под свечение 37 px с каждой стороны,
     плита 926×229 (пропорция 4.04), срез углов 88 px = поле + ободок.
     --btn-s — масштаб, CSS-px на один px картинки: 0.30 у кнопок меню
     (плита 280 px шириной), 0.20 у кнопок окон, 0.16 у маленьких.

     Кому достаётся автоматически — список ниже, и это ЕДИНСТВЕННОЕ место,
     куда дописывать новую семью: .btn, любая кнопка внутри .pm-card (все
     окна и карточка обучения), панель вызова в PvP, послебоевая панель.
     Новая кнопка в разметке — <button class="btn">; внутри окна класс не
     нужен. Роли: .btn--primary / .pm-btn--primary — главное действие,
     золотая подпись с тёплым свечением; .btn--danger / .pm-btn--danger —
     красная подпись; .btn--menu — широкая кнопка меню с иконкой;
     .btn--back — BACK; .btn--sm — маленькая; .plate — та же плита без
     нажатия, для заголовков.

     🔴 Фон, рамка и тень кнопки задаются только здесь. background:none и
     border:none стоят с !important нарочно: в разметке и в коде ещё живут
     инлайновые background:var(--fill-accent) и border-color — они бы
     просвечивали сквозь сколы по краю плиты. Общее button:hover выше по
     файлу сюда не достаёт по той же причине.
     ===================================================================== */
  :is(.btn, .plate, .pm-card button, .menu-challenge-panel button, .postbattle-btn){
    --btn-s:0.20;
    /* по умолчанию — плита без рун (slab_plain): на кнопках окон, сжатых по
       ширине, руны превращались в каракули. Широкие кнопки меню и плашки
       ниже переключают себя на плиту с рунами (slab) — там они фактура. */
    --btn-stone:url('../img/ui/btn/slab_plain.webp');
    --btn-fire:url('../img/ui/btn/slab_plain_fire.webp');
    position:relative; z-index:0; box-sizing:border-box;
    background:none !important; border:none !important; border-radius:0 !important;
    box-shadow:none !important; outline:none; appearance:none; -webkit-appearance:none;
    font-family:'EB Garamond',serif; font-weight:700; font-size:15px; letter-spacing:0.02em;
    color:var(--c-gold-bright); text-shadow:0 1px 3px rgba(0,0,0,0.9);
    line-height:1.2; min-height:38px; padding:8px 18px;
    transition:color 0.18s ease;
  }
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn){ cursor:pointer; }
  :is(.btn, .plate, .pm-card button, .menu-challenge-panel button, .postbattle-btn)::before,
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn)::after{
    content:''; position:absolute; inset:0; z-index:-1; pointer-events:none;
    border:calc(88px * var(--btn-s)) solid transparent;
    border-image:var(--btn-stone) 88 fill / 1 / calc(37px * var(--btn-s)) stretch;
  }
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn)::after{
    border-image-source:var(--btn-fire);
    opacity:0; transition:opacity 0.18s ease;
  }
  /* огонь: нажатие и клавиатура — везде; наведение — только там, где есть
     мышь, иначе на телефоне плита остаётся гореть после касания */
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):is(:active, :focus-visible)::after{ opacity:1; }
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):is(:active, :focus-visible){ color:var(--c-gold-hot); }
  @media (hover:hover){
    :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):hover::after{ opacity:1; }
    :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):hover{ color:var(--c-gold-hot); }
  }
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):disabled{ opacity:0.45; cursor:default; color:var(--c-gold-bright); }
  :is(.btn, .pm-card button, .menu-challenge-panel button, .postbattle-btn):disabled::after{ opacity:0; }
  /* роли: подпись, а не заливка — плита у всех одна */
  :is(.btn, .pm-card button, .postbattle-btn):is(.btn--primary, .pm-btn--primary, .postbattle-btn--accent){
    color:var(--c-gold-hot); text-shadow:0 0 10px rgba(255,170,50,0.55), 0 1px 3px rgba(0,0,0,0.9);
  }
  :is(.btn, .pm-card button):is(.btn--danger, .pm-btn--danger){ color:var(--c-danger-lit); }
  :is(.btn, .pm-card button, .menu-challenge-panel button):is(.btn--sm){
    --btn-s:0.16; font-size:13.5px; min-height:30px; padding:5px 12px;
  }
  /* 🔴 ИСКЛЮЧЕНИЕ ИЗ НАБОРА — отдельным правилом, а не оговоркой `:not(.no-slab)`
     ВНУТРИ набора. 16.09.2026 оговорка стояла внутри, и это сломало карточку бойца:
     у правила с `:not()` вес выше, и весь набор начал перебивать точечные правила
     раскладки — кнопка «Back» уехала из угла в общий ряд, а пять гнёзд снаряжения
     слетели с фигуры вниз. Нажимать стало нечего: на фигуре остались одни подписи.
     Правило-исключение только СНИМАЕТ плиту (её рисуют ::before и ::after) и ничего
     не весит для остальных кнопок. Типографику набора элемент перебивает сам —
     своим правилом из двух классов, как .chat-side .chathub-row ниже. */
  .pm-card button.no-slab::before, .pm-card button.no-slab::after{ content:none; }
  .pm-card button.no-slab{ min-height:0; }

  .postbattle-btn{ font-family:'Cinzel',serif; letter-spacing:0.03em; padding:9px 18px; }
  /* широкая кнопка меню: иконка слева, заголовок и подпись */
  .btn.btn--menu{
    --btn-s:0.30; --btn-stone:url('../img/ui/btn/slab.webp'); --btn-fire:url('../img/ui/btn/slab_fire.webp');
    width:100%; max-width:280px; aspect-ratio:926/229; min-height:0;
    display:flex; align-items:center; gap:12px; padding:0 14px 0 22px; text-align:left;
    font-family:'Pirata One','Cinzel',serif; font-weight:400; font-size:18px; letter-spacing:0.02em;
  }
  /* BACK и плашки-заголовки — тем же шрифтом, что кнопки меню (замечание Andy
     09.09.2026: другой шрифт на BACK и CAMPAIGN читался как ошибка). Вес правил у
     .btn.btn--back и .plate.plate--title — два класса, чтобы перебить общее
     правило набора; с одним классом плашка получала EB Garamond. */
  .btn.btn--back{
    --btn-s:0.30; --btn-stone:url('../img/ui/btn/slab.webp'); --btn-fire:url('../img/ui/btn/slab_fire.webp');
    width:196px; max-width:60%; aspect-ratio:926/229; min-height:0; padding:0;
    display:flex; align-items:center; justify-content:center;
    font-family:'Pirata One','Cinzel',serif; font-weight:400; font-size:21px; letter-spacing:0.04em;
    padding-top:2px; /* краска букв у Pirata One сидит на 1 px выше середины — замерено по снимку */
  }
  .btn-icon{ position:relative; width:34px; height:34px; flex-shrink:0; font-size:24px; line-height:34px; text-align:center; filter:drop-shadow(0 2px 4px rgba(0,0,0,0.6)); }
  .btn-icon img{ width:100%; height:100%; object-fit:contain; display:block; }
  .btn-text{ display:flex; flex-direction:column; gap:1px; min-width:0; }
  .btn-sub{ font-family:'EB Garamond',serif; font-size:12px; font-weight:400; letter-spacing:0; color:var(--c-gold-dim); text-shadow:0 1px 2px rgba(0,0,0,0.75); }
  /* плашка-заголовок: та же плита, без нажатия */
  .plate{ --btn-s:0.30; --btn-stone:url('../img/ui/btn/slab.webp'); display:flex; align-items:center; justify-content:center; min-height:0; padding:0; }
  .plate.plate--title{ width:210px; max-width:64%; aspect-ratio:926/229; padding-top:2px; font-family:'Pirata One','Cinzel',serif; font-weight:400; font-size:22px; letter-spacing:0.08em; text-shadow:0 2px 6px rgba(0,0,0,0.85); }
  /* нижний ряд главного меню: Options и Log out (Andy 09.09.2026 — выход должен быть
     словом внизу меню, а не иконкой в углу). Шрифт — тот же, что у кнопок меню и BACK,
     чтобы ряд читался частью меню, а не чужой вставкой. */
  #menuFootRow{ display:flex; align-items:center; justify-content:center; gap:14px; flex-wrap:wrap; margin-top:2px; }
  .btn.menu-foot-btn{
    --btn-s:0.24; --btn-stone:url('../img/ui/btn/slab.webp'); --btn-fire:url('../img/ui/btn/slab_fire.webp');
    width:168px; aspect-ratio:926/229; min-height:0; padding:2px 0 0;
    display:flex; align-items:center; justify-content:center;
    font-family:'Pirata One','Cinzel',serif; font-weight:400; font-size:19px; letter-spacing:0.05em;
  }

  /* ===== OPTIONS (Andy 09.09.2026) =====
     Ряд «название — значение — переключатель», под ним ползунок во всю ширину окна.
     Ползунок рисуем руками: у браузерного вида нет ничего общего с остальной игрой.
     Дорожка — тёмная щель с золотой каймой, бегунок — золотая заклёпка. */
  .opt-row{ display:flex; align-items:center; gap:10px; margin:0 0 6px; }
  .opt-label{ font-family:'Cinzel',serif; font-weight:700; font-size:15px; color:var(--c-gold-bright);
              text-shadow:0 1px 3px rgba(0,0,0,0.9); flex:1 1 auto; }
  .opt-val{ font-family:'EB Garamond',serif; font-size:13px; color:var(--c-gold-dim); min-width:42px; text-align:right; }
  .opt-val--hint{ font-style:italic; min-width:0; }
  /* V142 (25.09.2026): два класса, а не один. Окно — .pm-card, и набор кнопок
     (вес .pm-card button — класс и тег) перебивал одиночный .opt-toggle: On/Off
     выходили полноразмерными плитами, а не маленькими. */
  .pm-card .opt-toggle{ --btn-s:0.16; min-width:62px; font-size:13.5px; min-height:30px; padding:5px 10px; }
  .opt-range{ -webkit-appearance:none; appearance:none; width:100%; height:22px; margin:0 0 14px;
              background:transparent; cursor:pointer; display:block; }
  .opt-range:disabled{ cursor:default; opacity:0.45; }
  /* Кайма дорожки — общий токен --glass-line-lit (V142). Прежний --gold-dim
     объявлен только внутри боевого экрана (#newHudOverlay), в Options его нет —
     и кайма молча пропадала. */
  .opt-range::-webkit-slider-runnable-track{ height:8px; border-radius:4px;
    background:linear-gradient(180deg,#120d07,#2a1f12); border:1px solid var(--glass-line-lit);
    box-shadow:inset 0 1px 3px rgba(0,0,0,0.9); }
  .opt-range::-moz-range-track{ height:8px; border-radius:4px;
    background:linear-gradient(180deg,#120d07,#2a1f12); border:1px solid var(--glass-line-lit);
    box-shadow:inset 0 1px 3px rgba(0,0,0,0.9); }
  .opt-range::-webkit-slider-thumb{ -webkit-appearance:none; appearance:none; width:20px; height:20px;
    margin-top:-7px; border-radius:50%; border:1px solid #5a4220;
    background:radial-gradient(circle at 35% 30%, #f6e2ae, #b88f3a 60%, #6d4e1c);
    box-shadow:0 1px 4px rgba(0,0,0,0.8); }
  .opt-range::-moz-range-thumb{ width:20px; height:20px; border-radius:50%; border:1px solid #5a4220;
    background:radial-gradient(circle at 35% 30%, #f6e2ae, #b88f3a 60%, #6d4e1c);
    box-shadow:0 1px 4px rgba(0,0,0,0.8); }
  .opt-build{ margin:12px 0 0; text-align:center; font-family:'EB Garamond',serif; font-size:11px;
              color:var(--c-gold-dim); opacity:0.75; letter-spacing:0.03em; }

  /* плашки турнира и лиги над меню: та же плита, не на всю ширину, а по содержимому */
  .top-sticky-bar.btn{ width:auto; max-width:min(92vw, 520px); margin:6px auto 0;
    --btn-s:0.22; --btn-stone:url('../img/ui/btn/slab_plain.webp'); --btn-fire:url('../img/ui/btn/slab_plain_fire.webp');
    display:flex; align-items:center; justify-content:center; gap:10px;
    padding:10px 22px; font-family:'Cinzel',serif; font-size:17px; font-weight:700; white-space:nowrap; }

  /* ===== My Warrior — тёмное стекло во весь экран (V5, 09.09.2026; переделано
     17.09.2026, V70) =====
     Окно делится на три части слева направо: РЕЙКА СНАРЯЖЕНИЯ, ФИГУРА, СВЕДЕНИЯ.
     Сведения, в свой черёд, — на два столбца: слева сила и действие (атака,
     здоровье, защита, кнопка Save), справа перки бойца списком.

     🔴 ПОЧЕМУ РЕЙКА, А НЕ МЕДАЛЬОНЫ ПО ТЕЛУ (V70, часть 5). Гнёзда стояли на
     фигуре в процентах от её коробки: плитка 50 точек, картинка в ней 28, и та
     не своя вещь, а общий силуэт. Подписи висели рядом отдельными ярлычками и
     ложились на героя и друг на друга (снимок 17.09: «Magic Sword» поперёк ног).
     Числа не было вовсе — чтобы узнать, что даёт меч, надо было открыть окно.
     Рейка решает всё разом: плиты втрое крупнее, ничего ни на что не наезжает
     при любой высоте экрана, фигура открыта целиком, а на плите стоит настоящая
     картинка вещи, рамка цветом дороговизны, число и камешки перков.

     🔴 ВЕС ПРАВИЛ. Всё, что уточняет размеры кнопок (плиты гнёзд, «плюсы»),
     пишется ДВУМЯ классами — `.wc-frame .wc-gear`. Набор кнопок весит класс с
     элементом, и правило из двух классов его перебивает. 16.09.2026 это уже
     ломалось (V58): оговорка `:not()` внутри набора перевесила точечные правила
     карточки, и гнёзда слетели с фигуры вниз. Исключение `.no-slab` только
     снимает каменную плиту, размеров не трогает. */
  .wc-frame{
    position:relative; width:min(100%, 980px); height:min(calc(100vh - 28px), 620px);
    display:flex; align-items:stretch; padding:0; overflow:hidden;
  }
  .wc-frame .wc-backBtn{ position:absolute; top:10px; right:12px; z-index:6; }

  /* ---- левая часть: рейка снаряжения + фигура ---- */
  /* 🔴 СНАРЯЖЕНИЕ — ОРУЖЕЙНАЯ СТОЙКА (выбор Andy 18.09.2026 из трёх проб).
     До неё были две отвергнутые редакции, и обе по одной причине: у гнёзд не
     было МАТЕРИАЛА. Медальоны висели кружками поверх живописи — герой нарисован
     светом и тканью, а кружок нарисован интерфейсом, и вместе это читается
     наклейками на фотографии («всё выглядит убого», Andy). Рейка сбоку из тех же
     квадратов отбирала у бойца рост и стояла чужой чернотой на тёмной панели.

     Стойка решает это тем, что снаряжение на чём-то ЛЕЖИТ: одна каменная доска
     (та же плита, что у кнопок) с пятью выемками. Отдельных плиток нет — значит
     нет и стыков чужой черноты; выемка сделана не заливкой, а тенью: тёмной
     сверху и светлым следом снизу, как настоящая выбоина в камне. Фигура при
     этом нетронута и стоит во весь рост.

     🔴 ДВА ПРАВИЛА ВЕСА, без которых это не работало (разбор 18.09):
     1. Вид рисует ВНУТРЕННИЙ слой, а не кнопка: набор кнопок гасит у себя фон,
        рамку и тень пометкой «важно», и правила на кнопке до экрана не доживали.
     2. Селектор гнезда — из ДВУХ классов: общее правило ниши вещи (.item-niche)
        описано ниже по файлу и при равном весе побеждало, отчего коробка гнезда
        схлопывалась в ноль высоты и вещь пропадала с экрана вовсе. */
  .wc-fighter-panel{
    position:relative; flex:0 0 300px; box-sizing:border-box; padding:12px 8px;
    display:flex; align-items:flex-end; justify-content:center; gap:8px;
    border-right:1px dashed var(--glass-line);
  }
  .wc-sprite-wrap{
    position:relative; z-index:1; height:100%; width:auto; aspect-ratio:321/703;
    max-width:100%; display:block; flex:0 1 auto; min-width:0;
  }
  .wc-sprite-wrap #warriorPortrait{
    display:block; width:100%; height:100%; object-fit:contain; object-position:center bottom;
    filter:drop-shadow(0 14px 14px rgba(0,0,0,0.75));
  }
  /* ---- сама доска ---- */
  .wc-gear-zone{
    position:relative; flex:0 0 auto; align-self:stretch; box-sizing:border-box;
    width:clamp(64px, 17.5vh, 86px); padding:10px 0;
    display:flex; flex-direction:column; align-items:center; justify-content:space-evenly;
  }
  /* камень отдельным слоем позади: иначе его затемнение легло бы и на вещи */
  .wc-gear-zone::before{
    content:''; position:absolute; inset:0; z-index:0; pointer-events:none;
    border:14px solid transparent;
    border-image:url('../img/ui/btn/slab_plain.webp') 88 fill / 1 / 0 stretch;
    filter:brightness(0.62) saturate(0.85);
  }
  /* ---- гнездо: выемка в камне ---- */
  .wc-frame .wc-gear{
    --tier:#9aa0a6; --tier-lit:#d6dade; --tier-glow:rgba(154,160,166,0.30); --tier-edge:rgba(217,180,92,0.45);
    position:relative; z-index:1; padding:0; min-height:0; cursor:pointer;
    border:none; background:none; box-shadow:none; overflow:visible;
    /* 🔴 52 точки — не «покрасивее», а нижняя граница попадания пальца, и её
       стережёт test:card на трёх высотах экрана. Меньше делать нельзя: гнездо и
       лавку открывает, и вещь показывает. */
    width:clamp(52px, 13vh, 62px); height:clamp(52px, 13vh, 62px);
  }
  .wc-frame .wc-gear-niche{
    position:absolute; inset:0; display:block; border-radius:50%;
    background:radial-gradient(circle at 50% 44%, rgba(3,2,1,0.95) 42%, rgba(3,2,1,0.7) 76%, rgba(3,2,1,0.35) 100%);
    box-shadow:inset 0 4px 10px rgba(0,0,0,0.95), inset 0 -2px 4px rgba(255,220,160,0.16),
               0 1px 0 rgba(255,232,186,0.14);
  }
  .wc-frame .wc-gear-niche img{ position:absolute; left:13%; top:9%; width:74%; height:74%; animation-duration:5.6s; }
  .wc-frame .wc-gear--empty .wc-gear-niche img{ opacity:0.4; mix-blend-mode:normal; animation:none; filter:none; }
  .wc-frame .wc-gear--empty .wc-gear-niche{ box-shadow:inset 0 4px 10px rgba(0,0,0,0.95), inset 0 0 0 1px rgba(217,180,92,0.22); }
  .wc-frame .wc-gear:is(:hover,:active,:focus-visible) .wc-gear-niche{
    box-shadow:inset 0 4px 10px rgba(0,0,0,0.9), 0 0 14px var(--tier-glow), inset 0 0 12px var(--tier-glow);
  }
  /* 🔴 Три класса: исключение .no-slab снимает ::after у всех кнопок окна, и
     правило полегче просто не нарисовало бы этот плюс. */
  .wc-frame .wc-gear.wc-gear--empty::after{
    content:'+'; position:absolute; left:0; right:0; bottom:6%; z-index:6;
    font-family:'Cinzel',serif; font-size:clamp(13px, 3.6vh, 17px); font-weight:700; line-height:1;
    text-align:center; color:var(--c-gold-dim); opacity:0.9; text-shadow:0 1px 3px rgba(0,0,0,0.95);
    border:none; border-image:none; background:none;
  }
  /* 🔴 ЧИСЛО ВЕЩИ — ВНУТРИ ВЫЕМКИ, клеймом по нижнему краю (правка 18.09.2026 по
     снимку с телефона Andy). Стояло под кружком, в расчёте на зазор между
     гнёздами. На настоящем телефоне высоты меньше, чем на стенде: пять выемок по
     52 точки (ниже нельзя — палец) съедают доску целиком, зазора не остаётся, и
     число ложилось на соседний кружок. Внутри выемки зазоры не нужны вовсе.
     Урок: раскладка, которой нужен зазор, ломается на первом же экране, где его
     нет. Считать надо от худшего случая, а не от стенда. */
  .wc-gear-val{
    position:absolute; left:6%; right:6%; bottom:3%; z-index:5; text-align:center;
    font-family:'Cinzel',serif; font-size:clamp(9.5px, 2.7vh, 12px); font-weight:700; line-height:1.25;
    color:var(--c-gold-bright); text-shadow:0 1px 3px rgba(0,0,0,0.95);
    white-space:nowrap; overflow:hidden; border-radius:var(--r-pill);
    background:linear-gradient(180deg, rgba(4,3,2,0) 0%, rgba(4,3,2,0.8) 55%);
  }
  /* у пустого гнезда числа нет: силуэт и так говорит, какое это место, а слово
     «Helmet» шире доски и обрезалось краями */
  .wc-gear--empty .wc-gear-val{ display:none; }
  /* 🔵 ЦВЕТ ЧИСЛА ГОВОРИТ, ЧТО ВЕЩЬ ДАЁТ (правка 18.09.2026 по слову Andy).
     Порядок в стойке сверху вниз — меч, кольцо, шлем, доспех, сапоги: сперва
     атака, потом здоровье, потом три защиты подряд, и эти три стоят в том же
     порядке, что зоны защиты справа (голова, тело, ноги). Цветов ровно три,
     по числу смыслов, и они не новые — взяты с плиток и строк, которые уже
     стоят на карточке: янтарь = удар (плитка Attack), кость = здоровье
     (плитка Hits), синяя сталь = защита (числа зон). Больше цветов на доске
     не будет: ступень вещи показывает рамка гнезда, перки — камешки сверху,
     и если красить ещё и число, доска станет ярмаркой. */
  #slot_sword .wc-gear-val{ color:#ffcf7d; text-shadow:0 0 10px rgba(255,150,40,0.35), 0 1px 3px rgba(0,0,0,0.95); }
  #slot_ring  .wc-gear-val{ color:#eee9da; text-shadow:0 0 10px rgba(190,215,235,0.22), 0 1px 3px rgba(0,0,0,0.95); }
  #slot_helmet .wc-gear-val,
  #slot_armor  .wc-gear-val,
  #slot_boots  .wc-gear-val{ color:#a9c6ea; text-shadow:0 0 10px rgba(120,170,225,0.30), 0 1px 3px rgba(0,0,0,0.95); }
  /* камешки перков — дужкой по верхнему краю выемки */
  .wc-gear-pips{ position:absolute; top:-2px; left:50%; transform:translateX(-50%); z-index:6; display:flex; gap:3px; }
  .wc-gear-pips i{
    display:block; width:5px; height:5px; border-radius:50%;
    box-shadow:0 0 5px currentColor, 0 1px 2px rgba(0,0,0,0.9); background:currentColor;
  }

  /* ---- правая часть: два столбца ---- */
  .wc-info-panel{ flex:1 1 auto; min-width:0; box-sizing:border-box; display:flex; gap:clamp(8px, 2.43vh, 14px);
    padding:clamp(6px, 2.2vh, 12px) clamp(10px, 2.9vh, 16px) clamp(6px, 2.2vh, 12px) clamp(9px, 2.7vh, 14px); overflow:hidden; }
  /* 🔴 Прокрутка здесь — СТРАХОВКА, а не способ жить (разбор 17.09.2026). Первая
     редакция карточки была подогнана впритык под высоту стенда в 412 точек: на
     телефоне Andy в полном экране их 383, и нижняя строка ушла под край — а
     достать её было нечем, прокрутку я закрыл нарочно. Теперь размеры считаются
     от высоты экрана (ниже), и всё складывается само; прокрутка остаётся на
     случай телефона ещё ниже — чтобы ничто не могло стать недостижимым. */
  .wc-col{ display:flex; flex-direction:column; min-width:0; min-height:0; }
  .wc-col--main{ overflow-y:auto; }
  .wc-col--main{ flex:1 1 55%; }
  .wc-col--side{ flex:1 1 45%; padding-left:14px; border-left:1px dashed var(--glass-line); }

  .wc-fighter-id{ margin:0 0 8px; }
  .wc-fighter-name{ font-family:'Cinzel',serif; font-weight:700; font-size:clamp(13px, 3.9vh, 19px); color:var(--c-gold-bright);
    letter-spacing:0.02em; margin:0 0 clamp(3px, 1.2vh, 7px); text-shadow:0 2px 6px rgba(0,0,0,0.8);
    white-space:nowrap; overflow:hidden; text-overflow:ellipsis; }
  .wc-chips{ display:flex; flex-wrap:wrap; align-items:center; gap:5px 7px; }
  .wc-rankchip{ display:inline-block; font-family:'EB Garamond',serif; font-size:clamp(11px, 3.03vh, 13.5px); font-weight:600; color:var(--c-gold-bright);
    background:var(--glass-btn); border:1px solid var(--glass-line-lit); border-radius:var(--r-pill); padding:1px clamp(8px, 2.7vh, 11px); }
  /* 🔴 КОШЕЛЬ КРУПНЕЕ ОСТАЛЬНЫХ ФИШЕК (Andy 21.09.2026: «деньги нужно крупнее
     сделать символ»). Это единственное число на карточке, ради которого человек
     идёт к кузнецу, а оно было мельче звания. Монета выросла с 19 до 26 точек,
     число — до 18. Высоту карточки это не двигает: полоска звания рядом выше. */
  .wc-coin-pill{ display:inline-flex; align-items:center; gap:6px; font-family:'EB Garamond',serif; font-size:clamp(13px, 3.6vh, 18px); font-weight:700; color:var(--c-gold-bright);
    background:var(--glass-btn); border:1px solid var(--glass-line-lit); border-radius:var(--r-pill); padding:1px clamp(8px, 2.7vh, 11px) 1px 6px; cursor:help; }
  .wc-coin-pill img{ width:clamp(20px, 5.2vh, 26px); height:clamp(20px, 5.2vh, 26px); object-fit:contain; }
  /* 🔴 КТО СЛЕДУЮЩИЙ — НАД КНОПКОЙ, КОТОРАЯ В ЭТОТ БОЙ И ВЕДЁТ (V107).
     Заменила собой окно «Path Cleared». Колонка итогов на телефоне в альбомной
     узкая, около 150 точек, поэтому строк ДВЕ и обе наши: имя соперника и его
     цифры. Одной строкой браузер переносил текст сам, по случайному месту, и
     новость читалась как мелкий шрифт под кнопкой. */
  #pathClearedLine{ font-family:'EB Garamond',serif; line-height:1.25; }
  #pathClearedLine .pc-who{ font-size:clamp(14px, 3.9vh, 17px); font-weight:700; color:var(--c-gold-bright); }
  #pathClearedLine .pc-nums{ font-size:clamp(13px, 3.4vh, 15px); color:#a89268; margin-top:1px; }
  /* дорога до следующего звания — полоской, а не строчкой мелким серым */
  .wc-rankbar{ height:5px; margin:clamp(3px, 1.2vh, 7px) 0 2px; border-radius:3px; overflow:hidden;
    background:rgba(0,0,0,0.5); border:1px solid rgba(217,180,92,0.28); }
  .wc-rankbar-fill{ display:block; height:100%; width:0%; border-radius:3px;
    background:linear-gradient(90deg, #7a5a18, #ffd479); box-shadow:0 0 8px rgba(255,200,90,0.45); }
  .wc-nextrank{ font-family:'EB Garamond',serif; font-size:clamp(10px, 2.8vh, 13px); color:var(--c-gold-dim); margin:2px 0 0; }

  /* ---- полоса силы: два числа, которыми меряется боец ---- */
  .wc-power{ display:flex; gap:9px; margin:clamp(4px, 1.46vh, 9px) 0 clamp(4px, 1.7vh, 10px); }
  .wc-pw{
    position:relative; flex:1 1 0; min-width:0; box-sizing:border-box;
    padding:clamp(2px, 0.73vh, 5px) clamp(8px, 2.2vh, 11px) clamp(3px, 1.2vh, 7px);
    border-radius:var(--r-md); border:1px solid rgba(217,180,92,0.32); cursor:help;
    background:linear-gradient(180deg, rgba(46,35,19,0.62), rgba(12,9,6,0.75));
    box-shadow:inset 0 0 18px rgba(0,0,0,0.45);
  }
  .wc-pw b{ display:flex; align-items:center; gap:5px; font-family:'Cinzel',serif; font-size:clamp(9px, 2.55vh, 11.5px); font-weight:700;
    letter-spacing:0.14em; text-transform:uppercase; color:var(--c-gold-dim); }
  .wc-pw > span{ display:block; font-family:'Cinzel',serif; font-size:clamp(19px, 6.3vh, 33px); font-weight:700; line-height:1.06;
    color:var(--c-gold-bright); text-shadow:0 2px 8px rgba(0,0,0,0.8); }
  /* выросло после повышения — плита горит и показывает прибавку (V70, часть 1) */
  .wc-gain{ position:absolute; top:6px; right:9px; display:none; font-style:normal;
    font-family:'Cinzel',serif; font-size:15px; font-weight:700; color:var(--c-gold-hot);
    text-shadow:0 0 12px rgba(255,170,50,0.8), 0 1px 3px rgba(0,0,0,0.9); }
  /* ---- Атака и Здоровье различаются оттенком и значком, не двумя красками ----
     Голос игры — золото по тёмному, и два ярких цвета его бы перебили. Атака
     светится теплее (раскалённый металл), Здоровье — холоднее и бледнее (кость
     и сталь). Значок довершает: меч и сердце — те же, что на строках перков. */
  /* 🔴 КОВАНЫЙ ГЕРБ В ПЛИТЕ (18.09.2026). Живопись NanoBanana прекрасна на 64
     точках и слепнет на 15: темнеет, детали слипаются, цвет породы теряется —
     проверено листом сравнения. Поэтому маленький рабочий значок остался
     вектором, а живопись получила то место, где её размер настоящий: она стоит
     подложкой в плите, крупно и приглушённо. Читать её не нужно — она фактура. */
  .wc-pw-emblem{
    position:absolute; right:4px; bottom:2px; width:clamp(38px, 11vh, 54px); height:auto;
    opacity:0.2; pointer-events:none; filter:saturate(0.85);
    -webkit-mask-image:linear-gradient(200deg, #000 30%, rgba(0,0,0,0.25) 85%);
    mask-image:linear-gradient(200deg, #000 30%, rgba(0,0,0,0.25) 85%);
  }
  .wc-pw{ overflow:hidden; }
  .wc-pw-ico{ width:clamp(13px, 3.8vh, 16px); height:clamp(13px, 3.8vh, 16px); flex:0 0 auto;
    filter:drop-shadow(0 1px 1.5px rgba(0,0,0,0.85)); }
  .wc-pw--atk{ border-color:rgba(255,190,90,0.34); box-shadow:inset 0 0 20px rgba(0,0,0,0.45), inset 0 0 24px rgba(255,150,40,0.10); }
  .wc-pw--atk b{ color:#e3b877; }
  .wc-pw--atk > span{ color:#ffcf7d; text-shadow:0 0 16px rgba(255,150,40,0.28), 0 2px 8px rgba(0,0,0,0.85); }
  .wc-pw--hp{ border-color:rgba(226,224,205,0.28); box-shadow:inset 0 0 20px rgba(0,0,0,0.45), inset 0 0 24px rgba(200,220,235,0.06); }
  .wc-pw--hp b{ color:#c9c7b8; }
  .wc-pw--hp > span{ color:#eee9da; text-shadow:0 0 16px rgba(190,215,235,0.16), 0 2px 8px rgba(0,0,0,0.85); }
  .wc-pw.is-grown{ border-color:var(--c-gold-hot); animation:wcGrow 1.7s ease-in-out 4; }
  .wc-pw.is-grown .wc-gain{ display:block; animation:wcGainPop 1.7s ease-in-out 4; }
  @keyframes wcGrow{
    0%,100%{ box-shadow:inset 0 0 18px rgba(0,0,0,0.45); }
    50%{ box-shadow:inset 0 0 20px rgba(255,170,50,0.28), 0 0 18px rgba(255,170,50,0.45); }
  }
  @keyframes wcGainPop{ 0%,100%{ transform:translateY(0); opacity:0.85; } 50%{ transform:translateY(-2px); opacity:1; } }

  /* ---- защита по зонам ---- */
  .wc-def-title{ font-family:'Cinzel',serif; font-size:clamp(11px, 3.15vh, 14px); font-weight:700; color:var(--c-gold); letter-spacing:0.04em; margin-bottom:clamp(2px, 0.73vh, 5px); }
  .wc-def-title small{ font-family:'EB Garamond',serif; font-weight:500; color:var(--c-gold-dim); font-size:clamp(9.5px, 2.67vh, 12px); letter-spacing:0; }
  /* 🔵 Строка зоны крупнее и собрана слева (V120, Andy 21.09.2026: «в средней графе
     много пустого места… и это всё крупнее чем сейчас»). Раньше зона прижималась к
     левому краю, цифра к правому, и между ними зияло. Теперь под название зоны
     отведена одна ширина на три строки, дальше «+», цифра и значки иммунитета подряд,
     столбцы ровно друг под другом. Кегли растут с высотой экрана, на телефоне
     не вылезают: проверено сторожем test:card на трёх высотах. */
  .wc-def-row{ display:flex; align-items:center; justify-content:flex-start; gap:clamp(10px, 2.4vh, 18px); margin-bottom:clamp(2px, 1.2vh, 6px); }
  .wc-def-zone{ font-family:'Cinzel',serif; font-weight:700; letter-spacing:0.04em; min-width:4.8em;
                font-size:clamp(15px, 4.9vh, 20px); color:var(--c-gold-bright); cursor:help; }
  .wc-def-controls{ display:flex; align-items:center; gap:clamp(8px, 2vh, 14px); }
  /* Значки иммунитета зоны: щит со знаком стихии, тап показывает, какая вещь его даёт. */
  .wc-def-imm{ display:inline-flex; align-items:center; gap:6px; }
  .wc-def-imm:empty{ display:none; }
  .wc-def-imm-ico{ display:inline-flex; cursor:pointer; }
  .wc-def-imm-ico .perk-ico{ width:clamp(20px, 6.3vh, 26px); height:clamp(20px, 6.3vh, 26px); filter:drop-shadow(0 1px 2px rgba(0,0,0,0.8)); }
  /* синяя сталь — тот же цвет, что у чисел шлема/доспеха/сапог в стойке:
     глаз связывает нижние три гнезда с этими тремя строками (18.09.2026) */
  .wc-def-controls b{ font-family:'Cinzel',serif; font-weight:600; font-size:clamp(17px, 5.8vh, 24px); min-width:2em; text-align:right; color:#a9c6ea; }
  /* кнопка «+» ужимается вместе с экраном, но не меньше 28 точек: ниже этого
     в неё перестаёт попадать палец */
  .wc-frame .wc-def-controls button{ --btn-s:0.12; width:clamp(28px, 7.8vh, 38px); height:clamp(28px, 7.8vh, 38px);
    min-height:0; padding:0; font-size:clamp(15px, 4.4vh, 20px); line-height:1; }
  /* очки есть — плита горит и зовёт нажать; код лишь ставит .has-points, как раньше */
  .wc-frame .wc-def-controls button.has-points::after{ opacity:1; }
  .wc-frame .wc-def-controls button.has-points{ color:var(--c-gold-hot); }
  .wc-def-footer{ display:flex; justify-content:space-between; align-items:center; gap:10px; margin-top:clamp(2px, 0.49vh, 5px); }
  .wc-def-footer span{ font-size:clamp(11px, 3.03vh, 14px); color:var(--c-gold-dim); }
  /* 🔵 ОТВЕТ НА МГНОВЕННУЮ ЗАПИСЬ ОЧКА (решение Andy 21.09.2026: кнопки
     «Save points» больше нет, «+» пишет сразу). Без ответа мгновенная запись
     выглядит как «ничего не произошло»: цифра зоны выросла, а сохранилось оно
     или нет — непонятно. Поэтому два знака сразу: цифра зоны коротко вспыхивает
     золотом, а на месте бывшей кнопки встаёт слово. Надпись держит своё место
     прозрачностью, а не появлением, — иначе подвал дёргался бы по ширине. */
  .wc-def-footer .wc-alloc-note{ color:var(--c-gold-dim); opacity:0; transition:opacity 220ms ease; white-space:nowrap; }
  .wc-def-footer .wc-alloc-note.is-on{ opacity:1; }
  .wc-def-footer .wc-alloc-note.is-bad{ color:var(--c-danger-lit); }
  .wc-def-controls b.wc-def-saved{ animation:def-saved 760ms ease-out; }
  @keyframes def-saved{
    0%{ color:var(--c-gold-hot); text-shadow:0 0 14px rgba(255,213,74,0.85); transform:scale(1.22); }
    100%{ color:#a9c6ea; text-shadow:none; transform:none; }
  }
  @media (prefers-reduced-motion:reduce){ .wc-def-controls b.wc-def-saved{ animation:none; } }

  /* ---- два числа мастерства: блоки и идеальные раунды (просьба Andy 17.09.2026,
         «важные цифры скилла и должны лежать не сильно глубоко») ---- */
  /* строка мастерства прижата к низу столбца и отчёркнута: на мониторе столбец
     выше содержимого, и без черты эти два числа висели бы в пустоте */
  .wc-skill{ display:flex; align-items:center; flex-wrap:wrap; gap:4px clamp(8px, 2.43vh, 14px); margin-top:auto;
    padding-top:clamp(4px, 1.46vh, 9px); border-top:1px dashed var(--glass-line); }
  .wc-skill-num{ font-family:'EB Garamond',serif; font-size:clamp(10.5px, 2.91vh, 13.5px); color:var(--c-gold-dim); cursor:help; white-space:nowrap; }
  .wc-skill-num b{ font-family:'Cinzel',serif; font-size:clamp(12.5px, 3.4vh, 16px); font-weight:700; color:var(--c-gold-bright); margin-left:3px; }
  .wc-frame .wc-skill button{ margin-left:auto; }

  /* ---- правый столбец: перки бойца целиком ---- */
  /* 🔴 Заголовок правого столбца уступает место кнопке «Back»: она стоит в углу
     ОКНА, то есть поверх этого столбца. Без отступа и высоты первая строка перка
     уезжала прямо под неё (снимок 17.09.2026). */
  .wc-info-title{ font-family:'Cinzel',serif; font-size:clamp(11.5px, 3.28vh, 15px); font-weight:700; color:var(--c-gold); letter-spacing:0.04em;
    /* 🔴 34 точки — это не «на глаз», а высота кнопки «Back» плюс её отступ
       сверху: кнопка стоит в углу ОКНА, то есть поверх этого столбца. Меньше —
       и первая строка перка заезжает под неё краем (сторож ловит это числом,
       глаз не ловил). Ужимать вместе с экраном нельзя: кнопка не ужимается. */
    margin:0 0 3px; padding-right:78px; min-height:34px; flex:0 0 auto;
    display:flex; align-items:center;
    white-space:nowrap; overflow:hidden; text-overflow:ellipsis; }
  .wc-perk-count{ font-family:'EB Garamond',serif; font-style:normal; font-size:13px; color:var(--c-gold-dim); margin-left:6px; }
  .wc-perks{ flex:1 1 auto; min-height:0; overflow-y:auto; padding-right:4px; }
  .wc-perks .item-perk{ padding:4px 0; }
  /* от какой вещи перк: цвет — дороговизна той вещи, поэтому ставится кодом */
  .wc-perk-from{ display:block; font-style:normal; text-decoration:none; font-size:11px; letter-spacing:0.02em; opacity:0.85; }
  .wc-perks-empty{ font-size:13px; color:var(--c-gold-dim); font-style:italic; opacity:0.8; padding:6px 0; }
  .wc-fighter-actions{ display:flex; gap:6px; flex-wrap:wrap; margin-top:clamp(4px, 1.46vh, 9px); flex:0 0 auto; }
  .wc-manage{ margin-top:clamp(4px, 1.46vh, 9px); padding-top:clamp(4px, 1.46vh, 9px); border-top:1px dashed var(--glass-line);
    flex:0 0 auto; display:flex; gap:5px; flex-wrap:wrap; }
  .wc-frame .wc-manage button{ flex:1 1 auto; margin:0; }

  /* телефон в альбомной: окно низкое — всё ужимается, но НИЧЕГО не уезжает под
     край. Прокручивается только список перков (замер — tools/card_test.js). */
  /* 🔴 ТЕЛЕФОН В АЛЬБОМНОЙ. Кегли и отступы выше уже считаются от высоты экрана
     (clamp с vh) — здесь остаётся только то, что зависит от ШИРИНЫ и от общего
     устройства окна: ширина панели бойца, рейки гнёзд, поля столбцов. Прежний
     список из тридцати жёстких чисел снят: он был подогнан под высоту стенда в
     412 точек, и на экране в 383 карточка вылезала за дно. */
  @media (max-height:460px){
    .wc-frame{ height:calc(100vh - 20px); }
    .wc-fighter-panel{ flex-basis:248px; padding:8px 6px; gap:6px; }
    .wc-gear-val{ font-size:12.5px; }
    .wc-col--side{ padding-left:10px; }
    .wc-fighter-id{ margin-bottom:4px; }
    .wc-chips{ gap:4px 6px; }
  }
  /* Низкий экран (полный экран со скрытой полосой часов — так играет Andy).
     Кегли уже на своих нижних пределах: в кнопку «+» должен попадать палец, а
     числа — читаться. Дальше отыгрываем только воздухом между строками. */
  @media (max-height:400px){
    .wc-fighter-name{ margin-bottom:2px; }
    .wc-rankbar{ margin:3px 0 1px; }
    .wc-nextrank{ font-size:10px; margin-top:1px; }
    .wc-power{ margin:3px 0 4px; }
    .wc-def-row{ margin-bottom:0; }
    .wc-def-footer{ margin-top:1px; }
    .wc-skill{ padding-top:3px; }
    .wc-info-panel{ padding-top:5px; padding-bottom:5px; }
  }
  /* 🔴 Экран ниже 340 точек — телефон Andy в полном экране бывает и таким.
     Кегли уже на нижних пределах, поэтому здесь снимаем ЛИШНЕЕ, а не мельчим:
     строка «сколько очков до звания» повторяет то, что показывает полоска
     над ней, — на таком экране она уступает место. */
  @media (max-height:340px){
    .wc-nextrank{ display:none; }
    .wc-power{ margin:2px 0 3px; }
    .wc-info-panel{ padding-top:4px; padding-bottom:4px; }
    .wc-skill{ padding-top:2px; }
    .wc-chips{ gap:3px 5px; }
    .wc-def-title{ margin-bottom:1px; }
  }
  /* Совсем низкий экран: бойцу отдаём меньше ширины, рейку гнёзд поджимаем. */
  @media (max-height:380px){
    .wc-fighter-panel{ flex-basis:222px; padding:6px 4px; gap:5px; }
    .wc-info-title{ padding-right:70px; }
  }

  /* ---- окно Statistics: сюда уехала биография бойца (V70, 17.09.2026) ---- */
  /* два столбца, пока хватает ширины: числа слева, таблица «с кем дрался»
     справа. Иначе на телефоне в альбомной окно уезжало вниз на две высоты. */
  .wc-stat-cols{ display:flex; flex-wrap:wrap; gap:4px 18px; }
  .wc-stat-side{ flex:1 1 168px; min-width:0; }
  .wc-stat-block{ margin-bottom:10px; }
  /* 🔴 Сетка, а не ряд: подпись и число стоят в строке, пояснение уходит целой
     строкой ниже. Рядом они ломали подпись пополам («Blocked … blows»). */
  .wc-stat-line{ display:grid; grid-template-columns:1fr auto; align-items:baseline; gap:1px 10px;
    padding:4px 0; border-bottom:1px dashed rgba(217,180,92,0.22); }
  .wc-stat-line span{ grid-column:1; font-size:14px; color:var(--c-gold-dim); }
  .wc-stat-line b{ grid-column:2; font-family:'Cinzel',serif; font-size:17px; font-weight:700; color:var(--c-gold-bright); }
  .wc-stat-line small{ grid-column:1 / -1; font-size:11.5px; color:var(--c-gold-dim); opacity:0.75; }
  .wc-stat-head{ font-family:'Cinzel',serif; font-size:14px; font-weight:700; color:var(--c-gold); letter-spacing:0.04em; margin:4px 0 6px; }
  .wc-stat-table{ width:100%; border-collapse:collapse; font-size:13.5px; }
  .wc-stat-table th{ text-align:left; padding:3px 4px; font-family:'Cinzel',serif; font-weight:700; font-size:12.5px; color:var(--c-gold-dim); letter-spacing:0.04em; }
  .wc-stat-table td{ padding:3px 4px; border-top:1px solid rgba(217,180,92,0.18); color:var(--c-gold-bright); }

  .menu-coin-icon{
    object-fit:contain; display:block;
    filter:drop-shadow(0 2px 4px rgba(0,0,0,0.6));
  }

  /* Кастомный чекбокс "I'm available for battle" в стиле золото/резьба */
  .menu-avail-check{ appearance:none; -webkit-appearance:none; width:16px; height:16px; margin:0;
    border:1.5px solid rgba(217,180,92,0.6); border-radius:var(--r-xs); background:var(--glass-btn);
    cursor:pointer; position:relative; flex-shrink:0;
  }
  .menu-avail-check:checked{ background:rgba(217,180,92,0.85); border-color:var(--c-gold-bright); }
  .menu-avail-check:checked::after{ content:'✓'; position:absolute; inset:0; display:flex; align-items:center; justify-content:center; font-size:12px; font-weight:900; color:var(--c-wood-800); }

  /* Панель "Or challenge a player directly" — тёмное стекло + золото, как попапы */

  .menu-challenge-panel{
    background:rgba(10,8,6,0.6); border:1px solid var(--glass-line);
    backdrop-filter:blur(8px); -webkit-backdrop-filter:blur(8px);
    box-shadow:0 6px 20px rgba(0,0,0,0.5), inset 0 0 24px rgba(0,0,0,0.3);
  }



  #onlineList p{ color:var(--c-gold-dim) !important; }
  #onlineList div{ color:#e0918c !important; border-color:rgba(255,255,255,0.15) !important; background:rgba(0,0,0,0.2); }
  /* строки игроков: маленькая плита, цвет подписи задаёт код по состоянию игрока */
  #onlineList .online-player-btn{ --btn-s:0.16; min-height:32px; padding:6px 10px; font-size:14px; font-weight:600; text-align:left; }

  @keyframes waitingSpin{ to{ transform:rotate(360deg); } }

  /* ===== ЧАТ (16.09.2026) — одно окно на все беседы =====
     Прежний вид собирался в августе и с тех пор только чинился по сути: четыре
     окна-близнеца по 320 точек, синий кружок вызова, серые подписи — язык, на
     котором игра больше нигде не говорит. Здесь всё приведено к общему: тёмное
     стекло с золотой вязью (.pm-card), заголовок каменной плитой, кнопки — плита
     из единого набора.
     🔴 Мелкие значки (⚑, «‹», «✕») кнопками НЕ делаются, а если делаются —
     носят класс .no-slab: любая кнопка внутри окна одевается в плиту, и её края
     в 37 точек налезают на текст сообщения. Это и была жалоба Andy. */
  #chatHubBtn{
    position:fixed; right:14px; bottom:14px; z-index:59;
    width:58px; height:44px; --btn-s:0.16; padding:0;
    display:none; align-items:center; justify-content:center;
    color:var(--c-gold-bright); cursor:pointer;
  }
  #chatHubBtn svg{ width:22px; height:22px; position:relative; z-index:3; }
  #chatHubBtnDot{
    position:absolute; top:3px; right:6px; width:11px; height:11px; border-radius:var(--r-round);
    background:var(--fill-danger); border:2px solid rgba(0,0,0,0.55); display:none; z-index:4;
  }

  /* Значок чата — один рисунок на все кнопки игры (V3). Смайлик 💬 был последним
     эмодзи в интерфейсе: на телефоне и на ПК он рисуется системным шрифтом и
     выглядит гостем из другой игры. Цвет берётся от подписи кнопки. */
  .chat-ico{ display:inline-flex; width:17px; height:17px; vertical-align:-3px; margin-right:6px; flex-shrink:0; }
  .chat-ico svg{ width:100%; height:100%; display:block; }

  /* --- окно целиком --- */
  /* Запросы в друзья в окне чата (27.09.2026). */
  .chat-req-row{ display:flex; flex-direction:column; gap:6px; padding:8px 6px 10px; border-bottom:1px solid rgba(217,180,92,0.14); }
  .chat-req-text{ display:flex; flex-direction:column; min-width:0; }
  .chat-req-name{ font-weight:700; color:var(--gold-bright,#f3e2bd); overflow:hidden; text-overflow:ellipsis; white-space:nowrap; }
  .chat-req-sub{ font-size:12px; color:var(--text-muted,#b8a98c); }
  .chat-req-btns{ display:flex; gap:8px; }
  .chat-req-btns .btn{ flex:1 1 0; }
  /* Правила сообщества: ссылка в списке бесед и окно перед первым сообщением (27.09.2026). */
  .chat-rules-link{ display:block; margin:14px 4px 2px; font-size:13px; color:var(--text-muted,#b8a98c); text-decoration:underline; }
  .chat-rules-card{ padding:22px 22px 18px; width:360px; max-width:calc(100vw - 32px); max-height:calc(100dvh - 20px); overflow-y:auto; box-sizing:border-box; text-align:left; }
  .chat-rules-title{ font-family:'Cinzel',serif; font-size:18px; font-weight:700; margin:0 0 10px; text-align:center; color:var(--gold-bright,#f3e2bd); }
  .chat-rules-lead{ font-size:14px; line-height:1.45; margin:0 0 8px; }
  .chat-rules-list{ font-size:14px; line-height:1.45; margin:0 0 10px; padding-left:20px; }
  .chat-rules-full{ font-size:13px; margin:0 0 14px; text-align:center; }
  .chat-rules-full a{ color:var(--gold-bright,#f3e2bd); }
  .chat-rules-btns{ display:flex; gap:10px; justify-content:center; }
  .pm-card .chat-rules-btns .btn{ flex:1 1 0; }
  .chat-overlay{
    position:fixed; inset:0; z-index:58; box-sizing:border-box;
    padding:10px; padding-top:calc(var(--bars-h,0px) + 10px);
    background:rgba(0,0,0,0.55);
    display:flex; align-items:center; justify-content:center;
  }
  .chat-window{
    width:min(980px, 100%); height:min(620px, 100%);
    padding:10px 14px 12px; box-sizing:border-box;
    display:flex; flex-direction:column; overflow:hidden;
  }
  .chat-head{ display:flex; align-items:center; gap:8px; flex-shrink:0; padding:0 0 8px; }
  /* Плита-заголовок растянута по тексту, а не по картинке: с aspect-ratio плиты
     заголовок «Global chat» либо не влезал, либо задирал голову окна на треть
     высоты телефона в альбомной. */
  .chat-head-title{
    flex:0 1 auto; margin:0 auto; min-width:170px; max-width:60%; height:38px; padding:0 30px;
    font-family:'Pirata One','Cinzel',serif; font-weight:400; font-size:19px; letter-spacing:0.06em;
    text-shadow:0 2px 6px rgba(0,0,0,0.85); white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
  }
  .chat-head .chat-head-btn{
    flex-shrink:0; width:34px; height:34px; padding:0; border:0; background:none;
    color:var(--c-gold); font-size:22px; line-height:1; cursor:pointer;
    display:flex; align-items:center; justify-content:center; border-radius:var(--r-round);
  }
  .chat-head .chat-head-btn:hover{ color:var(--c-gold-hot); background:rgba(217,180,92,0.12); }

  .chat-body{ flex:1; min-height:0; display:flex; gap:10px; }
  .chat-side{
    width:216px; flex-shrink:0; overflow-y:auto; box-sizing:border-box;
    display:flex; flex-direction:column; gap:2px;
    background:rgba(0,0,0,0.26); border-radius:10px; padding:6px 5px;
    border:1px solid rgba(217,180,92,0.14);
  }
  .chat-side-label{
    font-family:'Cinzel',serif; font-size:10.5px; letter-spacing:0.12em; text-transform:uppercase;
    color:var(--c-gold-dim); padding:8px 8px 3px;
  }
  .chat-side-label:first-child{ padding-top:2px; }
  .chat-conv{ flex:1; min-width:0; display:flex; flex-direction:column; position:relative; }
  .chat-messages{
    flex:1; min-height:0; overflow-y:auto; box-sizing:border-box;
    display:flex; flex-direction:column; gap:5px; padding:8px 10px;
    background:rgba(0,0,0,0.26); border-radius:10px; border:1px solid rgba(217,180,92,0.14);
  }

  /* --- строки списка бесед --- */
  .chat-side .chathub-row{
    display:flex; align-items:center; gap:9px; width:100%; text-align:left; box-sizing:border-box;
    padding:7px 8px; border:1px solid transparent; border-radius:9px;
    background:transparent; cursor:pointer; font-family:'EB Garamond',serif;
    color:var(--c-gold-bright); min-height:0;
    /* набор кнопок пишет всё полужирным — строке беседы это не идёт */
    font-weight:400; text-shadow:none;
  }
  .chat-side .chathub-row:hover{ background:rgba(217,180,92,0.10); border-color:rgba(217,180,92,0.22); }
  .chat-side .chathub-row--active{ background:rgba(217,180,92,0.17); border-color:rgba(217,180,92,0.40); }
  .chathub-avatar{
    width:32px; height:32px; border-radius:var(--r-round); flex-shrink:0;
    display:flex; align-items:center; justify-content:center; font-size:13px;
    font-family:'Cinzel',serif; font-weight:700; color:var(--c-gold-hot);
    background:rgba(217,180,92,0.16); border:1px solid rgba(217,180,92,0.3);
  }
  .chathub-name{ font-family:'Cinzel',serif; font-size:13.5px; font-weight:700; color:var(--c-gold-bright); }
  .chathub-sub{ font-size:11.5px; color:var(--c-gold-dim); margin-top:1px; }
  .chathub-dot{
    width:9px; height:9px; border-radius:var(--r-round); background:var(--fill-danger);
    flex-shrink:0; display:none; margin-left:auto;
  }
  .chathub-status-dot{ width:8px; height:8px; border-radius:var(--r-round); flex-shrink:0; }
  .chat-empty{
    font-family:'EB Garamond',serif; font-size:12.5px; color:var(--c-gold-dim);
    margin:0; padding:8px 10px; line-height:1.35;
  }
  .chat-empty--mid{ margin:auto; text-align:center; max-width:280px; }

  /* --- лента --- */
  .chat-bubble{
    position:relative; max-width:74%; box-sizing:border-box;
    border-radius:12px; padding:5px 11px 4px;
    border:1px solid rgba(217,180,92,0.16);
  }
  .chat-bubble--mine{ align-self:flex-end; background:rgba(217,180,92,0.15); border-color:rgba(217,180,92,0.32); }
  .chat-bubble--theirs{ align-self:flex-start; background:rgba(0,0,0,0.42); }
  /* сообщение, которое ушло на сервер, но ещё не вернулось из базы */
  .chat-bubble--pending{ opacity:0.55; }
  .chat-bubble--tail{ margin-top:-3px; }
  .chat-bubble .cb-nick{
    font-family:'Cinzel',serif; font-size:11.5px; color:var(--c-gold); margin-bottom:1px;
  }
  .chat-bubble .cb-text{
    font-family:'EB Garamond',serif; font-size:14.5px; line-height:1.32;
    color:var(--c-gold-bright); word-break:break-word; white-space:pre-wrap;
  }
  .chat-bubble .cb-time{ font-size:10px; color:var(--c-gold-dim); margin-top:1px; text-align:right; }
  /* Значок действий: НЕ кнопка (см. красную пометку выше) — span с ролью кнопки. */
  /* Значок стоит СНАРУЖИ пузыря — со стороны пустого поля: у чужого справа, у
     своего слева. Внутри угла он подпирал последнее слово: перекрытия нет, а
     тесно. Снаружи он ничего не касается на любой длине сообщения. */
  .chat-bubble--theirs .cb-flag{ right:-19px; }
  .chat-bubble--mine .cb-flag{ left:-19px; }
  .cb-flag{
    position:absolute; top:50%; transform:translateY(-50%); width:16px; height:16px; padding:0;
    display:flex; align-items:center; justify-content:center;
    font-size:12px; line-height:1; color:var(--c-gold-dim); cursor:pointer;
    opacity:0.5; transition:opacity 0.15s, color 0.15s; user-select:none;
  }
  .cb-flag:hover{ opacity:1; color:var(--c-gold-hot); }
  /* Сообщение, на которое жалоба уже ушла: галочка вместо флажка, видна всегда —
     иначе на второй раз человек снова гадает, отправилось ли. */
  .cb-flag--reported{ color:var(--c-success-lit); opacity:0.9; }
  @media (hover:hover){ .chat-bubble .cb-flag--reported{ opacity:0.75; } }
  @media (hover:hover){ .chat-bubble .cb-flag{ opacity:0; } .chat-bubble:hover .cb-flag{ opacity:0.75; } }
  .chat-day{
    align-self:center; font-family:'Cinzel',serif; font-size:10.5px; letter-spacing:0.1em;
    text-transform:uppercase; color:var(--c-gold-dim);
    background:rgba(0,0,0,0.4); border-radius:8px; padding:2px 10px; margin:4px 0 1px;
  }
  .chat-new-line{
    display:flex; align-items:center; gap:8px; margin:3px 0 1px;
    font-family:'Cinzel',serif; font-size:10.5px; letter-spacing:0.1em; text-transform:uppercase;
    color:var(--c-danger-lit);
  }
  .chat-new-line::before, .chat-new-line::after{
    content:''; flex:1; height:1px; background:rgba(214,106,74,0.45);
  }
  .chat-jump{
    position:absolute; left:50%; transform:translateX(-50%); bottom:56px; z-index:5;
    --btn-s:0.14; font-size:12px; min-height:26px; padding:3px 12px; white-space:nowrap;
  }

  /* --- строка ввода --- */
  .chat-input-row{ display:flex; align-items:center; gap:8px; padding-top:8px; flex-shrink:0; }
  .chat-input-row input{ flex:1; min-width:0; box-sizing:border-box; padding:9px 12px; font-size:15px; }
  /* Браузерное кольцо фокуса — белое и в этом окне выглядит чужим. Поле должно
     отзываться на нажатие тем же золотом, что и всё вокруг. */
  .chat-input-row input:focus{
    outline:none;
    border-color:var(--c-gold) !important;
    box-shadow:0 0 0 1px rgba(217,180,92,0.35), inset 0 1px 6px rgba(0,0,0,0.6);
  }
  /* «Send» (G75, 26.09.2026). Andy: «в чате нет кнопки "отправить"». Кнопка была, но
     её размер одним классом проигрывал набору кнопок (вес .pm-card button выше) —
     она выходила мелким камешком 53×30 у самого края, и глаз её не находил. Теперь
     два класса, высота вровень со строкой ввода, подпись главного действия.
     Тусклая, пока строка пуста (aria-disabled ставит 04-chat.js) — как выключенная
     кнопка набора, но палец по ней не проваливается и клавиатура не сворачивается. */
  .chat-input-row .chat-send{
    --btn-s:0.18; flex-shrink:0; min-width:84px; min-height:40px; padding:6px 20px;
    font-size:16px; letter-spacing:0.04em;
  }
  .chat-input-row .chat-send[aria-disabled="true"]{
    opacity:0.45; cursor:default; color:var(--c-gold-bright); text-shadow:0 1px 3px rgba(0,0,0,0.9);
  }
  .chat-input-row .chat-send[aria-disabled="true"]::after{ opacity:0; }
  .chat-chars{ font-size:11px; color:var(--c-gold-dim); min-width:24px; text-align:right; display:none; }
  .chat-chars--near{ display:block; color:var(--c-danger-lit); }

  /* --- узкий экран: колонки по очереди --- */
  @media (min-width:760px){ #chatBackBtn{ display:none; } }
  @media (max-width:759px){
    .chat-side{ width:100%; }
    .chat-window[data-view="list"] .chat-conv{ display:none; }
    .chat-window[data-view="conv"] .chat-side{ display:none; }
    .chat-bubble{ max-width:86%; }
  }
  @keyframes firstStrikePulse{
    0%,100%{ transform:scale(1); opacity:0.92; }
    50%{ transform:scale(1.14); opacity:1; }
  }
  .first-strike-icon{
    position:absolute; top:6%; font-size:32px; line-height:1; color:var(--c-gold-hot);
    text-shadow:0 0 14px rgba(255,213,74,0.85), 0 3px 8px rgba(0,0,0,0.9), 0 0 5px rgba(0,0,0,0.95);
    display:none; z-index:47; pointer-events:none;
    animation:firstStrikePulse 1.2s ease-in-out infinite;
  }

  /* =====================================================================
     НАСТАВНИК (22-coach.js) — подсветка живого интерфейса вместо табличек.

     Устройство: затемнение собрано из ЧЕТЫРЁХ панелей вокруг подсвеченного
     места, а не из одной с дыркой. Причина простая: дырка, вырезанная тенью
     (box-shadow spread), не ловит нажатия — сквозь «затемнение» можно было бы
     ткнуть куда угодно. Четыре панели ловят нажатия сами, а промежуток между
     ними и есть окно, в которое проходит палец. Ровно то, что нужно шагу
     «выбери три удара»: мимо не нажмёшь.

     Кольцо (#coachRing) поверх — только рисунок, нажатий не ловит.

     Почему координаты считаются от самого элемента (getBoundingClientRect),
     а не забиты числами: боевой холст 1700x760 целиком масштабируется через
     transform под окно, и любые вбитые координаты разъехались бы на первом
     же телефоне.
     ===================================================================== */
  /* 🔴 Слой сам нажатий НЕ ловит — иначе он накрыл бы весь экран и окно в
     затемнении перестало бы быть окном. Ловят только четыре панели и карточка. */
  #coachOverlay{ position:fixed; inset:0; z-index:64; display:none; pointer-events:none; }
  #coachOverlay.coach-on{ display:block; }
  .coach-scrim{
    position:fixed; pointer-events:auto; background:rgba(6,4,3,0.72);
    transition:top .3s cubic-bezier(.2,.8,.25,1), left .3s cubic-bezier(.2,.8,.25,1),
               width .3s cubic-bezier(.2,.8,.25,1), height .3s cubic-bezier(.2,.8,.25,1);
  }
  #coachRing{
    position:fixed; pointer-events:none; display:none;
    border:2px solid var(--c-gold); border-radius:var(--r-lg);
    box-shadow:0 0 0 1px rgba(6,4,3,0.9), 0 0 24px 5px rgba(217,180,92,0.42),
               inset 0 0 16px rgba(217,180,92,0.18);
    transition:top .3s cubic-bezier(.2,.8,.25,1), left .3s cubic-bezier(.2,.8,.25,1),
               width .3s cubic-bezier(.2,.8,.25,1), height .3s cubic-bezier(.2,.8,.25,1);
    animation:coachRingPulse 2.2s ease-in-out infinite;
  }
  @keyframes coachRingPulse{
    0%,100%{ box-shadow:0 0 0 1px rgba(6,4,3,0.9), 0 0 20px 3px rgba(217,180,92,0.34),
                        inset 0 0 16px rgba(217,180,92,0.14); }
    50%{ box-shadow:0 0 0 1px rgba(6,4,3,0.9), 0 0 30px 8px rgba(217,180,92,0.55),
                    inset 0 0 18px rgba(217,180,92,0.24); }
  }
  /* Карточка — тот же .pm-card, что у всех окон игры: тёмное стекло и резная
     золотая рамка приходят оттуда, здесь только размер и разбивка. */
  #coachCard{
    position:fixed; pointer-events:auto; width:min(320px, calc(100vw - 28px));
    padding:15px 17px 13px; box-sizing:border-box;
    transition:top .3s cubic-bezier(.2,.8,.25,1), left .3s cubic-bezier(.2,.8,.25,1);
    animation:coachCardIn .26s ease-out;
  }
  @keyframes coachCardIn{ from{ opacity:0; transform:translateY(9px); } to{ opacity:1; transform:none; } }
  /* Ромб-указатель от карточки к подсвеченному месту. Ставится за резной
     рамкой (::before у .pm-card занимает inset:0), поэтому вынесен наружу
     отрицательным отступом и своим z-index. */
  .coach-beak{
    position:absolute; width:12px; height:12px; z-index:3;
    background:linear-gradient(135deg,#e6c87d,var(--c-gold));
    border:1px solid var(--c-gold-bright); transform:rotate(45deg);
    box-shadow:0 0 10px rgba(217,180,92,0.5);
  }
  .coach-beak.coach-beak-up{ top:-7px; left:calc(50% - 6px); }
  .coach-beak.coach-beak-down{ bottom:-7px; left:calc(50% - 6px); }
  .coach-beak.coach-beak-left{ left:-7px; top:calc(50% - 6px); }
  .coach-beak.coach-beak-right{ right:-7px; top:calc(50% - 6px); }
  #coachTitle{
    font-family:'Cinzel',serif; font-weight:700; font-size:14.5px; letter-spacing:0.04em;
    color:var(--c-gold-bright); margin:0 0 6px; text-transform:uppercase;
  }
  /* Ниша под вещь соперника — знакомство с перками (20.09.2026). Показывается
     только у этих шагов, у остальных прячется скриптом. Картинки вещей лежат на
     чёрном фоне (img/items_jpg), поэтому ниша тоже тёмная: тогда не видно шва
     между картинкой и рамой. */
  /* Зачин карточки перка: «Look at your opponent's SWORD:» — название гнезда
     в цвете, чтобы человек связал перк с конкретной железкой (правка Andy
     21.09.2026). Пусто и не видно у всех остальных шагов. */
  #coachLead{
    display:none; margin:0 0 7px; font-size:13.5px; font-style:italic;
    color:rgba(243,226,189,0.72); text-shadow:0 1px 3px rgba(0,0,0,0.75);
  }
  /* Шутка — своей строкой, курсивом и приглушённо: глаз сразу отделяет дело
     от прибаутки. Кегль вровень с основным текстом (правка Andy 21.09.2026:
     «размер текста шутки маловат»). */
  #coachJoke{
    display:none; margin:6px 0 0; font-size:16px; line-height:1.45; font-style:italic;
    color:rgba(243,226,189,0.72); text-shadow:0 1px 3px rgba(0,0,0,0.75);
  }
  /* 🔴 Цветное НЕ РУБИТСЯ ПЕРЕНОСОМ (правка Andy 21.09.2026): формула висит
     одним куском. Поэтому куски в текстах нарочно короткие — длинную цветную
     фразу в карточку 320 точек одной строкой не втиснуть. */
  .coach-k{ font-weight:700; font-size:17.5px; white-space:nowrap; }
  /* Карточка знакомства с перком: название перка крупное — на нём держится вся
     карточка (форма Andy 21.09.2026). У остальных шагов заголовок прежний. */
  #coachCard.coach-perk-card #coachTitle{ font-size:21px; line-height:1.12; margin-bottom:9px; }
  #coachArt{
    display:none; margin:0 0 8px; padding:4px;
    background:rgba(0,0,0,0.55);
    border:1px solid var(--c-gold-dim, rgba(200,168,90,0.45));
    border-radius:5px; text-align:center;
  }
  #coachArtImg{
    display:block; width:100%; height:88px; object-fit:contain; border-radius:3px;
  }
  /* 🔴 ЧИТАЕМОСТЬ ТЕКСТА НАСТАВНИКА (U15, Andy 19.09.2026: «текст описания
     наставника — мелковат и сероват, плохо читается»).
     Было 14px цветом 86% от пергамента — на светлом кадре боя буквы сливались
     с полупрозрачной карточкой. Стало 16px полным цветом пергамента, строка
     чуть просторнее и тень под буквами: она отрывает их от того, что за
     карточкой, а без неё цвет пришлось бы гнать в белый и терять голос. */
  #coachText{
    font-family:'EB Garamond',serif; font-size:16px; line-height:1.55;
    color:var(--text-primary); margin:0;
    text-shadow:0 1px 2px rgba(0,0,0,0.75);
  }
  #coachFoot{
    display:flex; align-items:center; gap:8px; margin-top:13px;
  }
  #coachDots{ display:flex; gap:5px; margin-right:auto; }
  .coach-dot{
    width:6px; height:6px; border-radius:var(--r-round);
    border:1px solid var(--glass-line-lit); background:none;
  }
  .coach-dot.coach-dot-on{ background:var(--c-gold); border-color:var(--c-gold); }
  #coachFoot button{ --btn-s:0.16; font-size:13.5px; min-height:32px; padding:6px 14px; }
  /* Шаг, который ждёт действия игрока: вместо кнопки «дальше» — счётчик
     сделанного. Он же объясняет, почему кнопки нет. */
  #coachWait{
    font-family:'EB Garamond',serif; font-size:12.5px; font-weight:600;
    color:var(--c-gold-hot); letter-spacing:0.03em; margin-left:auto;
    animation:coachWaitPulse 1.6s ease-in-out infinite;
  }
  @keyframes coachWaitPulse{ 0%,100%{ opacity:0.62; } 50%{ opacity:1; } }
  /* Подсказка-оговорка: без затемнения и без кнопок, сама уходит.
     Занимает место полноэкранного окна «выбери три удара и три блока». */
  #coachNudge{
    position:fixed; z-index:67; display:none; pointer-events:none;
    width:max-content; max-width:min(280px, calc(100vw - 24px));
    padding:9px 13px; box-sizing:border-box; border-radius:var(--r-md);
    background:var(--glass-solid); border:1px solid var(--glass-line-lit);
    box-shadow:0 6px 22px rgba(0,0,0,0.5);
    font-family:'EB Garamond',serif; font-size:13.5px; line-height:1.4;
    color:var(--c-gold-bright);
    animation:coachCardIn .2s ease-out;
  }
  /* Телефон в альбомной — единственный вид телефона, который игра допускает
     (вертикальный она закрывает просьбой повернуть). Экран там низкий, а не
     узкий, поэтому подгоняемся по высоте, а не по ширине. */
  @media (max-width:560px), (max-height:430px){
    #coachCard{ padding:11px 13px 10px; width:min(300px, calc(100vw - 24px)); }
    #coachTitle{ font-size:13px; margin-bottom:4px; }
    /* На телефоне в альбомной высота на вес золота: ниша ужимается, но не
       исчезает — про вещь и говорим. */
    #coachArt{ margin-bottom:6px; padding:3px; }
    #coachArtImg{ height:62px; }
    #coachLead{ font-size:12.5px; margin-bottom:5px; }
    #coachJoke{ font-size:14px; margin-top:5px; }
    .coach-k{ font-size:15.5px; }
    #coachCard.coach-perk-card #coachTitle{ font-size:18px; margin-bottom:6px; }
    /* На низком экране телефона карточка ужимается — но не за счёт букв:
       ниже 14px наставника уже не читают на ходу (U15). */
    #coachText{ font-size:14px; line-height:1.5; }
    #coachFoot{ margin-top:10px; }
    #coachFoot button{ font-size:12.5px; padding:5px 11px; }
  }

  /* =====================================================================
     ВЕЩЬ: ПЛИТА И ЦЕРЕМОНИЯ ПОЯВЛЕНИЯ (17.09.2026, задача Andy про гринд)
     Разбор и решение — docs/паспорт/02-контент.md, раздел «Вещь: плита и
     церемония». Коротко, зачем всё ниже.

     Было: вещь показывалась плоским прямоугольником с волосяной рамкой в
     цвет тира, картинка лежала на чёрном поле, текст — мелкий серый. Это
     выпадало из игры, где всё остальное сделано камнем и золотом, и
     обесценивало любой эффект: сцена приводила к форме из браузера.

     🔴 Картинки вещей — JPEG с ЧЁРНЫМ фоном (альфы у них нет). Поэтому
     ниша смешивает картинку режимом screen: чёрное становится прозрачным,
     и вещь светится в каменной нише вместо того, чтобы лежать в чёрном
     квадрате. Отсюда же требование к нише — тёмный фон: на светлом screen
     выбеливает картинку.

     Один набор на пять мест: лавка, окно купленной вещи, окно трофея с
     выбором, карточка гнезда на фигуре, награды турнира.
     ===================================================================== */
  .item-plate{
    --tier:#9aa0a6; --tier-lit:#d6dade; --tier-glow:rgba(154,160,166,0.30); --tier-edge:rgba(154,160,166,0.55);
    position:relative; box-sizing:border-box; overflow:hidden;
    border-radius:var(--r-lg);
    background:linear-gradient(180deg, rgba(28,22,15,0.94), rgba(9,7,5,0.97));
    color:var(--c-gold-bright); font-family:'EB Garamond',serif;
  }
  .item-plate--t1{ --tier:#9aa0a6; --tier-lit:#dfe3e7; --tier-glow:rgba(154,160,166,0.30); --tier-edge:rgba(154,160,166,0.55); }
  .item-plate--t2{ --tier:#4a90d9; --tier-lit:#b6d8fb; --tier-glow:rgba(74,144,217,0.42); --tier-edge:rgba(120,180,240,0.70); }
  .item-plate--t3{ --tier:#c9a227; --tier-lit:#ffdf87; --tier-glow:rgba(201,162,39,0.50); --tier-edge:rgba(230,190,80,0.78); }
  .item-plate--t4{ --tier:#9b6bd1; --tier-lit:#e0c2ff; --tier-glow:rgba(155,107,209,0.52); --tier-edge:rgba(190,140,250,0.80); }
  /* камень: та же плита, что у кнопок, но приглушённая — она фактура, а не кнопка */
  .item-plate::before{
    content:''; position:absolute; inset:0; z-index:0; pointer-events:none; opacity:0.6;
    border:12px solid transparent;
    border-image:url('../img/ui/btn/slab_plain.webp') 88 fill / 1 / 0 stretch;
  }
  /* кайма тира поверх всего: тонкая линия + утопленная тень, как у оправы */
  .item-plate::after{
    content:''; position:absolute; inset:0; z-index:5; pointer-events:none; border-radius:inherit;
    border:1px solid var(--tier-edge);
    box-shadow:inset 0 0 20px rgba(0,0,0,0.75), inset 0 0 26px var(--tier-glow), 0 2px 10px rgba(0,0,0,0.6);
  }
  .item-plate > *{ position:relative; z-index:2; }
  /* горизонтальная (ниша слева, слова справа) и столбиком (лавка) */
  .item-plate--row{ display:flex; align-items:stretch; gap:12px; padding:10px 13px; }
  .item-plate--col{ display:flex; flex-direction:column; align-items:center; gap:6px; padding:9px 10px 11px; text-align:center; }
  .item-plate--dim{ filter:saturate(0.35) brightness(0.72); }
  .item-plate--dim .item-niche img{ opacity:0.72; }

  /* ---- ниша: камень, луч снизу, ореол, кольцо рун, пылинки ---- */
  .item-niche{
    position:relative; flex:0 0 auto; overflow:hidden; border-radius:var(--r-md);
    background:radial-gradient(ellipse at 50% 52%, rgba(4,3,8,0.97) 42%, rgba(4,3,8,0.82) 66%, rgba(4,3,8,0) 88%);
  }
  /* 🔴 Свет в нише держим слабым нарочно. Первая версия светила в полную силу,
     и вещь, смешанная режимом screen, тонула в собственном ореоле: на снимке
     была цветная клякса без меча. Теперь ореол — подложка, а не заливка. */
  /* 🔴 У ниши ДОЛЖЕН быть свой размер по умолчанию. Без него она в любом новом
     месте растягивалась во всю плиту: в окне наград турнира вещь заняла окно
     целиком, а слова исчезли (снимок 17.09.2026). Точечные правила окон ниже
     этот размер перебивают. */
  .item-plate--row .item-niche{ width:clamp(80px, 26vh, 132px); aspect-ratio:1/1; align-self:center; }
  .item-niche img{
    position:relative; z-index:3; display:block; width:100%; height:100%; object-fit:contain;
    mix-blend-mode:screen; animation:itemFloat 4.4s ease-in-out infinite;
    filter:drop-shadow(0 0 9px var(--tier-glow)) drop-shadow(0 3px 6px rgba(0,0,0,0.7));
    /* 🔴 Картинка вещи — непрозрачный JPEG. Без этой маски её края ложились на
       камень чётким прямоугольником (снимок 17.09.2026), и ниша читалась
       наклейкой. Маска растворяет углы, и остаётся свечение в камне. */
    -webkit-mask-image:radial-gradient(ellipse at 50% 50%, #000 56%, rgba(0,0,0,0) 84%);
    mask-image:radial-gradient(ellipse at 50% 50%, #000 56%, rgba(0,0,0,0) 84%);
  }
  .item-niche-beam{
    content:''; position:absolute; left:50%; bottom:-4%; width:132%; height:96%; transform:translateX(-50%);
    background:linear-gradient(0deg, var(--tier-glow), rgba(0,0,0,0) 62%);
    clip-path:polygon(34% 100%, 66% 100%, 92% 0, 8% 0);
    opacity:0.4; animation:itemBeam 5.2s ease-in-out infinite; pointer-events:none; z-index:1;
    filter:blur(3px);
  }
  .item-niche-halo{
    position:absolute; inset:22%; border-radius:50%; pointer-events:none; z-index:1;
    background:radial-gradient(circle, var(--tier-glow), rgba(0,0,0,0) 62%);
    opacity:0.55; filter:blur(6px);
    animation:itemHalo 3.6s ease-in-out infinite;
  }
  /* кольцо рун — только у дорогих вещей: у простых оно было бы обманом */
  .item-niche-runes{ display:none; }
  .item-plate--t3 .item-niche-runes, .item-plate--t4 .item-niche-runes{
    display:block; position:absolute; inset:6%; border-radius:50%; z-index:2; pointer-events:none;
    opacity:0.32; mix-blend-mode:screen;
    background:repeating-conic-gradient(from 0deg, var(--tier-lit) 0deg 1.2deg, rgba(0,0,0,0) 1.2deg 9deg);
    -webkit-mask:radial-gradient(circle, rgba(0,0,0,0) 68%, #000 70%, #000 75%, rgba(0,0,0,0) 77%);
    mask:radial-gradient(circle, rgba(0,0,0,0) 68%, #000 70%, #000 75%, rgba(0,0,0,0) 77%);
    animation:itemSpin 26s linear infinite;
  }
  .item-plate--t4 .item-niche-runes{ opacity:0.5; animation-duration:18s; }
  @keyframes itemFloat{ 0%,100%{ transform:translateY(0); } 50%{ transform:translateY(-4%); } }
  @keyframes itemBeam{ 0%,100%{ opacity:0.3; } 50%{ opacity:0.5; } }
  @keyframes itemHalo{ 0%,100%{ opacity:0.4; transform:scale(0.94); } 50%{ opacity:0.68; transform:scale(1.06); } }
  @keyframes itemSpin{ from{ transform:rotate(0deg); } to{ transform:rotate(360deg); } }

  /* ---- лента тира ---- */
  .item-ribbon{
    display:inline-block; font-family:'Cinzel',serif; font-weight:700; font-size:11.5px; letter-spacing:0.16em;
    color:var(--tier-lit); text-shadow:0 0 12px var(--tier-glow), 0 1px 2px rgba(0,0,0,0.95);
    padding:2px 12px; white-space:nowrap;
    background:linear-gradient(180deg, rgba(0,0,0,0.55), rgba(0,0,0,0.15));
    border-top:1px solid var(--tier-edge); border-bottom:1px solid var(--tier-edge);
  }
  .item-body{ display:flex; flex-direction:column; justify-content:center; min-width:0; flex:1 1 auto; gap:3px; }
  /* 🔴 Плита обязана занять окно. Без этого она жалась влево, и справа
     оставалась пустая стена — окно выглядело недоделанным (снимок 17.09.2026). */
  .item-win-body > .item-plate{ flex:1 1 auto; }
  .item-name{ font-family:'Cinzel',serif; font-weight:700; font-size:15px; color:var(--c-gold-bright); letter-spacing:0.02em; }
  .item-stat{
    font-family:'Cinzel',serif; font-weight:700; font-size:26px; line-height:1.05; color:var(--c-gold-hot);
    text-shadow:0 2px 0 rgba(0,0,0,0.8), 0 0 18px rgba(255,190,70,0.35);
  }
  .item-stat span{ font-family:'EB Garamond',serif; font-size:12.5px; font-weight:400; color:var(--c-gold-dim); letter-spacing:0.06em; }
  .item-perks{ display:flex; flex-direction:column; }
  .item-perk{
    display:flex; align-items:center; gap:7px; padding:3px 0; font-size:12.5px; line-height:1.25;
    border-top:1px solid rgba(217,180,92,0.16);
  }
  .item-perk > span{ flex:1 1 auto; min-width:0; }
  .item-perk > i{ flex:0 0 auto; margin-left:auto; }
  .item-perk:first-child{ border-top:none; }
  .item-perk :is(svg, img.perk-ico){ flex:0 0 auto; margin-top:1px; width:20px; height:20px;
    filter:drop-shadow(0 1px 1.5px rgba(0,0,0,0.85)); }
  .item-perk b{ font-family:'Cinzel',serif; font-weight:700; color:var(--c-gold-bright); }
  .item-perk i{ font-style:normal; font-weight:700; color:var(--c-gold-hot); }
  /* объяснение перка: спрятано, разворачивается по нажатию (17.09.2026) */
  .item-perk{ cursor:help; }
  .item-perk:focus-visible{ outline:1px solid var(--glass-line-lit); outline-offset:2px; }
  .item-perk-ask{
    font-style:normal; font-size:10px; font-weight:700; margin-left:5px; padding:0 4px;
    border:1px solid rgba(217,180,92,0.45); border-radius:50%; color:var(--c-gold-dim); opacity:0.75;
  }
  @media (hover:hover){ .item-perk:hover .item-perk-ask{ opacity:1; color:var(--c-gold-hot); border-color:var(--c-gold-hot); } }

  /* ---- всплывающее объяснение перка (17.09.2026) --------------------------
     🔴 Жалоба Andy: «таблица резко разъезжается вверх… плюс белым некрасивым
     окном просто дублируется надпись». Подсказок было две: системный ярлычок
     браузера (атрибут title — покрасить нельзя, только снять) и текст ВНУТРИ
     строки, под который таблица честно раздвигалась.
     Теперь окошко одно, лежит поверх страницы (position:fixed) и раскладку не
     трогает ни на точку. Мышь его не ловит (pointer-events:none) — иначе оно
     само бы гасило наведение на строку под собой. */
  .item-tip{
    position:fixed; z-index:400; left:0; top:0; max-width:min(300px, 92vw);
    padding:7px 11px 8px; box-sizing:border-box; pointer-events:none;
    font-family:'EB Garamond',serif; font-size:12.5px; line-height:1.32;
    color:#e6d6b0; text-align:left;
    background:linear-gradient(180deg, rgba(30,23,14,0.97), rgba(15,11,7,0.97));
    border:1px solid rgba(217,180,92,0.55); border-radius:6px;
    box-shadow:0 7px 22px rgba(0,0,0,0.6), inset 0 0 16px rgba(0,0,0,0.5);
    opacity:0; visibility:hidden; transition:opacity 0.12s ease;
  }
  .item-tip.is-on{ opacity:1; visibility:visible; }
  .item-tip b{
    display:block; margin-bottom:2px; font-family:'Cinzel',serif; font-size:12px;
    font-weight:700; color:var(--c-gold-bright); letter-spacing:0.03em;
  }
  .item-tip::after{
    content:''; position:absolute; left:var(--tip-x, 50%); transform:translateX(-50%);
    width:0; height:0; border-left:7px solid transparent; border-right:7px solid transparent;
  }
  .item-tip:not(.item-tip--below)::after{ top:100%; border-top:7px solid rgba(217,180,92,0.55); }
  .item-tip--below::after{ bottom:100%; border-bottom:7px solid rgba(217,180,92,0.55); }
  /* 🔴 ОКНО РАЗБОРА УДАРА (V104/V108, 21.09.2026) — тот же камень, что у
     .item-tip выше. Оно одно на три содержимого: разбор удара, из чего собрана
     защита зоны и из чего собрана сила удара. Строка в нём из трёх частей:
     название слева, итог покрупнее золотом, за тире — из чего он собрался.
     Порядок столбцов держит min-width у названия: числа встают в колонку, и
     глаз бежит по ней, не читая всего подряд. */
  .strike-tip{
    box-sizing:border-box; max-width:min(360px, 92vw); padding:9px 12px 10px;
    font-family:'EB Garamond',serif; font-size:12.5px; line-height:1.35;
    color:#e6d6b0; text-align:left;
    background:linear-gradient(180deg, rgba(30,23,14,0.97), rgba(15,11,7,0.97));
    border:1px solid rgba(217,180,92,0.55); border-radius:6px;
    box-shadow:0 7px 22px rgba(0,0,0,0.6), inset 0 0 16px rgba(0,0,0,0.5);
  }
  .strike-tip .tip-row{ display:flex; gap:7px; align-items:baseline; margin:1px 0; }
  .strike-tip .tip-k{
    font-family:'Cinzel',serif; font-size:11px; font-weight:700; letter-spacing:0.06em;
    color:var(--c-gold); flex:0 0 auto; min-width:74px;
  }
  .strike-tip .tip-v{
    font-family:'Cinzel',serif; font-size:13.5px; font-weight:700;
    color:var(--c-gold-hot); flex:0 0 auto;
  }
  .strike-tip .tip-s{ color:#bda97e; }
  /* 🔵 ИТОГ УДАРА ОТДЕЛЁН ЧЕРТОЙ (просьба Andy 21.09.2026: «тотальный damage
     тоже нужно выделить немного»). Раньше TOTAL стоял такой же строкой, как всё
     остальное, и терялся в списке — хотя это единственное число, ради которого
     список и читают. Черта тонкая и золотая: отделяет, но не рвёт окно надвое. */
  .strike-tip .tip-row--total{
    margin-top:4px; padding-top:4px;
    border-top:1px solid rgba(217,180,92,0.38);
  }
  .strike-tip .tip-row--total .tip-k{ color:var(--c-gold-bright); }
  .strike-tip .tip-row--total .tip-v{ font-size:16px; color:var(--c-gold-hot);
    text-shadow:0 0 12px rgba(255,213,74,0.45); }
  /* Заголовок внутри окна — им разделены «Attack» и «Sword perks» в разборе
     силы удара: это не строка с числом, а подпись над группой. */
  .strike-tip .tip-head{
    font-family:'Cinzel',serif; font-size:11px; font-weight:700; letter-spacing:0.1em;
    color:var(--c-gold-bright); text-transform:uppercase; margin:6px 0 2px;
  }
  .strike-tip .tip-head:first-child{ margin-top:0; }
  .strike-tip .tip-line{ margin:1px 0; }
  @media (max-width:760px){
    .strike-tip{ font-size:11.5px; padding:7px 10px 8px; max-width:min(320px, 92vw); }
    .strike-tip .tip-k{ min-width:64px; font-size:10px; }
    .strike-tip .tip-v{ font-size:12.5px; }
    .strike-tip .tip-row--total .tip-v{ font-size:14.5px; }
  }

  .item-none{ font-size:12.5px; color:var(--c-gold-dim); opacity:0.7; font-style:italic; }

  /* ---- столбик разницы между старой и новой вещью ---- */
  /* то, что не по карману */
  .item-plate--poor{ opacity:0.45; filter:saturate(0.4); }
  .item-diff{
    display:flex; flex-direction:column; align-items:center; justify-content:center; gap:5px;
    flex:0 0 auto; min-width:78px; padding:0 4px; text-align:center;
    font-family:'Cinzel',serif; font-size:13px;
    background:linear-gradient(90deg, rgba(217,180,92,0) 0%, rgba(217,180,92,0.16) 50%, rgba(217,180,92,0) 100%);
    -webkit-mask:linear-gradient(180deg, transparent, #000 18%, #000 82%, transparent);
    mask:linear-gradient(180deg, transparent, #000 18%, #000 82%, transparent);
  }
  .item-diff-row{ white-space:nowrap; text-shadow:0 1px 2px rgba(0,0,0,0.9); }
  .item-diff-row small{ display:block; font-family:'EB Garamond',serif; font-size:10.5px; letter-spacing:0.08em; color:var(--c-gold-dim); }
  .item-diff .up{ color:var(--c-success-lit); }
  .item-diff .down{ color:var(--c-danger-lit); }
  .item-diff .same{ color:var(--c-gold-dim); }
  .item-diff-arrow{ font-size:17px; line-height:1; color:var(--c-gold); opacity:0.8; }

  /* ---- цена в лавке ---- */
  .item-price{ display:flex; align-items:center; justify-content:center; gap:5px; white-space:nowrap; }
  .item-price svg{ flex:0 0 auto; }

  /* =====================================================================
     ЦЕРЕМОНИЯ. Слои лежат внутри самого окна: затемнение, холст искр и
     вспышка. Тычок по экрану обрывает её и показывает карточку целиком —
     на двадцатой вещи никакая красота не должна стоять на пути.
     ===================================================================== */
  .item-scene{ position:fixed; inset:0; z-index:0; pointer-events:none; }
  /* 🔴 Искры и вспышка — ПОВЕРХ карточки. Первая сборка держала их под ней, и
     весь сноп бил в обратную сторону экрана: на записи сцены видны были только
     края колец, выходящие за окно (разбор 17.09.2026). */
  .item-scene--top{ z-index:5; }
  .item-scene-dark{ position:absolute; inset:0; background:#000; opacity:0; transition:opacity 0.45s ease; }
  .item-scene-fx{ position:absolute; inset:0; width:100%; height:100%; }
  /* вспышка бьёт из ниши, а не из середины экрана: место ставит JS (--fx-x/--fx-y) */
  /* 🔴 Вспышка бьёт НА ВЕСЬ ЭКРАН (17.09.2026). Была в 260 точек — на телефоне
     это пятно вокруг карточки, и удар читался как «мигнуло». Радиус теперь
     ставит JS по цене вещи (--fx-r), и у магической он больше экрана. */
  .item-scene-flash{
    position:absolute; inset:0; opacity:0; mix-blend-mode:screen;
    background:radial-gradient(circle var(--fx-r,420px) at var(--fx-x,50%) var(--fx-y,50%), rgba(255,255,255,0.96) 0%, var(--tier, #fff) 26%, rgba(0,0,0,0) 74%);
  }
  .item-scene-flash.on{ animation:itemFlash 0.42s ease-out; }
  @keyframes itemFlash{ 0%{ opacity:0.82; } 26%{ opacity:0.4; } 100%{ opacity:0; } }
  .item-shake{ animation:itemShake 0.55s cubic-bezier(.36,.07,.19,.97); }
  @keyframes itemShake{
    0%,100%{ transform:translate3d(0,0,0); }
    12%{ transform:translate3d(-7px,4px,0) rotate(-0.5deg); }
    26%{ transform:translate3d(6px,-4px,0) rotate(0.45deg); }
    42%{ transform:translate3d(-5px,-2px,0); }
    58%{ transform:translate3d(4px,3px,0) rotate(-0.25deg); }
    76%{ transform:translate3d(-2px,-1px,0); }
  }
  .item-hidden{ opacity:0 !important; }
  .item-in-stamp{ animation:itemStamp 0.42s cubic-bezier(.2,1.45,.35,1) both; }
  @keyframes itemStamp{
    0%{ opacity:0; transform:scale(2.3); filter:blur(7px); }
    55%{ opacity:1; filter:blur(0); }
    100%{ opacity:1; transform:scale(1); filter:blur(0); }
  }
  .item-in-rise{ animation:itemRise 0.5s cubic-bezier(.16,.9,.3,1) both; }
  @keyframes itemRise{ from{ opacity:0; transform:translateY(16px); } to{ opacity:1; transform:translateY(0); } }
  .item-in-perk{ animation:itemPerkIn 0.3s cubic-bezier(.2,1.3,.35,1) both; }
  @keyframes itemPerkIn{ from{ opacity:0; transform:translateX(-14px); } to{ opacity:1; transform:translateX(0); } }
  /* вещь в нише поднимается из столба света — только у дорогих */
  .item-in-summon .item-niche img{ animation:itemSummon 1.1s cubic-bezier(.16,.85,.3,1) both, itemFloat 4.4s ease-in-out 1.1s infinite; }
  @keyframes itemSummon{ from{ opacity:0; transform:translateY(46%) scale(0.72); filter:brightness(2.4) blur(4px); } to{ opacity:1; transform:translateY(0) scale(1); filter:brightness(1) blur(0); } }

  /* =====================================================================
     ОКНА ВЕЩЕЙ — АЛЬБОМНЫЕ, БЕЗ ПРОКРУТКИ (17.09.2026).
     🔴 Игра идёт только в альбомной: на телефоне это 412 точек высоты и
     915 ширины. Прежние окна были вертикальными карточками в 280–340 точек
     посреди пустого экрана, и содержимое уходило вниз под край: в окне
     трофея из 912 точек было видно 286 — кнопок выбора не видно вовсе.
     Теперь всё раскладывается поперёк, а кнопки прибиты к низу окна.
     ===================================================================== */
  .item-win{
    width:min(96vw, 860px); max-height:calc(100vh - 20px);
    display:flex; flex-direction:column; gap:8px; padding:12px 16px 13px; box-sizing:border-box;
  }
  .item-win-head{ display:flex; align-items:center; justify-content:space-between; gap:12px; flex:0 0 auto; }
  .item-win-title{ font-family:'Cinzel',serif; font-weight:700; font-size:15px; color:var(--c-gold-bright); margin:0; letter-spacing:0.03em; }
  .item-win-sub{ font-family:'EB Garamond',serif; font-size:12.5px; color:var(--c-gold-dim); margin:0; }
  .item-win-body{ flex:1 1 auto; min-height:0; display:flex; gap:10px; align-items:stretch; }
  .item-win-foot{ flex:0 0 auto; display:flex; gap:10px; align-items:center; justify-content:center; }
  .item-win-foot button{ min-width:132px; }
  .item-purse{ display:flex; align-items:center; gap:6px; font-family:'Cinzel',serif; font-weight:700; font-size:15px; color:var(--c-gold-hot); white-space:nowrap; }
  .item-purse svg{ flex:0 0 auto; }
  /* лавка: четыре тира в ряд поперёк экрана */
  .shop-row{ display:grid; grid-template-columns:repeat(4, 1fr); gap:9px; flex:1 1 auto; min-height:0; }
  .shop-row .item-plate{ min-height:0; }
  /* ниша тира — КВАДРАТ: с width:100% и потолком высоты она выходила широкой
     полосой, и вещь в ней лежала как в щели (замечено на снимке 17.09.2026) */
  .shop-row .item-niche{ height:min(112px, 21vh); aspect-ratio:1/1; width:auto; max-width:100%; }
  .shop-tier-stat{ font-family:'EB Garamond',serif; font-size:12px; color:var(--c-gold-dim); line-height:1.3; }
  .shop-tier-perks{ font-family:'EB Garamond',serif; font-size:12px; color:var(--tier-lit); opacity:0.9; }
  .shop-row button{ width:100%; --btn-s:0.16; min-height:30px; font-size:14px; padding:4px 8px; }
  /* окно купленной вещи и карточка гнезда: ниша слева, слова справа */
  .item-win--one{ width:min(92vw, 610px); }
  .item-win--one .item-niche{ width:min(38vw, 210px); aspect-ratio:1/1; }
  /* окно трофея: две вещи и столбик разницы между ними */
  .compare-row{ display:flex; gap:8px; align-items:stretch; flex:1 1 auto; min-height:0; }
  .compare-row .item-plate{ flex:1 1 0; min-width:0; }
  .compare-row .item-niche{ width:min(20vw, 132px); aspect-ratio:1/1; align-self:center; }
  .item-side{ font-family:'Cinzel',serif; font-size:10.5px; letter-spacing:0.18em; color:var(--c-gold-dim); }
  /* низкий экран (телефон в альбомной) — ужимаем, но НЕ прокручиваем */
  @media (max-height:430px){
    .item-win{ padding:9px 12px 10px; gap:6px; }
    .item-win-title{ font-size:13.5px; }
    .item-win-sub{ font-size:11.5px; }
    .item-win-foot button{ min-height:32px; font-size:13.5px; padding:5px 12px; }
    .item-name{ font-size:13.5px; }
    .item-stat{ font-size:22px; }
    .item-perk{ font-size:11.5px; padding:2px 0; }
    .item-tip{ font-size:11.5px; padding:6px 9px 7px; max-width:min(260px, 92vw); }
    .item-tip b{ font-size:11px; }
    .compare-row .item-niche{ width:min(18vw, 108px); }
    .item-win--one .item-niche{ width:min(34vw, 172px); }
    .shop-row .item-niche{ height:min(88px, 21vh); }
    .item-ribbon{ font-size:10.5px; padding:1px 9px; }
  }

  /* ---- ОКНО ПОВЫШЕНИЯ ЗВАНИЯ (V81, 19.09.2026) ----
     Праздник тем же языком, что церемония вещи: камень, золото и луч из-за
     плиты. Своей картинки не просит — всё рисуется тенями и градиентом,
     поэтому окно ничего не ждёт с диска и выходит мгновенно. */
  .rankup-card{ position:relative; overflow:hidden; animation:rankup-in 460ms cubic-bezier(.2,.9,.25,1.4) both; }
  .rankup-rays{
    position:absolute; left:50%; top:-40%; width:260%; height:200%;
    transform:translateX(-50%); pointer-events:none; z-index:0; opacity:0.5;
    background:conic-gradient(from 0deg,
      rgba(255,213,74,0.20) 0deg, transparent 12deg, transparent 30deg,
      rgba(255,213,74,0.16) 42deg, transparent 54deg, transparent 72deg,
      rgba(255,213,74,0.20) 84deg, transparent 96deg, transparent 120deg,
      rgba(255,213,74,0.16) 132deg, transparent 144deg, transparent 180deg,
      rgba(255,213,74,0.20) 192deg, transparent 204deg, transparent 240deg,
      rgba(255,213,74,0.16) 252deg, transparent 264deg, transparent 300deg,
      rgba(255,213,74,0.20) 312deg, transparent 324deg, transparent 360deg);
    animation:rankup-spin 14s linear infinite;
  }
  .rankup-card > *:not(.rankup-rays){ position:relative; z-index:1; }
  .rankup-kicker{
    font-family:'Cinzel',serif; font-size:12px; letter-spacing:0.26em;
    color:var(--c-gold); text-transform:uppercase; margin-bottom:2px;
  }
  .rankup-title{
    font-family:'Cinzel',serif; font-size:26px; line-height:1.1; font-weight:700;
    color:var(--c-gold-hot); margin:0 0 12px;
    text-shadow:0 2px 0 rgba(0,0,0,0.75), 0 0 18px rgba(255,213,74,0.45);
    animation:rankup-glow 2.4s ease-in-out infinite;
  }
  .rankup-gains{ display:flex; gap:8px; justify-content:center; margin-bottom:10px; }
  .rankup-gain{
    flex:1 1 0; min-width:0; padding:8px 4px 7px;
    background:rgba(0,0,0,0.30); border:1px solid rgba(217,180,92,0.32); border-radius:var(--r-md);
    animation:rankup-pop 380ms ease-out both;
  }
  .rankup-gain b{ display:block; font-family:'Cinzel',serif; font-size:19px; color:var(--c-gold-hot); line-height:1.1; }
  .rankup-gain span{ display:block; font-family:'EB Garamond',serif; font-size:12px; color:var(--c-gold-dim); margin-top:2px; }
  .rankup-points{ font-family:'EB Garamond',serif; font-size:14px; color:var(--c-gold-bright); margin:0 0 14px; line-height:1.45; }
  .rankup-later{
    background:none; border:none; color:var(--c-gold-dim); font-family:'EB Garamond',serif;
    font-size:13px; margin-top:8px; cursor:pointer; text-decoration:underline;
  }
  @keyframes rankup-in{ from{ opacity:0; transform:scale(0.86) translateY(14px); } to{ opacity:1; transform:none; } }
  @keyframes rankup-spin{ to{ transform:translateX(-50%) rotate(360deg); } }
  @keyframes rankup-glow{ 50%{ text-shadow:0 2px 0 rgba(0,0,0,0.75), 0 0 30px rgba(255,213,74,0.75); } }
  @keyframes rankup-pop{ from{ opacity:0; transform:translateY(8px) scale(0.92); } to{ opacity:1; transform:none; } }
  /* Кому мешает мелькание — тому окно стоит смирно (системная настройка). */
  @media (prefers-reduced-motion:reduce){
    .rankup-card, .rankup-gain{ animation:none; }
    .rankup-rays{ animation:none; }
    .rankup-title{ animation:none; }
  }

  /* Подсветка нераспределённых очков в карточке: окно обещало «сейчас покажу,
     куда их деть» — карточка обязана это показать, а не оставить игрока искать. */
  .wc-points-call{ animation:points-call 1100ms ease-in-out 4; border-radius:var(--r-md); }
  @keyframes points-call{
    0%,100%{ box-shadow:0 0 0 0 rgba(255,213,74,0); }
    50%{ box-shadow:0 0 0 3px rgba(255,213,74,0.55), 0 0 16px rgba(255,213,74,0.35); }
  }
  @media (prefers-reduced-motion:reduce){ .wc-points-call{ animation:none; box-shadow:0 0 0 2px rgba(255,213,74,0.5); } }

  /* ===== M9: ТИТУЛЬНЫЙ ЭКРАН (24.09.2026) =====
     Обложка Andy во весь экран, внизу вопрос и каменная кнопка. Всё — только
     под классом .title-mode на #entryGateOverlay (ставит 03-audio.js); без него
     слои спрятаны и калитка выглядит по-прежнему.
     Картинка прижата к ВЕРХУ: название нарисовано в ней самой, и на телефоне,
     где экран длиннее картинки, обрезается низ (руки на рукоятях), а не буквы.
     Инлайновые стили карточки калитки перебиваются !important нарочно: это та
     же разметка, что у прежнего вида, — ради неё её и не трогали. */
  #entryGateOverlay .title-art, #entryGateOverlay .title-shade,
  #entryGateOverlay .title-spark, #entryGateOverlay .title-dark{ display:none; }
  #entryGateOverlay.title-mode{ background:#000 !important; overflow:hidden; }
  #entryGateOverlay.title-mode .title-art,
  #entryGateOverlay.title-mode .title-shade,
  #entryGateOverlay.title-mode .title-dark{ display:block; position:absolute; inset:0; pointer-events:none; }
  #entryGateOverlay.title-mode .title-art img{
    width:100%; height:100%; object-fit:cover; object-position:50% 0; display:block;
  }
  #entryGateOverlay.title-mode .title-shade{
    background:linear-gradient(to top, rgba(0,0,0,0.88) 0%, rgba(0,0,0,0.55) 16%, rgba(0,0,0,0) 36%);
  }
  #entryGateOverlay.title-mode .entry-card{
    position:absolute; left:50%; bottom:calc(14px + env(safe-area-inset-bottom, 0px));
    transform:translateX(-50%); z-index:2;
    background:none !important; border:none !important; box-shadow:none !important;
    padding:0 !important; width:auto !important; max-width:92vw;
    display:flex; flex-direction:column; align-items:center;
    transition:opacity 0.35s ease;
  }
  #entryGateOverlay.title-mode .entry-card::before{ content:none; }
  #entryGateOverlay.title-mode .entry-card{ backdrop-filter:none; -webkit-backdrop-filter:none; }
  #entryGateOverlay.title-mode .entry-ask{
    font-family:'Cinzel',Georgia,serif !important; font-weight:700 !important;
    font-size:17px !important; letter-spacing:0.1em; margin:0 0 6px !important;
    color:var(--c-gold-bright); text-shadow:0 2px 6px rgba(0,0,0,0.95), 0 0 14px rgba(0,0,0,0.8);
  }
  #entryGateOverlay.title-mode #entryGateBtn{
    --btn-s:0.30; --btn-stone:url('../img/ui/btn/slab.webp'); --btn-fire:url('../img/ui/btn/slab_fire.webp');
    width:236px !important; aspect-ratio:926/229; min-height:0; padding:2px 0 0 !important;
    display:flex; align-items:center; justify-content:center;
    font-family:'Pirata One','Cinzel',serif !important; font-weight:400 !important;
    font-size:24px !important; letter-spacing:0.05em; border-radius:0 !important;
  }
  /* вариант b: вопрос крупно — он и есть заголовок нижней полосы, кнопка скромнее */
  #entryGateOverlay.title-b .title-shade{
    background:linear-gradient(to top, rgba(0,0,0,0.92) 0%, rgba(0,0,0,0.7) 22%, rgba(0,0,0,0) 44%);
  }
  #entryGateOverlay.title-b .entry-ask{
    font-family:'Pirata One','Cinzel',serif !important; font-weight:400 !important;
    font-size:32px !important; letter-spacing:0.06em; margin:0 0 4px !important;
  }
  #entryGateOverlay.title-b #entryGateBtn{ width:196px !important; font-size:21px !important; }
  /* вариант c: плита тлеет, как угли, — зовёт нажать */
  #entryGateOverlay.title-c #entryGateBtn::after{ animation:title-ember 2.6s ease-in-out infinite; }
  @keyframes title-ember{ 0%,100%{ opacity:0.08; } 50%{ opacity:0.75; } }

  /* после нажатия: кнопка гаснет, в скрещении мечей вспыхивает искра, экран
     темнеет за 5 с и держится чёрным, пока в музыке не отзвучит «It is chess.»
     (03-audio.js, TITLE_REVEAL_AT), потом калитка тает в то, что уже готово под
     ней — меню или вход */
  #entryGateOverlay.title-going .entry-card{ opacity:0; pointer-events:none; }
  #entryGateOverlay.title-mode .title-dark{ background:#000; opacity:0; }
  #entryGateOverlay.title-going .title-dark{ opacity:1; transition:opacity 5s cubic-bezier(0.45,0,0.75,1); }
  #entryGateOverlay.title-gone{ opacity:0; transition:opacity 0.7s ease; pointer-events:none; }
  #entryGateOverlay.title-mode .title-spark{
    position:absolute; width:260px; height:260px; margin:-130px 0 0 -130px; border-radius:50%;
    pointer-events:none; z-index:1; opacity:0; mix-blend-mode:screen;
    background:radial-gradient(circle, rgba(255,250,225,1) 0%, rgba(255,196,90,0.85) 16%, rgba(255,120,30,0.35) 38%, rgba(255,90,20,0) 66%);
  }
  #entryGateOverlay.title-mode .title-spark.on{ display:block; animation:title-spark 0.9s ease-out forwards; }
  @keyframes title-spark{
    0%{ opacity:0; transform:scale(0.2); }
    12%{ opacity:1; transform:scale(1.15); }
    100%{ opacity:0; transform:scale(1.9); }
  }
  @media (prefers-reduced-motion:reduce){
    #entryGateOverlay.title-c #entryGateBtn::after{ animation:none; }
    #entryGateOverlay.title-mode .title-spark.on{ animation-duration:0.01s; }
  }

  /* ===== ГЛАВНОЕ МЕНЮ: ДВА ВАРИАНТА НА ВЫБОР ANDY (24.09.2026) =====
     Andy: «сами эти две плашки и две кнопки под ними… так себе». Разбор: щиты
     не пара (разный размер и низ), светлая бахрома по краю, надписи тонут в
     узоре, «ELO-Rating» новичку ни о чём, Options и Log out весят столько же,
     сколько главный выбор. Варианты — классом на #modeOverlay (ставит
     06-auth.js по ?menu=a|b); без класса все новые слои спрятаны.
       a — список слов слева на затемнении, пейзаж открыт целиком;
       b — щиты чистые и одной высоты, Campaign главный и тлеет.
     Общее у обоих: табличка героя слева сверху, шестерёнка справа сверху
     вместо Options/Log out/двери. */
  #modeOverlay .menu-shade, #modeOverlay .menu-hero, #modeOverlay .menu-gear,
  #modeOverlay .menu-list{ display:none; }
  #modeOverlay:is(.menu-a, .menu-b) .menu-hero{
    display:flex; flex-direction:column; position:absolute; z-index:3;
    top:calc(14px + env(safe-area-inset-top, 0px)); left:18px; pointer-events:none;
  }
  /* Два героя — две строки: у кампании и у дуэлей имена разные (Andy 25.09.2026). */
  .menu-hero{ gap:2px; }
  .menu-hero .mh-row{ display:flex; align-items:baseline; gap:8px; }
  .menu-hero .mh-label{ font-family:'Cinzel',serif; font-size:10px; letter-spacing:0.16em; min-width:5.6em;
    text-transform:uppercase; color:var(--c-gold-dim); text-shadow:0 1px 3px rgba(0,0,0,0.9); }
  .menu-hero .mh-name{ font-family:'Cinzel',serif; font-weight:700; font-size:17px; color:var(--c-gold-bright);
    text-shadow:0 2px 8px rgba(0,0,0,0.9); max-width:34vw; overflow:hidden; text-overflow:ellipsis; white-space:nowrap; }
  .menu-hero .mh-name.mh-none{ font-weight:400; font-style:italic; font-size:13px; color:var(--c-gold-dim); }
  #modeOverlay:is(.menu-a, .menu-b) .menu-gear{
    display:flex; align-items:center; justify-content:center; position:absolute; z-index:2;
    top:calc(12px + env(safe-area-inset-top, 0px)); right:14px; width:46px; height:46px; padding:0;
    border-radius:50% !important; border:1px solid rgba(217,180,92,0.45) !important;
    background:rgba(10,8,6,0.55) !important; cursor:pointer; transition:transform 0.15s ease, box-shadow 0.15s ease;
    box-shadow:0 2px 10px rgba(0,0,0,0.6) !important;
  }
  .menu-gear svg{ width:26px; height:26px; fill:var(--c-gold); filter:drop-shadow(0 1px 2px rgba(0,0,0,0.8)); }
  @media (hover:hover){ .menu-gear:hover{ transform:rotate(30deg); } }
  #modeOverlay:is(.menu-a, .menu-b) #topExitBtn,
  #modeOverlay:is(.menu-a, .menu-b) #menuFootRow,
  #modeOverlay:is(.menu-a, .menu-b) #menuBoard > div:first-child{ display:none; }

  /* --- вариант a: список слов --- */
  #modeOverlay.menu-a .menu-shade{
    display:block; position:absolute; inset:0; z-index:1; pointer-events:none;
    background:linear-gradient(90deg, rgba(0,0,0,0.78) 0%, rgba(0,0,0,0.45) 32%, rgba(0,0,0,0) 58%);
  }
  #modeOverlay.menu-a #menuBoard{ display:none !important; }
  #modeOverlay.menu-a .menu-embers{ display:block; position:absolute; inset:0; width:100%; height:100%;
    z-index:1; pointer-events:none; }
  #modeOverlay .menu-embers{ display:none; }
  .menu-title{ font-family:'UnifrakturMaguntia','Pirata One',serif; font-size:clamp(40px, 9vh, 78px); line-height:1;
    background:linear-gradient(180deg, #f4f1ea 0%, #b9b4aa 38%, #6f6a62 52%, #d8d3ca 70%, #8d877e 100%);
    -webkit-background-clip:text; background-clip:text; color:transparent;
    filter:drop-shadow(0 2px 0 #1a1612) drop-shadow(0 4px 10px rgba(0,0,0,0.9)); margin-left:-2px; }
  .menu-rule{ display:flex; align-items:center; gap:8px; width:clamp(200px, 30vw, 360px); margin:2px 0 6px; }
  .menu-rule i{ flex:1; height:1px; background:linear-gradient(90deg, rgba(217,180,92,0), rgba(217,180,92,0.85), rgba(217,180,92,0)); }
  .menu-rule b{ width:8px; height:8px; transform:rotate(45deg); background:var(--c-gold); box-shadow:0 0 8px rgba(255,170,60,0.6); }
  #modeOverlay.menu-a .menu-list{
    display:flex; flex-direction:column; align-items:flex-start; gap:clamp(10px, 3vh, 26px);
    position:absolute; z-index:2; left:clamp(22px, 7vw, 120px); top:50%; transform:translateY(-44%);
  }
  .menu-item{
    background:none !important; border:none !important; box-shadow:none !important; padding:4px 0;
    position:relative; text-align:left; cursor:pointer; display:flex; flex-direction:row; align-items:center; gap:14px;
    color:var(--c-gold-bright); -webkit-tap-highlight-color:transparent;
  }
  .menu-item .mi-text{ display:flex; flex-direction:column; gap:2px; }
  /* эмблемы разной ширины — ставим в одинаковую рамку, чтобы слова начинались с одной линии */
  .menu-item .mi-medal{ height:clamp(44px, 10vh, 78px); width:clamp(84px, 19vh, 150px); object-fit:contain; flex-shrink:0;
    filter:drop-shadow(0 4px 8px rgba(0,0,0,0.8)); transition:transform 0.2s ease, filter 0.2s ease; }
  .menu-item--main .mi-medal{ height:clamp(52px, 12.5vh, 96px); }
  .menu-item .mi-medal{ object-position:50% 50%; }
  @media (hover:hover){ .menu-item:hover .mi-medal{ transform:scale(1.06);
    filter:drop-shadow(0 0 12px rgba(255,150,40,0.5)) drop-shadow(0 4px 8px rgba(0,0,0,0.8)); } }
  .menu-item .mi-title{ font-family:'Pirata One','Cinzel',serif; font-size:clamp(34px, 7.2vh, 60px);
    line-height:1; letter-spacing:0.03em; text-shadow:0 2px 10px rgba(0,0,0,0.9); transition:color 0.2s ease, text-shadow 0.2s ease; }
  .menu-item .mi-sub{ font-family:'EB Garamond',serif; font-size:clamp(13px, 2.4vh, 17px); color:var(--c-gold-dim);
    letter-spacing:0.04em; text-shadow:0 1px 3px rgba(0,0,0,0.9); }
  .menu-item--main .mi-title{ font-size:clamp(42px, 9.5vh, 80px); color:var(--c-gold-hot); }
  /* уголёк слева от слова: тлеет у главного, вспыхивает у того, на что навели */
  .menu-item::before{ content:none; position:absolute; left:0; top:calc(50% - 4px); width:8px; height:8px;
    border-radius:50%; background:radial-gradient(circle, #ffd27a 0%, #ff8a2a 55%, rgba(255,90,20,0) 72%);
    opacity:0; transform:scale(0.6); transition:opacity 0.2s ease, transform 0.2s ease; }
  .menu-item--main::before{ animation:menu-ember 2.6s ease-in-out infinite; }
  @keyframes menu-ember{ 0%,100%{ opacity:0.25; transform:scale(0.7); } 50%{ opacity:1; transform:scale(1.25); } }
  .menu-item--main .mi-title{ animation:menu-ember-text 2.6s ease-in-out infinite; }
  @keyframes menu-ember-text{ 0%,100%{ text-shadow:0 2px 10px rgba(0,0,0,0.9); }
    50%{ text-shadow:0 0 18px rgba(255,150,40,0.55), 0 2px 10px rgba(0,0,0,0.9); } }
  .menu-item:is(:active, :focus-visible)::before{ opacity:1; transform:scale(1.3); }
  .menu-item:is(:active, :focus-visible) .mi-title{ color:var(--c-gold-hot);
    text-shadow:0 0 22px rgba(255,150,40,0.8), 0 2px 10px rgba(0,0,0,0.9); }
  @media (hover:hover){
    .menu-item:hover::before{ opacity:1; transform:scale(1.3); }
    .menu-item:hover .mi-title{ color:var(--c-gold-hot); text-shadow:0 0 22px rgba(255,150,40,0.8), 0 2px 10px rgba(0,0,0,0.9); }
  }

  /* --- «A+» на фоне Andy с героем (картинка 3 из GAME/NEWLook/Menue/MainMenue,
     24.09.2026): герой сидит у скалы слева — список уходит направо. Название —
     в пустом небе над замком, Campaign и Duel — на пустом поле под ним,
     затемнение справа, чтобы герой оставался светлым. --- */
  #modeOverlay.menu-a .menu-bg{ background-image:url('../img/menu/menu_hero_1920.webp') !important; background-position:50% 50% !important; }
  @media (max-width:599px), (max-height:599px){
    #modeOverlay.menu-a .menu-bg{ background-image:url('../img/menu/menu_hero_1280.webp') !important; }
  }
  #modeOverlay.menu-a .menu-shade{
    background:linear-gradient(270deg, rgba(0,0,0,0.72) 0%, rgba(0,0,0,0.42) 26%, rgba(0,0,0,0) 48%);
  }
  #modeOverlay.menu-a .menu-list{
    left:auto; right:clamp(18px, 5vw, 96px); top:calc(clamp(10px, 8vh, 80px) + 30px); bottom:clamp(10px, 6vh, 64px);
    transform:none; justify-content:space-between; gap:0;
  }
  #modeOverlay.menu-a .menu-list .menu-item--main{ margin-top:auto; margin-bottom:clamp(6px, 2.4vh, 22px); }

  /* --- вариант b: щиты в порядке --- */
  #modeOverlay.menu-b .crest-btn{ height:clamp(200px, 52vh, 420px); position:relative; }
  #modeOverlay.menu-b #menuBoard > div:nth-child(2){ align-items:center !important; gap:clamp(24px, 6vw, 72px) !important; }
  #modeOverlay.menu-b #topCampaignBtn{ height:clamp(220px, 58vh, 470px); }
  #modeOverlay.menu-b #topCampaignBtn::before{ content:''; position:absolute; inset:-8% -14%; z-index:-1;
    background:radial-gradient(ellipse at 50% 55%, rgba(255,140,40,0.34) 0%, rgba(255,110,30,0.12) 42%, rgba(255,90,20,0) 68%);
    animation:menu-crest-ember 2.6s ease-in-out infinite; pointer-events:none; }
  @keyframes menu-crest-ember{ 0%,100%{ opacity:0.35; } 50%{ opacity:1; } }
  @media (prefers-reduced-motion:reduce){
    .menu-item--main::before, .menu-item--main .mi-title, #modeOverlay.menu-b #topCampaignBtn::before{ animation:none; }
  }

  /* ===== «A+», второй круг (Andy 24.09.2026, вечер): «со шрифтами странновато…
     меню выглядит бедно… тени под буквами, чтобы выдвигались при наведении…
     больше оживления». Всё — только под .menu-a. =====
     Буквы — кованое золото (заливка по буквам + тёмный ободок и тень через
     filter: text-shadow под background-clip:text в Chrome ложится ПОВЕРХ заливки
     и мутит её). Подписи — Cinzel, как «Aren't you afraid?» на обложке
     (?msub=fell — IM Fell English, старая печатная книга, для сравнения). */
  #modeOverlay.menu-a .menu-item .mi-title{
    background:linear-gradient(180deg, #fff3c4 0%, #f2c75c 34%, #a8741f 56%, #e9b64c 74%, #7c5314 100%);
    -webkit-background-clip:text; background-clip:text; color:transparent; text-shadow:none !important;
    filter:drop-shadow(0 1px 0 #2a1a08) drop-shadow(0 3px 2px rgba(0,0,0,0.85)) drop-shadow(0 6px 14px rgba(0,0,0,0.75));
    animation:none !important; transition:filter 0.25s ease;
  }
  #modeOverlay.menu-a .menu-item:not(.menu-item--main) .mi-title{
    background:linear-gradient(180deg, #f6ecd6 0%, #d9c6a0 38%, #8f7a55 58%, #cdb88f 76%, #6b5a3c 100%);
    -webkit-background-clip:text; background-clip:text;
  }
  #modeOverlay.menu-a .menu-item--main .mi-title{ animation:menu-gold-breathe 3s ease-in-out infinite !important; }
  @keyframes menu-gold-breathe{
    0%,100%{ filter:drop-shadow(0 1px 0 #2a1a08) drop-shadow(0 3px 2px rgba(0,0,0,0.85)) drop-shadow(0 6px 14px rgba(0,0,0,0.75)); }
    50%{ filter:drop-shadow(0 1px 0 #2a1a08) drop-shadow(0 3px 2px rgba(0,0,0,0.85)) drop-shadow(0 0 16px rgba(255,150,40,0.55)); }
  }
  #modeOverlay.menu-a .menu-item{ transition:transform 0.28s cubic-bezier(0.2,0.8,0.3,1.2); transform-origin:0 50%; }
  #modeOverlay.menu-a .menu-item:is(:focus-visible, .hot){ transform:translateX(-12px) scale(1.07); }
  #modeOverlay.menu-a .menu-item:is(:focus-visible, .hot) .mi-title{ animation:none !important;
    filter:drop-shadow(0 1px 0 #2a1a08) drop-shadow(0 3px 2px rgba(0,0,0,0.85)) drop-shadow(0 0 20px rgba(255,160,50,0.85)); }
  #modeOverlay.menu-a .menu-item .mi-sub{
    font-family:'Cinzel',serif; font-weight:600; font-size:clamp(11px, 2.1vh, 15px); letter-spacing:0.14em;
    text-transform:uppercase; color:#cdb68a; display:flex; align-items:center; gap:8px;
  }
  html.msub-fell #modeOverlay.menu-a .menu-item .mi-sub{ font-family:'IM Fell English',serif; font-weight:400;
    font-style:italic; text-transform:none; letter-spacing:0.02em; font-size:clamp(14px, 2.6vh, 19px); }
  /* орнамент: подпись между двумя золотыми чёрточками */
  #modeOverlay.menu-a .menu-item .mi-sub::before,
  #modeOverlay.menu-a .menu-item .mi-sub::after{ content:''; width:22px; height:1px;
    background:linear-gradient(90deg, rgba(217,180,92,0), rgba(217,180,92,0.9)); }
  #modeOverlay.menu-a .menu-item .mi-sub::after{ background:linear-gradient(90deg, rgba(217,180,92,0.9), rgba(217,180,92,0)); }
  /* эмблемы: в покое — железо с золотом (одна гамма с буквами), под рукой — свои цвета */
  #modeOverlay.menu-a .menu-item .mi-medal{
    filter:grayscale(0.92) sepia(0.55) saturate(0.85) brightness(0.82) contrast(1.15) drop-shadow(0 4px 8px rgba(0,0,0,0.85));
    transition:filter 0.6s ease, transform 0.28s ease;
  }
  #modeOverlay.menu-a .menu-item:is(:focus-visible, .hot) .mi-medal{
    filter:drop-shadow(0 0 12px rgba(255,150,40,0.55)) drop-shadow(0 4px 8px rgba(0,0,0,0.85)); transform:scale(1.06);
  }

  /* --- жизнь меню --- */
  #modeOverlay .menu-flash, #modeOverlay .menu-fog, #modeOverlay .menu-fire{ display:none; }
  #modeOverlay.menu-a .menu-flash, #modeOverlay.menu-a .menu-fog, #modeOverlay.menu-a .menu-fire{
    display:block; position:absolute; inset:0; z-index:1; pointer-events:none; }
  #modeOverlay.menu-a.menu-fx-off :is(.menu-flash, .menu-fog, .menu-fire){ display:none; }
  /* полосы тумана шире экрана (им надо куда ползти) — обрезаем по краю, иначе меню
     «вырастает» вбок и вниз и отращивает полосы прокрутки */
  #modeOverlay.menu-a .menu-fog{ overflow:hidden; }
  /* молния: небо коротко светлеет, вспышку ведёт 06-auth.js */
  #modeOverlay.menu-a .menu-flash{ opacity:0; mix-blend-mode:screen;
    background:radial-gradient(ellipse at 62% 18%, rgba(200,215,255,0.75) 0%, rgba(150,170,230,0.35) 30%, rgba(120,140,200,0) 62%); }
  /* отсвет костра на герое: тёплое пятно слева снизу, мерцает неровно */
  #modeOverlay.menu-a .menu-fire{ mix-blend-mode:soft-light;
    background:radial-gradient(ellipse 34% 30% at 22% 100%, rgba(255,150,60,0.55) 0%, rgba(255,110,40,0.22) 45%, rgba(255,90,20,0) 100%);
    animation:menu-fire 3.3s steps(1, end) infinite, menu-fire-soft 1.7s ease-in-out infinite; }
  @keyframes menu-fire{ 0%{opacity:0.85} 13%{opacity:0.62} 21%{opacity:0.95} 34%{opacity:0.7} 47%{opacity:0.9}
    58%{opacity:0.6} 71%{opacity:1} 83%{opacity:0.72} 92%{opacity:0.88} }
  @keyframes menu-fire-soft{ 0%,100%{ transform:scale(1); } 50%{ transform:scale(1.04) translateY(-4px); } }
  /* туман: две полупрозрачные полосы медленно ползут по полю навстречу друг другу */
  #modeOverlay.menu-a .menu-fog i{ position:absolute; left:-30%; width:160%; bottom:-6%; height:42%;
    background:radial-gradient(ellipse at 30% 60%, rgba(190,195,210,0.22) 0%, rgba(190,195,210,0) 55%),
               radial-gradient(ellipse at 75% 70%, rgba(170,178,196,0.18) 0%, rgba(170,178,196,0) 50%);
    filter:blur(6px); animation:menu-fog 48s linear infinite alternate; }
  #modeOverlay.menu-a .menu-fog i:nth-child(2){ bottom:4%; height:30%; opacity:0.8; animation-duration:67s; animation-direction:alternate-reverse; }
  @keyframes menu-fog{ from{ transform:translateX(-8%); } to{ transform:translateX(8%); } }
  /* 🔴 Фон стоит неподвижно (Andy 24.09.2026: «то, что фон ездит туда-сюда, когда
     мышкой двигаешь, — плохо»). Сдвиг за мышкой был, и увеличенная под него
     картинка вылезала за экран — меню отрастило полосы прокрутки («рамка»). */
  @media (prefers-reduced-motion:reduce){
    #modeOverlay.menu-a :is(.menu-fire, .menu-fog i){ animation:none; }
  }
  /* 🔴 ЧЁРНАЯ ПОЛОСА СВЕРХУ — место под плашку турнира, которую меню само же и
     закрывало: плашки стоят в потоке страницы под всеми слоями, а слой меню
     резервировал под них отступ и красил его своим фоном. В новом меню отступа
     нет, а плашка, пока меню на экране, встаёт поверх неба сверху по центру
     (класс menu-a-shown ставит 06-auth.js, только пока меню видно — в бою и
     окнах плашки живут как раньше). */
  #modeOverlay.menu-a{ padding-top:0 !important; overflow:hidden !important; }
  /* всё живое (туман, мерцающий костёр) не выходит за экран */
  #modeOverlay.menu-a #menuBoardWrap{ overflow:hidden; height:100%; }
  /* z-index — с !important: у плашек в разметке прямо вписан z-index:40 */
  html.menu-a-shown .top-sticky-bar{ position:fixed; z-index:51 !important; left:50%; transform:translateX(-50%);
    top:calc(10px + env(safe-area-inset-top, 0px)); margin:0; }
  html.menu-a-shown #tournamentBar:not([style*="none"]) ~ #leagueBar{ top:calc(64px + env(safe-area-inset-top, 0px)); }

  /* окно Options в том же голосе, пока идёт проба нового меню: подписи строк уже Cinzel,
     пояснения — IM Fell English, переключатели — Cinzel */
  html.menu-a-on #optionsOverlay .opt-val{ font-family:'IM Fell English',serif; font-size:15px; }
  html.menu-a-on #optionsOverlay .opt-toggle{ font-family:'Cinzel',serif; font-weight:700; font-size:12.5px; letter-spacing:0.06em; }
  html.menu-a-on #optionsOverlay .opt-build{ font-family:'IM Fell English',serif; font-size:12px; }
  html.menu-a-on #optionsOverlay #optLogoutBtn{ font-family:'Cinzel',serif; font-size:13px; letter-spacing:0.06em; }

  /* ===== V73: меню появляется из темноты (24.09.2026; втрое медленнее — ~8 с,
     слово Andy 25.09.2026: «раза в три медленнее проявлялось, но нажималось сразу,
     если не хочется смотреть шоу») =====
     Класс .menu-intro на #modeOverlay ставит 06-auth.js (menuIntroStart) один раз
     за запуск и снимает через ~3 с или по тычку. Всё ниже — только пока он стоит;
     без него меню в обычном виде, поэтому «тычок — всё на месте» бесплатен.
     Время блика на названии — --glint-at (подгоняется под «En Garde!» в музыке). */
  #modeOverlay .menu-veil{ display:none; }
  #modeOverlay:is(.menu-intro, .menu-intro-low) .menu-veil{
    display:block; position:absolute; inset:0; z-index:2; pointer-events:none;
    /* у ног героя вуаль тоньше — костёр проступает первым */
    background:radial-gradient(ellipse 34% 34% at 22% 100%, rgba(0,0,0,0.25) 0%, #000 72%);
    animation:intro-veil 4.2s cubic-bezier(0.5,0,0.3,1) both;
  }
  #modeOverlay.menu-intro-low .menu-veil{ animation-duration:0.5s; }
  @keyframes intro-veil{ from{ opacity:1; } to{ opacity:0; } }

  #modeOverlay.menu-intro .menu-title{ position:relative; animation:intro-rise 2.7s ease-out 0.3s both; }
  #modeOverlay .menu-title{ position:relative; }
  /* блик: копия букв с яркой полосой, пролетающей по ним слева направо */
  #modeOverlay.menu-intro .menu-title::after{
    content:attr(data-text); position:absolute; left:0; top:0; white-space:nowrap;
    background:linear-gradient(100deg, rgba(255,255,255,0) 42%, rgba(255,250,235,0.95) 50%, rgba(255,255,255,0) 58%);
    background-size:260% 100%; background-position:120% 0;
    -webkit-background-clip:text; background-clip:text; color:transparent;
    animation:intro-glint 0.9s ease-in-out var(--glint-at, 1s) both;
  }
  @keyframes intro-glint{ from{ background-position:120% 0; } to{ background-position:-20% 0; } }
  @keyframes intro-rise{ from{ opacity:0; transform:translateY(8px); } to{ opacity:1; transform:none; } }

  #modeOverlay.menu-intro .menu-rule{ animation:intro-rule 1.7s ease-out 3.2s both; }
  @keyframes intro-rule{ from{ transform:scaleX(0); opacity:0; } to{ transform:scaleX(1); opacity:1; } }

  /* слова загораются: из темноты и размытого жара — в чёткое золото */
  #modeOverlay.menu-intro .menu-item{ animation:intro-ignite 2.4s cubic-bezier(0.2,0.7,0.3,1) 4s both; }
  #modeOverlay.menu-intro .menu-item:not(.menu-item--main){ animation-delay:5.5s; }
  @keyframes intro-ignite{
    0%{ opacity:0; filter:brightness(2.4) blur(6px); transform:translateX(18px); }
    60%{ opacity:1; filter:brightness(1.5) blur(0); }
    100%{ opacity:1; filter:none; transform:none; }
  }
  #modeOverlay.menu-intro :is(.menu-hero, .menu-gear){ animation:intro-rise 1.8s ease-out 6.9s both; }
  @media (prefers-reduced-motion:reduce){
    #modeOverlay.menu-intro *, #modeOverlay.menu-intro *::after{ animation-duration:0.01s !important; animation-delay:0s !important; }
  }
