/**
 * Оформление сайта (макет «Studio»). Поверх Bootstrap 5, не вместо него.
 *
 * ЦВЕТА: здесь живёт только НЕЙТРАЛЬ (фон, линии, текст) — она общая для всех палитр.
 * Акцентная шестёрка (--tc-accent, --tc-accent-soft, --tc-accent-faint, --tc-accent-ink, --tc-accent-deep, --tc-on) приходит переменными из PHP:
 * layout печатает их из include/site_config.php по палитре текущего пользователя.
 * Поэтому в этом файле НЕТ ни одного акцентного цвета литералом — только var().
 */

:root {
    --tc-white: #ffffff;
    --tc-page: #f5f7fa;
    --tc-panel: #fbfcfe;
    --tc-line: #e4e8f0;
    --tc-line2: #eef1f6;
    --tc-ink: #0f172a;
    --tc-body: #334155;
    --tc-mut: #64748b;
    --tc-faint: #94a3b8;
    --tc-gold: #f0b429;
    --tc-danger: #c0392b;
    --tc-danger-soft: #fdeeee;
    /* Зелёный «верно» — такая же СМЫСЛОВАЯ пара красному, а не акцент палитры:
       в режиме обучения зелёный и красный работают только парой, и если бы «верно»
       красилось акцентом, на янтарной палитре пара развалилась бы. Приглушённый —
       сетка номеров и подсветка вариантов второстепенны и не должны кричать. */
    --tc-good: #2f7a4f;
    --tc-good-soft: #e6f2ea;
    --tc-good-faint: #f4faf6;
    /**
     * ШКАЛА РЕЗУЛЬТАТА — «справился / средне / завалил». Такая же СМЫСЛОВАЯ тройка,
     * как пара «верно/неверно» выше, и по той же причине она не акцент палитры: на
     * янтарной палитре «справился» и «завалил» покрасились бы одним цветом и перестали
     * быть парой. Заведена 22.09.2026 по заказу владельца («нужно сочные, красно
     * зелененькие») — цвета здесь НАСЫЩЕННЕЕ приглушённой пары обучения: это картинка,
     * которую читают издалека, а не подсветка строки с текстом.
     */
    --tc-ok: #16a34a;
    --tc-ok-soft: #dcfce7;
    --tc-mid: #f59e0b;
    --tc-mid-soft: #fef3c7;
    --tc-bad: #e11d48;
    --tc-bad-soft: #ffe4e6;

    --tc-radius: 16px;
    --tc-radius-sm: 11px;
    --tc-radius-pill: 999px;
    --tc-shadow: 0 1px 2px rgba(15, 23, 42, .04), 0 8px 24px rgba(15, 23, 42, .06);
    --tc-shadow-lg: 0 18px 44px rgba(15, 23, 42, .12);

    /* Bootstrap читает свои переменные — отдаём ему наши. */
    --bs-font-sans-serif: 'Plus Jakarta Sans', 'Segoe UI', system-ui, -apple-system, sans-serif;
    --bs-body-bg: var(--tc-page);
    --bs-body-color: var(--tc-body);
    --bs-emphasis-color: var(--tc-ink);
    --bs-secondary-color: var(--tc-mut);
    --bs-border-color: var(--tc-line);
    --bs-border-radius: var(--tc-radius-sm);
    --bs-border-radius-sm: 9px;
    --bs-border-radius-lg: var(--tc-radius);
    --bs-link-color: var(--tc-accent);
    --bs-link-hover-color: var(--tc-ink);
    --bs-heading-color: var(--tc-ink);
}

html, body { min-height: 100%; }
body {
    display: flex;
    flex-direction: column;
    background: var(--tc-page);
    color: var(--tc-body);
    -webkit-font-smoothing: antialiased;
}
main { flex: 1 0 auto; }

h1, h2, h3, h4, h5, h6, .h1, .h2, .h3, .h4, .h5, .h6 {
    color: var(--tc-ink);
    font-weight: 700;
    letter-spacing: -.02em;
}
.display-4, .display-5, .display-6 { font-weight: 800; letter-spacing: -.035em; }
a { text-decoration: none; }
a:hover { text-decoration: none; }

/* КРОШКИ СЕРЫЕ ЦЕЛИКОМ (заказ владельца 22.09.2026: «цвет не синий сделать, пусть всё
   серенькое будет как последнее»). Крошки — это подпись «где я», а не главное действие
   страницы: синий ряд над заголовком спорил с ним и тянул нажатие на себя. Ссылками они
   при этом остались, и под курсором это видно. */
.breadcrumb { --bs-breadcrumb-divider-color: var(--tc-faint); }
.breadcrumb a { color: var(--tc-mut); }
.breadcrumb a:hover, .breadcrumb a:focus-visible { color: var(--tc-ink); text-decoration: underline; }

/* ИМЯ ЧЕЛОВЕКА — ВСЕГДА ССЫЛКА НА ЕГО СТРАНИЦУ (правило владельца 22.09.2026: «если
   где-то имя юзера — это сразу ссылка на его профиль»). Один класс на все места, чтобы
   имя в отзыве, в карточке ленты и в кабинете вело себя одинаково: цвет берётся у
   соседнего текста, а ссылкой имя становится под курсором — иначе ряд подписей превратился
   бы в частокол синевы. */
.t-userlink { color: inherit; }
.t-userlink:hover, .t-userlink:focus-visible { color: var(--tc-accent-ink); text-decoration: underline; }
/* Имя внутри карточки со `stretched-link`: заголовок накрывает карточку целиком, и без
   своего слоя нажатие по имени уходило бы на тест. */
.t-userlink--over { position: relative; z-index: 2; }

/* --- Кнопки --- */
.btn {
    --bs-btn-border-radius: var(--tc-radius-sm);
    font-weight: 600;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: .5rem;
}
.btn-lg { --bs-btn-padding-y: .85rem; --bs-btn-padding-x: 1.6rem; --bs-btn-font-size: 1rem; }
.btn-primary {
    --bs-btn-bg: var(--tc-accent);
    --bs-btn-border-color: var(--tc-accent);
    --bs-btn-color: var(--tc-on);
    --bs-btn-hover-bg: var(--tc-accent-ink);
    --bs-btn-hover-border-color: var(--tc-accent-ink);
    --bs-btn-hover-color: var(--tc-on);
    --bs-btn-active-bg: var(--tc-accent-ink);
    --bs-btn-active-border-color: var(--tc-accent-ink);
    --bs-btn-disabled-bg: var(--tc-accent-soft);
    --bs-btn-disabled-border-color: var(--tc-accent-soft);
    --bs-btn-disabled-color: var(--tc-mut);
}
.btn-outline-primary {
    --bs-btn-color: var(--tc-accent-ink);
    --bs-btn-border-color: var(--tc-line);
    --bs-btn-bg: var(--tc-white);
    --bs-btn-hover-bg: var(--tc-accent-faint);
    --bs-btn-hover-border-color: var(--tc-accent);
    --bs-btn-hover-color: var(--tc-accent-ink);
    --bs-btn-active-bg: var(--tc-accent-faint);
    --bs-btn-active-border-color: var(--tc-accent);
    --bs-btn-active-color: var(--tc-accent-ink);
}
.btn-outline-secondary {
    --bs-btn-color: var(--tc-body);
    --bs-btn-border-color: var(--tc-line);
    --bs-btn-bg: var(--tc-white);
    --bs-btn-hover-bg: var(--tc-page);
    --bs-btn-hover-border-color: var(--tc-line);
    --bs-btn-hover-color: var(--tc-ink);
    --bs-btn-active-bg: var(--tc-page);
    --bs-btn-active-border-color: var(--tc-line);
    --bs-btn-active-color: var(--tc-ink);
}
.btn-warning {
    --bs-btn-bg: var(--tc-gold);
    --bs-btn-border-color: var(--tc-gold);
    --bs-btn-color: var(--tc-ink);
    --bs-btn-hover-bg: var(--tc-gold);
    --bs-btn-hover-border-color: var(--tc-gold);
    --bs-btn-hover-color: var(--tc-ink);
}
.btn-link { --bs-btn-color: var(--tc-accent); --bs-btn-hover-color: var(--tc-ink); }

