/* ============================================================
   static/css/skin.css   — НОВЫЙ ФАЙЛ (Этап 3, подытог «стекло везде»)
   ------------------------------------------------------------
   НАДЕВАЕТ СТЕКЛО ИЗ glass.css НА УЖЕ СУЩЕСТВУЮЩУЮ РАЗМЕТКУ.

   Главная мысль файла: ни один шаблон не переписывается. Все
   селекторы ниже целятся в классы и теги, которые в проекте уже
   стоят — .tile, .qcard, .verdict, .file-card, .tabs, .card,
   .weekgrid, .auth__card и так далее. Поэтому:

   • откат — это удалить <link> на glass.css и skin.css из base.html,
     и сайт станет ровно таким, каким был;
   • ни одна миграция не нужна, ни один вид не меняется;
   • риск сводится к «что-то выглядит не так», а не к потере данных.

   app.css НЕ ПЕРЕПИСЫВАЕТСЯ. Часть его правил (рамки и фоны карточек)
   этот файл перекрывает. Это осознанный размен: 790 строк рабочего
   кода на живом проде трогать ради чистоты — плохая сделка (D-49
   запрещает не только опасные, но и необязательные правки).

   ══════ ПРО ВЕС СЕЛЕКТОРОВ — ЧИТАТЬ ДО ПРАВОК ══════
   Порядок загрузки в base.html:
       pico → app.css → glass.css → skin.css → {% block extra_head %}
   schedule.css и stats.css приезжают ИЗ extra_head, то есть ПОЗЖЕ
   этого файла. При равном весе побеждают они.

   Отсюда правило, которое выглядит странно, но обязательно:
   все правила раздела 10 (расписание) начинаются с `body `.
   Это поднимает вес с (0,1,0) до (0,1,1) и позволяет перебить
   schedule.css, не трогая его. Тот же приём и та же грабля, что
   в D-62: `body:not(.pico) td` весом (0,1,2) уже перебивал однажды
   `.mini td` весом (0,1,1), и мини-календарь молча разъезжался.

   !important не используется нигде, кроме @media print в glass.css.
   ============================================================ */


/* ══════════════════════════════════════════════════════════════
   1 · ЛИСТ СТРАНИЦЫ
   Модель ровно та же, что на дашборде ученика: внешнее стекло (.gl)
   и плиты внутри него (.plot). Здесь роль внешнего стекла играет
   <main class="sheet">, а роль плит — таблицы, поля, карточки.

   Почему один лист, а не карточка на каждый абзац. Обычная страница
   проекта — это документ: заголовок, текст, таблица, форма. Разложи
   их по отдельным стёклам — получится россыпь плиток, между которыми
   глаз ищет, что к чему относится. Один лист читается как лист.
   ══════════════════════════════════════════════════════════════ */
main.sheet{
  position:relative;
  border-radius:20px;
  background:var(--gl-fill);
  /* Размытие у листа СЛАБЕЕ, чем у карточек (--sheet-blur, а не
     --gl-blur). Лист высокий и прокручивается, а backdrop-filter
     пересчитывается на каждый кадр прокрутки. За стеклом при этом
     плавный градиент, на котором сила размытия почти не видна, —
     то есть экономим бесплатно. */
  -webkit-backdrop-filter:blur(var(--sheet-blur)) saturate(150%);
  backdrop-filter:blur(var(--sheet-blur)) saturate(150%);
  border:1px solid var(--gl-edge);
  box-shadow:var(--gl-shadow);
  padding:1.35rem 1.6rem 1.9rem;
  margin:0 0 2rem;
  isolation:isolate;
}
main.sheet::before{
  content:"";position:absolute;inset:0;border-radius:inherit;
  border:1px solid var(--gl-inner);pointer-events:none;z-index:5;
}
main.sheet::after{
  content:"";position:absolute;left:8%;right:8%;top:0;height:1px;
  background:linear-gradient(90deg,transparent,var(--gl-hi),transparent);
  pointer-events:none;z-index:5;opacity:.9;
}
/* Первый и последний потомок не должны отбивать лист изнутри
   вторым отступом — иначе сверху появляется пустая полоса. */
main.sheet > :first-child{margin-top:0}
main.sheet > :last-child{margin-bottom:0}

@media (max-width:640px){
  main.sheet{padding:1rem 1rem 1.3rem;border-radius:16px}
}


/* ══════════════════════════════════════════════════════════════
   2 · ШАПКА САЙТА
   Была подчёркнутой полосой, стала стеклянной панелью. Разметка
   в base.html та же: header.site + .brand + ссылки + .spacer + форма.
   ══════════════════════════════════════════════════════════════ */
