/*
 * Каркас кабинета. Один на все четыре роли — различается только меню.
 *
 * Четыре размера, и на каждом меню ведёт себя по-своему:
 *
 *   до 640      телефон   меню внизу, под большой палец
 *   640–1119    планшет   меню лентой сверху, прокручивается вбок
 *   1120–1799   ноутбук   меню слева, привычный кабинет
 *   от 1800     телевизор то же, но крупнее: смотрят с трёх метров
 *
 * Все размеры берутся из переменных, поэтому «сделать крупнее на телевизоре»
 * — это правка блока переменных, а не пересборка раскладки.
 */

.app {
    display: grid;
    grid-template-columns: var(--sidebar-w) minmax(0, 1fr);
    min-height: 100vh;
    min-height: 100dvh;
}

/* ---------- Сайдбар ---------- */

.sidebar {
    background: var(--bg-card);
    border-right: 1px solid var(--border);
    padding: var(--space-4) var(--space-3);
    display: flex;
    flex-direction: column;
    gap: var(--space-4);
    position: sticky;
    top: 0;
    height: 100vh;
    height: 100dvh;
    overflow-y: auto;
    z-index: var(--z-sidebar);
}

.logo {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    padding: 0 var(--space-2) var(--space-4);
    border-bottom: 1px solid var(--border);
    /* Логотип стал ссылкой домой — но выглядеть должен логотипом,
       а не синей строкой с подчёркиванием. */
    color: var(--text-primary);
}
.logo:hover { text-decoration: none; }
.logo:hover .logo__name { color: var(--accent); }

.logo__mark {
    width: 36px;
    height: 36px;
    border-radius: var(--radius-sm);
    background: var(--accent-gradient);
    color: var(--accent-on-fill);
    display: grid;
    place-items: center;
    font-weight: var(--weight-bold);
    flex: none;
}

.logo__name { font-weight: var(--weight-semibold); line-height: 1.2; }
.logo__org { display: block; font-size: var(--text-xs); color: var(--text-muted); font-weight: var(--weight-normal); }

.nav { display: flex; flex-direction: column; gap: 2px; }

.nav__group {
    font-size: var(--text-xs);
    text-transform: uppercase;
    letter-spacing: .06em;
    color: var(--text-muted);
    font-weight: var(--weight-semibold);
    padding: var(--space-4) var(--space-2) var(--space-1);
}

.nav__link {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    min-height: var(--tap-target);
    padding: 0 var(--space-3);
    border-radius: var(--radius-sm);
    color: var(--text-secondary);
    font-size: var(--text-sm);
    font-weight: var(--weight-medium);
    transition: background var(--transition), color var(--transition);
}

.nav__link:hover { background: var(--bg-subtle); color: var(--text-primary); text-decoration: none; }
.nav__link.is-active { background: var(--accent-soft); color: var(--accent); font-weight: var(--weight-semibold); }

.nav__icon { flex: none; display: grid; place-items: center; }
.nav__label { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }

/* Короткая подпись включается только на телефоне: «Задания в классе»
   в нижнее меню не помещается, а обрезанное слово хуже короткого. */
.nav__label--short { display: none; }

.nav__badge {
    margin-left: auto;
    background: var(--accent-fill);
    color: var(--accent-on-fill);
    font-size: var(--text-xs);
    font-weight: var(--weight-bold);
    padding: 1px var(--space-2);
    border-radius: var(--radius-pill);
    flex: none;
}

/* ---------- Основная область ---------- */

.main { min-width: 0; display: flex; flex-direction: column; }

.topbar {
    display: flex;
    align-items: center;
    gap: var(--space-4);
    padding: var(--space-3) var(--space-6);
    background: var(--bg-card);
    border-bottom: 1px solid var(--border);
    position: sticky;
    top: 0;
    z-index: var(--z-header);
}

.topbar__brand { display: none; color: var(--text-primary); align-items: center; gap: var(--space-2); font-weight: var(--weight-semibold); }
.topbar__spacer { margin-left: auto; }

/* ---------- Выбор языка и темы ----------
   Раньше здесь стояли шесть кнопок в два ряда: три языка и три темы.
   На планшете они съедали половину шапки, а имя человека при этом
   обрезалось. Стало два элемента: список языков и одна кнопка темы. */