/* --- Карточки, поля, бейджи --- */
.card {
    --bs-card-border-color: var(--tc-line);
    --bs-card-border-radius: var(--tc-radius);
    --bs-card-inner-border-radius: calc(var(--tc-radius) - 1px);
    --bs-card-bg: var(--tc-white);
}
.card.shadow-sm { box-shadow: var(--tc-shadow) !important; }

.form-control, .form-select {
    border-color: var(--tc-line);
    border-radius: var(--tc-radius-sm);
    padding: .7rem .9rem;
    color: var(--tc-ink);
}
.form-control::placeholder { color: var(--tc-faint); }
.form-label { font-size: .8rem; font-weight: 700; color: var(--tc-mut); text-transform: uppercase; letter-spacing: .1em; }
.form-check-input:checked { background-color: var(--tc-accent); border-color: var(--tc-accent); }
.form-switch .form-check-input:checked { background-color: var(--tc-accent); }

.badge { font-weight: 600; border-radius: var(--tc-radius-pill); padding: .4em .8em; }
.text-bg-primary { background: var(--tc-accent) !important; color: var(--tc-on) !important; }
.text-bg-light { background: var(--tc-page) !important; color: var(--tc-body) !important; }
.text-bg-secondary { background: var(--tc-page) !important; color: var(--tc-mut) !important; }
.text-bg-success { background: var(--tc-accent-faint) !important; color: var(--tc-accent-ink) !important; }
.text-primary { color: var(--tc-accent) !important; }
.bg-primary { background-color: var(--tc-accent) !important; }
.text-secondary, .text-body-secondary { color: var(--tc-mut) !important; }
/* Разбор ответов: верно — акцентом палитры, неверно — красным (он не палитра, а смысл). */
.border-success { border-color: var(--tc-accent-soft) !important; }
.border-danger { border-color: var(--tc-danger-soft) !important; }
.t-ok { color: var(--tc-accent-ink); }
/* .t-good — «верно» статусным зелёным (режим обучения). На странице разбора после теста
   осталось прежнее .t-ok акцентом палитры: там зелёно-красной пары нет и менять вид
   готового экрана ради единообразия не стали. */
.t-good { color: var(--tc-good); }
.t-bad { color: var(--tc-danger); }
.t-icon--bad { background: var(--tc-danger-soft); color: var(--tc-danger); }

.progress { background: var(--tc-line2); border-radius: var(--tc-radius-pill); }
.progress-bar { background: var(--tc-accent); }
.progress-bar.bg-success { background: var(--tc-accent) !important; }

.alert { border-radius: var(--tc-radius); border-color: var(--tc-line); }
/* Сообщение после редиректа («You are logged in»): под ним складывались его собственный
   нижний отступ и верхний отступ `main` — щель вдвое больше, чем над ним (жалоба владельца
   23.09.2026). Отступ под сообщением теперь равен отступу над ним (mt-3). */
.t-flash .alert:last-child { margin-bottom: 0; }
.t-flash + main { padding-top: 1rem !important; }
.alert-light { background: var(--tc-white); }

.nav-tabs { --bs-nav-tabs-border-color: var(--tc-line); border-bottom-width: 1px; gap: .25rem; }
.nav-tabs .nav-link {
    border: 0;
    border-bottom: 2px solid transparent;
    color: var(--tc-mut);
    font-weight: 600;
    padding: .7rem 1rem;
}
.nav-tabs .nav-link:hover { color: var(--tc-ink); }
.nav-tabs .nav-link.active { color: var(--tc-ink); background: transparent; border-bottom-color: var(--tc-accent); }

.pagination { --bs-pagination-color: var(--tc-body); --bs-pagination-border-color: var(--tc-line); --bs-pagination-border-radius: var(--tc-radius-sm); --bs-pagination-hover-bg: var(--tc-page); }
.page-item.active .page-link { background: var(--tc-accent); border-color: var(--tc-accent); color: var(--tc-on); }

.table { --bs-table-color: var(--tc-body); --bs-table-border-color: var(--tc-line2); }
.table > thead { --bs-table-bg: var(--tc-panel); }
.table > thead th { font-size: .72rem; letter-spacing: .1em; text-transform: uppercase; color: var(--tc-faint); font-weight: 700; }

/* Выбранный пункт меню красится ПАЛИТРОЙ: у бутстрапа тут свой синий, чужой сайту. */
.dropdown-menu {
    --bs-dropdown-border-color: var(--tc-line); --bs-dropdown-border-radius: var(--tc-radius-sm);
    --bs-dropdown-link-active-bg: var(--tc-accent); --bs-dropdown-link-active-color: var(--tc-on);
    box-shadow: var(--tc-shadow);
}

/* Фокус: синее bootstrap-обрамление снято глобально, клавиатурный фокус остаётся своим. */
.form-control:focus, .form-select:focus, .form-check-input:focus,
.form-control-color:focus, .btn:focus, .btn:focus-visible, .accordion-button:focus {
    box-shadow: none;
    outline: 0;
}
.form-control:focus, .form-select:focus { border-color: var(--tc-accent); }
.form-check-input:focus { border-color: var(--tc-line); }
.btn:focus-visible, .form-control:focus-visible, .form-select:focus-visible,
.form-check-input:focus-visible, a:focus-visible {
    outline: 2px solid var(--tc-accent);
    outline-offset: 2px;
}

/* --- Шапка --- */
.t-bar { background: var(--tc-white); border-bottom: 1px solid var(--tc-line); }
.t-bar .navbar-brand { font-weight: 800; letter-spacing: -.02em; color: var(--tc-ink); font-size: 1.2rem; }
.t-bar .nav-link { color: var(--tc-mut); font-weight: 500; padding: .35rem 0; border-bottom: 2px solid transparent; }
.t-bar .nav-link:hover { color: var(--tc-ink); }
/* Пункты шапки не переносятся по словам: на русском подписи длиннее, и «Все / тесты»
   в две строки ломало высоту шапки. Не влезает — сжимается поле поиска, а не подписи. */
.t-bar .nav-link, .t-bar .btn { white-space: nowrap; }
.t-bar .nav-link.active { color: var(--tc-ink); font-weight: 600; border-bottom-color: var(--tc-accent); }
.t-search { max-width: 17rem; }

/* Бургер после закрытия меню не должен стоять «выделенным» (жалоба владельца 23.09.2026):
   фокус остаётся на кнопке, и кольцо бутстрапа висело вокруг неё. Клавиатуре кольцо
   оставляем — только по :focus-visible, как у остальных кнопок. */
.t-bar .navbar-toggler:focus { box-shadow: none; outline: none; }
.t-bar .navbar-toggler:focus-visible { outline: 2px solid var(--tc-accent); outline-offset: 2px; }
/* А пока меню ОТКРЫТО, кольцо стоит (владелец 23.09.2026: «просил убрать выделение
   при закрытом бургере, а при открытом не убирать»). Держится оно на состоянии меню
   (`aria-expanded`, его ставит бутстрап), а не на фокусе — поэтому и снимается ровно
   с закрытием. Кольцо то же, что у бутстрапа. */
.t-bar .navbar-toggler[aria-expanded="true"] { box-shadow: 0 0 0 var(--bs-navbar-toggler-focus-width); }