.pico > header.site, header.site{
  position:relative;
  display:flex;align-items:center;gap:.85rem;flex-wrap:wrap;
  border:1px solid var(--gl-edge);
  border-radius:16px;
  background:var(--gl-fill);
  -webkit-backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  box-shadow:var(--gl-shadow);
  padding:.5rem .9rem;
  margin:0 0 14px;
  isolation:isolate;
}
header.site::after{
  content:"";position:absolute;left:10%;right:10%;top:0;height:1px;
  background:linear-gradient(90deg,transparent,var(--gl-hi),transparent);
  pointer-events:none;opacity:.9;
}
header.site .brand{font-weight:600;letter-spacing:-.01em;font-size:.95rem}
header.site .brand b{color:var(--aa-accent)}
/* Этап 6: логотип стал ССЫЛКОЙ на главную. Правило «header.site a» ниже
   красит все ссылки шапки в пилюли приглушённым цветом — логотипу
   возвращаем прежний вид; пилюля проступает только при наведении.
   Именно inherit, а не var(--pico-color): внутри ссылки Pico сам
   переопределяет --pico-color на акцентный, и логотип стал бы бирюзовым. */
.pico header.site a.brand, header.site a.brand{
  color:inherit;font-size:.95rem;
  padding:.34rem .55rem;margin-left:-.55rem;
}
.pico header.site a.brand:hover, header.site a.brand:hover{color:inherit}

/* Ссылки шапки — стеклянные пилюли. Наведение подсвечивает края,
   а не подчёркивает: подчёркивание на полупрозрачном фоне рябит. */
.pico header.site a, header.site a{
  text-decoration:none;font-size:.86rem;line-height:1;
  color:var(--pico-muted-color);
  padding:.34rem .62rem;border-radius:10px;
  border:1px solid transparent;
  transition:border-color .12s, color .12s, background-color .12s;
}
.pico header.site a:hover, header.site a:hover{
  color:var(--aa-accent);
  border-color:var(--pill-edge);
  background:var(--pill-fill);
}
/* .is-current уже предусмотрен в app.css — подсветку делаем заметнее. */
.pico header.site a.is-current, header.site a.is-current{
  color:var(--pico-color);font-weight:600;
  border-color:var(--pill-edge);background:var(--pill-fill);
}
header.site .spacer{margin-left:auto;font-size:.82rem}

/* Кнопка «Выйти». Форма .inline уже описана в app.css, здесь только
   вид самой кнопки. */
.pico header.site form.inline button{
  padding:.32rem .7rem;font-size:.8rem;line-height:1;border-radius:10px;
  background:var(--pill-fill);border:1px solid var(--pill-edge);
  color:var(--pico-muted-color);
}
.pico header.site form.inline button:hover{
  border-color:var(--aa-bad);color:var(--aa-bad);background:var(--aa-bad-bg);
}

@media (max-width:640px){
  header.site{gap:.4rem;padding:.45rem .6rem}
  .pico header.site a, header.site a{padding:.3rem .45rem;font-size:.8rem}
}


/* ══════════════════════════════════════════════════════════════
   3 · СООБЩЕНИЯ И ПРЕДУПРЕЖДЕНИЯ
   Полоска слева остаётся — она за секунду говорит «хорошо/плохо».
   Меняется только поверхность: плита вместо плоской заливки.
   ══════════════════════════════════════════════════════════════ */
ul.messages{list-style:none;padding:0;margin:0 0 14px}
ul.messages li{
  position:relative;
  padding:.6rem .9rem;margin-bottom:.5rem;
  border:0;border-left:3px solid var(--aa-idle);
  border-radius:4px 14px 14px 4px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);
  box-shadow:inset 0 0 0 1px var(--pl-ring), 0 8px 20px -16px rgba(16,24,40,.4);
}
ul.messages li.success{border-left-color:var(--aa-ok)}
ul.messages li.error  {border-left-color:var(--aa-bad);color:inherit}
ul.messages li.warning{border-left-color:var(--aa-wait)}

.warn{
  border:0;border-left:3px solid var(--aa-wait);
  border-radius:4px 14px 14px 4px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  padding:.7rem .95rem;margin:1.1rem 0;
}
.warn > :first-child{margin-top:0}
.warn > :last-child{margin-bottom:0}