.topbar__locale { display: flex; }

.locale-pick {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding-left: var(--space-2);
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--bg-page);
    min-height: var(--tap-target);
}
.locale-pick__icon { display: inline-flex; color: var(--text-muted); }
.locale-pick__select {
    /* Своя рамка не нужна — она у обёртки, иначе рамок будет две. */
    border: 0;
    background: transparent;
    color: var(--text-primary);
    font: inherit;
    font-weight: var(--weight-semibold);
    padding: 0 var(--space-2) 0 0;
    min-height: var(--tap-target);
}

.topbar__icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: var(--tap-target);
    height: var(--tap-target);
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--bg-page);
    color: var(--text-secondary);
}
.topbar__icon:hover { color: var(--text-primary); background: var(--bg-subtle); }

/* Профиль в шапке — ссылка: язык, тема и пароль лежат за ней, и
   искать их в меню человек не должен. */
.who {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    line-height: 1.3;
    padding: var(--space-1) var(--space-2);
    border-radius: var(--radius-sm);
    color: var(--text-primary);
    min-height: var(--tap-target);
    min-width: 0;
}
.who__avatar {
    display: none;
    align-items: center;
    justify-content: center;
    width: 34px;
    height: 34px;
    flex-shrink: 0;
    border-radius: 50%;
    background: var(--accent-soft);
    color: var(--accent);
}
.who__text {
    display: flex;
    flex-direction: column;
    align-items: flex-end;
    min-width: 0;
}

.who:hover { background: var(--bg-subtle); text-decoration: none; }
.who__name { display: block; font-size: var(--text-sm); font-weight: var(--weight-semibold); }
.who__role { display: block; font-size: var(--text-xs); color: var(--text-muted); text-transform: uppercase; letter-spacing: .04em; }

.page {
    padding: var(--space-6);
    flex: 1;
    width: 100%;
    max-width: var(--page-max);
    margin-inline: auto;

    /* Верхние блоки страницы разделены.

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

       Место одно: сама страница. Тогда новый экран получает ритм
       даром, а забыть его нельзя. */
    display: flex;
    flex-direction: column;
    gap: var(--space-5);
}

/* Точность .page.page--play, а не .page--play: отступы страницы
   переопределяются в медиазапросах ниже, и правило той же точности,
   стоящее выше, там молча проигрывает. Экран игры на планшете получал
   16 точек отступа со всех сторон — как раз на планшете, где места
   меньше всего. */
/* Страница игры: плеер занимает всё, что осталось от окна.

   Ограничение ширины снято намеренно. `--page-max` держит строку
   читаемой длины — это про текст. Игру же смотрят с задней парты и с
   проектора, и обрезать её до 1440 значит выбросить треть панели.

   Отступов нет по той же причине: рамка вокруг космоса ничего не даёт,
   а высоту забирает. */
.page.page--play {
    padding: 0;
    max-width: none;
    /* Строкой, а не столбцом: плеер здесь один и занимает всё.
       И без зазора — рамки вокруг космоса быть не должно. */
    display: flex;
    flex-direction: row;
    gap: 0;
    min-height: 0;
}
.page.page--play > .tr-player {
    flex: 1;
    min-width: 0;
    border-radius: 0;
    /* Расти — можно, сжиматься — нет.

       Игре нужно около 640: шапка, поле сцены на 340 и подвал со
       счётчиком. Сожмём ниже — поле обрежется, а Космик, который
       всплывает от нижнего края, всплывёт за него.

       Вверх наоборот: на планшете 768×1024 от окна остаётся 880, и
       занять их полезно — игру смотрят с задней парты. */
    min-height: 640px;
    display: flex;
    flex-direction: column;
}
.page.page--play .tr-screen,
.page.page--play .tr-shell {
    flex: 1;
    min-height: 0;
}

/* Поле игры по центру свободной высоты.

   Когда плеер занимал ровно 640, разницы не было. Теперь на планшете
   ему достаётся 760, и без этого сцена липла к верху, а под ней
   оставалась пустая треть экрана — ребёнок смотрел вниз на пустоту.

   Центрируется сцена, а не всё содержимое: текст задания остаётся
   сверху, где его ищут. */
