/* ============================================================
 * game.css — かなあてのゲーム画面・結果・ホームのメニュー・配布用カード
 *
 * 仕様 §6-5 / §7 / §10。
 * - 色は tokens.css の変数を使うこと(独自カラー名は作らない)。
 * - 動きは CSS だけで書く(jQuery 等のライブラリは使わない)。
 * - prefers-reduced-motion: reduce では無限ループ系を全部止め、
 *   登場・裏返しは即時表示に切り替える(必須)。
 * ============================================================ */

/* --- タイルの判定色(§6-1)---------------------------------------- */
:root {
  --tile-hit:  #3FAE5C;
  --tile-near: #3B82F6;
  --tile-blow: #E0B23A;
  --tile-miss: #7A7A86;
  --tile-empty-border:  #C9C9D2;
  --tile-filled-border: #8A8A96;

  /* 動的寸法(board.js が実測して入れる) */
  --tile-size: 44px;
  --kbd-key-w: 32px;
  --kbd-key-h: 40px;
  --board-w: 200px;
}

html.cb {
  --tile-hit: #E69F00;
  --tile-near: #0072B2;
  --tile-blow: #CC79A7;
}

/* ============================================================
 * ホーム画面(§6-5)
 * ============================================================ */

/* --- Hero(2026-09-22 オーナー指示「TOP を Hero 化。フォントを大きくして横にキャラ」)---
   旧 appbar(小さな題字 + 📊/⚙)を畳んでここに統合した。2行の grid:
       1段目 = 大きな題字 | 📊 ⚙
       2段目 = ひとこと    | かなもん
   2段目の高さを決めるのは**かなもん**なので、en / de / ru の長いひとことが 3〜4行に
   なっても Hero の高さは変わらない(ひとことを全幅に敷くより縦が短く済む)。
   (!) 寸法は clamp。短い画面では下の @media (max-height: 700px) で詰める
       —— 360x640 + バナー予約でメニュー4行が画面内に残ることを実測して決めた値。 */
.hero-top {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  grid-template-areas:
    "title actions"
    "lead  mascot";
  align-items: center;
  column-gap: var(--space-sm);
  row-gap: var(--space-xs);
}

.hero-top__title {
  grid-area: title;
  margin: 0;
  font-size: clamp(2rem, 11vw, 2.75rem);
  font-weight: 800;
  line-height: 1.15;
  letter-spacing: 0.06em;
  color: var(--fg);
}

.hero-top__actions {
  grid-area: actions;
  display: flex;
  align-items: center;
  gap: var(--space-xs);
}

/* ひとことは tutorial.3 を使い回している(新しいキーを作らない)。
   題字が「何のアプリか」、この行が「なぜ毎日やるか」を 1行で言う。 */
.hero-top__lead {
  grid-area: lead;
  margin: 0;
  font-size: 0.8125rem;
  font-weight: 600;
  line-height: 1.5;
  color: var(--fg-muted);
}

/* 連続日数などの一言 */
.top-streak {
  margin: 0;
  text-align: center;
  font-size: 0.875rem;
  font-weight: 700;
  color: var(--fg-muted);
}

.top-streak[hidden] { display: none; }

.top-social {
  margin: 0;
  text-align: center;
  font-size: 12px;
  opacity: .7;
}
.top-social[hidden], .top-yesterday[hidden] { display: none; }

.top-yesterday {
  width: 100%;
  padding: var(--space-md);
  background: var(--bg-elev);
  border: 2px solid var(--line);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-sm);
  color: var(--fg);
  font: inherit;
  font-size: 13px;
  text-align: left;
  cursor: pointer;
}

/* ことばを おくる(2026-09-22 に設定から移設)。**主役のメニュー4つと競らせない**ので
   Jelly は当てず、きのうの答え(.top-yesterday)と同じ静かな札にする。 */
.top-submit {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  width: 100%;
  padding: var(--space-sm) var(--space-md);
  background: transparent;
  border: 2px dashed var(--line);
  border-radius: var(--radius-lg);
  color: var(--fg);
  font: inherit;
  cursor: pointer;
  transition: transform 120ms ease-out, background-color 120ms ease-out;
}
.top-submit:active {
  transform: translateY(2px);
  background: var(--bg-elev);
}
.top-submit__label {
  font-size: 0.9375rem;
  font-weight: 800;
}
.top-submit__sub {
  font-size: 0.75rem;
  font-weight: 600;
  color: var(--fg-muted);
}

/* メニュー */
.menu {
  display: flex;
  flex-direction: column;
  gap: var(--space-sm);
}

button.menu__item {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 2px;
  width: 100%;
  padding: var(--space-md);
  background: var(--bg-elev);
  border: 2px solid var(--line);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-sm);
  cursor: pointer;
  font: inherit;
  color: var(--fg);
  /* (!) 押した時に少し沈む */
  transition: transform 120ms ease-out, box-shadow 120ms ease-out;
}
button.menu__item:active {
  transform: translateY(2px);
  box-shadow: var(--shadow-sm);
}

.menu__label {
  font-size: 1.125rem;
  font-weight: 800;
}
.menu__sub {
  font-size: 0.75rem;
  font-weight: 600;
  opacity: 0.72;
}

/* 主役ボタン(§6-5)— 1.4倍(素の <button> 用。Jelly 版は下) */
button.menu__item--main {
  padding: calc(var(--space-md) * 1.4) var(--space-md);
  background: var(--gold);
  border-color: var(--gold-deep);
  color: var(--on-accent);
  animation: menu-float 4s ease-in-out infinite;
}
.menu__item--main .menu__label {
  font-size: 1.5rem;
}
.menu__item--main .menu__sub {
  font-size: 0.875rem;
  opacity: 0.8;
}

/* Jelly UI 版のメニュー(2026-09-22)。塗りは <jelly-button variant>(accent=ゴールド / white=地)、
   寸法は jelly-bridge.css と同じ流儀で `[size]` 付きのホストにトークンを上書きする
   (Jelly が shadow の :host に既定値を書くので、:root に置くと負ける)。
   中身は .menu__stack(見出し+説明の2行)。素の button 用の塗りは上の `button.menu__item`。 */
jelly-button.menu__item { display: block; width: 100%; }
jelly-button.menu__item[size] {
  --jelly-button-height: 66px;
  --jelly-button-radius: var(--radius-lg);
}
jelly-button.menu__item--main[size] { --jelly-button-height: 84px; }
jelly-button.menu__item--main { animation: menu-float 4s ease-in-out infinite; }
.menu__stack {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  line-height: 1.3;
}