/* Блок «требуют внимания» на странице тренажёра и у учителя. */
.attention{
  border:0;border-left:3px solid var(--aa-wait);
  border-radius:4px 14px 14px 4px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  padding:.9rem 1.05rem;margin:1rem 0 1.5rem;
}

/* Пустое состояние — пунктирная рамка на плите, как .emptybox
   на дашборде. */
.empty{
  border:1px dashed var(--gl-line);border-radius:14px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  padding:1.5rem;text-align:center;color:var(--pico-muted-color);
}


/* ══════════════════════════════════════════════════════════════
   4 · ТАБЛИЦЫ
   ------------------------------------------------------------
   ДВЕ ЛОВУШКИ, ИЗ-ЗА КОТОРЫХ ЭТИ ПРАВИЛА ВЫГЛЯДЯТ ТАК СТРАННО.

   1. Первая версия целилась в `body:not(.pico) td` — вес (0,2,1).
      Это перебило бы `.mini td` (0,1,1) из schedule.css, и в
      мини-календаре появились бы горизонтальные линии, а числа
      месяца разъехались бы. РОВНО ТА ЖЕ ГРАБЛЯ, что описана
      в D-62: она уже ломала этот календарь один раз.

   2. Голый `.pico table` накрыл бы и `.tpt` на дашборде ученика —
      таблица тем получила бы вторую плиту внутри стеклянной
      плитки. Дашборд утверждён и не должен меняться (D-85).

   Поэтому таблицы оформляются НЕ вообще, а только там, где есть
   лист: `main.sheet table`. Дашборды листа не имеют — и остаются
   нетронутыми по построению, а не по недосмотру.

   border-collapse меняется на separate намеренно: при collapse
   браузер не скругляет углы таблицы, ячейки вылезают за радиус
   и плита получается с прямыми углами. border-spacing:0
   сохраняет прежний вид, поэтому геометрия строк не меняется.
   ══════════════════════════════════════════════════════════════ */
main.sheet table,
body .sched__main table{
  width:100%;
  border-collapse:separate;border-spacing:0;
  border-radius:14px;overflow:hidden;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px) saturate(140%);
  backdrop-filter:blur(10px) saturate(140%);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 1px 0 var(--pl-edge);
  margin-bottom:1.2rem;
}
main.sheet th, main.sheet td,
body .sched__main th, body .sched__main td{
  background:transparent;
  border:0;border-bottom:1px solid var(--gl-line);
  text-align:left;
}
main.sheet thead th, body .sched__main thead th{
  font-size:.72rem;letter-spacing:.05em;text-transform:uppercase;
  color:var(--pico-muted-color);font-weight:700;
}
main.sheet tbody tr:last-child td,
body .sched__main tbody tr:last-child td{border-bottom:0}
main.sheet tbody tr:hover td{background:rgba(var(--aa-accent-rgb),.05)}

/* ══════════════════════════════════════════════════════════════
   5 · ПОЛЯ ВВОДА, ФОРМЫ, КНОПКИ
   ══════════════════════════════════════════════════════════════ */
.pico input:not([type=checkbox]):not([type=radio]):not([type=range]):not([type=file]),
.pico select, .pico textarea,
:where(body:not(.pico)) input[type=text], :where(body:not(.pico)) input[type=password],
:where(body:not(.pico)) input[type=datetime-local], :where(body:not(.pico)) input[type=number],
:where(body:not(.pico)) select, :where(body:not(.pico)) textarea{
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  border:1px solid var(--pl-edge);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  border-radius:11px;
  color:var(--pico-color);
}
.pico input:focus, .pico select:focus, .pico textarea:focus{
  border-color:rgba(var(--aa-accent-rgb),.55);
  box-shadow:inset 0 0 0 1px var(--pl-ring), 0 0 0 3px rgba(var(--aa-accent-rgb),.16);
}
.pico label{font-weight:600;font-size:.88rem}
.pico small{color:var(--pico-muted-color)}

/* Кнопка-действие остаётся заливной: это главный элемент формы,
   и стеклянной её делать нельзя — потеряется в фоне. */
