/* aiJudge の画面の見た目。**配色と共通部品はこの 1 か所にだけ置く**（#184）。

   以前は `apps/studentweb` と `apps/reviewconsole` の `base.html` に
   `<style>` として丸ごと 2 部あり、95 の規則が同じ内容で重複していた。
   配色の定義（先頭の `:root` と 2 つの夜の block）は 55 行が完全に一致して
   いて、その中のコメント自身が「片方だけ直すと気づきにくい壊れ方をする」と
   書いてある ── その警告は 1 ファイル内の 2 つの block についてのものだが、
   2 つのファイルの間でも同じことが起きる。防ぐ仕組みは何も無かった。

   **ここは両アプリが読む共有分だけ。** 片方の画面にしか出ない部品は
   `learner.css` / `console.css` に分けてある。分けるのは配信量のためでは
   なく、**それぞれのアプリに当たる規則を切り出し前と同じに保つため** ──
   まとめて配ると、学習者側の `.inline-field .body input`（チェックボックスを
   除外していない）が教員コンソールのチェックボックスにも効き始める。

   夜の配色は **2 か所から当てる**。`@media` は「OS が夜」で、明示的に昼を
   選んでいたら当てない。`[data-theme="dark"]` は「この人が夜を選んだ」。
   値を 1 か所にまとめられないのは CSS の制約で、変数を 2 度書くしかない
   （#181）。 */

/* 書体。**見出しもゴシック**（#185）。明朝は端末に依存し、Windows は
   游明朝、無い環境では既定の `serif` に落ちるので、見出しの顔が機械ごとに
   変わる。本文との差は太さと字間で作る。 */
:root{
  --font-body:"Hiragino Sans","Noto Sans JP",system-ui,sans-serif;
  --font-display:"Hiragino Sans","Noto Sans JP",system-ui,sans-serif;
}
:root{
  --paper:#eef1f7; --surface:#fff; --surface-2:#f5f7fb;
  --ink:#151a26; --ink-2:#3b4356; --muted:#69718a;
  --line:#cfd4e1; --line-soft:#e2e5ee;
  --shu:#b03a29; --shu-soft:#f3e3e0;
  --verd:#1c6d67; --verd-soft:#dfedeb;
  /* 対応が要ることを表す色（琥珀）。**朱とは別に持つ** ── 朱は「確定した
     否定的な事実」で、こちらは「人が押さないと先へ進まない」を意味する。 */
  --kin:#8a5a00; --kin-soft:#f7ecd6;
  /* 藍（#185）。**移動と現在地にだけ使う。**

     以前はリンクも朱だったので、「押して移る」と「確定した否定的な事実」が
     同じ色で並んでいた。移動を藍に移すと、朱は判定の意味だけを担える ──
     判定の三色（朱・琥珀・緑青）に藍を混ぜないこと。 */
  --ai:#1b4f8f; --ai-2:#2f6ab5; --ai-soft:#e3ecf8;
  /* 頁の頭（#185）。**昼夜を通して濃い。**

     貼り付いているので、長い一覧を送っても「いまどこで何を見ているか」が
     画面の上端に残る。濃い面の上では文字も罫もまとめて反転させること ──
     背景だけ濃くすると、墨色の見出しが読めなくなる。

     `--head-shu` は帯の中で使う朱。**意味は変えず明るさだけ合わせる** ──
     `--shu`（#b03a29）は濃紺の上では沈んで読めない。 */
  --head-bg:#123256; --head-ink:#eaf1fa; --head-muted:#9db6d4;
  --head-line:#1d4674; --head-shu:#f0a18e;
  /* 等幅（#215）。**レールは既にこの名前で引いていたのに、定義が無かった** ──
     `var()` の参照先が無い宣言は落ちるだけで、警告も出ずに書体が本文に戻る。
     件数が等幅でないと、桁ごとに幅が変わって右端で揃わない。 */
  --font-mono:ui-monospace,"SFMono-Regular",monospace;
  /* 入口の押し釦の地（#212）。**`--ai` を地に使ってはいけない** ── あれは
     文字色で、夜は明るい側（#8fb0dd）へ反転する。白文字を載せると
     2.2:1 にしかならず、画面の唯一の操作が読めなくなる。地は昼夜とも
     白文字が 4.5:1 を超える濃さで持つ（昼 8.2:1・夜 5.5:1）。 */
  --go-bg:#1b4f8f; --go-ink:#ffffff;
  /* フッタのぶんだけ入口の面を低くする（#212）。**`:has()` が効かない
     ブラウザ向けの控えの値**で、実測に基づく（画面が狭いとフッタが
     折り返して 101px まで伸びるので、そこでは少しはみ出す）。効く側では
     下の flex がこの値を使わずに正確に埋める。 */
  --gate-reserve:80px;
}
/* 夜の配色。**同じ値を 2 か所から当てる**（#181）。

   `prefers-color-scheme` だけだと、見る人が選べない ── 端末が昼設定の
   学生は暗い講義室で読めず、端末が夜設定の教員はプロジェクタに出せない。
   かといって OS 追従を捨てると、いま何も設定せずに夜で見えている人が
   昼に戻ってしまう。だから **OS 追従を既定に残したまま、明示の選択が
   両方向で勝つ**ようにする。

   - `@media` は「OS が夜」── ただし明示的に昼を選んでいたら当てない
   - `[data-theme="dark"]` は「この人が夜を選んだ」

   値を 1 か所にまとめられないのは CSS の制約で、変数を 2 度書くしかない。
   **片方だけ直すと、選んだときと OS 追従のときで色が違う**という、
   気づきにくい壊れ方をする。 */