@keyframes menu-float {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-2px); }
}

/* 他アプリ紹介(共通部品が入れる) */
.home-promo {
  width: 100%;
  max-width: var(--content-max);
  margin: 0 auto;
}

/* ============================================================
 * ゲーム画面(§6 / §7)
 * ============================================================ */

.screen--game {
  gap: var(--space-sm);
  /* 2026-09-22 マス拡大: 上 8px・下 0(下端の余白は .kbd が safe-area と --banner-reserve を持つ)。
     app.css の .screen(上 16 / 下 40 + safe-area + reserve)を上書きする。
     メッセージのトーストを絶対配置するための基準にもなる */
  position: relative;
  padding-block: 8px 0;
}

/* ゲームバー(上部帯) */
.gamebar {
  display: flex;
  align-items: center;
  gap: var(--space-sm);
  padding: var(--space-xs) var(--space-md);
  padding-top: calc(var(--space-xs) + env(safe-area-inset-top));
  min-height: 48px;
}

.gamebar__title {
  margin: 0;
  /* 題字は縮めない(欠けると何の画面か分からなくなる)。詰まるのは候補数の側。 */
  flex: 0 0 auto;
  min-width: 0;
  /* (!) **折り返させない。** 折り返すと gamebar が 2 行ぶんに伸びて盤面が下がる。
     日本語の「きょうの4もじ」+「こうほ のこり 31,390」は、Android の Noto Sans CJK
     (デスクトップのフォントより字幅が広い)で 411px 幅に収まらず実際に折り返した
     —— 2026-09-22 のリリース前検品。**ブラウザでは再現しない**ので実機で見ること。 */
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  font-size: 1.125rem;
  font-weight: 800;
  letter-spacing: 0.04em;
  color: var(--fg);
}

/* ============================================================
 * かなもん(マスコット・2026-09-22 オーナー指示「静かに動く」)
 *   gamebar の右端 52px。レイアウトの高さは増やさない(上下 -4px で 44px に収める)。
 *   動きは 2 本だけ: 外側 .kanamon が 9 秒で ±1.5deg 傾き、内側の絵が 5 秒で 1.5px 浮いて 2.5% 呼吸する。
 *   正解: .kanamon--happy を 2.8 秒付ける。喜び顔へ opacity で切り替え、外側が一度 6px ふわっと上がって戻る。
 *   (!) 外側と内側で transform を分ける(同じ要素に 2 本載せると食い合う。okane の mascot と同じ)
 * ============================================================ */
.kanamon {
  flex: 0 0 auto;
  position: relative;
  width: 52px;
  height: 52px;
  margin: -4px 0 -4px 4px;    /* 52px の絵を 44px の枠に載せ、gamebar(min-height 48)の高さを増やさない(実測 52→52)。
                                 右寄せはタイトルの flex:1 が担う(候補数が間に入る) */
  cursor: pointer;
  user-select: none;
  -webkit-user-select: none;
  -webkit-tap-highlight-color: transparent;
  animation: kanamon-sway 9s ease-in-out infinite;
}
.kanamon__img {
  position: absolute;
  inset: 0;
  display: block;
  width: 100%;
  height: 100%;
  object-fit: contain;
  transform-origin: 50% 100%;
  /* ライト背景(--cream)は体の色と同じなので、薄い落ち影で輪郭の外に段差を作る(紺背景ではほぼ見えない) */
  filter: drop-shadow(0 2px 3px rgba(30, 42, 68, 0.28));
  animation: kanamon-breathe 5s ease-in-out infinite;
  transition: opacity 260ms ease;
}
.kanamon__img--happy { opacity: 0; }
.kanamon--happy .kanamon__img--idle { opacity: 0; }
.kanamon--happy .kanamon__img--happy { opacity: 1; }
.kanamon--happy { animation: kanamon-lift 2.8s ease-in-out both; }
@keyframes kanamon-sway {
  0%, 100% { transform: rotate(-1.5deg); }
  50%      { transform: rotate(1.5deg); }
}
@keyframes kanamon-breathe {
  0%, 100% { transform: translateY(0) scale(1, 1); }
  50%      { transform: translateY(-1.5px) scale(1.01, 1.025); }
}
@keyframes kanamon-lift {
  0%   { transform: translateY(0); }
  18%  { transform: translateY(-6px); }
  55%  { transform: translateY(-2px); }
  100% { transform: translateY(0); }
}

/* ホーム Hero の大きい版(2026-09-22)。動きはゲーム画面と同じ(静かに揺れて呼吸する)で、
   違うのは寸法と足元の台だけ。
   (!!) ライトテーマでは体の色 #FAF3E3 が背景 --cream と**同じ値**なので、
        52px の時に効いていた薄い落ち影だけでは、この大きさだと輪郭が背景に溶ける。
        --bg-elev の丸い台を敷いて段差を作る(紺のダークでは control な明るい円として馴染む)。 */
/* 絵 + 名前の包み。grid の位置決めはこちらが持つ(2026-09-22 オーナー指示で名前を下に置いた) */
.hero-top__mascot {
  grid-area: mascot;
  justify-self: end;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  margin: 0;
}
.hero-top__mascot-name {
  font-size: 0.6875rem;
  font-weight: 700;
  letter-spacing: 0.08em;
  line-height: 1;
  color: var(--fg-muted);
}

.kanamon--hero {
  width: clamp(76px, 26vw, 108px);
  height: clamp(76px, 26vw, 108px);
  margin: 0;
}
.kanamon--hero::before {
  content: "";
  position: absolute;
  inset: 8% 2% 0;
  border-radius: 50%;
  background: var(--bg-elev);
  opacity: 0.66;
}
.kanamon--hero .kanamon__img {
  filter: drop-shadow(0 3px 6px rgb(30 42 68 / 0.24));
}

/* 短い画面(360x640 や横向き)では Hero を詰める。メニュー4行を画面内に残すのが優先 */
@media (max-height: 700px) {
  .hero-top__title { font-size: clamp(1.75rem, 9vw, 2.25rem); }
  .kanamon--hero { width: 76px; height: 76px; }
}

/* メッセージ帯 */
/* 2026-09-22 マス拡大: 常時 36px の枠をやめ、盤面とキーボードの隙間に重ねるトーストにした。
   位置は board.js が実測して入れる --kbd-h(キーボードの実高)から逆算する */