/**
 * МЕНЮ НА ТЕЛЕФОНЕ — ПОВЕРХ СТРАНИЦЫ, а не в её потоке (23.09.2026, жалоба владельца:
 * «меню при открытии подтормаживает, панель должна открываться над сайтом, а не двигать
 * его вниз»). Бутстрап раскрывает меню, ТЯНУЯ ВЫСОТУ, и каждый кадр раскрытия сдвигал
 * всё под шапкой — раскладка страницы целиком шестьдесят раз в секунду. Теперь меню —
 * панель поверх, появляется прозрачностью и сдвигом (это делает видеокарта). Высоту
 * бутстрапа снимаем: анимацию даёт класс `show`. Тот же приём, что на sketchbe.com.
 * Не возвращать меню в поток и не анимировать высоту/отступы.
 *
 * Панель — ПРОДОЛЖЕНИЕ ШАПКИ, а не отдельное окно (владелец 23.09.2026: «к правой части
 * без отступов, как её часть, чтобы визуально это было открытое меню, а не окно какое-то
 * левое»): во всю ширину шапки, вплотную под ней, без скруглений сверху и без своей
 * рамки по бокам; кромка шапки уходит под панель, текст стоит по линии логотипа.
 */
@media (max-width: 991.98px) {
    .t-bar .navbar-collapse {
        position: absolute;
        top: 100%;
        left: 0;
        right: 0;
        margin-top: -1px;
        padding: .25rem calc(var(--bs-gutter-x, 1.5rem) * .5) 1rem;
        background: var(--tc-white);
        border-bottom: 1px solid var(--tc-line);
        box-shadow: 0 14px 24px rgba(15, 23, 42, .10);
    }
    .t-bar .navbar-collapse.collapsing {
        height: auto !important;
        transition: none;
    }
    .t-bar .navbar-collapse.show {
        animation: t-nav-drop .16s cubic-bezier(.22, .61, .36, 1);
    }
    /* Затемнение сайта ПОД открытым меню (владелец 23.09.2026: «меню сливается, непонятно,
       где конец меню, а где сайт, и что это вообще меню»). Лежит сразу под панелью и
       только ниже неё — шапка остаётся светлой, значит меню читается как её часть.
       Нажатие по затемнению закрывает меню (скрипт в layout.php) и до сайта не доходит. */
    .t-bar .navbar-collapse.show::after {
        content: "";
        position: absolute;
        top: 100%;
        left: 0;
        right: 0;
        height: 100vh;
        margin-top: 1px;
        background: rgba(15, 23, 42, .38);
    }
    .t-bar .t-search { max-width: none; }

    /* Аккаунт левее бургера: в разметке он после меню, место задаёт `order`. */
    .t-nav-user { order: 1; margin-left: auto; margin-right: .25rem; }
    .t-bar .navbar-toggler { order: 2; }
    .t-bar .navbar-collapse { order: 3; }
}
@keyframes t-nav-drop {
    from { opacity: 0; transform: translateY(-8px); }
    to   { opacity: 1; transform: none; }
}
@media (prefers-reduced-motion: reduce) {
    .t-bar .navbar-collapse.show { animation: none; }
}

.t-nav-user__btn {
    display: inline-flex; align-items: center; justify-content: center;
    width: 2.5rem; height: 2.5rem; padding: 0;
    border: 0; border-radius: 50%;
    background: transparent; color: var(--tc-mut);
    font-size: 1.5rem; line-height: 1; text-decoration: none;
}
.t-nav-user__btn:focus { outline: none; box-shadow: none; }
.t-nav-user__btn:focus-visible { outline: 2px solid var(--tc-accent); outline-offset: 2px; }
.t-avatar {
    width: 2.1rem; height: 2.1rem; border-radius: 50%;
    background: var(--tc-accent-soft); color: var(--tc-accent-ink);
    font-weight: 700; font-size: .85rem;
    display: inline-flex; align-items: center; justify-content: center;
}

/* Крупная буква — шапка страницы автора: там она не подпись к строке, а сам знак человека. */
.t-avatar--lg { width: 4rem; height: 4rem; font-size: 1.6rem; }

/* --- Мелкие общие детали макета --- */
.t-lab { font-size: .68rem; letter-spacing: .12em; text-transform: uppercase; font-weight: 700; color: var(--tc-faint); }
.t-chip {
    display: inline-flex; align-items: center; gap: .45rem;
    border-radius: var(--tc-radius-pill);
    font-size: .8rem; font-weight: 600;
    padding: .4rem .85rem;
    background: var(--tc-page); color: var(--tc-body);
    border: 1px solid transparent;
}
/* Мелкий чип: навигация по темам и тегам. Она ведёт по сайту, но не спорит
   с заголовками и карточками — поэтому легче основного чипа и по кеглю, и по насыщенности. */
.t-chip--sm {
    font-size: .72rem; font-weight: 500; letter-spacing: .01em;
    padding: .2rem .6rem; gap: .3rem;
    color: var(--tc-mut);
}
.t-chip--sm i { font-size: .66rem; opacity: .65; }
.t-chip--sm:hover { color: var(--tc-ink); border-color: var(--tc-line2); }
.t-chip--accent { background: var(--tc-accent-faint); color: var(--tc-accent-ink); }
.t-chip--on { background: var(--tc-accent); color: var(--tc-on); }
.t-chip--line { background: var(--tc-white); border-color: var(--tc-line); }
/* Плашка-КНОПКА с подсказкой (результат автора отзыва). Кнопка здесь нужна ради фокуса:
   на телефоне подсказку открывают нажатием, а `<span>` нажать некуда. Значит и выглядеть
   она обязана плашкой, а не кнопкой: свой фон и рамку браузера снимаем, курсор — вопрос. */
.t-chip--hint {
    cursor: help; font: inherit; font-size: .8rem; font-weight: 600;
    line-height: inherit; text-align: inherit;
}
.t-chip--hint:hover { border-color: var(--tc-line2); }
.t-icon {
    width: 2.6rem; height: 2.6rem; border-radius: var(--tc-radius-sm);
    background: var(--tc-accent-faint); color: var(--tc-accent);
    display: inline-flex; align-items: center; justify-content: center;
    flex-shrink: 0; font-size: 1.15rem;
}
.t-icon--lg { width: 5.2rem; height: 5.2rem; border-radius: var(--tc-radius); font-size: 2.4rem; }
.t-icon--plain { background: var(--tc-page); color: var(--tc-faint); }
/* На тонированной плашке фон иконки совпал бы с фоном блока — делаем белым. */
.t-tint .t-icon { background: var(--tc-white); }
.t-tint { background: var(--tc-accent-faint); }
/* Шапка страницы теста: знак слева, бейджи и заголовок — колонкой справа от него.
   Колонка, а не обтекание: длинное название не должно затекать под знак, а при
   переносе — рваться о его край. min-width: 0 обязателен, иначе длинное слово
   в заголовке распирает колонку флекса и выносит бейджи за карточку. */
.t-testhead { display: flex; align-items: flex-start; gap: 1rem; }
.t-testhead__body { min-width: 0; flex: 1 1 auto; }
.t-testhead__body h1 { overflow-wrap: anywhere; }
/* ВЕРХНИЙ РЯД ШАПКИ — МЕЛКИЙ (заказ владельца 22.09.2026: «слишком крупные, отжирают место,
   оттягивают внимание»). Это ПРИЗНАКИ теста — топик, число вопросов, автор, — а не действия:
   они подписывают заголовок и спорить с ним весом не должны. Мельчим только здесь: те же
   плашки в карточках лент стоят в другом окружении и своего размера не меняют. */
.t-testhead .t-chip { font-size: .72rem; padding: .22rem .6rem; gap: .3rem; }
/* А вот ЗНАК внутри мелкой плашки мельчить нельзя — наоборот, он крупнее подписи (заказ
   владельца 22.09.2026: «иконки этих кнопок чуть побольше, сейчас их просто не видно»).
   Подпись читают, знак УЗНАЮТ: контурная мишень в девять пикселей превращается в пятнышко,
   и плашка «0 прохождений» перестаёт отличаться от «1 форк». */