.pico button, .pico a[role=button],
:where(body:not(.pico)) button{
  border-radius:11px;
}
/* Второстепенные кнопки — стекло. */
.pico button.secondary, .pico button.outline,
.pico a[role=button].secondary, .pico a[role=button].outline,
:where(body:not(.pico)) button.secondary, :where(body:not(.pico)) button.outline{
  background:var(--pill-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  border:1px solid var(--pill-edge);
  color:var(--pico-muted-color);
  box-shadow:none;
}
.pico button.secondary:hover, .pico button.outline:hover,
.pico a[role=button].secondary:hover, .pico a[role=button].outline:hover{
  border-color:var(--aa-accent);color:var(--aa-accent);
  background:rgba(var(--aa-accent-rgb),.10);
}

/* Кнопка «Разметить» на странице проверки — ссылка, Pico её кнопкой
   не считает, поэтому оформляется отдельно (правило уже было
   в app.css §12, здесь только скругление под общий стиль). */
.btn-draw{border-radius:11px;padding:.36rem .9rem}

/* Разделитель */
.pico hr, :where(body:not(.pico)) hr, .hair{
  border:0;border-top:1px solid var(--gl-line);margin:1.8rem 0;
}


/* ══════════════════════════════════════════════════════════════
   6 · ВКЛАДКИ, ФИЛЬТРЫ, ПАГИНАТОР
   ══════════════════════════════════════════════════════════════ */
.tabs{
  display:inline-flex;gap:.25rem;flex-wrap:wrap;
  margin:1rem 0 1rem;padding:.25rem;
  border:0;border-radius:13px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 1px 0 var(--pl-edge);
}
.pico .tabs a, :where(body:not(.pico)) .tabs a{
  padding:.32rem .78rem;border-radius:10px;
  text-decoration:none;color:var(--pico-muted-color);
  border:1px solid transparent;font-size:.88rem;line-height:1.35;
}
.pico .tabs a:hover, :where(body:not(.pico)) .tabs a:hover{
  background:var(--pill-fill);color:var(--pico-color);
}
.pico .tabs a.active, :where(body:not(.pico)) .tabs a.active{
  background:var(--aa-accent);color:#fff;border-color:transparent;
  box-shadow:0 4px 12px -6px rgba(var(--aa-accent-rgb),.9);
}

/* Полоса фильтров — плита, чтобы поля не висели в воздухе. */
.filters{
  display:flex;gap:.5rem;align-items:center;flex-wrap:wrap;
  margin-bottom:1.1rem;padding:.5rem .65rem;
  border-radius:13px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 1px 0 var(--pl-edge);
}
.pico .filters label{font-size:.82rem;font-weight:600;margin:0}

.pager{
  display:flex;gap:1rem;align-items:center;margin-top:1.25rem;
  font-size:.88rem;
}
.pico .pager a{
  text-decoration:none;padding:.3rem .7rem;border-radius:10px;
  background:var(--pill-fill);border:1px solid var(--pill-edge);
}
.pico .pager a:hover{border-color:var(--aa-accent)}


/* ══════════════════════════════════════════════════════════════
   7 · КАРТОЧКИ ПРОЕКТА
   Всё, что в app.css было «рамка + var(--aa-surface)», становится
   плитой. Классы те же, разметка не трогается.
   ══════════════════════════════════════════════════════════════ */
.tile, .panel, .qcard, .review-box, .file-card,
.qb-saved__row, .qb-header-strip,
.pico details, :where(body:not(.pico)) details{
  border:0;
  border-radius:14px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px) saturate(140%);
  backdrop-filter:blur(12px) saturate(140%);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 1px 0 var(--pl-edge);
}
/* Полоса шапки партии и полоса состояния захода сохраняют
   акцентную грань слева — она и есть их смысл. */
.qb-header-strip{
  border-left:3px solid var(--aa-accent);
  border-radius:4px 14px 14px 4px;
}
.qcard{padding:1.05rem 1.15rem 1.2rem}
.panel{overflow:hidden}
.panel__head{border-bottom:1px solid var(--gl-line)}
.pico details{padding:.7rem 1rem}
.pico summary{cursor:pointer;font-weight:600}

/* Вердикт в тренажёре. Полоска-состояние остаётся, фон — плита
   с подмешанным цветом состояния. */
.verdict{
  border:0;border-left:3px solid var(--aa-idle);
  border-radius:4px 14px 14px 4px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
}
.verdict.is-ok {border-left-color:var(--aa-ok);background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 0 60px -14px var(--aa-ok)}
.verdict.is-bad{border-left-color:var(--aa-bad);background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 0 60px -14px var(--aa-bad)}

/* Зона перетаскивания файлов. Два разных класса — #drop-zone
   у виджета домашек и .qb-drop у конвейера банка задач (D-69);
   объединять их нельзя, а выглядеть они должны одинаково. */
#drop-zone, .qb-drop{
  border:2px dashed var(--gl-line);border-radius:14px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  color:var(--pico-muted-color);
}
#drop-zone.over, .qb-drop.over{
  border-color:var(--aa-accent);
  background:rgba(var(--aa-accent-rgb),.10);
}