@media (prefers-color-scheme: dark){
  :root:not([data-theme="light"]){
    --paper:#0d1119; --surface:#151a25; --surface-2:#1b212d;
    --ink:#dee3ef; --ink-2:#b4bccd; --muted:#828ca6;
    --line:#2a3140; --line-soft:#212836;
    --shu:#e4826f; --shu-soft:#2e1f1c;
    --verd:#5eb2ab; --verd-soft:#152a29;
    --kin:#e0ab52; --kin-soft:#2b2314;
    --ai:#8fb0dd; --ai-2:#a9c4ea; --ai-soft:#182234;
    --head-bg:#0b1c30; --head-ink:#d8e6f5; --head-muted:#7e9ab8;
    --go-bg:#2f6ab5;
    --head-line:#153252; --head-shu:#f0a18e;
  }
}
:root[data-theme="dark"]{
  --paper:#0d1119; --surface:#151a25; --surface-2:#1b212d;
  --ink:#dee3ef; --ink-2:#b4bccd; --muted:#828ca6;
  --line:#2a3140; --line-soft:#212836;
  --shu:#e4826f; --shu-soft:#2e1f1c;
  --verd:#5eb2ab; --verd-soft:#152a29;
  --kin:#e0ab52; --kin-soft:#2b2314;
  --ai:#8fb0dd; --ai-2:#a9c4ea; --ai-soft:#182234;
  --head-bg:#0b1c30; --head-ink:#d8e6f5; --head-muted:#7e9ab8;
  --go-bg:#2f6ab5;
  --head-line:#153252; --head-shu:#f0a18e;
}
/* フォーム部品（チェックボックス・スクロールバー・素の select）にも配色を
   伝える。伝えないと、夜の画面に白いチェックボックスだけが浮く。

   **`@media` の側にも要る。** ここは明示の選択の分しか無かったので、
   OS が夜で切り替えを触っていない人 ── つまり既定のままの人 ── だけ、
   暗い画面に明るいフォーム部品が出ていた（#181 の実装が半分だった）。
   配色の値と同じで、**2 か所に書くしかない**。 */
@media (prefers-color-scheme: dark){
  :root:not([data-theme="light"]){color-scheme:dark}
}
:root[data-theme="dark"]{color-scheme:dark}
:root[data-theme="light"]{color-scheme:light}
*{box-sizing:border-box}
/* **選択欄は中身で幅を決めない。** `select` の最小幅はいちばん長い選択肢の
   幅になる ── 科目プロファイルの一覧のような長い項目が 1 つあると、それ
   だけで頁が横に伸びる（実測 786px・視野 390px、#231）。 */
select{max-width:100%}
[hidden]{display:none!important}
body{margin:0;background:var(--paper);color:var(--ink);
  font-family:var(--font-body);line-height:1.75}
main{max-width:1100px;margin:0 auto;padding:32px 24px 80px}
/* 2 面の画面だけ広く使う（#185）。1100px を 2 つに割ると、答案の行が
   折り返し始める ── コードを読む面は幅がそのまま可読性である。 */
main.wide{max-width:1440px}
/* 見出しはゴシック太。字間を締めて本文との差を作る（#185）。 */
h1,h2,h3{font-family:var(--font-display);font-weight:700;letter-spacing:.01em;line-height:1.4}
h1{font-size:1.45rem;margin:0 0 4px}
h2{font-size:1.05rem;margin:32px 0 10px}
/* **移動は藍**（#185）。判定の一次操作（確定）だけが朱のまま ── 人が
   判定を下す行為だからで、リンクは移動でしかない。 */
a{color:var(--ai)}
.card{background:var(--surface);border:1px solid var(--line-soft);border-radius:4px;padding:20px 22px;margin-bottom:20px}
.note{border-left:3px solid var(--verd);background:var(--verd-soft);padding:12px 16px;
  border-radius:0 3px 3px 0;font-size:.9rem;color:var(--ink-2);margin-bottom:20px}
.note.warn{border-left-color:var(--shu);background:var(--shu-soft)}
/* 「読んでおくべきこと」。**朱でも緑青でもない**（#194）── 朱は確定した
   否定的な事実、緑青は済んだこと。デモコースの断りはどちらでもなく、
   「これから操作する人に効く注意」なので琥珀である（`.pill.attn` と同じ
   意味の色を、面の側にも用意する）。 */
.note.act{border-left-color:var(--kin);background:var(--kin-soft)}
table{border-collapse:collapse;width:100%;font-size:.9rem;table-layout:auto}
/* 「説明」のように長い列に残りを吸わせ、他の列を潰させない。 */
td.fit,th.fit{width:1%;white-space:nowrap}
td.grow,th.grow{width:auto}
/* 最初の列（観点名など）に最小幅を与える。与えないと、隣の列に押されて
   「変数名と構造の分かりやす／さ」のように 1 文字だけ折り返される。 */
table td:first-child,table th:first-child{min-width:12em}
@media (max-width:720px){table td:first-child,table th:first-child{min-width:0}}
th,td{text-align:left;padding:9px 12px;border-bottom:1px solid var(--line-soft);vertical-align:top}
/* フォームの中の小項目。**罫線で区切る** ── 見出しの余白だけで分けると、
   項目の切れ目が中身の量に左右され、観点のように密な塊と提出形式のように
   疎な塊が並ぶと、どこまでが 1 項目なのか読み取れない。 */
/* 学習者に出ていない課題の行（#83）。**消えたようには見せない** ── 記録は
   残っており、開けば編集も取り消しもできる。数えるときに紛れないだけの差を付ける。 */
/* 行のどこを押しても開く（JavaScript が付けたときだけ）。 */
tr.row-link[data-clickable]:hover{background:var(--surface-2)}
thead th{font-size:.72rem;letter-spacing:.08em;text-transform:uppercase;color:var(--muted);
  font-weight:400;background:var(--surface-2)}
code,pre,.mono{font-family:var(--font-mono)}
/* 承認待ちの課題は、**生成されたままの文面**を出す（整形すると、モデルが
   何を書いたのかが分からなくなる）。ただし**折り返す** ── 問題文は散文で、
   折り返しても意味は変わらない。下の `pre.code` が折り返さないのは、
   コードは折り返すと意味が変わるからで、事情が違う（#266）。 */
pre.statement{white-space:pre-wrap;overflow-wrap:anywhere}
pre.code{margin:0;overflow-x:auto;background:var(--surface-2);border:1px solid var(--line-soft);
  border-radius:3px;padding:14px 0;font-size:.8rem;line-height:1.65}