.page.page--play .tr-shell__content {
    display: flex;
    flex-direction: column;
}
.page.page--play .tr-stage {
    flex: 1;
    display: flex;
    flex-direction: column;
    justify-content: center;
}
.page__head { margin-bottom: 0; }
.page__title { margin-bottom: var(--space-1); }
.page__lede { color: var(--text-secondary); font-size: var(--text-sm); max-width: 74ch; margin: 0; }

.grid { display: grid; gap: var(--space-4); }
.grid--2 { grid-template-columns: repeat(auto-fit, minmax(min(100%, 300px), 1fr)); }
.grid--3 { grid-template-columns: repeat(auto-fill, minmax(min(100%, 250px), 1fr)); }
/*
 * `auto-fit`, а не `auto-fill`: этой сеткой выкладываются ряды чисел
 * из трёх-четырёх карточек, и лишняя пустая колонка в конце ряда
 * выглядит как не загрузившийся блок. `auto-fill` оставляет пустые
 * дорожки, `auto-fit` их схлопывает.
 */
.grid--4 { grid-template-columns: repeat(auto-fit, minmax(min(100%, 190px), 1fr)); }

.stack { display: flex; flex-direction: column; gap: var(--space-4); }
.row { display: flex; align-items: center; gap: var(--space-3); flex-wrap: wrap; }

/* =========================================================
   ПЛАНШЕТ: меню лентой сверху
   ========================================================= */

@media (max-width: 1119px) {
    /*
     * Строки заданы явно: лента меню по содержимому, работа — остальное.
     *
     * Без этого сетка распределяла свободную высоту поровну между двумя
     * строками (`align-content` у грида по умолчанию тянет), и лента
     * меню высотой в 44 точки занимала 267 — четверть экрана планшета
     * под одну строку кнопок. Заметить это глазами трудно: лента
     * тёмная, и пустота под ней выглядит как отступ.
     */
    .app {
        grid-template-columns: 1fr;
        grid-template-rows: auto minmax(0, 1fr);
    }

    .sidebar {
        position: sticky;
        top: 0;
        height: auto;
        flex-direction: row;
        align-items: center;
        gap: var(--space-2);
        overflow-x: auto;
        overflow-y: hidden;
        border-right: 0;
        border-bottom: 1px solid var(--border);
        padding: var(--space-2) var(--space-3);
        scrollbar-width: thin;
    }

    .logo { border-bottom: 0; padding: 0 var(--space-2) 0 0; flex: none; }
    .nav { flex-direction: row; gap: var(--space-1); }
    .nav__group { display: none; }

    /* Пункт не сжимается: лента прокручивается вбок целиком.
       Иначе «Классы и ученики» превращается в «Классы и учени…», и
       разделы становится невозможно различить — а обрезанное название
       хуже прокрутки. */
    .nav__link { padding: 0 var(--space-3); flex: none; }
    .nav__label { overflow: visible; text-overflow: clip; }
    .topbar { padding: var(--space-3) var(--space-4); }
    .page { padding: var(--space-4); }
}

/* =========================================================
   ТЕЛЕФОН: меню внизу, под большой палец
   ========================================================= */

@media (max-width: 639px) {
    .app { padding-bottom: var(--bottom-nav-h); }

    .sidebar {
        position: fixed;
        inset: auto 0 0 0;
        top: auto;
        border-bottom: 0;
        border-top: 1px solid var(--border);
        padding: var(--space-1) var(--space-1) env(safe-area-inset-bottom, 0);
        justify-content: space-around;
        box-shadow: var(--shadow-lg);
    }

    .logo { display: none; }
    .topbar__brand { display: flex; }

    .nav { flex: 1; justify-content: space-around; gap: 0; }

    .nav__link {
        flex-direction: column;
        gap: 2px;
        justify-content: center;
        min-width: 0;
        flex: 1;
        padding: var(--space-1) 2px;
        font-size: 10px;
        border-radius: var(--radius-sm);
    }

    .nav__label { display: none; }
    .nav__label--short { display: block; font-size: 10px; max-width: 100%; }

    .nav__badge {
        position: absolute;
        margin: 0;
        transform: translate(14px, -12px);
        font-size: 9px;
        padding: 0 5px;
    }

    .nav__link { position: relative; }

    /* Профиль на телефоне — кружок со значком.

       Имя обрезалось на середине («Сатпаева Айг…»), а обрезанное имя
       не говорит ничего и выглядит поломкой. Кружок — привычный вход
       в свой профиль; имя целиком лежит за ним, на самом экране. */
    .who__text { display: none; }
    .who__avatar { display: inline-flex; }
    .who { padding: 0; }

    .page { padding: var(--space-3); }
    .topbar { padding: var(--space-2) var(--space-3); gap: var(--space-2); }

    /* Логотип и профиль не сжимаются, сжимается и прокручивается середина. */
    .topbar__brand,
    .who { flex: none; }

    /* Язык остаётся: он теперь занимает одну ячейку, а не три кнопки,
       и на планшете в классе его меняют чаще, чем кажется. */
    .locale-pick { padding-left: var(--space-1); }
}