.t-testhead .t-chip i { font-size: 1.15em; }
/* Знак теста — белый квадрат на тёплой плашке, и без кромки он с ней сливался краями
   (заказ владельца 22.09.2026: «вокруг иконки слева лёгкий светло-серенький бордер»). */
.t-testhead .t-icon { border: 1px solid var(--tc-line); }
/* На телефоне знак отдаёт ширину тексту: во всю величину он съедал четверть строки,
   и бейджи рассыпались по трём этажам — ровно та экономия места, ради которой
   заголовок сюда и переехал. */
@media (max-width: 575.98px) {
    .t-testhead { gap: .75rem; }
    .t-testhead .t-icon--lg { width: 3.4rem; height: 3.4rem; font-size: 1.5rem; }
}
/* Действия страницы теста стоят ПОД описанием рядом по двое (заказ владельца 22.09.2026).
   Сетка, а не флекс: каждая кнопка лежит в своей форме, и ширина колонки не должна
   зависеть от длины подписи — «Fork» обязан быть ровно той же ширины, что «Add to
   favorites». align-items: start — у кнопки обучения снизу висит подпись, и тянуть
   соседнюю кнопку под её рост незачем. На телефоне колонка одна: половина узкого
   экрана короче самой подписи. */
.t-actions { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: .75rem; align-items: start; }
/* Кнопка действия — РОСЛАЯ и с крупной подписью (заказ владельца 22.09.2026: «кнопки
   какие-то растянутые и узкие»). Причина не в ширине: ширину задаёт колонка сетки, и
   уменьшать её нельзя — тогда ряд по двое перестанет быть рядом. Лечится ростом: кнопка
   в пол-карточки шириной обязана быть и высокой, иначе читается полосой. Числа едут
   переменными бутстрапа — той же дверью, что у остальных кнопок темы. */
.t-actions .btn {
    --bs-btn-padding-y: .8rem;
    --bs-btn-padding-x: 1.2rem;
    --bs-btn-font-size: 1.05rem;
    min-height: 3.4rem;
}
@media (max-width: 575.98px) { .t-actions { grid-template-columns: 1fr; } }

/* «В избранное» и «Форк» — маленькие кнопки в подвале карточки, как «☆ Star» на
   гитхабе (23.09.2026, заказ владельца: «по сути это второстепенные функции»).
   Серая плашка с кромкой, а не контурная кнопка темы: рядом со Start они не должны
   выглядеть действием того же ранга. Выбранное избранное — звезда цветом акцента. */
.t-minor { display: flex; flex-wrap: wrap; gap: .4rem; }
.t-minor__btn {
    --bs-btn-padding-y: .2rem;
    --bs-btn-padding-x: .6rem;
    --bs-btn-font-size: .78rem;
    --bs-btn-font-weight: 600;
    --bs-btn-color: var(--tc-ink);
    --bs-btn-bg: var(--tc-page);
    --bs-btn-border-color: var(--tc-line);
    --bs-btn-hover-color: var(--tc-ink);
    --bs-btn-hover-bg: var(--tc-line2);
    --bs-btn-hover-border-color: var(--tc-line);
    --bs-btn-active-color: var(--tc-ink);
    --bs-btn-active-bg: var(--tc-line2);
    --bs-btn-active-border-color: var(--tc-line);
    display: inline-flex; align-items: center; gap: .35rem;
}
.t-minor__btn .bi { font-size: .85rem; color: var(--tc-mut); }
.t-minor__btn.is-on .bi { color: var(--tc-accent); }

/* Кнопка обучения со ЗНАКОМ ВОПРОСА СРАЗУ ПОСЛЕ ПОДПИСИ (заказ владельца 22.09.2026).
   Устройство и причина — в комментарии у разметки (templates/pages/test.php): знак это
   отдельная кнопка, а кнопку в кнопку не вложить, поэтому форму отправляет невидимая
   кнопка-подложка на всё лицо, а подпись со знаком лежат поверх неё.
   Подпись нажатий НЕ ловит (`pointer-events: none`) — иначе она перехватывала бы у
   подложки половину лица кнопки. */
.t-learn { position: relative; }
.t-learn__hit {
    position: absolute; inset: 0; width: 100%; height: 100%;
    padding: 0; border: 0; background: none; border-radius: inherit; cursor: pointer;
}
.t-learn__hit:focus { outline: none; }
.t-learn:focus-within { border-color: var(--tc-accent); background: var(--tc-accent-faint); }
.t-learn__label {
    position: relative; pointer-events: none;
    display: inline-flex; align-items: center; gap: .5rem;
}
/* Знак — ПРОСТО КРУЖОК С ВОПРОСОМ ВНУТРИ, без серой заливки (прямые слова владельца).
   Поэтому глиф контурный (`bi-question-circle`, а не `-fill`) и фона у кнопки нет: на
   кнопке любая подложка читалась бы пятном. */
.t-hint {
    position: relative; flex: 0 0 auto;
    width: 1.1rem; height: 1.1rem; padding: 0; border: 0; border-radius: 50%;
    background: transparent; color: var(--tc-faint);
    display: inline-flex; align-items: center; justify-content: center;
    font-size: 1rem; line-height: 1; cursor: help;
}
.t-hint:hover, .t-hint:focus-visible { color: var(--tc-accent); }

.t-empty { border: 1.5px dashed var(--tc-line); border-radius: var(--tc-radius); background: var(--tc-page); }
.t-hero { background: var(--tc-white); border-bottom: 1px solid var(--tc-line); }
.t-scene { max-width: 100%; height: auto; }

/* --- Шапка каталога: заголовок, поиск и сортировка одной полосой, картинка сбоку ---
   Высоту полосы задаёт левая колонка (заголовок + строка + поиск), а не картинка:
   картинка подрезана до её роста, поэтому пустоты сверху и снизу не остаётся. */
.t-cathead { display: flex; align-items: center; gap: 1.5rem; }
.t-cathead__main { flex: 1 1 auto; min-width: 0; }
.t-cathead__art { flex: 0 0 auto; line-height: 0; }

.t-find__form { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }
.t-find__q { flex: 1 1 13rem; min-width: 0; width: auto; }

/* Полоса над лентой: счёт слева, кнопка сортировки справа (порядок — не фильтр). */
.t-listbar { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem .9rem; }
.t-listbar .dropdown-toggle { font-size: .78rem; font-weight: 500; }

/* Подпись слева от чипов: две темы (топики и теги) не забирают по отдельному этажу. */
.t-facets { display: grid; grid-template-columns: max-content 1fr; gap: .5rem .9rem; align-items: center; }
@media (max-width: 575.98px) {
    .t-facets { grid-template-columns: 1fr; gap: .3rem .9rem; }
    .t-find__count { margin-left: 0; }
}

/* --- ЦВЕТ ТЕМЫ (taxonomy.topic_hues, 23.09.2026: «всё серое, бледное») ---
   Оттенок приходит переменной --t-hue из конфига, светлота и насыщенность — отсюда,
   одни на все темы: так ни одна тема не кричит громче соседки. */
.t-hue { background: hsl(var(--t-hue) 85% 93%); color: hsl(var(--t-hue) 62% 36%); }


/* Метка «это тема — показать только её» над выдачей: цвет темы, ссылка справа. */
.t-exact {
    display: flex; flex-wrap: wrap; align-items: center; gap: .5rem .75rem;
    padding: .6rem .9rem; border-radius: var(--tc-radius-sm);
    background: var(--tc-accent-faint); color: var(--tc-accent-ink); font-size: .88rem;
}
.t-exact.t-hue { background: hsl(var(--t-hue) 85% 94%); color: hsl(var(--t-hue) 62% 30%); }
.t-exact__go { margin-left: auto; font-weight: 700; color: inherit; white-space: nowrap; }
.t-exact__go:hover { text-decoration: underline; }
.t-icon--sm { width: 2rem; height: 2rem; font-size: .95rem; }