pre.code .ln{display:block;padding:0 16px;white-space:pre}
pre.code .ln .n{display:inline-block;width:3em;color:var(--muted);user-select:none;text-align:right;margin-right:1em}
pre.code .ln.hl{background:var(--shu-soft);border-left:3px solid var(--shu);padding-left:13px}
/* 数式（サーバ側で MathML に変換済み・statement.py）。別行立ては中央、
   長い式は横スクロールに逃がす ── 折り返せない要素なので、逃がさないと
   ページ全体が横に伸びる。 */
.statement .math.block{overflow-x:auto;margin:1em 0;text-align:center}
.statement math{font-size:1.05em}
.statement > *:first-child{margin-top:0}
.statement > *:last-child{margin-bottom:0}
.statement h2,.statement h3,.statement h4,.statement h5{font-size:1rem;margin:1.2em 0 .4em;color:var(--ink)}
.statement pre{background:var(--surface);border:1px solid var(--line-soft);border-radius:3px;
  padding:10px 12px;overflow-x:auto;font-size:.82rem}
.statement code{font-size:.85em}
.statement ul,.statement ol{padding-left:1.4em}
.statement hr{border:0;border-top:1px solid var(--line-soft);margin:1.2em 0}
/* 課題文に貼った画像（#64）。**幅は 1 行の `{width=...}` が決める**
   （`images.DISPLAY_WIDTH`）。ここで縛るのは 2 つだけ:
   `height:auto` で縦横比を保ち、狭い画面では本文の幅を超えさせない
   （指定幅が画面より広い日は、幅の指定ではなく画面のほうが正しい）。 */
.statement img{max-width:100%;height:auto;border-radius:2px}
/* 課題文に内部スクロールを付けない。付けると全体を一度に読めず、
   長い課題文ほど読みにくくなる。ページ全体のスクロールで読ませる。
   横に溢れるのはコードブロックだけで、そちらは pre 側で処理する。 */
.statement{font-size:.9rem;color:var(--ink-2);
  border:1px solid var(--line-soft);border-radius:3px;
  padding:14px 16px;background:var(--surface-2)}
fieldset{border:1px solid var(--line-soft);border-radius:3px;padding:14px 18px;margin:0 0 16px}
legend{font-weight:700;font-size:.95rem;padding:0 6px}
.desc{font-size:.85rem;color:var(--muted);margin:0 0 12px}
.levels{display:flex;flex-direction:column;gap:6px}
/* **折り返させる。** 段階の行は 1 本の flex で、狭いと最後に縮むのは説明文
   （`.lv-text`）である ── 日本語の min-content は 1 文字なので、**説明が
   幅 14px・高さ 271px の縦書きになっていた**（実測。判定の画面は 2 面で、
   右の面は画面の半分しかない）。いちばん起きるのが選ばれている段階で、
   そこにだけ「システム判定」「あなたの blind 採点」の札が並んで幅を奪う。

   縮めるのではなく**行を折る**。説明文には下限を持たせ、入らなければ次の
   行へ送る ── 札と割合は縮まない（`white-space:nowrap`）。 */
.levels label{display:flex;flex-wrap:wrap;gap:4px 10px;align-items:baseline;
  font-size:.88rem;
  padding:7px 10px;border:1px solid var(--line-soft);border-radius:3px;cursor:pointer}
.levels label:hover{background:var(--surface-2)}
.levels input:checked + .lv{font-weight:700;color:var(--shu)}
.lv{flex:0 0 auto;min-width:5.5em}
/* 説明文。**余った幅を取り、足りなければ行ごと下りる。** */
.lv-text{flex:1 1 12em;min-width:8em}
/* 知識要素の並び（#327）。**札を折り返す** ── 課題によっては 5 つ以上
   並ぶので、1 行に押し込めると読めない。 */
.kcs{display:flex;flex-wrap:wrap;gap:6px;margin:0}
/* 別の画面へ渡る導線（#328/#335）。**押す場所に見せる** ── 文字のリンクを
   行の値（ログイン ID など）に貼ると、行き先が読めないうえに、値そのものが
   リンクなのだと読まれる。

   地は持たない。**押し釦は 1 画面に 1 つの主役**で、朱の釦が並ぶとどれが
   本筋の操作なのか分からなくなる ── 枠だけで「押せる」を示し、色は移動の藍。

   **学生と教員の両方が使う**ので共有の側に置く（`console.css` ではない）。 */
.button-link{display:inline-block;font-size:.82rem;line-height:1.2;
  padding:5px 10px;border:1px solid var(--line);border-radius:3px;
  color:var(--ai);text-decoration:none;white-space:nowrap}
.button-link:hover{background:var(--surface-2);border-color:var(--ai)}
/* 知識要素ごとの行（#335）。**学生と教員で同じ部品**（`_mastery_rows.html`）。

   数値と図を並べる ── 図だけだと 62% と 64% が読み分けられず、数値だけだと
   知識要素どうしを見比べるのに読み上げが要る。 */
.kcrow{padding:14px 16px}
.kcrow-head{display:flex;flex-wrap:wrap;gap:6px 14px;align-items:baseline;
  justify-content:space-between}
.kcrow-name{display:flex;flex-wrap:wrap;gap:4px 8px;align-items:baseline}
.kcrow-nums{font-size:.9rem;white-space:nowrap}
/* 帯は 2 本とも同じ物差し（0〜100%）。**縦に並べる** ── 知識要素をまたいで
   長さを見比べられるようにする。 */
.kcbars{display:flex;flex-direction:column;gap:3px;margin:10px 0 0}
.kcbar{display:block;height:.55rem;background:var(--surface-2);
  border-radius:99px;overflow:hidden}
.kcbar-fill{display:block;height:100%;border-radius:99px;min-width:2px}
/* 習熟度は藍（移動でも判定でもない、推定の値）。確信度は同じ色の薄い側 ──
   **別の色にしない**：判定の三色（朱・琥珀・緑青）と混ざると、推定値が
   判定として読まれる。 */