/* Карточки загруженных файлов */
.file-card{padding:.45rem;cursor:grab}
.file-preview img{border-radius:9px}
.pico .file-delete{
  box-shadow:0 4px 10px -4px rgba(217,53,38,.8);
}

/* Отрендеренный Markdown */
.md{border-left:2px solid rgba(var(--aa-accent-rgb),.35);padding-left:.95rem}


/* ══════════════════════════════════════════════════════════════
   8 · КАРТИНКИ РАБОТ И УСЛОВИЙ
   Страницы проверки, домашки, тренажёра. Рамка вокруг скана —
   та же плита, чтобы белый лист фотографии не висел в воздухе.
   ══════════════════════════════════════════════════════════════ */
.pages img, .big-pages img, .task-files img, .task-strip img{
  border:0;border-radius:12px;
  box-shadow:0 0 0 1px var(--pl-ring), 0 12px 28px -20px rgba(16,24,40,.5);
}
.qcard__fig{
  border:0;border-radius:12px;overflow:hidden;
  background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
}
.qthumb{border:0;border-radius:9px;box-shadow:0 0 0 1px var(--pl-ring)}


/* ══════════════════════════════════════════════════════════════
   9 · МЕТКИ: чипы, оценки, значки
   Формы уже правильные (app.css §8), меняется только материал.
   ══════════════════════════════════════════════════════════════ */
.chip{
  border-color:var(--pill-edge);
  background:var(--pill-fill);
  -webkit-backdrop-filter:blur(8px);backdrop-filter:blur(8px);
}
.chip--audience{border-color:rgba(var(--aa-accent-rgb),.45);color:var(--aa-accent)}
.chip--ok  {border-color:rgba(2,151,100,.45); color:var(--aa-ok)}
.chip--bad {border-color:rgba(217,53,38,.45); color:var(--aa-bad)}
.chip--wait{border-color:rgba(151,112,0,.45); color:var(--aa-wait)}

.badge{
  border-radius:999px;padding:.1rem .5rem;
  box-shadow:0 4px 10px -6px rgba(217,53,38,.9);
}
.badge-ann{box-shadow:0 4px 10px -6px rgba(2,151,100,.9)}

.grade{
  border-radius:9px;
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  -webkit-backdrop-filter:blur(6px);backdrop-filter:blur(6px);
}

/* Шкала — сквозной элемент проекта. Оставляем геометрию,
   добавляем внутреннюю грань, чтобы не выглядела плоской. */
.scale{box-shadow:inset 0 0 0 1px var(--pl-ring)}


/* ══════════════════════════════════════════════════════════════
   10 · РАСПИСАНИЕ  (schedule.css)
   ------------------------------------------------------------
   ГЕОМЕТРИЯ СЕТКИ НЕ ТРОГАЕТСЯ НИ ОДНИМ ПРАВИЛОМ. Сетка недели
   построена абсолютным позиционированием, у окошек занятий top
   и height приходят числами из Python. Любая правка размеров,
   отступов или display здесь ломает раскладку молча.

   Меняются ТОЛЬКО поверхности. Проще всего это делается через
   собственные переменные schedule.css: подменяем --sched-surface
   и --sched-line, и всё, что на них опирается, едет само.

   `body ` в начале каждого селектора обязателен: schedule.css
   грузится из extra_head, то есть ПОСЛЕ этого файла, и при равном
   весе побеждает он. См. шапку файла.
   ══════════════════════════════════════════════════════════════ */
body .sched{
  --sched-surface: transparent;
  --sched-line: var(--gl-line);
  --sched-line-strong: var(--gl-line);
}

/* Боковые карточки и сама сетка — стекло. */
body .card, body .weekgrid{
  border:1px solid var(--gl-edge);
  border-radius:16px;
  background:var(--gl-fill);
  -webkit-backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  box-shadow:var(--gl-shadow);
}
body .card__head{border-bottom:1px solid var(--gl-line)}

/* .card встречается и ВНЕ расписания — на странице занятия у учителя
   (teach/lesson_detail.html), а она идёт с листом. Стекло внутри
   стекла выглядит мутным пятном, поэтому там .card становится плитой.
   Вес (0,2,1) против (0,1,1) выше — правило выигрывает без !important. */
main.sheet .card{
  border:0;border-radius:14px;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(12px);backdrop-filter:blur(12px);
  box-shadow:inset 0 0 0 1px var(--pl-ring), inset 0 1px 0 var(--pl-edge);
}
body .card__head a:hover{background:var(--pill-fill)}