/* --- ПОИСК КАТАЛОГА: темы, метка и запрос в ОДНОМ поле (23.09.2026) --- */
.t-qbox {
    display: flex; align-items: stretch; gap: 0;
    background: var(--tc-white); border: 1.5px solid var(--tc-line);
    border-radius: var(--tc-radius); padding: .3rem;
    box-shadow: 0 6px 18px rgba(15, 23, 42, .05);
}
.t-qbox:focus-within { border-color: var(--tc-accent); }
.t-qbox__topics { display: flex; }
/* Кнопка тем — заметная, в цвете палитры: это вход в каталог, а не мелкая настройка. */
.t-qbox__btn {
    display: inline-flex; align-items: center; gap: .45rem; white-space: nowrap;
    border: 0; border-radius: calc(var(--tc-radius) - .25rem);
    background: var(--tc-accent-faint); color: var(--tc-accent-ink);
    font-weight: 700; font-size: .9rem; padding: .45rem .85rem;
}
.t-qbox__btn:hover, .t-qbox__btn[aria-expanded="true"] { background: var(--tc-accent-soft); }
.t-qbox__chev { font-size: .7rem; transition: transform .15s; }
.t-qbox__btn[aria-expanded="true"] .t-qbox__chev { transform: rotate(180deg); }
.t-qbox__field {
    flex: 1 1 auto; min-width: 0; display: flex; align-items: center; gap: .5rem;
    padding: 0 .4rem 0 .8rem; margin: 0; cursor: text;
}
.t-qbox__icon { color: var(--tc-faint); }
.t-qbox__input {
    flex: 1 1 6rem; min-width: 0; border: 0; outline: 0; background: transparent;
    font-size: 1rem; color: var(--tc-ink); padding: .4rem 0;
}
.t-qbox__input::placeholder { color: var(--tc-faint); }
/* Подсказки браузера (прошлые запросы): выбранная заливала поле голубым фоном автозаполнения
   Chrome — жалоба владельца 23.09.2026. Цвет этого фона перекрыть нельзя, можно только
   бесконечно отложить его появление переходом; текст возвращаем в цвет поля.
   Правило на все поля поиска сайта, включая строку в шапке. */
input[type="search"]:-webkit-autofill,
input[type="search"]:-webkit-autofill:hover,
input[type="search"]:-webkit-autofill:focus {
    -webkit-text-fill-color: var(--tc-ink);
    transition: background-color 600000s 0s, color 600000s 0s;
}
.t-qbox__go { flex: none; font-weight: 700; border-radius: calc(var(--tc-radius) - .25rem); padding-inline: 1.1rem; }

/* Метка в строке поиска — как флейр на реддите: цвет темы, крестик снимает. */
.t-qchip {
    display: inline-flex; align-items: center; gap: .35rem; flex: 0 1 auto; min-width: 0;
    border-radius: var(--tc-radius-pill); padding: .25rem .3rem .25rem .65rem;
    background: var(--tc-accent-soft); color: var(--tc-accent-ink);
    font-size: .82rem; font-weight: 700; white-space: nowrap;
}
/* Сжимается ТОЛЬКО подпись (многоточием); знак и крестик — нет. Голый текст внутри flex-метки
   был анонимным элементом с min-width по содержимому: сжать его было нельзя, и на телефоне
   сжимался крестик — вылезал за край метки на плейсхолдер (жалоба владельца 23.09.2026). */
