/* КАРТА ПУТИ — ГЛАВНЫЙ ЭКРАН НА ДАННЫХ КУРСА (MAP-STEP-OPEN-27.09, этап 3; learning_path_spec §7а, версия 3, композиция 2 «Дорога»).
   Вид — утверждённый макет v5 (public/proto_path/index5.html, 26–27.09): стили перенесены из него без изменения, кроме: убраны
   композиции 1/3, книжная карточка, карточка шага (тап открывает шаг сразу, п.9) и служебные переключатели макета; `.bottom .wrap`
   → `.bottom .bw` (у курса `.wrap` глобальный — course.css); экран шага — настоящий движок курса (course-step.js) и режим «страница».
   Шкала типографики: 11 (капитель) · 12 (мета) · 14 (текст) · 15 (подпись) · 16 (юнит) · 24 (уровень). Ритм отступов 4/8/12/16/24.
   Цвет типа шага: грамматика #4878B1, упражнение #1FA3A3, слова #15A06B. */
:root { --proto-w: 520px; --bar-h: 48px; --blue: #3E6898; --d: 76px; --dock-top: 0px; }
@media (min-width: 760px) { :root { --proto-w: 760px; } }
body { background: var(--color-bg); color: var(--color-text); }
.pa { position: relative; max-width: var(--proto-w); margin: 0 auto; padding: 0 16px calc(118px + env(safe-area-inset-bottom, 0px)); overflow-x: clip; }
#hdr, #dock { display: contents; }
.ic { width: 24px; height: 24px; display: block; } .ic path { fill: none; stroke: currentColor; stroke-width: 2; stroke-linecap: round; stroke-linejoin: round; }
/* ---- ВЕРХ — ДВА ЯРУСА (HOME-HEADER-V2-29.09; PO ~18:1x «дизайн верха экрана хороший, берём его», макет №524) ----
   ярус 1 (.hd-wrap, уезжает при прокрутке вниз): «Starter ▾» · 4 значка направлений · поиск · меню — одна строка;
   ярус 2 (.dock5, остаётся): где ты сейчас (.names5 — раздел · юнит по прокрутке) · % ; ниже шкала — 10 отрезков по разделам.
   ПК ≥ 1200 px — тот же верх колонкой слева (конец блока), разделы уровня списком (.toc5). Было (до 29.09): 316 px шапки с повторами. */
.ibtn { width: 44px; height: 44px; border-radius: 50%; border: 0; background: none; color: inherit; display: inline-grid; place-items: center; cursor: pointer; flex: none; padding: 0; }
.ibtn .ic { width: 22px; height: 22px; }
.hd5 { display: flex; align-items: center; gap: 8px; padding: 10px 0 4px; }
.hd5-l { flex: none; }
.hd5-r { display: flex; flex: none; }
.hd5 .ibtn { color: var(--color-text-muted); }
.hd5 .topbar__btn { color: var(--color-text-muted); } @media (hover: hover) { .hd5 .topbar__btn:hover { background: var(--color-hover); } }
.hd5 .topbar__actions { gap: 0; }
.hd5-title { display: inline-flex; align-items: center; gap: 4px; border: 0; background: none; padding: 0; font: 800 22px/1.15 var(--font-base); letter-spacing: -.01em; color: var(--color-text); cursor: pointer; text-align: left; white-space: nowrap; }
.hd5-title .ic { width: 20px; height: 20px; color: var(--color-text-muted); margin-top: 2px; }
/* направления — значками в строке шапки; подписи и счёт — в колонке ПК */
.scuts { display: flex; flex: 1; justify-content: flex-end; gap: 4px; min-width: 0; }
.scut { display: flex; align-items: center; gap: 12px; text-decoration: none; color: inherit; min-width: 0; border-radius: 12px; }
.scut-ring { position: relative; width: 36px; height: 36px; flex: none; }
.scut-ring svg.ring { position: absolute; inset: 0; width: 100%; height: 100%; transform: rotate(-90deg); }
.scut-ring svg.ring circle { fill: none; stroke-width: 4; } .scut-ring .tr { stroke: var(--color-mode-track); } .scut-ring .pr { stroke: var(--s); stroke-linecap: round; stroke-dasharray: var(--len) 999; }
.scut-ring .ic { position: absolute; left: 50%; top: 50%; width: 20px; height: 20px; margin: -10px 0 0 -10px; color: var(--s); }
.scut b, .scut small { display: none; }
.toc5 { display: none; }
/* ---- ВЕРХ: липкий контейнер = шапка (уезжает/приезжает по направлению скролла) + док (шкала + названия) ---- */
/* ВЕРХ — ЧАСТЬ СТРАНИЦЫ (HOME-HEADER-NATIVE-27.09): лежит на рельсе во всю высоту страницы и едет вместе с картой тем же скроллом
   телефона; две границы «прилипания» держат его: не выше «шапка спрятана, док у края» (top) и не ниже «шапка видна целиком» (bottom).
   Числа ставит код: --st-top = T − H (T — синяя полоса К1, H — высота шапки), --st-bot = высота экрана − T − высота верха. */
.top5-rail { position: absolute; top: 0; bottom: 0; left: 0; right: 0; z-index: 7; pointer-events: none; }
.top5-lead { height: 0; }
.top5-space { height: var(--s5, 0px); }
.top5 { position: sticky; top: calc(env(safe-area-inset-top, 0px) + var(--st-top, 0px)); bottom: calc(var(--st-bot, 0px) - env(safe-area-inset-top, 0px)); padding: 0 16px; background: var(--color-bg); box-shadow: 0 10px 14px -12px rgba(0,0,0,.22); pointer-events: auto; }   /* сдвиг — по скроллу 1:1 (transform из JS, без переходов); раскладка не меняется — карта не прыгает */
.hd-wrap { display: block; }
/* ярус 2: [где ты сейчас · оглавление] [ % ] / шкала во всю ширину */
.dock5 { display: grid; grid-template-columns: minmax(0, 1fr) auto; column-gap: 10px; align-items: center; padding: 2px 0 10px; }
.scale5 { display: contents; }
.sc5-head { grid-column: 2; grid-row: 1; font-size: 14px; font-weight: 600; }
.sc5-pct b { font-size: 15px; font-weight: 800; color: var(--color-accent-ink); }
.sc5-track { grid-column: 1 / -1; grid-row: 2; position: relative; height: 6px; border-radius: 3px; background: var(--color-mode-track); margin: 8px 0 2px; }
.sc5-fill { position: absolute; left: 0; top: 0; bottom: 0; border-radius: 3px; background: var(--color-primary); }
.sc5-part { position: absolute; top: -8px; bottom: -8px; cursor: pointer; }
/* разделы — просветы во всю высоту полосы: 10 лёгких отрезков (PO 29.09 15:39: «разделы на шкале… сделать более легковесно») */
.sc5-tick { position: absolute; top: 0; bottom: 0; width: 3px; margin-left: -1.5px; background: var(--color-bg); z-index: 1; }
.sc5-thread { position: absolute; top: 50%; height: 3px; margin-top: -1.5px; background: #9A9384; border-radius: 2px; z-index: 2; transition: opacity .15s; } .sc5-thread.off { opacity: 0; }
.sc5-ball { position: absolute; top: 50%; border-radius: 50%; padding: 0; z-index: 4; transition: left .12s linear; }
.sc5-ball.main { width: 16px; height: 16px; margin: -8px 0 0 -8px; background: #fff; border: 3px solid var(--color-primary); box-shadow: 0 2px 6px rgba(0,0,0,.25); cursor: pointer; }
.sc5-ball.view { width: 11px; height: 11px; margin: -5.5px 0 0 -5.5px; background: #9A9384; border: 2px solid #fff; box-shadow: 0 1px 3px rgba(0,0,0,.25); z-index: 3; transition: left .12s linear, opacity .15s, transform .15s; }
.sc5-ball.view.off { opacity: 0; transform: scale(.4); }
.tk-win { display: inline-block; overflow: hidden; vertical-align: bottom; position: relative; }
.tk-stack { will-change: transform; } .tk-line { height: 1.2em; line-height: 1.2em; white-space: nowrap; }
.names5 { grid-column: 1; grid-row: 1; position: relative; min-width: 0; padding-right: 40px; }
.tk-names5 { display: block; width: 100%; height: 42px; } .tk-names5 .tk-line { height: 42px; line-height: 1.2; }
.nm5 { height: 42px; display: flex; flex-direction: column; justify-content: center; gap: 2px; }
.nm5-part { font-size: 11.5px; color: var(--color-text-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.nm5-part span { letter-spacing: .08em; text-transform: uppercase; font-weight: 700; font-size: 10.5px; }   /* «РАЗДЕЛ 2 ИЗ 10» капителью, название — обычным регистром (длинные названия капителью не читаются) */
.nm5-part i { font-style: normal; }
.nm5-unit { font-size: 16px; font-weight: 700; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.nm5-unit b { color: var(--color-accent-ink); margin-right: 8px; }
.nm5-open { position: absolute; right: 0; top: 4px; width: 34px; height: 34px; border-radius: 50%; border: 1px solid var(--color-border); background: var(--color-surface); color: var(--color-text-muted); display: grid; place-items: center; cursor: pointer; padding: 0; }
.nm5-open .ic { width: 20px; height: 20px; }
/* ---- ПК ≥ 1200 px: верх — колонкой слева (PO 29.09 15:39 «на ПК больше понравилось боковое расположение»), карта — от самого верха.
   Колонка: Starter · поиск · меню / направления списком со счётом / где ты сейчас + % + шкала / разделы уровня (текущий — по прокрутке).
   Рельс верха становится фиксированным: «прилипание» (--st-top/--st-bot, место на рельсе) здесь не работает — не нужно. */
@media (min-width: 1200px) {
  .top5-rail { position: fixed; left: 24px; top: 24px; right: auto; bottom: auto; width: 300px; z-index: 30; transition: opacity .25s var(--ease-exit, ease); }
  /* КОЛОНКА ГАСНЕТ В НАЧАЛЕ РАСКРЫТИЯ ШАГА И ВОЗВРАЩАЕТСЯ ПОСЛЕ СВОРАЧИВАНИЯ (MAP-RAIL-FADE-15.10; PO 15.10 21:4x: «при раскрытии левое
     боковое меню главного экрана закрывается после раскрытия упражнения, да и закрывается тоже с рывком»): колонка живёт в странице карты
     (.pa), а та пряталась одним кадром в КОНЦЕ раскрытия (body.map-step) — колонка висела поверх растущего круга и пропадала разом; на
     сворачивании — так же появлялась разом. Теперь на время морфа (body.a5-morphing, map-anim.js mount / finish) она тает за .25 с */
  body.a5-morphing .top5-rail { opacity: 0; pointer-events: none; }
  /* шаг открыт — колонка уже прозрачна, без перехода: сворачивание начинается с неё прозрачной (замер 15.10: иначе первые 3 кадра морфа
     она гасла с полной видимости — страница карты при открытом шаге скрыта content-visibility, колонка «видна» под ней) */
  body.map-step .top5-rail { opacity: 0; transition: none; }
  .top5-lead { display: none; }
  .top5-space { height: 0; }
  .top5 { position: static; transform: none; max-height: calc(100vh - 48px); overflow-y: auto; padding: 16px 18px; background: var(--color-surface);
          border: 1px solid var(--color-border); border-radius: 20px; box-shadow: 0 10px 30px -14px rgba(0,0,0,.25); }
  .hd5 { flex-wrap: wrap; padding-top: 0; }
  .hd5-r { margin-left: auto; }
  .hd5-title { font-size: 24px; }
  .scuts { order: 3; flex: 0 0 100%; flex-direction: column; gap: 2px; margin-top: 8px; }
  .scut { padding: 5px 4px; }
  @media (hover: hover) { .scut:hover { background: var(--color-hover); } }
  .scut b { display: block; font-size: 14.5px; font-weight: 700; }
  .scut small { display: block; margin-left: auto; font-size: 12px; color: var(--color-text-muted); white-space: nowrap; }
  .dock5 { margin-top: 10px; padding-top: 12px; border-top: 1px solid var(--color-border); }
  .sc5-tick { background: var(--color-surface); }   /* просвет — цвета карточки колонки */
  .toc5 { display: flex; flex-direction: column; gap: 2px; margin-top: 10px; padding-top: 10px; border-top: 1px solid var(--color-border); }
  .toc5-i { display: flex; gap: 10px; align-items: center; font: inherit; font-size: 13px; color: var(--color-text-muted); padding: 5px 6px; border: 0;
            background: none; border-radius: 10px; cursor: pointer; text-align: left; }
  .toc5-i i { flex: none; width: 22px; height: 22px; border-radius: 50%; background: var(--c, var(--color-primary)); color: #fff; font-style: normal;
              font-size: 11.5px; font-weight: 700; display: grid; place-items: center; }
  .toc5-i span { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
  .toc5-i.on { background: color-mix(in srgb, var(--c, var(--color-primary)) 13%, transparent); color: var(--color-text); font-weight: 700; }
  @media (hover: hover) { .toc5-i:hover { background: var(--color-hover); } }
}
/* ---- ТРОПА ---- */
.trail5 { padding-top: 4px; }
/* дорога проявляется уже на месте текущего шага (map.js trailShow, §7б п.7: при возврате на главный экран не показывать начало карты
   и потом прыгать к своему месту) */
#trail { transition: opacity .3s var(--ease-enter, ease); }
#trail.trail-pending { opacity: 0; }
/* КАРТА ПРОЯВЛЯЕТСЯ ЦЕЛИКОМ (PO 14.10: «при закрытии отрывка надо сделать, чтобы также мягко появлялась карта, а сейчас рывки, дёрганье,
   подгрузки, смена цвета»; замер 14.10: плашка «Продолжить» из разметки видна раньше всего, шапка, тропа и карточка «Не записан голос»
   дорисовываются скриптом в разное время, потом прокрутка к своему шагу). До сборки (body.map-boot — с первого кадра, map.phtml) не видно
   ничего, кроме фона; шапка, док, тропа, низ с «Продолжить» и «к текущему шагу» проявляются вместе, когда тропа уже на месте своего шага
   (map.js trailShow); скрипт не снял за 4 с (сбой) — показывается само, как страница отрывка (components.css rt2BootSafe) */
.pa, .bottom, #jump { transition: opacity .3s var(--ease-enter, ease); }
body.map-boot .pa, body.map-boot .bottom, body.map-boot #jump { opacity: 0; animation: mapBootSafe 0s linear 4s forwards; }
@keyframes mapBootSafe { to { opacity: 1; } }
.tr5 { position: relative; padding: 6px 0 8px; }
/* УЧАСТОК ВДАЛИ НЕ РАСКЛАДЫВАЕТСЯ (MAP-FAST-BOOT-14.10, learning_path_spec §7в п. 1; map-render.js Sections): участок раздела вдали
   от экрана браузер пропускает — место держит заглушка высоты (contain-intrinsic-block-size из скрипта); у экрана (t5-near) — разложен
   целиком; до установки карты на место (t5-hold) — только участок текущего шага. ПК с пейзажем на всю ширину (data-bleed) — без этого:
   рисунок там выходит за колонку, а пропуск обрезает его по краю участка */
.t5-cv > .tr5 { content-visibility: auto; }
.t5-cv.t5-hold > .tr5 { content-visibility: hidden; }
.t5-cv > .tr5.t5-near, [data-bleed] .t5-cv > .tr5 { content-visibility: visible; }
.tr5-line { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; }
.tr5-line path { fill: none; stroke-width: 5; stroke-dasharray: 2 10; stroke-linecap: round; }
.tr5-line .tr5-done { stroke: var(--color-primary); opacity: .55; } .tr5-line .tr5-ahead { stroke: var(--color-border-strong); }
.ms5 { position: relative; z-index: 2; display: flex; align-items: center; justify-content: center; gap: 10px; margin: 14px 0 6px; }
.ms5-mark { width: 38px; height: 38px; border-radius: 12px; background: var(--color-surface); border: 2px solid var(--color-primary-soft); color: var(--color-accent-ink); display: grid; place-items: center; transform: rotate(45deg); }
.ms5-mark .ic { width: 18px; height: 18px; transform: rotate(-45deg); }
.ms5-text { display: flex; flex-direction: column; max-width: calc(100% - 60px); }
.ms5-text small { font-size: 11px; letter-spacing: .08em; text-transform: uppercase; color: var(--color-text-muted); }
.ms5-text b { font-size: 14px; line-height: 1.25; }
.u5-mark { height: 0; }
/* воздух между шагами (PO 27.09 20:2x: «чтобы тропинка спускалась ниже, потом только был круг, потом опять ниже и поворачивала в сторону,
   чтобы на экране меньше помещалось кружков и текста»): шаг кружков ~100 → ~140 px на телефоне (было padding 8px), десктоп 11 → 32px */
.n5 { position: relative; z-index: 2; display: flex; align-items: center; gap: 12px; width: 100%; border: 0; background: none; padding: 26px 0; text-align: left; cursor: pointer; font: inherit; color: inherit; --d: 76px; }
.n5.k-lesson { --d: 92px; } .n5.k-words { --d: 64px; }
@media (min-width: 760px) { .n5 { --d: 96px; } .n5.k-lesson { --d: 116px; } .n5.k-words { --d: 80px; } }
.n5.left { flex-direction: row; padding-left: 4px; } .n5.right { flex-direction: row-reverse; padding-right: 4px; text-align: right; }
.n5.mid { flex-direction: column; align-items: center; text-align: center; gap: 6px; }
.c5 { position: relative; flex: none; width: var(--d); height: var(--d); border-radius: 50%; display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 2px; background: var(--color-surface); border: 3px solid var(--c); color: var(--c); box-shadow: 0 2px 0 rgba(0,0,0,.05); transition: transform .12s; }
.n5:active .c5 { transform: scale(.96); }
.c5 .c5-ic { width: calc(var(--d) * .34); height: calc(var(--d) * .34); }
.c5-word { font-size: calc(var(--d) * .14); font-weight: 700; line-height: 1; letter-spacing: -.01em; }
.k-book .c5-word { font-size: calc(var(--d) * .3); }
.c5-ok { position: absolute; right: -3px; bottom: -3px; width: 24px; height: 24px; border-radius: 50%; background: var(--c); border: 2px solid var(--color-surface); display: grid; place-items: center; }
.c5-ok .ic { width: 14px; height: 14px; color: #fff; } .c5-ok .ic path { stroke-width: 3; }
.is-ahead .c5 { border-color: color-mix(in srgb, var(--c) 45%, var(--color-border-strong)); color: color-mix(in srgb, var(--c) 78%, var(--color-text)); }
.is-done .c5 { background: var(--c); color: #fff; border-color: var(--c); }
.is-cur .c5 { background: var(--c); color: #fff; box-shadow: 0 0 0 5px color-mix(in srgb, var(--c) 26%, transparent); animation: pulse 1.8s ease-in-out infinite; }
@keyframes pulse { 50% { box-shadow: 0 0 0 11px color-mix(in srgb, var(--c) 10%, transparent); } }
.l5 { display: flex; flex-direction: column; gap: 3px; min-width: 0; max-width: calc(100% - var(--d) - 12px); font-size: 15px; line-height: 1.22; }
.t5-zig .l5 { max-width: calc(58% - var(--d) * .5); }
.t5-center .l5 { max-width: min(100%, 270px); align-items: center; background: var(--color-bg); padding: 2px 8px; border-radius: 8px; }
.l5 b { font-weight: 600; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden; }
.is-ahead .l5 b { color: var(--color-text-muted); font-weight: 500; }
.k-lesson .l5 b { font-size: 16px; font-weight: 700; }
.l5 small { font-size: 12px; color: var(--color-text-faint); }
.l5-you { display: inline-block; align-self: flex-start; padding: 2px 9px; border-radius: 999px; background: var(--c); color: #fff; font-style: normal; font-size: 11px; font-weight: 700; letter-spacing: .02em; }
.n5.right .l5-you { align-self: flex-end; } .n5.mid .l5-you { align-self: center; }
@media (min-width: 760px) { .l5 { font-size: 16px; } .l5 small { font-size: 13px; } .n5 { padding: 32px 0; } }
/* ---- плитка шага-отрывка (BOOKS-MAP-ALGO-13.10; макет proto_path/index5.html .bk5): обложка слева — «круг» узла (дорога идёт через неё),
   справа — «книга · отрывок n из N», название, кружки отрывков книги (пройденные залиты, этот обведён), «шаг N». Цвет — свой, --bk (макет
   #F2922E): оформления карты перекрашивают --c узла цветом раздела. Плашку подписи и круглую обводку оформлений ([data-scene], [data-design])
   плитка не берёт — она сама плашка (первая проба 13.10: обложка вылезала за плитку, справа — узкая плашка, 24 кружка в шесть рядов).
   Состояния — как у кружков: пройден — ✓ на обложке, текущий — пульс вокруг плитки, впереди — тише. Обложки нет — цветная с названием ---- */
:root .n5.bk5 { --d: 62px; --bk: #F2922E; display: grid; grid-template-columns: 62px 1fr; align-items: center; gap: 12px; width: min(100%, 360px); margin: 14px auto; padding: 10px 12px 10px 10px; border-radius: 16px; background: var(--color-surface); border: 2px solid color-mix(in srgb, var(--bk) 65%, var(--color-border)); box-shadow: 0 3px 12px rgba(0,0,0,.10); text-align: left; }
.n5.bk5 .bk5-cover, [data-scene] .n5.bk5 .bk5-cover, [data-design] .n5.bk5 .bk5-cover { width: 62px; height: 90px; border-radius: 8px; border: 0; overflow: hidden; padding: 0; background: linear-gradient(160deg, #F2A24E, #C25E0A); color: #fff; box-shadow: inset 0 0 0 2px rgba(255,255,255,.35); transform: none; animation: none; }
:root .n5.bk5 .bk5-cover::after { content: none; }
.n5.bk5 .dz-halo { border-radius: 10px; border-color: var(--bk); }
.bk5-cover img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; }
.bk5-cover .c5-ic { position: relative; width: 22px; height: 22px; }
.bk5-cover .bk5-ct { position: relative; font-size: 10px; line-height: 1.15; padding: 0 5px; text-align: center; overflow-wrap: anywhere; display: -webkit-box; -webkit-line-clamp: 4; -webkit-box-orient: vertical; overflow: hidden; }
.bk5-cover:not(.noimg) .c5-ic, .bk5-cover:not(.noimg) .bk5-ct { display: none; }
/* пройденный отрывок — зелёная галка справа вверху плитки (BOOK-TILE-DONE-15.10; PO 15.10 21:4x «покажем пройденность зелёной галкой справа
   вверху на плитке, соотнести с другими объектами»): там же, где у кружков шагов (map-design .c5-ok — справа вверху круга), на краю
   плитки; зелёная — «пройдено», как отрывок в книге (--color-learned). Было — в углу обложки (overflow: hidden обложки обрезал круг) */
:root .n5.bk5 > .c5-ok, [data-scene] .n5.bk5 > .c5-ok, [data-design] .n5.bk5 > .c5-ok { right: -9px; top: -9px; bottom: auto; width: 26px; height: 26px;
  background: var(--color-learned); border: 2px solid var(--color-surface); box-shadow: 0 1px 3px rgba(0,0,0,.18); }
:root .n5.bk5 > .c5-ok .ic, [data-design] .n5.bk5 > .c5-ok .ic { color: #fff; }
.n5.bk5 .l5, [data-scene] .n5.bk5 .l5, [data-design] .n5.bk5 .l5 { max-width: none; margin: 0; padding: 0; background: none; box-shadow: none; border-radius: 0; align-items: flex-start; gap: 4px; }
.n5.bk5 .bk5-kind { font-size: 11px; letter-spacing: .08em; text-transform: uppercase; color: color-mix(in srgb, var(--bk) 80%, var(--color-text)); font-weight: 700; }
:root .n5.bk5 .l5 b { color: var(--color-text); font-weight: 700; }
/* КРУЖКИ ОТРЫВКОВ (PO 13.10 23:4x: «должно быть видно какой именно отрывок в этом шаге, общее количество отрывков и пройденные отрывки
   (пройденные, текущий, остальные неактивные)»): пройденный — залит; отрывок этой плитки — яркое кольцо, крупнее; остальные — серые.
   Было: все кружки оранжевым контуром — 2–5 почти как текущий (снимок стенда 13.10) */
/* размер (BOOK-BEAD-OPEN-14.10; сценарий №951 п. 0 «кружки крупнее: сейчас 18 точек — пальцем не попасть»): 24 пикс., текущий — 28, между ними
   6 пикс.; нажатие — по кружку и его зазору (::after, +3 пикс.: зоны соседей не перекрываются). Было 18 / 22 и 4 пикс. */
.bk5-beads { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; margin: 2px 0; }
.bead5 { position: relative; box-sizing: border-box; width: 24px; height: 24px; border-radius: 50%; border: 1.5px solid var(--color-border-strong); color: var(--color-text-muted); font: 700 10px/1 var(--font-base); display: grid; place-items: center; cursor: pointer; }
.bead5::after { content: ''; position: absolute; inset: -3px; border-radius: 50%; }
.bead5.done { background: var(--bk); border-color: var(--bk); color: #fff; }
.bead5.this { width: 28px; height: 28px; font-size: 11px; border: 2px solid var(--bk); color: color-mix(in srgb, var(--bk) 80%, var(--color-text)); box-shadow: 0 0 0 3px color-mix(in srgb, var(--bk) 30%, transparent); }
.bead5.this.done { color: #fff; }
.n5.bk5.is-cur { box-shadow: 0 0 0 5px color-mix(in srgb, var(--bk) 24%, transparent), 0 3px 12px rgba(0,0,0,.10); }
.n5.bk5.is-ahead { border-color: color-mix(in srgb, var(--bk) 35%, var(--color-border)); }
:root .n5.bk5.is-ahead .l5 b { font-weight: 600; }
/* ПК — шире, но НЕ выше телефона (BOOK-TILE-PC-15.10; PO 15.10 21:4x: «На ПК даже без надписи эта плитка с аудиокнигой выглядит слишком
   большой по высоте»; замер 15.10: 142 пикс. — обложка 84 × 118 задавала высоту, текст справа — 91): обложка и кружки — как на телефоне
   (62 × 90, 24 / 28), плитка ≈ 115 пикс. Было: обложка 84 × 118, кружки 26 / 30 */
@media (min-width: 760px) { :root .n5.bk5 { width: min(100%, 420px); } }
/* ---- низ ---- */
.jump { position: fixed; right: 16px; bottom: calc(104px + env(safe-area-inset-bottom, 0px)); z-index: 9; display: inline-flex; align-items: center; gap: 6px; padding: 8px 12px 8px 10px; border-radius: 999px; border: 1px solid var(--color-border-strong); background: color-mix(in srgb, var(--color-surface) 82%, transparent); backdrop-filter: blur(6px); color: var(--color-accent-ink); font: 600 12px/1 var(--font-base); opacity: 0; pointer-events: none; transition: opacity .2s; box-shadow: 0 2px 10px rgba(0,0,0,.10); }
.jump .ic { width: 16px; height: 16px; } .jump.on { opacity: .92; pointer-events: auto; } .jump.down .ic { transform: rotate(180deg); }
.bottom { position: fixed; left: 0; right: 0; bottom: 0; z-index: 8; padding: 10px 16px calc(12px + env(safe-area-inset-bottom, 0px)); background: linear-gradient(to top, var(--color-bg) 72%, transparent); }
.bottom .bw { max-width: var(--proto-w); margin: 0 auto; }
.go5 { display: flex; align-items: center; gap: 12px; width: 100%; padding: 10px 14px 10px 10px; border-radius: 18px; border: 0; background: var(--color-primary); color: #fff; font: inherit; cursor: pointer; text-align: left; box-shadow: 0 6px 18px rgba(72,120,177,.35); }
.go5-ic { width: 42px; height: 42px; border-radius: 50%; background: rgba(255,255,255,.18); display: grid; place-items: center; flex: none; } .go5-ic .ic { width: 22px; height: 22px; }
.go5-txt { display: flex; flex-direction: column; min-width: 0; flex: 1; } .go5-txt b { font-size: 16px; font-weight: 700; } .go5-txt small { font-size: 12px; color: inherit; opacity: .92; white-space: nowrap;   /* color: inherit — иначе base.css красит small в серый (на синем не читается) */ overflow: hidden; text-overflow: ellipsis; }
.go5 .arr { font-size: 22px; flex: none; }
/* КАРТОЧКА «НЕ ЗАПИСАН ГОЛОС» над «Продолжить» (REC-REMINDER-06.10, course_player_algorithm.md §7в Н5; map.js recCard). Вид — макет PO
   «Вариант Б» (06.10, tools/grammar/tmp/mock_unrecorded.js — те же числа): в потоке низа, над кнопкой, а не поверх карты */
.rec5 { display: flex; gap: 12px; align-items: flex-start; margin: 0 0 10px; padding: 14px 14px 12px; background: var(--color-surface); color: var(--color-text);
  border: 1px solid var(--color-border-strong); border-radius: 16px; box-shadow: 0 6px 24px rgba(0,0,0,.18); font-size: 15px; line-height: 1.35; text-align: left; }
.rec5[hidden] { display: none; }
.rec5-ic { flex: none; width: 36px; height: 36px; border-radius: 50%; display: flex; align-items: center; justify-content: center; font-size: 18px; background: var(--color-primary-soft); }
.rec5-body { flex: 1; min-width: 0; }
.rec5-t { font-weight: 700; margin-bottom: 2px; }
.rec5-s { color: var(--color-text); overflow-wrap: anywhere; }
.rec5-m { color: var(--color-text-faint); font-size: 13px; margin-top: 2px; }
.rec5-m[hidden] { display: none; }
.rec5-b { display: flex; gap: 8px; margin-top: 10px; }
.rec5-go { border: 0; border-radius: 10px; padding: 9px 16px; font: inherit; font-weight: 600; background: var(--color-primary); color: var(--color-on-primary); cursor: pointer; }
.rec5-no { border: 0; border-radius: 10px; padding: 9px 12px; font: inherit; background: transparent; color: var(--color-text-faint); cursor: pointer; }
/* окна */
.shade { position: fixed; inset: 0; z-index: 19; background: rgba(0,0,0,.28); display: none; } .shade.open { display: block; }
.sheet { position: fixed; left: 0; right: 0; bottom: 0; z-index: 20; transform: translateY(110%); transition: transform .28s var(--ease-move, ease); background: var(--color-surface); border-radius: 20px 20px 0 0; box-shadow: 0 -8px 30px rgba(0,0,0,.18); padding: 12px 16px calc(18px + env(safe-area-inset-bottom, 0px)); max-height: 80vh; overflow: auto; }
.sheet.open { transform: none; }
.sheet::before { content: ''; display: block; width: 38px; height: 4px; border-radius: 2px; background: var(--color-border-strong); margin: 0 auto 10px; }
.sheet h4 { margin: 4px 0 8px; font-size: 16px; }
/* ИЗБРАННОЕ (STEP-FAVORITES-27.09, PO 27.09 07:33: «помечать шаги как избранные, чтобы легко найти и повторить… вкладка в содержании курса,
   где будут только отмеченные шаги») — звёздочка в карточке шага и на экране шага, значок на кружке карты, вкладка в оглавлении */
.fav5 { display: inline-flex; align-items: center; justify-content: center; width: 38px; height: 38px; border-radius: 50%; border: 1px solid var(--color-border); background: var(--color-surface); color: var(--color-text-muted); cursor: pointer; padding: 0; transition: color .2s, border-color .2s, transform .12s; }
.fav5:active { transform: scale(.92); } .fav5 svg { width: 20px; height: 20px; display: block; } .fav5 path { fill: none; stroke: currentColor; stroke-width: 1.8; stroke-linejoin: round; transition: fill .2s; }
.fav5.on { color: #E9A100; border-color: color-mix(in srgb, #E9A100 45%, var(--color-border)); } .fav5.on path { fill: currentColor; }
.c5-fav { position: absolute; left: -3px; top: -3px; width: 22px; height: 22px; border-radius: 50%; background: #E9A100; color: #fff; display: grid; place-items: center; box-shadow: 0 0 0 2px var(--color-bg); }
.c5-fav svg { width: 13px; height: 13px; } .c5-fav path { fill: currentColor; stroke: none; }
.toc-tabs { display: grid; grid-template-columns: 1fr 1fr; gap: 4px; padding: 3px; border-radius: 12px; background: var(--color-surface-alt); margin: 0 0 10px; }
.toc-tabs button { border: 0; border-radius: 9px; background: transparent; font: 600 13px/1 var(--font-base, system-ui); color: var(--color-text-muted); height: 34px; cursor: pointer; }
.toc-tabs button.on { background: var(--color-surface); color: var(--color-text); box-shadow: 0 1px 4px rgba(0,0,0,.12); }
.toc-fav { display: flex; align-items: center; gap: 10px; padding: 9px 10px; border-radius: 10px; border: 0; background: none; text-align: left; font: inherit; color: inherit; cursor: pointer; }
.toc-fav:hover { background: var(--color-hover); }
.toc-fav .dot { width: 30px; height: 30px; border-radius: 50%; background: var(--c); display: grid; place-items: center; flex: none; } .toc-fav .dot .ic { width: 16px; height: 16px; } .toc-fav .dot .ic path { stroke: #fff; }
.toc-fav .tt { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; } .toc-fav .tt b { font-size: 14px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; } .toc-fav .tt small { font-size: 12px; color: var(--color-text-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.toc-empty { padding: 12px 10px 16px; font-size: 14px; line-height: 1.45; color: var(--color-text-muted); }
.lv-list, .toc { display: flex; flex-direction: column; gap: 6px; }
.toc[hidden] { display: none; }   /* вкладки оглавления: [hidden] иначе перебит display:flex (04_ANTI_PATTERNS S45) */
.lv-item { display: grid; grid-template-columns: 1fr auto; gap: 2px 10px; padding: 10px 12px; border-radius: 12px; border: 1px solid var(--color-border); background: var(--color-surface); cursor: pointer; text-align: left; font: inherit; color: inherit; }
.lv-item.on { border-color: var(--color-primary); background: var(--color-primary-soft); }
.lv-item b { font-size: 15px; } .lv-item small { font-size: 12px; color: var(--color-text-muted); grid-column: 1; } .lv-item .pct { grid-row: 1 / span 2; align-self: center; font-weight: 800; color: var(--color-accent-ink); }
.lv-item i { grid-column: 1 / -1; display: block; height: 4px; border-radius: 2px; background: var(--color-mode-track); overflow: hidden; margin-top: 4px; } .lv-item i::after { content: ''; display: block; height: 100%; width: var(--w); background: var(--color-primary); }
.toc-part { font-size: 11px; letter-spacing: .08em; text-transform: uppercase; color: var(--color-text-muted); margin: 8px 0 2px; }
.toc-unit { display: flex; align-items: center; gap: 10px; padding: 9px 10px; border-radius: 10px; border: 0; background: none; text-align: left; font: inherit; color: inherit; cursor: pointer; }
.toc-unit:hover { background: var(--color-hover); } .toc-unit.cur { background: var(--color-primary-soft); }
.toc-unit .no { width: 30px; height: 30px; border-radius: 50%; display: grid; place-items: center; font-size: 12px; font-weight: 800; color: var(--color-accent-ink); background: var(--color-surface-alt); flex: none; }
.toc-unit.done .no { background: var(--color-primary); color: #fff; }
.toc-unit .tt { flex: 1; min-width: 0; font-size: 14px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; } .toc-unit small { font-size: 12px; color: var(--color-text-muted); flex: none; }
/* ---- ПЕРЕХОДЫ (path5_anim.js; слои из anim.html v11) ---- */
.n5.ghost .c5 { visibility: hidden; }
/* пульс спрятанного кружка стоит (S58 16.10, PO: «на телефоне нормально, только на компьютере»): анимацию в спрятанном слое браузер ведёт
   сам по кадрам, и каждый кадр — пересборка слоёв всей страницы карты (Layerize) — 27 мс на ПК с пейзажем на всю ширину; весь морф кружок
   спрятан (ghost), пульс не виден — остановлен без потерь (замер: кадр раскрытия 33 → 18 мс вместе с морфом анимацией браузера, map-anim.js) */
.n5.ghost .dz-halo { animation: none; }
.n5.revive .c5 { animation: revive .8s cubic-bezier(.4,0,.2,1); }
@keyframes revive { 0% { transform: scale(.9); } 55% { transform: scale(1.06); } 100% { transform: scale(1); } }
.n5.fresh .c5-ok { animation: tick .6s cubic-bezier(.2,0,0,1) .35s both; }
@keyframes tick { 0% { transform: scale(0); } 75% { transform: scale(1.06); } 100% { transform: scale(1); } }
.n5.is-done .c5 { transition: background-color .9s cubic-bezier(.4,0,.2,1), color .9s cubic-bezier(.4,0,.2,1), box-shadow .9s cubic-bezier(.4,0,.2,1); }
.a5-rim { position: fixed; z-index: 18; border-radius: 50%; pointer-events: none; transform-origin: 50% 50%; will-change: transform; visibility: hidden; }
.a5-win { position: fixed; z-index: 20; border-radius: 50%; overflow: hidden; transform-origin: 50% 50%; will-change: transform; visibility: hidden; }
.a5-cap { position: fixed; z-index: 21; border-radius: 50%; pointer-events: none; transform-origin: 50% 50%; will-change: transform; visibility: hidden; color: #fff; }
.a5-fill { position: absolute; inset: 0; border-radius: 50%; transform: scale(0); will-change: transform; }
/* значок и слово кружка — свой слой в размере кружка, только прозрачность (map-anim.js mount / apply; ANIM-RULES-12.10 п. 4: не растёт
   из точки и не размывается — было .a5-num внутри слоя заливки, со scale) */
.a5-ico { position: fixed; z-index: 22; display: grid; place-items: center; pointer-events: none; visibility: hidden; opacity: 0; color: #fff; will-change: opacity; }
.a5-in { display: flex; flex-direction: column; align-items: center; justify-content: center; font-weight: 700; line-height: 1; letter-spacing: -.01em; }
.a5-in .ic { display: block; } .a5-in .ic path { stroke: #fff; }
body.a5-morphing .a5-rim, body.a5-morphing .a5-win, body.a5-morphing .a5-cap, body.a5-morphing .a5-ico { visibility: visible; }
/* ЭКРАН ШАГА (MAP-STEP-OPEN-27.09). В раскрытии и сворачивании — слой во весь экран (круглое окно растёт/сжимается, map-anim.js);
   между ними — ОБЫЧНАЯ СТРАНИЦА (body.map-step): карта скрыта, прокручивается окно — движки шагов (упражнения, уроки, «Слова»)
   прокручивают окно, как в ленте курса. Шапка шага липнет сверху: тип, «юнит · шаг N из T», ☆, ×; название — в шапке самого шага. */
#a5-step { position: fixed; z-index: 20; left: 0; top: 0; width: 100vw; height: 100vh; background: var(--color-bg); transform-origin: 50% 50%; opacity: 0; pointer-events: none; overflow: auto; will-change: transform, opacity; }
#a5-step.inwin { position: absolute; }
#a5-step.open { pointer-events: auto; }
body.map-step #a5-step { position: static; width: auto; height: auto; overflow: visible; opacity: 1; transform: none; will-change: auto; }
body.map-step .pa, body.map-step .bottom, body.map-step .jump { display: none; }
/* КАРТА ПОД ОТКРЫТЫМ ШАГОМ — РАЗЛОЖЕННОЙ (ANIM-RULES-12.10 п. 5 «без замираний»; обход по кадрам 12.10): display: none выбрасывал
   раскладку всей карты (≈ 36 500 элементов), и «Далее» / «×» стояли 0,2–0,6 с, пока браузер раскладывал её заново (замер: 199–276 мс
   на возврат). content-visibility: hidden — карта не рисуется и места не занимает, но раскладка сохранена: возврат — 5 мс.
   Браузер без него (до 2020–2024 гг.) — как было, display: none. Нижний отступ карты (место под «Продолжить») — 0: скрытая карта
   высотой в свои поля (содержимое не считается) иначе стояла бы над шагом пустой полосой 118 точек; на раскладку содержимого нижний
   отступ не влияет — сохранённая раскладка годна */
@supports (content-visibility: hidden) { body.map-step .pa { display: block; content-visibility: hidden; padding-bottom: 0; } }
.sh6 { position: sticky; top: 0; z-index: 6; background: var(--color-bg); border-bottom: 1px solid var(--color-border); }
.sh6-in { max-width: 640px; margin: 0 auto; padding: 8px 16px; display: flex; align-items: center; gap: 8px; min-height: 54px; box-sizing: border-box; }
.sh6 .kind { display: inline-flex; align-items: center; gap: 6px; font-size: 12px; font-weight: 700; padding: 3px 10px; border-radius: 999px; color: #fff; background: var(--c); flex: none; }
.sh6 .kind .ic { width: 16px; height: 16px; } .sh6 .kind .ic path { stroke: #fff; }
.sh6 .meta { flex: 1; min-width: 0; font-size: 12px; color: var(--color-text-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.sh6 .x { width: 38px; height: 38px; border-radius: 50%; border: 1px solid var(--color-border); background: var(--color-surface); color: var(--color-text); font-size: 18px; line-height: 1; cursor: pointer; flex: none; padding: 0; }
.sh6 .fav5 { flex: none; }
.a5-sparklayer { position: absolute; left: 0; top: 0; width: 0; height: 0; z-index: 25; pointer-events: none; }
.a5-spark { position: absolute; left: 0; top: 0; width: 22px; height: 22px; margin: -11px 0 0 -11px; border-radius: 50%; border: 3px solid #fff; box-shadow: 0 2px 8px rgba(0,0,0,.25); transform: scale(0); will-change: transform; visibility: hidden; }
.a5-sparkpath { position: absolute; left: 0; top: 0; width: 0; height: 0; overflow: visible; pointer-events: none; } .a5-sparkpath path { fill: none; stroke: none; }
.a5-toast { position: fixed; left: 16px; right: 16px; bottom: calc(20px + env(safe-area-inset-bottom, 0px)); z-index: 30; max-width: 496px; margin: 0 auto; padding: 10px 14px; border-radius: 12px; background: var(--color-surface); border: 1px solid var(--color-border); box-shadow: 0 4px 16px rgba(0,0,0,.15); font-size: 14px; text-align: center; }