/* Мини-календарь: подсветки — на токенах проекта. */
body .mini a:hover{background:var(--pill-fill)}
body .mini .in-week{background:rgba(var(--aa-accent-rgb),.14);border-radius:.4rem}
body .mini .today{outline:2px solid var(--aa-accent);border-radius:.4rem}
body .mini .dot::after{background:var(--aa-accent)}

/* Кнопки навигации по неделям — стеклянные пилюли. */
body .navbtn{
  border:1px solid var(--pill-edge);
  border-radius:11px;
  background:var(--pill-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  color:var(--pico-color);
}
body .navbtn:hover{border-color:var(--aa-accent);color:var(--aa-accent)}
body .navbtn--accent{
  background:rgba(var(--aa-accent-rgb),.14);
  border-color:rgba(var(--aa-accent-rgb),.45);
  color:var(--aa-accent);
}

/* Окошко занятия. Голубой из schedule.css заменён на фирменный
   акцент проекта — иначе на бирюзовом фоне две разные синевы. */
body .sched{
  --lesson-bg: rgba(var(--aa-accent-rgb), .18);
  --lesson-border: rgba(var(--aa-accent-rgb), .60);
  --lesson-ink: var(--aa-accent);
  --done-bg: var(--aa-ok-bg);
  --done-border: rgba(2,151,100,.45);
  --done-ink: var(--aa-ok);
  --cancel-ink: var(--aa-bad);
  --today-bg: rgba(var(--aa-accent-rgb), .07);
  --now-line: var(--aa-bad);
  --sched-muted: var(--pico-muted-color);
}
body .lesson{border-radius:8px}
body .daycol.is-weekend{background:rgba(111,120,135,.045)}

/* Полоса-предупреждение в расписании учителя */
body .warnstrip{
  border-radius:4px 13px 13px 4px;
  border-left:3px solid var(--aa-wait);
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  padding:.55rem .8rem;
}

/* Итоговая строка под сеткой */
body .summary{
  border-radius:13px;padding:.5rem .8rem;
  background:var(--pl-fill);
  -webkit-backdrop-filter:blur(10px);backdrop-filter:blur(10px);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
}

/* Страницы расписания идут БЕЗ .pico (у них свой body_class),
   поэтому базовые кнопки и поля им даёт app.css §11. Скругляем
   их под общий стиль. */
body:not(.pico) .filter label:hover{background:var(--pill-fill);border-radius:.4rem}


/* ══════════════════════════════════════════════════════════════
   11 · РИСОВАЛКА ПОМЕТОК — СТЕКЛА НЕТ, И ЭТО РЕШЕНИЕ
   ------------------------------------------------------------
   Цветной градиент под холстом мешает главному делу страницы:
   учитель оценивает, разборчивы ли КРАСНЫЕ пометки поверх скана.
   Фон, подкрашенный бирюзовым и оранжевым, меняет восприятие
   красного — то есть прибор начинает врать.

   Плюс к этому: холст перерисовывается на каждый мазок, а
   backdrop-filter вокруг него заставлял бы браузер пересчитывать
   размытие на том же кадре.

   Страница помечена body_class="no-glass" (см. templates/teach/
   annotate.html). Здесь только гасим то, что могло бы просочиться.
   ══════════════════════════════════════════════════════════════ */
body.no-glass main.sheet{
  background:none;box-shadow:none;border:0;padding:0;
  -webkit-backdrop-filter:none;backdrop-filter:none;
}
body.no-glass main.sheet::before,
body.no-glass main.sheet::after{content:none}
body.no-glass .toolbar{
  border-radius:12px;
  background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  padding:.5rem .6rem;
}


/* ══════════════════════════════════════════════════════════════
   12 · СТРАНИЦА ВХОДА
   Раскладка (сетка 1fr / 1.15fr, логотип слева, поля справа)
   остаётся из app.css §13. Меняется только карточка.
   ══════════════════════════════════════════════════════════════ */
.auth__card{
  position:relative;
  border:1px solid var(--gl-edge);
  border-radius:24px;
  background:var(--gl-fill);
  -webkit-backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  backdrop-filter:blur(var(--gl-blur)) saturate(180%);
  box-shadow:var(--gl-shadow);
  isolation:isolate;
}
.auth__card::before{
  content:"";position:absolute;inset:0;border-radius:inherit;
  border:1px solid var(--gl-inner);pointer-events:none;
}
.auth__card::after{
  content:"";position:absolute;left:12%;right:12%;top:0;height:1px;
  background:linear-gradient(90deg,transparent,var(--gl-hi),transparent);
  pointer-events:none;opacity:.9;
}
/* Тёплое свечение в углу карточки — тот же приём, что .glow
   на плитках дашборда. Обязательно absolute и под содержимым. */
.auth__card .glow{border-radius:24px;overflow:hidden}

.auth__error{
  border:0;border-left:3px solid var(--aa-bad);
  border-radius:4px 12px 12px 4px;
  background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  padding:.55rem .8rem;
}
/* На странице входа общий лист не нужен: карточка сама себе лист. */
body.auth-page main.sheet{
  background:none;box-shadow:none;border:0;padding:0;
  -webkit-backdrop-filter:none;backdrop-filter:none;
}
body.auth-page main.sheet::before,
body.auth-page main.sheet::after{content:none}


/* ══════════════════════════════════════════════════════════════
   13 · МЕЛОЧИ И ЧИТАЕМОСТЬ
   ══════════════════════════════════════════════════════════════ */

/* Заголовки на стекле стоят плотнее: у листа уже есть свой отступ,
   и пиковский --pico-typography-spacing-top добавлял второй. */
.pico main.sheet h1{--pico-typography-spacing-top:1.4rem}
.pico main.sheet h2{--pico-typography-spacing-top:1.7rem}
.pico main.sheet h3{--pico-typography-spacing-top:1.4rem}

/* Код внутри текста — маленькая плита. */
.pico code{
  background:var(--pl-fill);
  box-shadow:inset 0 0 0 1px var(--pl-ring);
  border-radius:6px;padding:.05rem .35rem;
}

/* Ссылки в тексте: подчёркивание на полупрозрачном фоне рябит,
   поэтому оно появляется только при наведении. */
.pico main.sheet a{text-decoration:none}
.pico main.sheet a:hover{text-decoration:underline}
/* …но не у того, что и так выглядит кнопкой или плиткой. */
.pico main.sheet a[role=button]:hover,
.pico main.sheet .tabs a:hover,
.pico main.sheet .btn-draw:hover{text-decoration:none}

/* Спарклайн — тот же материал, что на дашборде учителя. */
.spark polyline{stroke:var(--aa-accent)}


/* ══════════════════════════════════════════════════════════════
   14 · ЕДИНАЯ ШИРИНА ПОЛЕЙ
   ------------------------------------------------------------
   Было четыре разные ширины, и прыжок между вкладками бросался
   в глаза:

     .container        60% экрана   — кабинет, домашки, тренажёр,
                                      темы, очередь, все формы
     .container-wide   80%          — статистика, банк задач,
                                      расписание
     .sched-wide       ≤ 82rem      — содержимое расписания внутри
     .container-fluid  весь экран   — рисовалка пометок

   На мониторе 1920 это 1152 → 1536 → 1312 → 1920 px.

   Приводим .container к 80% — то есть ровно к ширине страницы
   статистики ученика. Две ширины остаются намеренно:

     • рисовалка пометок — холсту нужен весь экран, иначе рукопись
       мельчает и пометки становится не разглядеть;
     • .sched-wide — семь колонок недели шире 1300 px выглядят
       разреженно; ограничитель в schedule.css остаётся.

   Про длинный текст можно не беспокоиться: за него отвечает
   .measure{max-width:46rem} из app.css §1, и она не зависит
   от ширины страницы.

   ВАЖНО ПРО МЕДИАЗАПРОС. В app.css §1 есть
       @media (max-width:1160px){ .container{width:auto;min-width:0} }
   Он идёт РАНЬШЕ этого файла. Если объявить здесь только
   безусловное .container{width:80%;min-width:58rem}, оно перебьёт
   правило из медиазапроса при равном весе (0,1,0) — и на телефоне
   страница станет шире экрана с горизонтальной прокруткой.
   Поэтому медиазапрос ПОВТОРЯЕТСЯ ниже. Это не копипаста
   по недосмотру, а обязательное условие.
   ══════════════════════════════════════════════════════════════ */
.container{
  max-width:none;
  width:80%;
  min-width:58rem;
  margin-inline:auto;
  padding-inline:0;
}
@media (max-width:1160px){
  .container{width:auto;min-width:0;padding-inline:1rem}
}

/* Высота шапки. Разнобой был следствием ширины, а не отдельной
   болезнью: у header.site стоит flex-wrap, и при 60% семь ссылок
   учителя не помещались в строку и переносились на вторую.
   При одинаковой ширине перенос теперь одинаковый на всех
   страницах. min-height — страховка на случай, когда у роли
   ссылок мало и строка получается короче обычного. */
.pico > header.site, header.site{min-height:2.9rem}

/* ══════════════════════════════════════════════════════════════
   15 · АНИМАЦИЯ ПЕРЕХОДА · «МАСШТАБ»
   ------------------------------------------------------------
   Содержимое страницы появляется одним движением: проявляется
   и одновременно подрастает с 98,5% до натуральной величины.
   Читается как «панель встала на место» — на стекле это ложится
   лучше всего, потому что повторяет поведение физической вещи.

   ЧТО ИМЕННО АНИМИРУЕТСЯ И ПОЧЕМУ НЕ БОЛЬШЕ.
   Сайт — обычный Django с полной перезагрузкой страницы. Когда
   браузер уходит на новый адрес, старую страницу отрисовать уже
   нечем — она просто исчезает. Поэтому анимируется ТОЛЬКО
   появление новой. Это не упрощение: настоящий переход
   «старое уходит — новое приходит» умеет лишь View Transitions
   API, а он до сих пор не работает в Firefox.

   ШАПКА САЙТА В АНИМАЦИИ НЕ УЧАСТВУЕТ. Она живёт вне <main>,
   и ни один селектор ниже её не задевает. Проверяется смоуком.

   JAVASCRIPT НЕ НУЖЕН ВОВСЕ. Одно правило на трёх селекторах.
   ══════════════════════════════════════════════════════════════ */
:root{
  --page-in:    180ms;   /* длительность появления */
  --page-scale: .985;    /* с какого масштаба начинаем */
}

@keyframes aa-zoom{
  from{opacity:0;transform:scale(var(--page-scale))}
  to  {opacity:1;transform:none}
}

/* ── Что именно едет ───────────────────────────────────────────
   Три области, по одной на каждый тип страницы. Каждая берётся
   ЦЕЛИКОМ, одним куском — в этом и есть отличие от варианта
   со ступеньками: движение одно, а не пятнадцать.

     main.sheet    обычная страница: лист со всем содержимым
     .statpage     дашборд статистики (шапка раздела + бенто-сетка)
     .sched-wide   расписание (полоса недели + сетка)

   Рисовалка пометок сюда не попадает вовсе: у неё <main> без
   класса sheet, и ни один из трёх селекторов на неё не встаёт.
   Холст должен появляться мгновенно. */
main.sheet,
.statpage,
.sched-wide{
  animation:aa-zoom var(--page-in) cubic-bezier(.22,.8,.3,1) both;
}

/* ── Точка опоры — ВЕРХНИЙ КРАЙ, и это важно ───────────────────
   По умолчанию transform-origin стоит в центре элемента. На
   короткой странице разницы нет, но страница домашнего задания
   с фотографиями решения бывает высотой в три экрана. При опоре
   в центре масштаб 98,5% сдвигает ВИДИМУЮ верхнюю часть вниз
   примерно на 22 px, и вместо «панель встала на место»
   получается «страница дёрнулась сверху вниз».

   С опорой в верхнем крае верх остаётся на месте, а подрастает
   то, что ниже. Заодно исчезает риск, что содержимое на миг
   выедет выше границы окна и подмигнёт полосой прокрутки. */
main.sheet,
.statpage,
.sched-wide{
  transform-origin:50% 0;
}

/* ── Когда анимации не должно быть ─────────────────────────────

   1. Системная настройка «уменьшить движение». Её включают не
      из вредности: у части людей движение интерфейса вызывает
      головокружение и тошноту (вестибулярные расстройства).
      Масштабирование в этом смысле хуже простого проявления,
      поэтому правило обязательно.
   2. Печать. Элемент с opacity:0 в момент печати ушёл бы на
      бумагу белым пятном. fill-mode:both делает это
      маловероятным, но проверять на боевой печати проверенной
      работы ученика — плохая идея.
   3. Рисовалка пометок — у неё <main> без класса sheet, поэтому
      отдельного правила не требуется. Строка ниже оставлена
      как явная страховка: если когда-нибудь понадобится вернуть
      ей лист, анимация всё равно не включится.                 */
@media (prefers-reduced-motion: reduce){
  main.sheet, .statpage, .sched-wide{animation:none}
}
@media print{
  main.sheet, .statpage, .sched-wide{animation:none}
}
body.no-glass main.sheet{animation:none}