.t-qchip > i, .t-qchip__x { flex: none; }
.t-qchip__label { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.t-qchip.t-hue { background: hsl(var(--t-hue) 85% 90%); color: hsl(var(--t-hue) 62% 30%); }
.t-qchip__x {
    display: inline-flex; align-items: center; justify-content: center;
    width: 1.3rem; height: 1.3rem; border-radius: 50%; color: inherit; font-size: .65rem;
}
.t-qchip__x:hover { background: rgba(15, 23, 42, .1); }

/* Список тем: сетка плиток со знаком темы и числом тестов. */
.t-topicmenu {
    width: min(40rem, calc(100vw - 2rem)); padding: 1rem;
    border-radius: var(--tc-radius); border: 1px solid var(--tc-line);
    box-shadow: 0 18px 40px rgba(15, 23, 42, .14);
}
.t-topicmenu__hint { font-size: .8rem; color: var(--tc-mut); margin: 0 0 .75rem; }
.t-topicmenu__grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(11.5rem, 1fr)); gap: .35rem; }
.t-topicmenu__item {
    display: flex; align-items: center; gap: .6rem; padding: .4rem .5rem;
    border-radius: var(--tc-radius-sm); color: var(--tc-ink); font-weight: 600; font-size: .88rem;
}
.t-topicmenu__item:hover, .t-topicmenu__item.is-on { background: var(--tc-page); color: var(--tc-ink); }
.t-topicmenu__item.is-on { box-shadow: inset 0 0 0 1.5px var(--tc-accent); }
.t-topicmenu__label { flex: 1 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.t-topicmenu__n { font-size: .75rem; color: var(--tc-faint); font-variant-numeric: tabular-nums; }
.t-topicmenu__tags { margin-top: .9rem; padding-top: .8rem; border-top: 1px solid var(--tc-line2); }

@media (max-width: 575.98px) {
    /* Одна строка и на телефоне: кнопка тем сжимается до знака, поле берёт остальное. */
    .t-qbox__btnlabel { display: none; }
    .t-qbox__btn { padding: .45rem .6rem; }
    .t-qbox__field { padding-left: .5rem; gap: .35rem; }
    .t-qbox__icon { display: none; }
    .t-qchip { max-width: 55%; }
    .t-qbox__go { display: none; }
    .t-topicmenu__grid { grid-template-columns: 1fr 1fr; }
}

/* Кольцевой счётчик: заполнение задаёт --tc-ring-pct, цвет — акцент палитры. */
.t-ring { position: relative; display: inline-flex; }
.t-ring svg { display: block; transform: rotate(-90deg); }
.t-ring__track { stroke: var(--tc-line); }
.t-ring__bar { stroke: var(--tc-accent); }
.t-ring__label {
    position: absolute; inset: 0;
    display: flex; flex-direction: column; align-items: center; justify-content: center;
    line-height: 1;
}
.t-ring__value { font-size: 1.6rem; font-weight: 800; letter-spacing: -.03em; color: var(--tc-ink); }
.t-ring--sm .t-ring__value { font-size: 1.1rem; }

/* Сетка номеров вопросов. */
.t-qgrid { display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: .35rem; }
.t-qgrid__cell {
    height: 1.9rem; border-radius: 8px;
    display: flex; align-items: center; justify-content: center;
    font-size: .78rem; font-weight: 700;
    background: var(--tc-page); color: var(--tc-faint);
    text-decoration: none;
}
.t-qgrid__cell--done { background: var(--tc-accent-soft); color: var(--tc-accent-ink); }
.t-qgrid__cell--cur { background: var(--tc-accent); color: var(--tc-on); }
/* Режим обучения: верно/неверно прямо в сетке. Блок второстепенный, поэтому заливка
   мягкая, а цвет держит текст — ядовитых плашек здесь быть не должно. */
.t-qgrid__cell--ok { background: var(--tc-good-soft); color: var(--tc-good); }
.t-qgrid__cell--bad { background: var(--tc-danger-soft); color: var(--tc-danger); }
/* Пока стоишь на только что отвеченном вопросе, его результат тоже должен быть виден:
   заливка остаётся статусной, а «ты здесь» показывает обводка акцентом. */
.t-qgrid__cell--cur.t-qgrid__cell--ok,
.t-qgrid__cell--cur.t-qgrid__cell--bad { outline: 2px solid var(--tc-accent); outline-offset: 1px; }
.t-qgrid__cell--cur.t-qgrid__cell--ok { background: var(--tc-good-soft); color: var(--tc-good); }
.t-qgrid__cell--cur.t-qgrid__cell--bad { background: var(--tc-danger-soft); color: var(--tc-danger); }
a.t-qgrid__cell:hover { outline: 1.5px solid currentColor; }

/* --- Плеер: варианты ответа --- */
.play-option, .list-group-item.play-option {
    border: 1.5px solid var(--tc-line);
    border-radius: var(--tc-radius-sm) !important;
    margin-bottom: .6rem;
    padding: 1rem 1.1rem;
    cursor: pointer;
    background: var(--tc-white);
    transition: border-color .12s ease, background .12s ease;
}
.play-option:hover { border-color: var(--tc-accent); }
.play-option:has(.form-check-input:checked) { border-color: var(--tc-accent); background: var(--tc-accent-faint); font-weight: 600; }
.play-option .form-check-input { margin-top: .15rem; width: 1.15rem; height: 1.15rem; }
.play-option img { max-height: 160px; width: auto; border-radius: var(--tc-radius-sm); }

/* --- Режим обучения: закрытый вопрос --- */
/* Курсор-палец на закрытых вариантах врал бы, что их ещё можно выбрать. */
.play-option:has(.form-check-input:disabled) { cursor: default; }
.play-option--ok, .play-option--ok:hover,
.play-option--ok:has(.form-check-input:checked) {
    border-color: var(--tc-good); background: var(--tc-good-faint); color: var(--tc-good); font-weight: 600;
}
.play-option--bad, .play-option--bad:hover,
.play-option--bad:has(.form-check-input:checked) {
    border-color: var(--tc-danger); background: var(--tc-danger-soft); color: var(--tc-danger); font-weight: 600;
}
.play-option--mute, .play-option--mute:hover { opacity: .55; }
/* Кружок/галочка выбранного варианта — статусным цветом, а не акцентом палитры:
   оранжевая точка внутри зелёной карточки читается как чужеродная. */
.play-option--ok .form-check-input:checked { background-color: var(--tc-good); border-color: var(--tc-good); }
.play-option--bad .form-check-input:checked { background-color: var(--tc-danger); border-color: var(--tc-danger); }
.form-control.is-good, .form-control.is-good:focus { border-color: var(--tc-good); color: var(--tc-good); font-weight: 600; }
.form-control.is-bad, .form-control.is-bad:focus { border-color: var(--tc-danger); color: var(--tc-danger); font-weight: 600; }

/* Вердикт: тихая карточка под вариантами и она же внутри модалки. */
.t-verdict { border-radius: var(--tc-radius-sm); padding: 1rem 1.1rem; margin-bottom: 1.25rem; }
.t-verdict--ok { background: var(--tc-good-faint); }
.t-verdict--bad { background: var(--tc-danger-soft); }
.t-verdict__head { font-weight: 700; margin-bottom: .5rem; }
.t-verdict--ok .t-verdict__head { color: var(--tc-good); margin-bottom: 0; }
.t-verdict--bad .t-verdict__head { color: var(--tc-danger); }
/* Правильный ответ внутри вердикта обязан оставаться зелёным: без этих двух селекторов
   общее правило для dd перекрашивало его обратно в текст — проверено скриншотом. */
.t-verdict dd { color: var(--tc-body); margin-bottom: .4rem; }
.t-verdict dt { margin-bottom: .4rem; }
/* На телефоне подпись и значение идут в столбик — без этого отступа «Explanation»
   зрительно прилипает к следующей подписи, а не к своему тексту. */
@media (max-width: 575.98px) {
    .t-verdict dt { margin-top: .5rem; margin-bottom: .1rem; }
}
.t-verdict dd.t-good { color: var(--tc-good); }
.t-verdict dd.t-bad { color: var(--tc-danger); }

/* Кнопка «дальше» подмигивает зелёным, когда ответ верный. */
.btn.t-wink { background: var(--tc-good); border-color: var(--tc-good); animation: t-wink 1s ease-in-out infinite; }
.btn.t-wink:hover, .btn.t-wink:focus { background: var(--tc-good); border-color: var(--tc-good); }
@keyframes t-wink {
    0%, 100% { box-shadow: 0 0 0 0 rgba(47, 122, 79, .45); }
    50%      { box-shadow: 0 0 0 .5rem rgba(47, 122, 79, 0); }
}
@media (prefers-reduced-motion: reduce) {
    .btn.t-wink { animation: none; }
}
.play-media img { max-height: 320px; width: auto; border-radius: var(--tc-radius); }

/* --- Выбор палитры в кабинете --- */
.t-palette { display: grid; grid-template-columns: repeat(auto-fill, minmax(9.5rem, 1fr)); gap: .75rem; }
.t-palette__item {
    border: 2px solid var(--tc-line); border-radius: 13px;
    background: var(--tc-white); padding: .8rem; width: 100%;
    text-align: left; cursor: pointer;
}
.t-palette__item[aria-pressed="true"] { border-color: var(--tc-accent); background: var(--tc-accent-faint); }
.t-palette__swatches { display: flex; gap: .35rem; margin-bottom: .6rem; }
.t-palette__sw { width: 1.35rem; height: 1.35rem; border-radius: 7px; display: block; }
.t-palette__name { font-size: .85rem; font-weight: 600; color: var(--tc-body); }
.t-palette__item[aria-pressed="true"] .t-palette__name { font-weight: 700; color: var(--tc-accent-ink); }

/* --- Конструктор (разметку рисует editor.js, здесь только вид) --- */
.q-card { transition: box-shadow .12s ease, opacity .12s ease; border-radius: var(--tc-radius); }
.q-card.is-dragging { opacity: .45; }
.q-card.is-drop-target { box-shadow: 0 0 0 2px var(--tc-accent); }
.q-card.has-errors { border-color: var(--bs-danger); }
.q-handle { cursor: grab; touch-action: none; color: var(--tc-faint); }
.q-handle:active { cursor: grabbing; }
.q-collapsed .q-body { display: none; }
.q-summary { display: none; }
.q-collapsed .q-summary { display: block; }
.answer-thumb { max-height: 64px; width: auto; border-radius: .35rem; }
.question-thumb { max-height: 200px; width: auto; border-radius: var(--tc-radius-sm); }
.q-num { min-width: 2.25rem; }
.editor-bar {
    position: sticky; bottom: 0; z-index: 5;
    background: var(--tc-white);
    border-top: 1px solid var(--tc-line);
}

/* --- Рейтинг звёздами --- */
.star-input { display: inline-flex; flex-direction: row-reverse; gap: .15rem; }
.star-input input { position: absolute; opacity: 0; width: 0; height: 0; }
.star-input label { cursor: pointer; font-size: 1.5rem; line-height: 1; color: var(--tc-line); }
.star-input label:hover,
.star-input label:hover ~ label,
.star-input input:checked ~ label { color: var(--tc-gold); }
.t-stars { color: var(--tc-gold); }

/* Длинный JSON не должен растягивать страницу по горизонтали. */
pre.json-block {
    max-height: 22rem; overflow: auto;
    background: var(--tc-ink); color: #e6edf3;
    padding: 1rem; border-radius: var(--tc-radius);
    font-size: .8rem; line-height: 1.6;
}
.table-responsive { -webkit-overflow-scrolling: touch; }

/* --- Телефон: главное действие уезжает вниз, под большой палец --- */
.t-actionbar {
    position: sticky; bottom: 0; z-index: 10;
    background: var(--tc-white);
    border-top: 1px solid var(--tc-line);
    padding: .75rem 1rem calc(.75rem + env(safe-area-inset-bottom));
    margin: 1.5rem -.75rem 0;
}
@media (min-width: 768px) {
    .t-actionbar { position: static; background: transparent; border-top: 0; padding: 0; margin: 1.5rem 0 0; }
}
@media (max-width: 575.98px) {
    .display-4, .display-5, .display-6 { font-size: calc(1.6rem + 1.4vw); }
    .t-ring--hero svg { width: 96px; height: 96px; }
}

/* --- Статистика теста: правая колонка страницы /tests/<id> (22.09.2026) ---
   Графики рисуются на CSS и SVG, без библиотек: значений в колонке десяток,
   а чужой скрипт перед отрисовкой страницы — это чужой домен и лишний запрос.

   ЦВЕТ ЗДЕСЬ СМЫСЛОВОЙ, а не палитры (переделано 22.09.2026 по заказу владельца:
   «нужно сочные, красно зелененькие»). Результат — это шкала «справился / средне /
   завалил», и она обязана читаться одинаково на любой палитре: на янтарной обе
   крайности покрасились бы одним цветом. Токены --tc-ok/--tc-mid/--tc-bad заведены
   рядом с такой же смысловой парой «верно/неверно» режима обучения. Акцент палитры
   остаётся там, где смысла нет: состав теста — это «сколько работы», а не оценка. */

/* Этажи колонки разделяет линия, но первый этаж без неё: линия под заголовком
   карточки читалась бы как её граница. */
.t-stat + .t-stat { margin-top: 1.1rem; padding-top: 1.1rem; border-top: 1px solid var(--tc-line2); }
.t-stat__h {
    font-size: .72rem; font-weight: 700; letter-spacing: .04em; text-transform: uppercase;
    color: var(--tc-mut); margin: 0 0 .7rem;
}
.t-stat__note { font-size: .74rem; color: var(--tc-faint); margin: .6rem 0 0; line-height: 1.45; }
.t-you { color: var(--tc-ink); font-weight: 600; }

/* «Вы это уже проходили» — мягкая плашка, а не тревога: это напоминание. */
.t-seen {
    display: flex; align-items: flex-start; gap: .45rem;
    background: var(--tc-accent-faint); color: var(--tc-accent-ink);
    border-radius: var(--tc-radius-sm); padding: .55rem .7rem;
    font-size: .78rem; line-height: 1.4; margin: 0 0 1rem;
}
.t-seen i { flex: none; margin-top: .1rem; }

/* --- ТАБЛО (заказ владельца: «может в виде табло, или часов») ---
   Значение стоит НАД подписью, а не в другом конце строки: в прежней строке
   «Typical time …… 14 min» между подписью и числом зияла половина колонки. */
.t-scores { display: grid; grid-template-columns: 1fr 1fr; gap: .6rem; }
.t-scores--one { grid-template-columns: 1fr; }
.t-score {
    /* Табло без оценки (время, число попыток) — тёплое, но не смысловое: рядом с
       красным или зелёным соседом серая плашка читалась бы как выключенная. */
    background: var(--tc-accent-faint); border-radius: var(--tc-radius-sm);
    padding: .7rem .8rem; min-width: 0;
    /* Объём табло — нижняя грань тенью без размытия: плашка выглядит нажимаемой
       клавишей, а не наклейкой. Тот же приём у клеток карты трудности ниже. */
    box-shadow: 0 3px 0 rgba(15, 23, 42, .08);
}
.t-score__val {
    display: block; font-size: 1.65rem; line-height: 1.1; font-weight: 800;
    color: var(--tc-ink); letter-spacing: -.02em;
    /* Цифры табло не должны плясать по ширине, пока значение меняется. */
    font-variant-numeric: tabular-nums;
}
/* Единица меньше числа: крупным набрано то, что читают, «min» и так понятно. */
.t-score__unit { font-size: .78rem; font-weight: 700; color: var(--tc-mut); margin-left: .12rem; }
.t-score__cap {
    display: flex; align-items: center; gap: .3rem; margin-top: .15rem;
    font-size: .72rem; color: var(--tc-mut); line-height: 1.25;
}
.t-score__cap i { font-size: .8rem; }
/* Табло с оценкой красится смыслом: 88 % — зелёное, 41 % — красное. */
.t-score--good { background: var(--tc-ok-soft); box-shadow: 0 3px 0 rgba(21, 128, 61, .22); }
.t-score--good .t-score__val { color: #15803d; }
.t-score--mid { background: var(--tc-mid-soft); box-shadow: 0 3px 0 rgba(180, 83, 9, .22); }
.t-score--mid .t-score__val { color: #b45309; }
.t-score--low { background: var(--tc-bad-soft); box-shadow: 0 3px 0 rgba(190, 18, 60, .22); }
.t-score--low .t-score__val { color: #be123c; }

/* --- ТРИ ГРУППЫ ПОЛОСАМИ (23.09.2026, заказ владельца: «переделай диаграмму на
   такой вот бар») ---
   Строка «● 11 aced it (85%+) …… 24 %», под ней дорожка с заливкой. До этого здесь
   стоял объёмный пирог: наклон искажал площадь долек, и числа всё равно жили в
   легенде рядом. У полосы число и длина стоят вместе — дублировать нечего. */
.t-bands { display: flex; flex-direction: column; gap: .75rem; }
.t-band__head {
    display: flex; align-items: center; gap: .4rem;
    font-size: .78rem; color: var(--tc-mut); margin-bottom: .3rem;
}
.t-band__n { color: var(--tc-ink); font-variant-numeric: tabular-nums; }
.t-band__label { min-width: 0; }
/* Процент прижат вправо: он читается столбиком по всем трём строкам. */
.t-band__pct { margin-left: auto; color: var(--tc-mut); font-variant-numeric: tabular-nums; }
.t-band__track {
    height: 16px; border-radius: var(--tc-radius-pill);
    background: var(--tc-line2); overflow: hidden;
}
/* Блик вдоль заливки — тот же, что у полосы состава ниже: одна рука рисовала. */
.t-band__fill {
    display: block; height: 100%; border-radius: var(--tc-radius-pill);
    background-image: linear-gradient(180deg, rgba(255, 255, 255, .3), rgba(0, 0, 0, .1));
}
.t-band--good .t-band__fill { background-color: var(--tc-ok); }
.t-band--mid  .t-band__fill { background-color: var(--tc-mid); }
.t-band--low  .t-band__fill { background-color: var(--tc-bad); }
/* Своя группа — жирной подписью, а не отдельной строкой: строка читалась бы как
   ещё одна доля. */
.t-band--me .t-band__label { color: var(--tc-ink); font-weight: 700; }

/* Легенда полосы состава. */
.t-mix__legend { display: flex; flex-wrap: wrap; gap: .3rem .9rem; margin-top: .7rem; }
.t-mix__item {
    display: inline-flex; align-items: center; gap: .4rem;
    font-size: .78rem; color: var(--tc-mut);
}
.t-mix__item strong { color: var(--tc-ink); min-width: 1.1rem; }

/* --- ОЦЕНКА ВРЕМЕНИ одной строкой «⏱ ~5 min» (23.09.2026, заказ владельца: «иконка
   таймера побольше, затем знак примерно и цифра») --- Подпись ушла в title: строка
   под плашкой и так говорит, что это прикидка. */
.t-est {
    display: inline-flex; align-items: center; gap: .55rem;
    margin-top: .9rem; padding: .5rem .85rem;
    background: var(--tc-accent-faint); border-radius: var(--tc-radius-sm);
    box-shadow: 0 3px 0 rgba(15, 23, 42, .08);
    cursor: default;
}
.t-est > .bi { font-size: 1.6rem; line-height: 1; color: var(--tc-accent-ink); }
.t-est__val {
    font-size: 1.5rem; line-height: 1.1; font-weight: 800; color: var(--tc-ink);
    letter-spacing: -.02em; font-variant-numeric: tabular-nums;
}

/* Кромка у кружка легенды — не украшение: самая светлая ступень на белой карточке
   иначе почти не видна, и строка легенды читается как строка без знака. */
.t-dot {
    width: .6rem; height: .6rem; border-radius: 50%; display: inline-block; flex: none;
    box-shadow: inset 0 0 0 1px rgba(15, 23, 42, .12);
}
.t-dot--good { background: var(--tc-ok); }
.t-dot--mid { background: var(--tc-mid); }
.t-dot--low { background: var(--tc-bad); }

/* --- Столбики СВОИХ попыток: ряд по времени, кольцом его не покажешь --- */
.t-bars { display: flex; align-items: flex-end; gap: 4px; height: 62px; }
.t-bars__bar {
    flex: 1 1 0; min-width: 0; border-radius: 4px 4px 2px 2px;
    /* Блик сверху и тень снизу — тот же объём, что у пирога: колонка, а не полоска. */
    background-image: linear-gradient(180deg, rgba(255, 255, 255, .35), rgba(0, 0, 0, .12));
    box-shadow: 0 2px 0 rgba(15, 23, 42, .18);
}
.t-bars__bar--good { background: var(--tc-ok); }
.t-bars__bar--mid { background: var(--tc-mid); }
.t-bars__bar--low { background: var(--tc-bad); }
/* Свежая попытка — та, ради которой смотрят, но приглушать ради неё соседние
   нельзя: блёклый столбик читается как «неудачная попытка», а не как «прошлая».
   Поэтому цвет у всех полный, а последняя помечена кромкой. */
.t-bars__bar--last { box-shadow: 0 2px 0 rgba(15, 23, 42, .18), 0 0 0 2px var(--tc-ink); }

/* --- Полоса состава теста ---
   Здесь цвет НЕ смысловой: вопрос с вводом руками не «плохой», он дороже по работе.
   Поэтому ступени одной акцентной краски, а не зелёный с красным. */
.t-mix {
    display: flex; height: 16px; border-radius: var(--tc-radius-pill);
    overflow: hidden; background: var(--tc-line2);
    box-shadow: 0 2px 0 rgba(15, 23, 42, .1);
}
/* Блик вдоль полосы делает из неё трубку, а не прямоугольник. */
.t-mix__part { background-image: linear-gradient(180deg, rgba(255, 255, 255, .38), rgba(0, 0, 0, .14)); }
.t-mix__part { display: block; height: 100%; }
.t-tone--1 { background: var(--tc-accent-soft); }
.t-tone--2 { background: var(--tc-accent); }
/* Самая тёмная ступень — accent-ink, а не accent-deep: deep почти чёрный и рядом
   с цветным кольцом читался как дыра в полосе. */
.t-tone--3 { background: var(--tc-accent-ink); }

/* --- Карта трудности вопросов ---
   Число колонок ставит art_heat по длине теста (иначе последний ряд остаётся с одной
   клеткой) — здесь только запасное значение. Шкала та же смысловая: зелёное берут все,
   красное валят почти все. Ступеней пять, а не плавный градиент: оттенок между «71 %»
   и «74 %» глазом всё равно не различить, а ступень читается сразу. */
.t-heat { display: grid; grid-template-columns: repeat(10, minmax(0, 1fr)); gap: 3px; }
.t-heat__cell {
    height: 1.7rem;
    display: flex; align-items: center; justify-content: center;
    border-radius: 4px; font-size: .58rem; font-weight: 700;
    background: var(--tc-page); color: var(--tc-faint);
    box-shadow: 0 2px 0 rgba(15, 23, 42, .12);
}
.t-heat__cell--h0 { background: var(--tc-ok); color: #fff; }
.t-heat__cell--h1 { background: var(--tc-ok-soft); color: #15803d; }
.t-heat__cell--h2 { background: var(--tc-mid-soft); color: #b45309; }
.t-heat__cell--h3 { background: var(--tc-mid); color: #fff; }
.t-heat__cell--h4 { background: var(--tc-bad); color: #fff; }

/* --- ПУБЛИЧНЫЙ ПРОФИЛЬ (23.09.2026) --- */

/* Картинка вместо буквы: тот же кружок, снимок режется по кругу. Кромка — чтобы светлое
   фото не растворялось в белой шапке. */
.t-avatar--img { object-fit: cover; padding: 0; box-shadow: inset 0 0 0 1px rgba(15, 23, 42, .08); border: 1px solid var(--tc-line); }
.t-avatar--md { width: 3.6rem; height: 3.6rem; font-size: 1.4rem; }

.t-profile__bio { color: var(--tc-body); max-width: 42rem; margin: -.2rem 0 .75rem; line-height: 1.5; overflow-wrap: anywhere; }
.t-profile__top { font-size: .85rem; margin: .75rem 0 0; display: flex; flex-wrap: wrap; align-items: center; gap: .35rem; }
.t-profile__top > .bi { color: var(--tc-bad); }
.t-profile__top a { font-weight: 600; color: var(--tc-ink); }

/* Шкалы «по темам»: подпись тёмная — это имя темы, а не доля людей, как у трёх полос. */
.t-band__label--ink { color: var(--tc-ink); font-weight: 600; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.t-band__note { color: var(--tc-faint); white-space: nowrap; }

/* Пройденные тесты — строками, а не карточками: здесь сравнивают результаты, и столбец
   процентов справа должен читаться сверху вниз одним взглядом. */
.t-taken__row {
    display: flex; align-items: center; gap: .9rem;
    padding: .8rem 1.5rem; border-top: 1px solid var(--tc-line2);
}
.t-taken__body { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; }
.t-taken__title { color: var(--tc-ink); font-weight: 600; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.t-taken__meta { font-size: .76rem; color: var(--tc-faint); }
.t-taken__bars { flex: none; width: 6.5rem; }
/* Столбик одной ширины во всех строках: растянутые на всю ячейку, две попытки выглядели
   вдвое «весомее» четырёх. Ряд прижат вправо — к числу, которое он объясняет. */
.t-taken__bars .t-bars { height: 30px; gap: 3px; justify-content: flex-end; }
.t-taken__bars .t-bars__bar { flex: 0 0 .7rem; }
.t-gain { color: #15803d; font-weight: 700; white-space: nowrap; }

/* Лучший балл теста — плашка смыслового цвета, ширина одна у всех: столбец ровный. */
.t-pct {
    flex: none; min-width: 3.6rem; text-align: center;
    font-weight: 800; font-variant-numeric: tabular-nums;
    border-radius: var(--tc-radius-pill); padding: .25rem .6rem; font-size: .9rem;
}
.t-pct--good { background: var(--tc-ok-soft); color: #15803d; }
.t-pct--mid  { background: var(--tc-mid-soft); color: #b45309; }
.t-pct--low  { background: var(--tc-bad-soft); color: #be123c; }

/* Отзывы в профиле: строками, как пройденные, — здесь листают, а не рассматривают. */
.t-rv { display: flex; align-items: flex-start; gap: .9rem; padding: .9rem 1.5rem; }
.t-rv + .t-rv { border-top: 1px solid var(--tc-line2); }
.t-rv__body { flex: 1 1 auto; min-width: 0; }
.t-rv__title { color: var(--tc-ink); font-weight: 600; }

/* Правка своего отзыва: тихая ссылка «✎ Edit», раскрывается на месте. */
.t-rvedit { margin-top: .4rem; }
.t-rvedit__toggle {
    display: inline-flex; align-items: center; gap: .3rem; cursor: pointer;
    font-size: .76rem; font-weight: 600; color: var(--tc-mut); list-style: none;
}
.t-rvedit__toggle::-webkit-details-marker { display: none; }
.t-rvedit__toggle:hover, .t-rvedit[open] .t-rvedit__toggle { color: var(--tc-accent-ink); }
.t-rvedit__form {
    margin-top: .5rem; padding: .75rem; max-width: 34rem;
    border: 1px solid var(--tc-line); border-radius: var(--tc-radius-sm); background: var(--tc-page);
}
.t-rvedit__form .star-input { display: inline-flex; }

@media (max-width: 575.98px) {
    .t-rv { padding: .8rem 1rem; gap: .65rem; }
    .t-taken__row { padding: .75rem 1rem; gap: .65rem; }
    .t-taken__bars { display: none; }
    .t-profile .btn { align-self: flex-start; }
}