.game-msg {
  position: absolute;
  left: 16px;
  right: 16px;
  /* 盤面の 1 行目に重ねる(メッセージが出る時点で 1 行目は判定済みか入力中の行より重要度が低い。
     下側に置くと入力中の最終行やキーボードの最上段を隠すので上に置く)。--gamebar-h は board.js が実測して入れる */
  top: calc(var(--gamebar-h, 52px) + 14px);
  z-index: 5;
  margin: 0 auto;
  width: fit-content;
  max-width: calc(100% - 32px);
  padding: 6px 14px;
  border-radius: var(--radius-pill);
  background: var(--bg-elev);
  box-shadow: 0 2px 10px rgba(0, 0, 0, 0.18);
  font-size: 0.875rem;
  font-weight: 700;
  color: var(--coral);
  text-align: center;
  pointer-events: none;
  transition: opacity 200ms;
}
.game-msg:not(.is-on) { opacity: 0; visibility: hidden; }   /* visibility も切る(.screen > * の登場アニメが opacity を 1 に戻すため) */
.game-msg:empty { display: none; }

/* のこり候補数(gamebar の右側・かなもん の左) */
.game-cands {
  font-size: 12px;
  text-align: right;
  opacity: .7;
  margin: 0;
  white-space: nowrap;
  /* 題字より先にこちらが詰まるようにする(副次情報)。余った幅を受け取り、
     入らなければ game.js の fitCands() が字を小さくする。 */
  flex: 1 1 auto;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
}
.game-cands[hidden] { display: none; }

/* ヒント帯 */
.hintbar {
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  align-items: center;
  justify-content: center;
  gap: 4px;
  padding: var(--space-xs) var(--space-md);
}
.hintbar[hidden] { display: none; }

button.hintbar__btn {
  appearance: none;
  border: 2px solid var(--gold);
  background: var(--bg-elev);
  color: var(--accent);
  border-radius: var(--radius-pill);
  padding: 6px 14px;
  font: inherit;
  font-weight: 700;
  cursor: pointer;
}
/* Jelly 版のヒントボタン(2026-09-22): 行に収まる 40px のピル */
jelly-button.hintbar__btn[size] {
  --jelly-button-height: 40px;
  --jelly-button-radius: var(--radius-pill);
}
.hintbar__msg {
  flex-basis: 100%;
  margin: 0;
  font-size: 0.8125rem;
  font-weight: 700;
  color: var(--accent);
  text-align: center;
}
.hintbar__giveup {
  appearance: none;
  border: 0;
  border-bottom: 1px solid currentColor;
  background: transparent;
  color: var(--fg-muted);
  padding: 4px 6px;
  font: inherit;
  font-size: 12px;
  cursor: pointer;
}

/* ----- 盤面 ----- */
.board {
  flex: none;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 6px;
  width: 100%;
  /* (!) バナーの余白はここに持たせない。
     盤面の下にはキーボードがあるので、余白は画面の下端 (#screen-game) が持つ。
     ここに padding を足すと calcTileSize() の計算と二重になり、
     キーボードの最下段が画面からはみ出す(2026-09-21 実測で発生)。 */
}

.board__row {
  display: grid;
  grid-template-columns: repeat(var(--cols, 4), var(--tile-size));
  gap: 6px;
  /* 結果確定後は色維持 */
}

/* ----- タイル ----- */
.tile {
  width: var(--tile-size);
  height: var(--tile-size);
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-elev);
  color: var(--fg);
  font-size: calc(var(--tile-size) * 0.5);
  font-weight: 700;
  border: 2px solid var(--tile-empty-border);
  border-radius: 10px;
  position: relative;
  /* 裏返しは回転で表現。transform-style を保つ */
  transition: background-color 200ms ease-out, border-color 200ms ease-out, color 200ms ease-out;
}

/* 入力中(文字が入っているだけ。まだ判定されていない) */
.tile:not(:empty):not(.tile--hit):not(.tile--near):not(.tile--blow):not(.tile--miss) {
  border-color: var(--tile-filled-border);
}

/* 判定後 */
.tile--hit {
  background: var(--tile-hit);
  border-color: var(--tile-hit);
  color: #FFFFFF;
}
.tile--near {
  background: var(--tile-near);
  border-color: var(--tile-near);
  color: #FFFFFF;
}
.tile--blow {
  background: var(--tile-blow);
  border-color: var(--tile-blow);
  color: #FFFFFF;
}
.tile--miss {
  background: var(--tile-miss);
  border-color: var(--tile-miss);
  color: #FFFFFF;
}

/* 前の行で当たった文字を引き継いだタイル(入力行のみ)。判定色の付いた行には付かない */
.tile.tile--carry:not(.tile--hit):not(.tile--near):not(.tile--blow):not(.tile--miss) {
  border-color: var(--tile-hit);
  color: var(--tile-hit);
}
.tile.tile--cursor {
  border-color: var(--tile-near);
  border-width: 3px;
}

/* 色覚多様性のため、状態記号をタイル右下に置く(§6-1) */
.tile::after {
  content: attr(data-glyph);
  position: absolute;
  right: 3px;
  bottom: 1px;
  font-size: 10px;
  line-height: 1;
  opacity: 0.92;
}
.tile:not([data-glyph])::after { content: ''; }

/* 入力中の pop(§6-4) */
@keyframes tile-pop {
  0%   { transform: scale(1); }
  50%  { transform: scale(1.08); }
  100% { transform: scale(1); }
}
.tile--pop {
  animation: tile-pop 80ms ease-out;
}

/* 裏返し(§6-4)— rotateX 0→360 */
@keyframes tile-flip {
  0%   { transform: rotateX(0deg); }
  100% { transform: rotateX(360deg); }
}
.tile--flip {
  animation: tile-flip 350ms ease-in-out;
}

/* 辞書外の入力で行を横に揺らす */
@keyframes row-shake {
  0%, 100% { transform: translateX(0); }
  20%      { transform: translateX(-8px); }
  40%      { transform: translateX(8px); }
  60%      { transform: translateX(-6px); }
  80%      { transform: translateX(4px); }
}
.board__row--shake {
  animation: row-shake 300ms ease-in-out;
}

/* ----- キーボード ----- */
.kbd {
  /* 下端バナーの予約分(--banner-reserve は ads.js が実測して入れる)。
     2026-09-22 まで max(60px, …) で広告が無くても 60px 空けていたが、nextgen のバナーは
     ネイティブ側で WebView を縮めるので固定 60px は無駄だった(マス拡大のため撤去) */
  margin-bottom: var(--banner-reserve, 0px);
  display: flex;
  flex-direction: column;
  align-items: stretch;
  gap: 4px;
  padding: 8px 16px;
  padding-bottom: calc(8px + env(safe-area-inset-bottom));
  background: var(--bg-elev);
  border-top: 1px solid var(--line);
}