.kcbar-fill.mastery{background:var(--ai)}
.kcbar-fill.confidence{background:var(--ai);opacity:.4}
.kcev{margin:12px 0 0}
.kcev summary{cursor:pointer;font-size:.85rem;color:var(--ai)}
/* 割合と札は縮まない ── 「1 0 0 %」や「シ ス テ ム」になる側に回らせない。 */
.levels label > .desc,
.levels label > .pill{flex:0 0 auto;white-space:nowrap;margin:0}
/* **語の途中で折らない。** 狭い幅で「ログア／ウト」と 2 行になっていた
   （携帯で実測）── 折れた押し釦は、押す場所にも文字にも見えない。入り
   きらないときは字の方を詰める（下の携帯向けの規則）。 */
button{font:inherit;font-weight:700;background:var(--shu);color:#fff;border:0;
  border-radius:3px;padding:10px 22px;cursor:pointer;white-space:nowrap}
/* **押せないボタンは押せないように見せる。** 見た目が同じだと、押しても
   何も起きないのを「壊れている」と読む。 */
button:disabled{opacity:.45;cursor:not-allowed}
button:disabled:hover{filter:none}
button:hover{filter:brightness(1.08)}
textarea{width:100%;font:inherit;font-size:.88rem;padding:10px 12px;border-radius:3px;
  border:1px solid var(--line);background:var(--surface);color:var(--ink);resize:vertical}
/* ピルは折り返さない。狭い列に入ると 1 文字ずつ縦に積まれる
   （「採点できませんでした」で実際にそうなった）。nowrap にすると
   表がその分の幅を確保する。 */
.pill{display:inline-block;font-size:.72rem;padding:2px 9px;border-radius:99px;
  border:1px solid var(--line);color:var(--muted);white-space:nowrap}
/* **色は「気分」ではなく「人が何かする必要があるか」で決める。**

     attn  人の操作を待っている。押さないと先へ進まない。いちばん目立たせる
     ok    済んだこと
     no    確定した否定的な事実。**操作は要らない**
     既定  参考の数え上げ・注記

   `no` に両方を背負わせていたときは、放っておいてよいものと、教員が開かない
   限り成績が閉じないものが同じ赤で並んでいた。同じ見え方なら、どちらも目に
   留まらない。

   **どの語をどの種別にするかはテンプレート側に書く。** ここに例を並べると、
   blind 採点の画面にまで判定の語が混ざる（この見出しは全ページに配られる）。

   **色だけに頼らない。** `attn` には記号を添える（色覚の差でも、白黒の
   印刷でも種別が読める必要がある）。 */
.pill.ok{color:var(--verd);border-color:var(--verd);background:var(--verd-soft)}
.pill.no{color:var(--shu);border-color:var(--shu);background:var(--shu-soft)}
.pill.attn{color:var(--kin);border-color:var(--kin);background:var(--kin-soft);
  font-weight:700;box-shadow:0 0 0 2px var(--kin-soft)}
.pill.attn::before{content:"! ";font-weight:700}
/* 欄の中身が**学生に見えるか**（2026-09-28）。観点の説明は提出後の結果画面に
   出るのに、画面は「AI が読む」としか言っておらず、回答例を書くと答えが漏れた。
   見える欄は琥珀（書く内容に注意が要る）、見えない欄は既定の色。**色だけに
   頼らない** ── ラベルの文言そのものが「見えます／見えません」と言う。 */
.visibility{display:inline-block;font-size:.72rem;font-weight:400;padding:1px 8px;
  border-radius:99px;border:1px solid var(--line);color:var(--muted);white-space:nowrap;
  margin-left:4px}
.visibility.shown{color:var(--kin);border-color:var(--kin);background:var(--kin-soft)}
/* 誰が判定したか（#185・P4）。**色ではなく記号で区別する** ── 白黒で
   印刷しても、色覚に差があっても読める必要がある。◇ が AI の判定、
   ▣ がテスト実行（決定的評価）。 */
.pill.ai,.pill.det{border-color:var(--line);background:var(--surface-2);color:var(--ink-2)}
.pill.ai::before{content:"◇ "}
.pill.det::before{content:"▣ "}
/* 朱の字。**インラインで色を書かない**（#185）── 反転した面（濃い頁の頭）
   では上書きできず、`#b03a29` が沈んで読めなくなる。 */
.late{color:var(--shu)}
/* 提出物の埋め込み（画像・動画）。同じ指定が 6 か所にインラインで
   書かれていたのをまとめたもの。 */
.embed{max-width:100%;border:1px solid var(--line);border-radius:3px}
.progress{height:6px;background:var(--line-soft);border-radius:99px;overflow:hidden;margin:10px 0 6px}
.progress > div{height:100%;background:var(--verd)}
.grid2{display:grid;grid-template-columns:1fr 1fr;gap:20px}
/* 頁の頭（#185）。**濃い面を上に置き、貼り付ける。**

   以前は「銘と利用者の帯」と「パンくずの帯」が別々の薄い面で、どちらも
   スクロールで消えていた。長い一覧（88 名 × 7 問）を送ると、いま何の
   一覧を見ているのか分からなくなる ── 帯を 1 つにまとめ、濃い面にして
   上端に残す。

   **中の文字と罫をまとめて反転させる。** 背景だけ濃くすると、墨色の
   見出しとリンクが読めない。 */
.topbar{position:sticky;top:0;z-index:20;background:var(--head-bg);
  border-bottom:1px solid var(--head-line);color:var(--head-ink)}