/* =========================================================
   ТЕЛЕВИЗОР И БОЛЬШИЕ ЭКРАНЫ: смотрят издалека
   ========================================================= */

@media (min-width: 1800px) {
    .topbar { padding: var(--space-4) var(--space-8); }
    .page { padding: var(--space-8); }
    .sidebar { padding: var(--space-5) var(--space-4); }
    .logo__mark { width: 44px; height: 44px; }
    .grid--3 { grid-template-columns: repeat(auto-fill, minmax(min(100%, 300px), 1fr)); }
    .grid--4 { grid-template-columns: repeat(auto-fit, minmax(min(100%, 230px), 1fr)); }
}

/* Загруженный логотип организации: на месте фирменного квадрата. */
.logo__img {
    width: 36px;
    height: 36px;
    border-radius: var(--radius-sm);
    object-fit: contain;
    flex: none;
    background: var(--bg-subtle);
}

@media (min-width: 1800px) {
    .logo__img { width: 44px; height: 44px; }
}

/* =========================================================
   КАБИНЕТ РЕБЁНКА — КОСМОС
   =========================================================
   Договорённость: у ребёнка космос, у педагога и владельца спокойный
   рабочий инструмент. Причина не в украшении: ребёнок приходит играть,
   и кабинет не должен выглядеть панелью администратора, из которой
   игра случайно запускается. Педагог наоборот работает — ему нужен
   инструмент, а не мультик.

   Космос тут сдержанный: подсветка сверху и звёзды, но не сцена из
   игры. Полноценный космос начинается в плеере, и переход туда должен
   ощущаться как вход, а не как продолжение того же экрана. */

.app[data-role="student"] .main {
    background:
        radial-gradient(ellipse 120% 60% at 50% -10%, var(--kid-glow) 0%, transparent 60%),
        var(--bg-page);
}

/* Звёзды рисуются фоном, а не элементами: тридцать точек в разметке —
   это тридцать узлов на каждой странице ради украшения. Тут их нет
   вовсе, и на планшете это заметно. */
.app[data-role="student"] .main::before {
    content: '';
    position: fixed;
    inset: 0;
    pointer-events: none;
    z-index: 0;
    background-image:
        radial-gradient(1.5px 1.5px at 12% 18%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1px 1px at 28% 42%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1.5px 1.5px at 47% 12%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1px 1px at 63% 55%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(2px 2px at 78% 24%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1px 1px at 88% 68%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1.5px 1.5px at 35% 78%, var(--kid-star) 50%, transparent 50%),
        radial-gradient(1px 1px at 8% 62%, var(--kid-star) 50%, transparent 50%);
}

/* Содержимое поверх звёзд. Без этого карточки перекрываются фоном и
   выглядят приглушёнными. */
.app[data-role="student"] .page { position: relative; z-index: 1; }

/* Ребёнку крупнее: он читает с планшета на коленях, а не с монитора,
   и половина наших детей — первоклассники. */
/* Детский кабинет крупнее на ступень — и это объявлено один раз, а не
   правится покомпонентно. Половина наших учеников первоклассники;
   компонент, который завтра захочет ту же разницу, берёт роль шкалы и
   получает её даром. */
.app[data-role="student"] {
    --size-page-title: var(--text-2xl);
    --size-stat-value: var(--text-2xl);
}
.app[data-role="student"] .card { border-radius: var(--radius-lg); }