.kbd__grid {
  display: grid;
  grid-template-columns: repeat(10, var(--kbd-key-w));
  grid-auto-rows: var(--kbd-key-h);
  gap: 4px;
  justify-content: center;
}

.kbd__cell {
  width: var(--kbd-key-w);
  height: var(--kbd-key-h);
}
.kbd__cell--empty { visibility: hidden; }

.kbd__key {
  appearance: none;
  font: inherit;
  font-size: calc(var(--kbd-key-h) * 0.5);
  font-weight: 800;
  background: var(--bg);
  color: var(--fg);
  border: 1px solid var(--line);
  border-radius: 8px;
  cursor: pointer;
  /* 押した時の沈み */
  transition: transform 80ms ease-out, background-color 200ms, color 200ms, border-color 200ms;
  min-width: 0;
  min-height: 0;
  position: relative;
}
.kbd__key:active {
  transform: translateY(1px);
}

/* キーボード色(各ベースキーに「最良の状態」を反映) */
.kbd__key--hit  { background: var(--tile-hit);  color: #FFFFFF; border-color: var(--tile-hit); }
.kbd__key--near { background: var(--tile-near); color: #FFFFFF; border-color: var(--tile-near); }
.kbd__key--blow { background: var(--tile-blow); color: #FFFFFF; border-color: var(--tile-blow); }
.kbd__key--miss { background: var(--tile-miss); color: #FFFFFF; border-color: var(--tile-miss); }

.kbd__key__memo {
  position: absolute;
  top: 1px;
  right: 3px;
  font-size: 10px;
  line-height: 1;
  pointer-events: none;
}
.kbd__key__memo--x { color: var(--tile-miss); }
.kbd__key__memo--o { color: var(--tile-hit); }

/* 変化形の印(キーの下部)。一族の誰かが判定済みのキーにだけ出る。
   2026-09-25 オーナー「未使用か使用済みか分かりにくい。最下段の ゛ ゜ くらい大きく」で作り直した
   (旧: 右下の 12px のチップ。未判定を 45% に薄めていたので、かえって「使用済み」に見えた)。
   ・まだ打っていない(open) = 色無し。背景は透明で、字だけをはっきり描く → 「まだ試せる」が目に入る
   ・打って判定済み(miss / blow / hit) = タイルと同じ色で塗り、少し沈める → 済んだものは目立たない
   ゛ ゜ は board.js が SVG で描く(最下段の ゛ ゜ キーと同じ字形)。 */
.kbd__key--marked {
  /* 字は上半分へ寄せて少し小さく(印と重ならないように。行箱の高さも字の大きさに詰める) */
  font-size: calc(var(--kbd-key-h) * 0.4);
  line-height: 1;
  padding-bottom: calc(var(--kbd-key-h) * 0.42);
}
.kbd__key__vmarks {
  position: absolute;
  left: 1px;
  right: 1px;
  bottom: 2px;
  height: calc(var(--kbd-key-h) * 0.4);
  display: flex;
  justify-content: center;
  gap: 1px;
  pointer-events: none;
}
.kbd__key__vmark {
  flex: 1 1 0;
  min-width: 0;
  max-width: 22px;
  height: 100%;
  border-radius: 4px;
  border: 1px solid var(--line);
  box-sizing: border-box;
  font-size: calc(var(--kbd-key-h) * 0.3);
  line-height: 1;
  font-weight: 800;
  display: flex;
  align-items: center;
  justify-content: center;
  overflow: hidden;
  color: var(--fg);
  background: transparent;
}
.kbd__key__vmark svg {
  width: 100%;
  height: 100%;
  padding: 1px 0;
  box-sizing: border-box;
  fill: none;
  stroke: currentColor;
  stroke-width: 2.6;
  stroke-linecap: round;
}
.kbd__key__vmark--miss { background: var(--tile-miss); border-color: var(--tile-miss); color: #FFFFFF; opacity: 0.75; }
.kbd__key__vmark--blow { background: var(--tile-blow); border-color: var(--tile-blow); color: #FFFFFF; opacity: 0.85; }
.kbd__key__vmark--hit  { background: var(--tile-hit);  border-color: var(--tile-hit);  color: #FFFFFF; opacity: 0.85; }
/* 面が塗られているキー(hit/near/blow/miss)の上では、色無し(open)は白い字 + 白の細枠、
   判定済みは白の枠で面との段差を作る */
.kbd__key--hit  .kbd__key__vmark, .kbd__key--near .kbd__key__vmark,
.kbd__key--blow .kbd__key__vmark, .kbd__key--miss .kbd__key__vmark { border-color: rgba(255,255,255,0.8); color: #FFFFFF; }

html.cb .tile--hit::after,
html.cb .tile--near::after,
html.cb .tile--blow::after,
html.cb .kbd__key--hit::after,
html.cb .kbd__key--near::after,
html.cb .kbd__key--blow::after {
  position: absolute;
  top: 1px;
  right: 3px;
  bottom: auto;
  color: #FFFFFF;
  font-size: 10px;
  line-height: 1;
  opacity: .85;
  pointer-events: none;
}
html.cb .tile--hit::after, html.cb .kbd__key--hit::after { content: '●'; }
html.cb .tile--near::after, html.cb .kbd__key--near::after { content: '◆'; }
html.cb .tile--blow::after, html.cb .kbd__key--blow::after { content: '▲'; }
html.cb .tile--miss::after { content: ''; }

/* 最下段 */
/* (!!) 2026-09-25: ん を五十音の段へ移した(わ列)あとも repeat(6) のままで**右端に空の列**が残り、
   行の高さも中身なりの 29px(五十音キーは 44px)だった。いちばん押す きめる が小さく、
   段の右端も揃っていなかった。キー 5 つに合わせ、けす・きめる を広く、高さは五十音キーと同じに。 */
.kbd__bottom {
  display: grid;
  grid-template-columns: 0.85fr 1fr 1fr 1fr 1.3fr 1.7fr;   /* 切り替え ゛ ゜ 小 けす きめる */
  grid-auto-rows: var(--kbd-key-h);
  gap: 4px;
  margin-top: 4px;
  /* PC ではキー幅に上限(48px)があるので、五十音の段と同じ幅に揃える。スマホは 100% の方が狭いので従来どおり */
  width: min(100%, calc(10 * var(--kbd-key-w) + 36px));
  margin-inline: auto;
}
.kbd__bottom .kbd__key {
  font-size: calc(var(--kbd-key-h) * 0.42);
  /* (!!) **折り返させない。** 折り返すと scrollWidth == clientWidth のままなので
     board.js の fitBottomLabels() が「収まっている」と判断して縮めず、
     キーの中で 2 行になる(ja の「きめる」が Android で実際にそうなった。
     2026-09-22 のリリース前検品。**ブラウザでは字幅が狭く再現しない**)。
     nowrap にすると横へ溢れるので実測で拾えるようになる。 */
  white-space: nowrap;
}
/* ことのは式(設定で切り替え。board.js の KBD_FULL_LOWER): 清音 5 段と、濁音・半濁音・小書き 5 段の区切り線 */
.kbd__sep {
  height: 2px;
  border-radius: 1px;
  background: var(--fg-muted);
  opacity: 0.45;
  width: min(100%, calc(10 * var(--kbd-key-w) + 36px));
  margin: 1px auto;
}
/* ゛ ゜ 小 を出さないので けす / きめる の 2 つ */
.kbd--full .kbd__bottom { grid-template-columns: 0.85fr 1fr 1.6fr; }
/* 配列の切り替えキー(最下段の左端)。絵 + 短い語の 2 段。語は key の font-size に比例(fitBottomLabels で縮む) */
.kbd__key--layout {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 2px;
  padding: 0 2px;
}
.kbd__layout-icon {
  width: 60%;
  max-width: 26px;
  height: auto;
  max-height: 45%;
  fill: currentColor;
  pointer-events: none;
}
.kbd__layout-line { stroke: currentColor; stroke-width: 1.2; fill: none; }
/* ことのは式では最下段が 3 キーで幅に余裕があるので、絵と語を横に並べて語を大きく */
.kbd--full .kbd__key--layout { flex-direction: row; gap: 6px; }
.kbd--full .kbd__layout-icon { width: 22px; max-height: 70%; }
.kbd--full .kbd__layout-label { font-size: 0.95em; }
.kbd__layout-label {
  font-size: 0.62em;
  line-height: 1;
  font-weight: 800;
  pointer-events: none;
}

.kbd__key--mod {
  background: var(--bg);
  color: var(--fg-muted);
}
/* ゛ ゜ キーの印(board.js が SVG で描く)。キーの高さに比例して中央に */
.kbd__key--mark {
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0;
}
.kbd__mark {
  width: calc(var(--kbd-key-h) * 0.62);
  height: calc(var(--kbd-key-h) * 0.62);
  fill: none;
  stroke: currentColor;
  stroke-width: 2.6;
  stroke-linecap: round;
  pointer-events: none;
}
.kbd__key--act {
  background: var(--line);
  color: var(--fg);
}
.kbd__key--enter {
  background: var(--accent);
  color: #FFFFFF;
  border-color: var(--accent);
}

/* ヒント使用時(§8): ヒントの行だけ濃く残して枠で示し、ほかの仮名キーを薄める。次に きめる で解除。
   最下段(゛ ゜ 小 けす きめる)は薄めない —— 2026-09-23 まで全部 30% にしていて「止まった」ように見えた。
   薄めたキーでも判定色(miss / blow)が読めるよう 0.5 に留める。 */
.kbd--dim .kbd__grid .kbd__key:not(.kbd__key--hintrow) { opacity: 0.5; }
.kbd--dim .kbd__key--hintrow { box-shadow: 0 0 0 2px var(--accent); }

/* 完了後はロック */
.kbd--locked { pointer-events: none; opacity: 0.6; }

/* ============================================================
 * 結果カード(§10)
 * ============================================================ */

.result {
  position: absolute;
  inset: 0;
  display: flex;
  /* (!) 中身が画面より高い時(短い画面・みんなの記録が付いた時)に上下が切れて押せなくならないよう、
     縦にスクロールできるようにし、中央寄せはカード側の margin:auto で行う
     (align-items:center のままだと、はみ出した上端にはスクロールしても届かない) */
  align-items: flex-start;
  justify-content: center;
  overflow-y: auto;
  -webkit-overflow-scrolling: touch;
  padding: var(--space-md);
  background: rgba(0, 0, 0, 0.45);
  z-index: 10;
}
.result > .result__card { margin: auto 0; }
.result[hidden] { display: none; }

.result__card {
  width: 100%;
  max-width: 420px;
  background: var(--bg-elev);
  border-radius: var(--radius-lg);
  padding: var(--space-lg);
  box-shadow: var(--shadow-lg);
  display: flex;
  flex-direction: column;
  gap: var(--space-md);
  /* 登場:60ms ずつ階段状 */
  animation: result-in 320ms ease-out;
}

@keyframes result-in {
  from { opacity: 0; transform: translateY(16px) scale(0.98); }
  to   { opacity: 1; transform: translateY(0) scale(1); }
}

.result__head {
  margin: 0;
  font-size: 1.75rem;
  font-weight: 800;
  text-align: center;
  color: var(--accent);
}

.result__answer {
  text-align: center;
  border-top: 1px solid var(--line);
  border-bottom: 1px solid var(--line);
  padding: var(--space-md) 0;
}
.result__answer-label {
  margin: 0 0 4px;
  font-size: 0.75rem;
  color: var(--fg-muted);
}
.result__answer-main {
  margin: 0;
  display: flex;
  align-items: baseline;
  justify-content: center;
  gap: 8px;
}
.result__answer-kana {
  font-size: 2rem;
  font-weight: 800;
  color: var(--fg);
}
.result__answer-kanji {
  font-size: 1rem;
  color: var(--fg-muted);
}
.result__answer-gloss {
  margin: 6px 0 0;
  font-size: 0.8125rem;
  color: var(--fg-muted);
}
.result__detail {
  display: inline-block;
  margin-top: 8px;
  font-size: 0.875rem;
  color: var(--sky);
  text-decoration: underline;
  cursor: pointer;
}

.result__stats {
  display: flex;
  flex-direction: column;
  gap: 4px;
}
/* 毎日のおしらせの誘い(2026-09-25)。主役(シェア)と競らせないので白・細め、いらない はテキスト */
.result__notify {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
}
jelly-button.result__notify-yes { display: block; width: 100%; }
button.result__notify-yes {
  width: 100%;
  appearance: none;
  border: 2px solid var(--line);
  background: var(--bg-elev);
  color: var(--fg);
  border-radius: var(--radius-md);
  padding: var(--space-sm) var(--space-md);
  font: inherit;
  font-weight: 700;
  cursor: pointer;
}
.result__notify-no {
  appearance: none;
  border: 0;
  background: none;
  color: var(--fg-muted);
  font: inherit;
  font-size: 12px;
  padding: 6px 12px;
  cursor: pointer;
}
/* 自分の盤面の色(2026-09-25)。共有されるグリッドと同じ見え方 */
.result__grid {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 4px;
}
.result__grid-row { display: flex; gap: 4px; }
.result__grid-cell {
  width: 20px;
  height: 20px;
  border-radius: 4px;
  background: var(--tile-miss);
}
.result__grid-cell--hit  { background: var(--tile-hit); }
.result__grid-cell--near { background: var(--tile-near); }
.result__grid-cell--blow { background: var(--tile-blow); }
.result__stat {
  margin: 0;
  text-align: center;
  font-weight: 700;
  font-size: 0.875rem;
}

button.result__share {
  appearance: none;
  border: 0;
  background: var(--money-green);
  color: #FFFFFF;
  border-radius: var(--radius-md);
  padding: var(--space-md);
  font: inherit;
  font-size: 1.125rem;
  font-weight: 800;
  cursor: pointer;
  box-shadow: var(--shadow-sm);
  transition: transform 80ms ease-out;
}
button.result__share:active { transform: translateY(1px); }

/* Jelly 版(2026-09-22): シェア=mint(緑)・つぎへ=white。どちらも block */
jelly-button.result__share,
jelly-button.result__next { display: block; width: 100%; }
jelly-button.result__share[size] { --jelly-button-font-size: 1.125rem; }

button.result__next {
  appearance: none;
  border: 2px solid var(--line);
  background: var(--bg-elev);
  color: var(--fg);
  border-radius: var(--radius-md);
  padding: var(--space-sm) var(--space-md);
  font: inherit;
  font-weight: 700;
  cursor: pointer;
}

.result__tomorrow {
  margin: 0;
  text-align: center;
  font-size: 0.8125rem;
  color: var(--fg-muted);
}

.result__social {
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.result__social-title {
  margin: 0;
  font-size: 14px;
  font-weight: 700;
}
.result__social-line, .result__social-rank {
  margin: 0;
  font-size: 12px;
  color: var(--fg-muted);
}
.result__social-you {
  margin: 0;
  font-size: 16px;
  font-weight: 700;
  color: var(--accent);
}
.result__mine {
  margin: 0;
  font-size: 16px;
  font-weight: 700;
  color: var(--accent);
  text-align: center;
}
.result__giveup {
  align-self: center;
  border-bottom: 1px solid currentColor;
  color: var(--fg-muted);
  padding: 4px 6px;
  font-size: 12px;
  text-decoration: none;
}
.result__social-top {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--space-sm);
}
.result__social-sub {
  margin: 0 0 2px;
  font-size: 12px;
  font-weight: 700;
}
.result__social-word {
  display: flex;
  justify-content: space-between;
  gap: 8px;
  font-size: 12px;
}

/* ============================================================
 * 分布バー(成績・結果で使う)
 * ============================================================ */
/* (!) ラベルの列は固定 24px だと「はずれ」が 2 行に折れ、Kaybedilen / Проигрыши はさらに崩れる。
   行ごとの grid では列幅が揃わないので、.dist 自体を 3 列の grid にして行は display:contents。
   ラベルの列は全行でいちばん長いラベルの幅になる(2026-09-25)。 */
.dist {
  display: grid;
  grid-template-columns: max-content 1fr 32px;
  align-items: center;
  column-gap: 8px;
  row-gap: 4px;
  font-size: 0.75rem;
  font-variant-numeric: tabular-nums;
}
.dist__row { display: contents; }
.dist__label { color: var(--fg-muted); white-space: nowrap; min-width: 1.5em; }
.dist__bar {
  height: 8px;
  background: var(--line);
  border-radius: 4px;
  overflow: hidden;
}
.dist__fill {
  height: 100%;
  background: var(--fg-muted);
  border-radius: 4px;
}
.dist__count {
  text-align: right;
  color: var(--fg);
}
.dist__row--hi .dist__fill { background: var(--money-green); }
.dist__row--hi .dist__label { color: var(--fg); font-weight: 800; }

/* ============================================================
 * せいせき(stats.js)
 * ============================================================ */
.stat {
  display: flex;
  flex-direction: column;
  gap: var(--space-lg);
}
.stat__sec {
  display: flex;
  flex-direction: column;
  gap: var(--space-sm);
}
.stat__title {
  margin: 0;
  font-size: 1.125rem;
  font-weight: 800;
}
.stat__sub {
  margin: 6px 0 0;
  font-size: 0.875rem;
  color: var(--fg-muted);
}
.stat__grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--space-sm);
}
.stat__cell {
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: var(--space-sm);
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.stat__cell-label {
  font-size: 0.6875rem;
  color: var(--fg-muted);
}
.stat__cell-value {
  font-size: 1.25rem;
  font-weight: 800;
  color: var(--fg);
  font-variant-numeric: tabular-nums;
}
.stat__cell-sub {
  font-size: 0.75rem;
  color: var(--accent);
}

.stat__social-sub {
  display: flex;
  flex-direction: column;
  gap: var(--space-xs);
}
.stat__social-title {
  margin: 0;
  font-size: .875rem;
}
.stat__social-line {
  margin: 0;
  color: var(--fg-muted);
  font-size: .75rem;
}

/* ============================================================
 * アーカイブ(game.js)
 * ============================================================ */
.archive {
  display: flex;
  flex-direction: column;
  gap: var(--space-md);
}
.archive__lead {
  margin: 0;
  font-size: 0.875rem;
  color: var(--fg-muted);
}
.archive__list {
  list-style: none;
  padding: 0;
  margin: 0;
  display: flex;
  flex-direction: column;
  gap: var(--space-xs);
}
.archive__item {
  display: grid;
  grid-template-columns: 88px minmax(0, 1fr) auto;
  align-items: center;
  gap: var(--space-sm);
  padding: var(--space-sm);
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
}
.archive__num {
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.archive__hash {
  font-weight: 800;
}
.archive__date {
  font-size: 0.6875rem;
  color: var(--fg-muted);
}
.archive__status {
  display: flex;
  flex-direction: column;
  gap: 2px;
  font-size: 0.75rem;
  min-width: 0;
}
.archive__tag {
  display: inline-block;
  padding: 1px 6px;
  border-radius: 4px;
  background: var(--bg);
  border: 1px solid var(--line);
  color: var(--fg-muted);
}
.archive__cta {
  display: flex;
  gap: 4px;
}
button.archive__play,
button.archive__unlock {
  appearance: none;
  border: 1px solid var(--line);
  background: var(--bg);
  color: var(--fg);
  font: inherit;
  font-weight: 700;
  border-radius: var(--radius-sm);
  padding: 4px 10px;
  cursor: pointer;
}
/* Jelly 版(2026-09-22): 4/5=accent・広告解放=white。一覧の行に収まる 40px。
   (!) Jelly の既定は --jelly-button-min-width: 168px。そのままだと 4/5 の2つで
   340px になり、360px 幅の行から 133px はみ出す(2026-09-23 実機で発覚。
   .screen の overflow-x:hidden に隠れて scrollWidth では検出できない)。 */
jelly-button.archive__play[size],
jelly-button.archive__unlock[size] {
  --jelly-button-height: 40px;
  --jelly-button-radius: var(--radius-sm);
  --jelly-button-font-size: 0.9375rem;
  --jelly-button-padding-inline: 12px;
}
jelly-button.archive__play[size] { --jelly-button-min-width: 56px; }
/* 解放ボタンは行に 1 つだけなので幅は文言なりだが、上限を切らないと
   文言の長い言語(it/nl/de/ru)で行から溢れる。jelly-button の中身は
   nowrap なので、上限に当たった言語ではラベルが切れる(ja は 145px で収まる)。 */
jelly-button.archive__unlock[size] {
  --jelly-button-min-width: 0px;
  --jelly-button-font-size: 0.8125rem;
  max-width: 168px;
}
button.archive__play {
  background: var(--gold);
  color: var(--on-accent);
  border-color: var(--gold-deep);
}
.archive__empty {
  text-align: center;
  color: var(--fg-muted);
}

/* ============================================================
 * トースト(共通 — app.js が appendChild で挿入)
 * ============================================================ */
.toast {
  position: fixed;
  left: 50%;
  bottom: calc(var(--space-xl) + env(safe-area-inset-bottom));
  transform: translateX(-50%);
  background: rgba(30, 42, 68, 0.92);
  color: #FFFFFF;
  padding: 10px 16px;
  border-radius: var(--radius-pill);
  font-size: 0.875rem;
  font-weight: 700;
  opacity: 0;
  pointer-events: none;
  transition: opacity 300ms;
  z-index: 100;
}
.toast.is-on { opacity: 1; }

/* ============================================================
 * チュートリアル
 * ============================================================ */
.tutorial {
  position: fixed;
  inset: 0;
  background: var(--bg);
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: var(--space-md);
  /* (!) targetSdk 36 の edge-to-edge 強制で、position:fixed の全画面オーバーレイは
         ステータスバー/ナビゲーションバーの下まで広がる。セーフエリアぶん内側に寄せる
         (2026-09-22 のリリース前検品。スキップが時計の下に隠れていた)。 */
  padding: calc(var(--space-lg) + env(safe-area-inset-top)) var(--space-lg)
           calc(var(--space-lg) + env(safe-area-inset-bottom));
  z-index: 200;
}
.tutorial__skip {
  position: absolute;
  /* (!) 絶対配置は padding box 基準なので、.tutorial の padding では下がらない。
         セーフエリアはここで足す(上のコメント参照)。 */
  top: calc(var(--space-md) + env(safe-area-inset-top));
  inset-inline-end: var(--space-md);
  appearance: none;
  background: none;
  border: 0;
  font: inherit;
  color: var(--fg-muted);
  text-decoration: underline;
  cursor: pointer;
}
.tutorial__page {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--space-lg);
  text-align: center;
}
.tutorial__title {
  margin: 0;
  font-size: 1.25rem;
  font-weight: 800;
  color: var(--fg);
  max-width: 28em;
}
.tutorial__note {
  margin: 0;
  font-size: 0.875rem;
  font-weight: 700;
  line-height: 1.5;
  color: var(--fg-muted);
  max-width: 28em;
}
.tutorial__demo {
  display: grid;
  grid-template-columns: repeat(4, 64px);
  gap: 8px;
}
.tutorial__demo-tile {
  width: 64px;
  height: 64px;
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--bg-elev);
  border: 2px solid var(--line);
  border-radius: 10px;
  font-size: 1.75rem;
  font-weight: 800;
  position: relative;
  animation: tile-flip 350ms ease-in-out;
  animation-delay: var(--delay, 0s);
  animation-fill-mode: both;
}
.tutorial__demo-tile::after {
  content: attr(data-glyph);
  position: absolute;
  right: 4px;
  bottom: 2px;
  font-size: 12px;
}
.tutorial__demo-tile[data-state="hit"]  { background: var(--tile-hit);  border-color: var(--tile-hit);  color: #FFFFFF; }
.tutorial__demo-tile[data-state="near"] { background: var(--tile-near); border-color: var(--tile-near); color: #FFFFFF; }
.tutorial__demo-tile[data-state="blow"] { background: var(--tile-blow); border-color: var(--tile-blow); color: #FFFFFF; }
.tutorial__demo-tile[data-state="miss"] { background: var(--tile-miss); border-color: var(--tile-miss); color: #FFFFFF; }

.tutorial__legend {
  display: flex;
  flex-direction: column;
  gap: 8px;
  font-size: 1rem;
}
.tutorial__legend-row {
  display: flex;
  align-items: center;
  gap: 12px;
}
/* 凡例 4 行目のミニキー(チップの説明)。盤面のキーと同じ見た目で、盤面の --kbd-key-h には依存しない */
.tutorial__legend-key {
  position: relative;
  flex: 0 0 auto;
  width: 40px;
  height: 44px;
  box-sizing: border-box;
  padding-bottom: 17px;
  --kbd-key-h: 44px;   /* 印の寸法(.kbd__key__vmarks)を盤面のキーと同じ比で出す */
  border-radius: 8px;
  border: 1px solid var(--line);
  background: var(--bg);
  color: var(--fg);
  font-size: 18px;
  font-weight: 800;
  display: flex;
  align-items: center;
  justify-content: center;
}
/* ja の凡例は文になった(2026-09-25)ので、折り返しても左揃えのまま読めるように */
.tutorial__legend-name {
  flex: 1 1 auto;
  min-width: 0;
  text-align: start;
  line-height: 1.35;
}
.tutorial__legend-tile { flex: 0 0 auto; }
.tutorial__legend-name--chips {
  flex: 1 1 auto;
  min-width: 0;
  text-align: start;   /* ページ全体は中央揃え。折り返した 2 行目が真ん中に寄らないように */
  font-size: 0.85rem;
  line-height: 1.35;
}
.tutorial__legend-tile {
  width: 36px;
  height: 36px;
  border-radius: 6px;
  display: flex;
  align-items: center;
  justify-content: center;
  color: #FFFFFF;
  font-weight: 800;
}
.tutorial__share {
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: var(--space-md);
  text-align: left;
  font-family: monospace;
  font-size: 0.875rem;
  line-height: 1.5;
  white-space: pre;
}
.tutorial__share-line { margin: 0; }

.tutorial__nav {
  display: flex;
  gap: var(--space-sm);
}
/* Jelly 版(2026-09-22): accent のピル 48px */
jelly-button.tutorial__next[size],
jelly-button.tutorial__start[size] {
  --jelly-button-height: 48px;
  --jelly-button-radius: var(--radius-pill);
}
button.tutorial__next,
button.tutorial__start {
  appearance: none;
  border: 0;
  background: var(--accent);
  color: #FFFFFF;
  border-radius: var(--radius-pill);
  padding: 10px 22px;
  font: inherit;
  font-weight: 800;
  font-size: 1rem;
  cursor: pointer;
}

/* ============================================================
 * 画面登場(全プロジェクト共通の規定 / §6-5)
 * 直下の要素を 60ms ずつ階段状にフェード+上スライド。
 * ============================================================ */
.screen > * {
  animation: screen-child-in 280ms ease-out both;
}
.screen > *:nth-child(1) { animation-delay: 0ms; }
.screen > *:nth-child(2) { animation-delay: 60ms; }
.screen > *:nth-child(3) { animation-delay: 120ms; }
.screen > *:nth-child(4) { animation-delay: 180ms; }
.screen > *:nth-child(5) { animation-delay: 240ms; }

@keyframes screen-child-in {
  from { opacity: 0; transform: translateY(8px); }
  to   { opacity: 1; transform: translateY(0); }
}

/* ============================================================
 * v3 ローマ字ガイド(§S4)・ローマ字入力バッファ(§S5)
 * 新規クラスのみ(既存セレクタの変更なし)。
 * .kbd__key__romaji はキー内部の絶対配置にし、offsetHeight を変えない
 * (board.js の calcTileSize の実測方式に影響させないため)。
 * ============================================================ */
.kbd__key__romaji {
  position: absolute;
  left: 0;
  right: 0;
  bottom: 1px;
  font-size: 9px;
  line-height: 1;
  font-weight: 700;
  text-align: center;
  opacity: 0.6;
  pointer-events: none;
}
.kbd--no-romaji .kbd__key__romaji {
  display: none;
}
/* 変化形のチップ(右下)が出たキーではローマ字ガイドを隠す(2026-09-22)。
   ガイドは下部中央・全幅で、30px 幅のキーに "ho" + チップ 2 つは同じ行に入らない。
   一族が判定済みのキーは学習者が既に見つけて打ったキーなので、ガイドより判定の方が価値が高い。 */
.kbd__key--marked .kbd__key__romaji {
  display: none;
}

/* 変換途中のアルファベット(入力行の右下に 11px で薄く。例: ky)。
   .tile は position:relative なので行末タイルの子に絶対配置する。 */
.romaji-buffer {
  position: absolute;
  right: 2px;
  bottom: 0;
  font-size: 11px;
  line-height: 1;
  font-weight: 700;
  opacity: 0.55;
  pointer-events: none;
}

/* ============================================================
 * v3 Web 版(§S7)。新規クラスのみ(既存セレクタの変更なし)。
 * いずれも hidden 始まりで web.js が enabled 時のみ中身を入れて開く。
 * ============================================================ */
.web-applink[hidden], .web-ad[hidden], .web-about[hidden] {
  display: none;
}

/* ホームのメニュー下のアプリ導線 1 行 */
.web-applink {
  margin: 0;
  text-align: center;
  font-size: 0.875rem;
  font-weight: 700;
}
.web-applink__link {
  color: var(--sky);
}

/* AdSense 枠 2 つ(top / result)。高さは固定しない(responsive) */
.web-ad {
  width: 100%;
  max-width: var(--content-max);
  margin: 0 auto;
  text-align: center;
}

/* SEO 本文 */
.web-about {
  width: 100%;
  max-width: var(--content-max);
  margin: 0 auto;
  display: flex;
  flex-direction: column;
  gap: var(--space-xs);
}
.web-about__title {
  margin: 0;
  font-size: 1rem;
  font-weight: 800;
  color: var(--fg);
}
.web-about__p {
  margin: 0;
  font-size: 0.8125rem;
  line-height: 1.7;
  color: var(--fg-muted);
}

/* 結果カードのアプリ導線 box(共有ボタンの下・AdSense 枠の上) */
.web-result-app {
  display: flex;
  flex-direction: column;
  gap: var(--space-xs);
  border-top: 1px solid var(--line);
  padding-top: var(--space-md);
}
.web-result-app__title {
  margin: 0;
  font-size: 1rem;
  font-weight: 800;
  text-align: center;
}
.web-result-app__list {
  margin: 0;
  padding: 0;
  list-style: none;
  font-size: 0.8125rem;
  text-align: center;
  color: var(--fg-muted);
}
.web-result-app__badges {
  display: flex;
  justify-content: center;
  gap: var(--space-sm);
}
.web-result-app__soon {
  margin: 0;
  font-size: 0.8125rem;
  text-align: center;
  color: var(--fg-muted);
}
.web-store-badge {
  display: inline-block;
  padding: 6px 14px;
  border: 1px solid var(--line);
  border-radius: var(--radius-pill);
  font-size: 0.8125rem;
  font-weight: 700;
  color: var(--fg);
  text-decoration: none;
}

/* せいせき画面の先頭の注意書き */
.web-stats-note {
  margin: 0;
  font-size: 0.8125rem;
  color: var(--fg-muted);
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  padding: var(--space-sm) var(--space-md);
}

/* ============================================================
 * prefers-reduced-motion: reduce(必須)
 *   ・無限ループ系は停止
 *   ・登場・裏返し・pop は即時表示
 * ============================================================ */
@media (prefers-reduced-motion: reduce) {
  .kanamon, .kanamon__img { animation: none !important; }
  /* タイルの pop・flip・shake は即時 */
  .tile--pop, .tile--flip, .board__row--shake,
  .tutorial__demo-tile {
    animation: none !important;
  }
  /* ホームの主役ボタンの浮遊 */
  .menu__item--main {
    animation: none !important;
  }
  /* ステージの登場 */
  .screen > * {
    animation: none !important;
    opacity: 1 !important;
    transform: none !important;
  }
  /* 結果カードの登場 */
  .result__card {
    animation: none !important;
  }
}