.topbar a{color:#cfe0f2}
.topbar :focus-visible{outline-color:#cfe0f2}
/* 帯の中の朱（遅延など）。**意味は変えず明るさだけ合わせる。** */
.topbar .late{color:var(--head-shu)}
header.top .inner{max-width:1100px;margin:0 auto;padding:10px 24px;display:flex;
  align-items:baseline;gap:16px;font-size:.85rem}
header.top .brand{font-weight:700;font-size:1rem;color:var(--head-ink);
  text-decoration:none;letter-spacing:.03em}
header.top .spacer{flex:1}
header.top form{margin:0}
header.top button{background:rgba(255,255,255,.08);color:var(--head-ink);
  border:1px solid var(--head-line);font-weight:400;padding:4px 12px;font-size:.8rem}
header.top button:hover{background:rgba(255,255,255,.16);filter:none}
.field{margin-bottom:14px}
.field label{display:block;font-size:.85rem;color:var(--ink-2);margin-bottom:4px}
.field input:not([type=checkbox]):not([type=radio]){width:100%;font:inherit;font-size:.9rem;padding:9px 12px;border-radius:3px;
  border:1px solid var(--line);background:var(--surface);color:var(--ink)}
.narrow{max-width:420px}
/* 文脈バナー。どのコースの何回目のどの課題を見ているかを全ページに出す。
   `.topbar` の中に入ったので、面の色は帯が持つ（ここでは持たない）。 */
.ctx{border-top:1px solid var(--head-line)}
.ctx .inner{max-width:1100px;margin:0 auto;padding:7px 24px;font-size:.8rem;
  color:var(--head-muted)}
.ctx b{color:var(--head-ink);font-weight:600}
.ctx a{text-decoration:none}
.ctx a:hover{text-decoration:underline}
/* パンくず。区切りは薄く、現在地だけ濃く。折り返しても経路が読めるように
   区切りごと折り返させる。 */
.trail{display:flex;flex-wrap:wrap;align-items:baseline;gap:2px 8px}
.trail [aria-current]{color:var(--head-ink)}
.sep{color:var(--head-muted);user-select:none;opacity:.7}
/* ボタンの置き場所。**原則は入力と同じ行の右端。** 目で追う順が
   「何を入れるか → 押す」で閉じ、フォームの終わりが行の右端で分かる。
   1 行に収まらない入力（textarea・項目が複数）だけ下に置き、そこでも
   右端に寄せて同じ読み方にする。 */
.inline-field{display:flex;align-items:flex-end;gap:12px;flex-wrap:wrap;margin-bottom:0}
.inline-field .body{flex:1;min-width:12rem}
.inline-field .body label{display:block;font-size:.85rem;color:var(--ink-2);margin-bottom:4px}
.inline-field > button{flex:none;margin-left:auto}
.actions{display:flex;justify-content:flex-end;gap:10px;margin-top:12px}
/* ログイン画面のように、カードの中身がボタン 1 つだけのとき用。
   `.actions`（右端寄せ）は複数の入力の下に添える前提で、単体だと
   カードの中で不釣り合いに小さく右に寄って見える。 */
.cta{display:flex}
.cta button{flex:1;padding:14px 22px;font-size:1rem}
.score{font-size:2rem;font-weight:700;color:var(--ink)}
.score .unit{font-size:1rem;color:var(--muted);font-weight:400}
@media (max-width:860px){.grid2{grid-template-columns:1fr}}
:focus-visible{outline:2px solid var(--ai);outline-offset:2px}
/* PDF の埋め込み。**高さを幅から導く。** 固定のピクセル値だと、幅が伸びる
   ほど比率が崩れ、A4 縦 1 ページが 1 画面に収まらない（#87）。

   A4 縦は 210:297。ブラウザ内蔵のビューアは道具箱とページ一覧をその中に
   描くので、紙のぶんが削られる。**その分を上に足す** ── 足りないより
   余るほうがよい（余白は無害だが、切れた答案は読めない）。

   `max-height` で画面の縦も見る。縦の狭い画面で紙の比率を優先すると、
   埋め込みだけで画面を使い切って前後の文脈が消える。 */
.pdf-embed{width:100%;aspect-ratio:210/297;max-height:85vh;min-height:520px;
  border:1px solid var(--line);border-radius:3px}
footer.app-footer{max-width:1100px;margin:24px auto 0;padding:12px 24px;text-align:right;
  font-size:.72rem;color:var(--muted);border-top:1px solid var(--line-soft)}
/* 配色の切り替え（#181）。**フッタに置く** ── ヘッダはログイン後にしか
   出ないが、配色はログインの有無とは関係がない（ログイン画面でも眩しい）。
   フッタは両アプリの全ページに必ずある唯一の場所である。

   JavaScript が無ければ出さない。無いときは従来どおり OS 追従で、
   押しても何も起きないボタンを見せない（この画面群の作法）。 */
/* JavaScript が無ければ出さない。押しても何も起きないボタンを見せない。
   隠し方はこの画面群の既存の作法に合わせる（`.js-only` を JS が外す）──
   別の仕組みを 2 つ持つと、片方を直したときにもう片方が取り残される。 */
.theme-switch{display:inline-flex;gap:0;align-items:center;margin-right:auto;
  border:1px solid var(--line-soft);border-radius:3px;overflow:hidden}
footer.app-footer .inner{max-width:none;display:flex;align-items:center;gap:12px}
.theme-switch button{appearance:none;background:transparent;border:0;
  padding:3px 9px;font:inherit;font-size:.72rem;color:var(--muted);cursor:pointer;line-height:1.9}
.theme-switch button+button{border-left:1px solid var(--line-soft)}
.theme-switch button:hover{background:var(--surface-2);color:var(--ink-2)}
/* いま効いている選択。`aria-pressed` を見る ── 見た目のための class を
   別に持つと、支援技術に伝わる状態と画面の状態がずれる。 */
.theme-switch button[aria-pressed="true"]{background:var(--surface);color:var(--ink);
  box-shadow:inset 0 0 0 1px var(--line-soft)}
/* ヘッダに置いたとき。フッタの `margin-right:auto`（左へ寄せる）は要らない。 */
.theme-switch.in-header{margin-right:0}

/* ==========================================================================
   左の常設の帯（#189・ADR 0017）
   ========================================================================== */
.app{display:grid;grid-template-columns:248px minmax(0,1fr);min-height:100vh}
.app > .col{min-width:0;display:flex;flex-direction:column}
/* **本題も縮めるようにする。** flex の項目は既定で `min-width:auto`＝
   min-content より小さくならない ── 折り返さない列を持つ表が 1 つあると、
   `main` ごと視野の外へ伸びる（#231・実測で 734px）。中で送る枠
   （表・コード・知識要素の一覧）はそれぞれ自分で持っている。 */
.app > .col > main{min-width:0;width:100%}
/* 開閉の部品は狭い画面だけのもの（#231）。広い画面では常設の帯に戻る。 */
.railtoggle,.rail .railopen{display:none}
.rail{background:var(--surface);border-right:1px solid var(--line);
  display:flex;flex-direction:column;position:sticky;top:0;height:100vh;
  overflow-y:auto}
.rail .brand{display:block;padding:14px 16px 12px;text-decoration:none;
  color:var(--ink);border-bottom:1px solid var(--line-soft)}
.rail .brand b{font-size:1rem;font-weight:700;display:block;line-height:1.35}
.rail .brand .side{font-size:.72rem;color:var(--muted)}
.rail .switch{padding:10px 16px;border-bottom:1px solid var(--line-soft);margin:0}
.rail .switch label{display:block;font-size:.68rem;letter-spacing:.08em;
  color:var(--muted);margin-bottom:3px}
.rail .switch select{width:100%;font-size:.82rem;padding:5px 7px}
.rail nav{flex:1;padding:6px 0}
.railnote{font-size:.72rem;color:var(--muted);padding:0 16px 12px;margin:0}

/* **階層はここで作る。** 大項目は全幅の帯で、小項目より字を小さくしない。
   小項目は帯より内側に字下げして従属を見せ、件数は同じ右端で揃える
   （揃っていないと縦に読み比べられない）。 */
.railgrp + .railgrp{margin-top:6px}
.railgrp .gh{font-size:.82rem;font-weight:700;letter-spacing:.06em;
  color:var(--ink);background:var(--ai-soft);padding:5px 16px;
  display:flex;align-items:center;gap:8px}
.railgrp .gh .n{font-family:var(--font-mono);font-size:.7rem;font-weight:400;
  color:var(--muted);margin-left:auto}
.railgrp .gi{padding:4px 8px 6px}
.rail a.nav{display:flex;align-items:center;gap:8px;
  padding:5px 10px 5px 16px;border-radius:3px;
  color:var(--ink-2);text-decoration:none;font-size:.86rem}
.rail a.nav:hover{background:var(--surface-2);color:var(--ink)}
.rail a.nav .t{flex:1;min-width:0}
/* 数字の補足（例: 確定処理の「自動確定待ち 12」・2026-09-25）。行を改めて小さく出す。 */
.rail a.nav{flex-wrap:wrap}
.rail a.nav .n{flex-basis:100%;font-size:.72rem;margin-top:-2px}
.rail a.nav .c{font-family:var(--font-mono);font-size:.75rem;color:var(--muted);
  min-width:2.6em;text-align:right;flex:none}
/* 人が押さないと進まない件数だけ琥珀。数え上げは薄いまま。 */
.rail a.nav .c.attn{color:var(--kin);font-weight:700;background:var(--kin-soft);
  border-radius:99px;padding:0 7px;min-width:0}
/* いま居る場所。**藍の縦罫**（移動の色・#185）。 */
.rail a.nav[aria-current]{background:var(--ai-soft);color:var(--ink);
  font-weight:700;box-shadow:inset 3px 0 0 var(--ai)}

/* 狭い画面。**帯を上に畳んで横に流す。** 縦に積むと帯だけで画面の 3 分の 1 を
   占め、本題が下に落ちる。**畳んだ時点で「左の帯」ではなくなるので、
   文言は位置を指してはいけない**（モックで一度書いて直した）。 */
@media (max-width:860px){
  /* **`1fr` ではなく `minmax(0,1fr)`。** 素の `1fr` は最小幅が min-content
     なので、縮まない中身（折り返さない列を持つ表など）があると、列ごと
     視野の外へ伸びる ── 畳んだはずの頁が横に動いていたのはこれ（#231）。
     広い幅の側は最初から `minmax(0,1fr)` で書いてある。 */
  .app{grid-template-columns:minmax(0,1fr)}
  .rail{position:static;height:auto;border-right:0;
    border-bottom:1px solid var(--line);
    flex-direction:row;flex-wrap:wrap;align-items:center;gap:12px;padding:6px 16px}
  .rail .brand,.rail .switch{border:0;padding:0}
  /* **添え字の行を詰める。** 本文の行送り（28px）を継ぐと、11px の字が
     25px の行箱に入る ── 実測で銘が 50px あり、文字は 33px しかなかった。 */
  .rail .brand .side{display:block;line-height:1.3}
  .rail .brand{flex:none}
  .rail .switch{flex:1;min-width:11rem}
  /* **横に送らせない**（#231）。以前は行き先を 1 本の帯に流して
     `overflow-x:auto` にしていたので、奥の行き先は横にスライドしないと
     見えなかった ── 移動のための部品が、移動を要求していた。

     畳んで、開いたら**縦に全部**出す。開閉は checkbox と label（素の
     HTML）で、script が無くても動く。 */
  /* **右端に置く。** 左に詰めると銘のすぐ隣に来て、押す場所が銘の長さで
     動く ── コース名は機関が決めるので、こちらでは決められない。右端なら
     どのコースでも同じ位置にある。`.switch` が無い画面では伸びる要素が
     無いので、`margin-left:auto` が要る（実測: 右端まで 179px 空いていた）。 */
  .rail .railopen{order:3;display:inline-flex;align-items:center;gap:6px;
    margin-left:auto;
    font-size:.85rem;font-weight:700;color:var(--ink);cursor:pointer;
    padding:6px 10px;border:1px solid var(--line);border-radius:3px}
  .rail .railopen:hover{background:var(--surface-2)}
  .railtoggle:focus-visible + .railopen{outline:2px solid var(--ai);outline-offset:2px}
  .railtoggle:checked + .railopen{background:var(--surface-2)}

  /* **行を分ける。** `width:100%` だけだと、折り返しの計算は
     `flex-basis` を見るので銘の右の細い列に入る（実測でそうなった）。 */
  .rail nav{order:4;flex:0 0 100%;display:none;padding:6px 0 2px}
  .railtoggle:checked ~ nav{display:block}
  /* 縦に積む ── 広い画面と同じ読み方（大項目の帯 + 字下げした小項目）。 */
  .railgrp{display:block;margin:0 0 6px}
  .railgrp + .railgrp{margin-top:0;border-left:0;padding-left:0}
  .railgrp .gh{font-size:.74rem}
  .railgrp .gi{display:block}
  .rail a.nav{padding:7px 10px 7px 18px}
  .railnote{order:5;padding:0}
}

/* デモコースの帯（#194）。**本文の頭に出す** ── 見出しより前に置くと
   コース名より先に注意書きを読ませることになり、毎ページ邪魔になる。
   見出しの直後で、最初に操作する前には必ず目に入る位置。 */
/* `.note` の 20px より広い ── 本文から切り離すための余白である（#215 まで
   `var(--s5)` を引いていたが、その変数はどこにも無く、宣言ごと落ちていた）。 */
.demo-banner{margin-bottom:28px}

/* 入口の面（#209）。**ログイン画面だけが体系の外に残っていた。**

   濃い帯（`.topbar`）は署名の入っている人にしか出ない ── 出すものが無い
   帯をログイン画面に流用すると、空の帯だけが浮く。代わりに**入口そのものを
   藍にする**。冠（濃い面を頁の頭に置く）と同じ判断を、面の全体に当てたもの。

   学習者とコンソールで同じ構図を使う。**同じ機関の同じシステムなので、
   教員が学習者の画面を開いたときに別のサービスに見えてはいけない。**

   間隔は px で書く ── この CSS に間隔の尺度は無い。 */
/* **入口はフッタを画面の外へ押し出してはいけない**（#212）。配色の切り替えは
   フッタにあり、ログイン前に触れられることがそこに置いた理由だった
   （`footer.app-footer` の注記）── `min-height:100vh` だと、その導線が
   必ず折り返しの下に落ちる。

   頁を縦の flex にして、残りの高さを面に渡す。**`:has()` で入口の頁だけに
   閉じる** ── `main` を常に flex にすると、余白の相殺が無くなって全頁の
   間隔が変わる。効かないブラウザでは下の `min-height` が控えとして残る。 */
body:has(.gate){min-height:100dvh;display:flex;flex-direction:column}
body:has(.gate) main{flex:1;display:flex;flex-direction:column}
/* **控えの `min-height` はここで外す。** 残すと flex が縮められず、
   フッタが折り返すほど狭い画面で控えの値ぶんだけはみ出す。 */
body:has(.gate) .gate{flex:1;min-height:0}
.gate{min-height:calc(100dvh - var(--gate-reserve));display:flex;flex-direction:column;
  justify-content:center;align-items:center;gap:28px;
  background:var(--head-bg);color:var(--head-ink);padding:48px 20px;
  /* `main` の余白と幅の制限を打ち消して、面を頁いっぱいに広げる
     （`main` は max-width:1100px・padding:32/24/80）。**入口に本文の段組みは
     要らず、藍が縁で切れていると帯の残骸に見える。** 左右は `main` の
     中央寄せごと外に出す必要があるので、負の余白ではなく視野幅で戻す。 */
  /* 幅は `auto` のまま、負の余白だけで外へ出す。**`width:100vw` を足すと
     二重にかかる** ── `100vw` は縦のスクロールバーを含み、`calc(50% - 50vw)`
     は `main` の内容ボックス基準なので、スクロールバーが場所を取る環境では
     両端がはみ出して横スクロールが生える。 */
  margin:-32px calc(50% - 50vw) -80px}
.gate-mark{text-align:center;max-width:30rem}
.gate-mark h1{color:var(--head-ink);border:0;margin:0 0 10px;
  font-size:2.4rem;letter-spacing:.04em}
/* **端数の行を作らない。** 案内文は入口に 1 つだけ置く短い文で、折り返すと
   「ます。」のように数文字だけが 2 行目に落ちる ── 1 行に収まらないこと
   自体より、その落ち方が読みにくい。`balance` は行の長さを揃えるので、
   折り返すときも同じくらいの 2 行になる。
   対応していない環境では通常の折り返しに戻るだけで、何も壊れない。 */
.gate-lead{color:var(--head-muted);font-size:.92rem;line-height:1.8;margin:0;
  text-wrap:balance}
/* 面は白。**押す場所を 1 つに絞る** ── 藍の上に藍の札を置くと、どこが
   操作なのか読み取りに一拍かかる。 */
.gate-card{background:var(--surface);color:var(--ink);border-radius:6px;
  padding:24px;width:min(26rem,100%);box-shadow:0 2px 18px rgba(0,0,0,.22)}
.gate-card form{margin:0}
/* ログインは**移動**であって判定ではない ── 朱ではなく藍（`--ai` の注記と
   同じ判断）。既定の `button` が朱なのでここで上書きする。 */
/* 地と文字を**両方**指定する。`button` の既定は `color:#fff` を継承させる
   形なので、地だけ替えると夜に白文字のまま明るい地へ載る（#212）。 */
.gate-go{width:100%;background:var(--go-bg);color:var(--go-ink);
  padding:12px 22px;font-size:.95rem;line-height:1.4}
.gate-note{color:var(--muted);font-size:.8rem;line-height:1.7;
  margin:14px 0 0;text-align:center;text-wrap:balance}
/* 管理側の入口（#326）。**構図は同じで、面の色だけが違う。**

   学習者の入口と同じ作りにするのは、同じ機関の同じシステムだからである
   （`login.html` の注記）。だが**どちらの扉の前にいるかは分からなければ
   ならない** ── 教員は 2 つの画面を並べて開く。構図まで変えると別のサービス
   に見えるので、変えるのは地の色だけにする。

   ここでの朱は**判定ではない**（判定の三色に混ぜない・`--shu` の注記）。
   「いまどちらの入口か」を言うだけの符牒で、この面から先には出てこない。

   置き換えるのは記号（`--head-*` と `--go-bg`）で、`.gate` の規則には触れ
   ない ── 2 つの入口が別の規則で描かれると、片方を直した日にもう片方が
   古いままになる。白文字の対比は藍と同じ水準で選んだ（昼 8.1:1・夜 5.5:1）。 */
.gate-admin{--head-bg:#5c1d16; --head-ink:#fbeeea; --head-muted:#d2a89f;
  --go-bg:#8f2f1b}
@media (prefers-color-scheme: dark){
  :root:not([data-theme="light"]) .gate-admin{--head-bg:#2a100c; --head-ink:#f2ddd8;
    --head-muted:#b98d84; --go-bg:#b5452f}
}
:root[data-theme="dark"] .gate-admin{--head-bg:#2a100c; --head-ink:#f2ddd8;
  --head-muted:#b98d84; --go-bg:#b5452f}
/* 入口に置く欄（`login_local.html`）。**札の中は本文の地**なので、
   通常の `.field` がそのまま効く。幅だけ札に合わせる。 */
.gate-card .field{margin:0 0 12px}
.gate-card .field input{width:100%}
.gate-card .actions{margin:16px 0 0}
.gate .note{margin-bottom:14px}
@media (max-width:480px){
  .gate{padding:32px 16px}
  .gate-mark h1{font-size:2rem}
  /* 機関の呼び名は長い（「龍大全学認証アカウントでログイン」で 16 字）。
     狭い画面では字を詰めて 1 行に収まりやすくする。**収まることは保証
     できない** ── 欄は 64 字まで受け付けるので、長い文言は折り返す。
     折り返しても読めるよう行間を持たせてあり、切り詰めはしない
     （機関が決めた名前を機械が縮めるほうが悪い）。 */
  .gate-go{font-size:.82rem;padding:12px 8px}
}

/* ==========================================================================
   携帯の幅（〜560px）
   ==========================================================================

   **教員も学習者も同じ体系で畳む。** 片方だけ直すと、同じ部品が画面に
   よって違う畳み方をする ── 学習者の画面で覚えた読み方が、教員の画面で
   通じなくなる。だから畳み方は `packages/webui` に 1 つ置く。

   対象の幅は 560px。860px 以下でレールは既に帯へ畳んでいるので、ここで
   扱うのは**その先の、1 行に 2 つ並べられない幅**である。 */
@media (max-width:560px){
  /* 頁の頭。**銘と出口を 1 行目に、身元を 2 行目に。** 以前は 3 つを
     1 行に詰めていて、名前が長いと押し釦まで折れていた（「ログア／ウト」）。
     出口（ログアウト）は幅が変わらないので、先に位置を決める。 */
  header.top .inner{flex-wrap:wrap;align-items:center;gap:6px 10px;padding:10px 16px}
  header.top .brand{order:1}
  /* 出口は 1 行目の右端へ。**間隔用の span では押せない** ── 折り返しの
     計算は `flex-basis` を見るので、基準 0 の要素は行を埋めない。 */
  header.top form{order:2;margin-left:auto}
  /* ここで行を分ける。身元とパスワード変更が 2 行目に並ぶ（以前は
     それぞれが 1 行を取り、帯が 115px あった）。 */
  /* **`spacer` は改行の役目だけ。行の間隔は行の側で取る。** ここに
     `row-gap` を効かせると、高さ 0 の行が隙間を 2 つ消費する ── 実測で
     上部バーは 93px あり、うち 6px が何も無い行のためだった。 */
  header.top .spacer{order:3;flex:0 0 100%;height:0;margin:0}
  header.top .inner{padding:8px 16px;gap:0 10px}
  /* 身元だけを 2 行目へ。**`.spacer` を巻き込まない** ── あれも `span` で、
     一緒に落とすと押し釦を右へ押す役が居なくなる（実際に銘の真横に並んだ）。 */
  header.top .inner > span:not(.spacer){order:4;font-size:.8rem;color:var(--head-muted);
    margin-top:6px}
  header.top button{padding:7px 12px;font-size:.8rem}
  .ctx .inner{padding:7px 16px}

  main{padding:20px 16px 56px}
  h1{font-size:1.35rem}

  /* **表は行を積む。** 列を横に送らせると、どの値がどの見出しのものか
     見出しが画面の外にあるあいだ分からない ── 表の意味が失われる。
     1 行を 1 枚の塊にし、各セルに見出しを添える（`data-label`）。

     添えるのはテンプレート側の仕事にした。**見出しはそのセルが何かを
     言う言葉**であって、機械が列の位置から推測してよいものではない。 */
  /* **この幅では表をすべて畳む。** 横に送る枠で包む案は採れなかった ──
     `display:block` にした表は内部が表のまま（無名の表ボックスができる）で、
     幅が親を押し広げ続ける。実測でそうなっていた（#231）。

     `data-label` が付いていない表は値だけが並ぶ。読めるが不十分なので、
     見出しを添えたものには `.stack` を付けて「済み」の印にしてある。 */
  table, table thead, table tbody, table tr, table td{display:block;width:auto}
  table thead{display:none}
  table tr{border:1px solid var(--line-soft);border-radius:4px;
    padding:10px 12px;margin:0 0 10px;background:var(--surface)}
  table td{border:0;padding:3px 0;white-space:normal;width:auto}
  table td.fit{width:auto}
  /* 見出しは値の前に、小さく。**空のセルは行ごと出さない** ── 見出しだけが
     並ぶと、無い値を探して読むことになる。 */
  table td[data-label]::before{content:attr(data-label);display:block;
    font-size:.7rem;letter-spacing:.06em;color:var(--muted)}
  table td:empty{display:none}

  /* 帯の中の並び。コンソールには「パスワード変更」が入る ── 身元と
     同じ行に置く（出口だけを 1 行目の右に残す）。 */
  header.top .inner > a:not(.brand){order:5;font-size:.8rem;margin-top:6px}
}

/* 副次のボタン（`button.minor`）。「コースの共通ルーブリックに復元」「外す」など
   は補助操作で、画面の一次操作（この問題を保存して更新する）
   と同じ朱の塊で並ぶと、どれを押せば保存されるのかが読めない。輪郭だけの
   小さめの釦にして、朱は保存に残す。 */
button.minor{background:transparent;color:var(--ink-2);border:1px solid var(--line);
  font-weight:600;font-size:.88rem;padding:7px 14px}
button.minor:hover{filter:none;background:var(--surface-2);border-color:var(--ink-2)}

/* 1 枚ずつ積む提出物の一覧（#283・学習者アプリ）。 */
.upload-list{margin:8px 0 0;padding-left:1.4em}
.upload-list li{display:flex;gap:10px;align-items:center;margin:4px 0}
.upload-list li .mono{flex:1 1 auto;word-break:break-all}
