/* Windmill — application styles
   Aesthetic: "midnight study" — ink black, warm cream text, amber accent, walnut board.
   Fonts: Fraunces (display), Instrument Sans (UI), JetBrains Mono (numbers). */

@import url('./fonts.css');

:root {
  --font-display: 'Fraunces', 'Iowan Old Style', Georgia, serif;
  --font-ui: 'Instrument Sans', 'Helvetica Neue', Arial, sans-serif;
  --font-mono: 'JetBrains Mono', 'SFMono-Regular', Menlo, monospace;

  --bg: #0a0c11;
  --bg-2: #10131a;
  --panel: #151922;
  --panel-2: #1b2029;
  --line: rgba(236, 230, 218, 0.08);
  --line-strong: rgba(236, 230, 218, 0.16);
  --text: #ece6da;
  --text-2: #b7b1a6;
  --muted: #8a8f9d;
  --accent: #e8b04b;
  --accent-ink: #1a1305;
  --accent-soft: rgba(232, 176, 75, 0.14);
  --danger: #e25c5c;
  --ok: #6cc070;

  /* Captured pieces sit on the page ground, not a board square: a halo the
     colour of the text keeps a black knight from vanishing into a dark strip. */
  --taken-halo: rgba(236, 230, 218, 0.55);

  --c-brilliant: #3dd3e4;
  --c-best: #62c56c;
  --c-excellent: #94c65f;
  --c-good: #b6c48a;
  --c-book: #b59a6b;
  --c-inaccuracy: #e6c14a;
  --c-mistake: #ee8a3c;
  --c-blunder: #e04f4f;

  --sq-light: #e8dabc;
  --sq-dark: #9a7451;
  --sq-last: rgba(232, 176, 75, 0.45);
  --sq-sel: rgba(232, 176, 75, 0.65);
  --sq-check: radial-gradient(circle, rgba(224, 79, 79, 0.9) 0%, rgba(224, 79, 79, 0.35) 55%, transparent 75%);

  --radius: 14px;
  --radius-sm: 8px;
  --shadow: 0 30px 80px -30px rgba(0, 0, 0, 0.8), 0 2px 6px rgba(0, 0, 0, 0.4);
  --rail-w: 84px;
  color-scheme: dark;
}

[data-theme="light"] {
  --taken-halo: rgba(20, 16, 8, 0.4);
  --bg: #f4efe4;
  --bg-2: #ebe4d5;
  --panel: #fffdf8;
  --panel-2: #f3eee2;
  --line: rgba(20, 16, 8, 0.09);
  --line-strong: rgba(20, 16, 8, 0.18);
  --text: #17130c;
  --text-2: #4b463c;
  --muted: #6b6459;
  --accent: #8c590e;
  --accent-ink: #fff;
  --accent-soft: rgba(140, 89, 14, 0.13);
  --shadow: 0 30px 60px -30px rgba(40, 30, 10, 0.35), 0 2px 6px rgba(40, 30, 10, 0.08);
  --sq-light: #efe2c4;
  --sq-dark: #a77c56;
  color-scheme: light;
}

* { box-sizing: border-box; }
[hidden] { display: none !important; }
html, body { height: 100%; }
body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font-ui);
  font-size: 14px;
  line-height: 1.45;
  -webkit-font-smoothing: antialiased;
  overflow: hidden;
}
body::before {
  /* subtle grain — absolutely positioned over the non-scrolling body, with no
     blend mode. A fixed, full-viewport mix-blend-mode layer causes repaint
     ghosting (duplicated content) in Android WebView, so avoid both here. */
  content: '';
  position: absolute; inset: 0; pointer-events: none; z-index: 0; opacity: 0.5;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='0.04'/%3E%3C/svg%3E");
}
button, input, select, textarea { font: inherit; color: inherit; }
button { cursor: pointer; }
a { color: inherit; }
/* An anchor styled as a button should look like one, underline included. */
a.btn { text-decoration: none; }
h1, h2, h3, h4 { margin: 0; font-weight: 500; }
::selection { background: var(--accent); color: var(--accent-ink); }

/* ---------- shell ---------- */
.shell { display: grid; grid-template-columns: var(--rail-w) 1fr; height: 100vh; height: 100dvh; position: relative; z-index: 1; }

.rail {
  display: flex; flex-direction: column; align-items: center;
  padding: 18px 0 14px; gap: 6px;
  background: var(--bg-2); border-right: 1px solid var(--line);
}
.brand { display: flex; flex-direction: column; align-items: center; gap: 2px; margin-bottom: 18px; text-decoration: none; }
.brand-mark {
  width: 40px; height: 40px; border-radius: 12px;
  background: var(--accent); color: var(--accent-ink);
  display: grid; place-items: center;
  font-family: var(--font-display); font-style: italic; font-weight: 600; font-size: 24px;
  box-shadow: 0 8px 20px -8px var(--accent);
}
.brand-name { font-family: var(--font-display); font-style: italic; font-size: 15px; color: var(--text-2); letter-spacing: 0.01em; }
.rail-nav { display: flex; flex-direction: column; gap: 4px; width: 100%; padding: 0 10px; }
.rail-btn {
  display: flex; flex-direction: column; align-items: center; gap: 4px;
  width: 100%; padding: 10px 4px; border: 0; border-radius: 10px;
  background: transparent; color: var(--muted); font-size: 11px; letter-spacing: 0.02em;
  transition: background 0.15s, color 0.15s;
}
.rail-btn svg { width: 22px; height: 22px; }
.rail-btn:hover { color: var(--text); background: var(--panel); }
.rail-btn.active { color: var(--accent); background: var(--accent-soft); }
.rail-spacer { flex: 1; }
.rail-foot { display: flex; flex-direction: column; gap: 4px; width: 100%; padding: 0 10px; }

.stage {
  min-width: 0; min-height: 0; overflow: auto; -webkit-overflow-scrolling: touch;
  /* Reserve the scrollbar's width even before there is anything to scroll. The
     move list grows as a game is played, and the moment it made the page taller
     than the screen a classic scrollbar appeared, took 10px of width, and nudged
     the centred board sideways by half of that. Overlay scrollbars take no space,
     so this changes nothing on platforms that use them. */
  scrollbar-gutter: stable;
}
.view { display: none; min-height: 100%; }
.view.active { display: block; }

.workspace {
  display: grid; grid-template-columns: minmax(320px, calc(100vh - 150px)) minmax(360px, 500px);
  gap: 22px; padding: 22px 24px; align-items: start; justify-content: center;
  max-width: 1440px; margin: 0 auto;
}


/* ---------- board column ---------- */
.board-col { display: flex; flex-direction: column; gap: 12px; min-width: 0; }
.board-frame { display: grid; grid-template-columns: 18px 1fr; gap: 10px; align-items: stretch; }
.evalbar {
  position: relative; border-radius: 6px; overflow: hidden;
  background: #1f1f22; border: 1px solid var(--line-strong);
}
.evalbar .white { position: absolute; left: 0; right: 0; bottom: 0; background: #f2ede2; transition: height 0.5s cubic-bezier(.4,0,.2,1); }
.evalbar.flipped .white { bottom: auto; top: 0; }
.evalbar .lbl {
  position: absolute; left: 0; right: 0; text-align: center;
  font-family: var(--font-mono); font-size: 9px; font-weight: 600; writing-mode: vertical-rl; transform: rotate(180deg);
}
.evalbar .lbl.top { top: 6px; color: #f2ede2; }
.evalbar .lbl.bottom { bottom: 6px; color: #1f1f22; }

.pboard {
  position: relative; width: 100%; aspect-ratio: 1 / 1;
  border-radius: 10px; overflow: hidden; user-select: none; touch-action: none;
  box-shadow: var(--shadow);
  background: var(--sq-dark);
}
.pboard-squares { position: absolute; inset: 0; display: grid; grid-template-rows: repeat(8, 1fr); }
/* Eight rows of eight, nested, so role=grid > role=row > role=gridcell is a
   valid structure without changing what is drawn. */
.pboard-row { display: grid; grid-template-columns: repeat(8, 1fr); }
.psq { position: relative; }
.psq.light { background: var(--sq-light); }
.psq.dark { background: var(--sq-dark); }
.psq.hl-last::after, .psq.hl-sel::after, .psq.hl-check::after, .psq.hl-dot::after, .psq.hl-capture::after,
.psq.hl-blunder::after, .psq.hl-mistake::after, .psq.hl-inaccuracy::after, .psq.hl-best::after, .psq.hl-brilliant::after, .psq.hl-mark::after {
  content: ''; position: absolute; inset: 0; pointer-events: none;
}
.psq.hl-last::after { background: var(--sq-last); }
.psq.hl-sel::after { background: var(--sq-sel); }
.psq.hl-check::after { background: var(--sq-check); }
.psq.hl-dot::after { background: radial-gradient(circle, rgba(0,0,0,0.28) 0 17%, transparent 18%); }
.psq.hl-capture::after { background: radial-gradient(circle, transparent 0 58%, rgba(0,0,0,0.3) 60% 100%); }
.psq.hl-blunder::after { box-shadow: inset 0 0 0 4px var(--c-blunder); }
.psq.hl-mistake::after { box-shadow: inset 0 0 0 4px var(--c-mistake); }
.psq.hl-inaccuracy::after { box-shadow: inset 0 0 0 4px var(--c-inaccuracy); }
.psq.hl-best::after { box-shadow: inset 0 0 0 4px var(--c-best); }
.psq.hl-brilliant::after { box-shadow: inset 0 0 0 4px var(--c-brilliant); }
.psq.hl-mark::after { box-shadow: inset 0 0 0 4px var(--accent); }

.pboard-coords { position: absolute; inset: 0; pointer-events: none; font-family: var(--font-mono); font-size: 10px; font-weight: 600; }
.pcoord { position: absolute; opacity: 0.55; }
.pcoord.file { bottom: 2px; width: 12.5%; text-align: right; padding-right: 4px; color: rgba(50, 32, 14, 0.7); }
.pcoord.rank { left: 3px; height: 12.5%; color: rgba(50, 32, 14, 0.7); }
.pboard-pieces { position: absolute; inset: 0; pointer-events: none; }
.ppiece {
  position: absolute; top: 0; left: 0; width: 12.5%; height: 12.5%;
  background-size: 100% 100%; background-repeat: no-repeat;
  transition: transform 0.18s cubic-bezier(.3,.1,.2,1);
}
.pboard-arrows { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; }
.parrow { stroke-linecap: round; }
.arrow-best { stroke: var(--c-best); fill: var(--c-best); }
.arrow-good { stroke: var(--c-good); fill: var(--c-good); }
.arrow-ok { stroke: var(--c-inaccuracy); fill: var(--c-inaccuracy); }
.arrow-meh { stroke: var(--c-mistake); fill: var(--c-mistake); }
.arrow-bad { stroke: var(--c-blunder); fill: var(--c-blunder); }
.arrow-user { stroke: var(--accent); fill: var(--accent); }
.arrow-threat { stroke: #b46cff; fill: #b46cff; }
.parrow { opacity: 0.85; }
.parrow-label rect { fill: #0b0d12; stroke-width: 0.02; }
.parrow-label text { fill: #fff; font-family: var(--font-mono); font-weight: 600; }
.label-best rect { stroke: var(--c-best); }
.label-good rect { stroke: var(--c-good); }
.label-ok rect { stroke: var(--c-inaccuracy); }
.label-meh rect { stroke: var(--c-mistake); }
.label-bad rect { stroke: var(--c-blunder); }
.pboard-drag { position: absolute; top: 0; left: 0; display: none; pointer-events: none; background-size: 100% 100%; z-index: 5; filter: drop-shadow(0 6px 8px rgba(0,0,0,0.4)); }

/* board toolbar */
.board-tools { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.nav-group { display: inline-flex; background: var(--panel); border: 1px solid var(--line); border-radius: 10px; overflow: hidden; }
.nav-group button { border: 0; background: transparent; color: var(--text-2); padding: 8px 12px; display: grid; place-items: center; }
.nav-group button:hover { background: var(--panel-2); color: var(--text); }
.nav-group button svg { width: 16px; height: 16px; }
.tool-spacer { flex: 1; }

.btn {
  display: inline-flex; align-items: center; gap: 7px;
  padding: 8px 13px; border-radius: 10px; border: 1px solid var(--line);
  background: var(--panel); color: var(--text); font-weight: 500; font-size: 13px;
  transition: background 0.15s, border-color 0.15s, transform 0.05s;
}
.btn:hover { background: var(--panel-2); border-color: var(--line-strong); }
.btn:active { transform: translateY(1px); }
.btn svg { width: 15px; height: 15px; }
.btn.primary { background: var(--accent); color: var(--accent-ink); border-color: transparent; }
.btn.primary:hover { filter: brightness(1.06); background: var(--accent); }
.btn.ghost { background: transparent; border-color: transparent; color: var(--text-2); }
.btn.ghost:hover { background: var(--panel); color: var(--text); }
.btn.sm { padding: 5px 9px; font-size: 12px; border-radius: 8px; }
.btn.xs { padding: 3px 8px; font-size: 11px; border-radius: 7px; white-space: nowrap; }
/* the Convert buttons sit inside rows that are themselves clickable */
.km .km-play, .moment .mo-play { opacity: 0.75; }
.km:hover .km-play, .moment:hover .mo-play { opacity: 1; }
.btn.active { border-color: var(--accent); color: var(--accent); background: var(--accent-soft); }
.btn[disabled] { opacity: 0.5; cursor: not-allowed; }
.btn.danger { color: var(--danger); }

/* player strips */
.player-strip { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 2px 4px; font-size: 13px; }
.player-strip .name { font-weight: 600; }
.player-strip .rating { color: var(--muted); font-family: var(--font-mono); font-size: 12px; margin-left: 6px; }
.player-strip .acc { font-family: var(--font-mono); font-size: 12px; color: var(--accent); }
.player-strip > :first-child { flex: 0 0 auto; }

/* Captured pieces. They take the slack between name and clock, and duplicates
   overlap so a full sweep of eight pawns still fits a phone strip. */
.taken { display: flex; align-items: center; flex: 1 1 auto; min-width: 0; height: 17px; }
.tkps { display: flex; align-items: center; min-width: 0; overflow: hidden; }
.tkp { width: 17px; height: 17px; flex: 0 0 auto; margin-left: 2px; background-size: contain; background-repeat: no-repeat; background-position: center; filter: drop-shadow(0 0 1px var(--taken-halo)); }
.tkp.same { margin-left: -6px; }
.tkd { flex: 0 0 auto; margin-left: 6px; font-family: var(--font-mono); font-size: 12px; font-weight: 600; color: var(--text-2); }
.player-strip .acc, .player-strip .clock { flex: 0 0 auto; }

.rep-badge {
  font-style: normal; font-size: 10.5px; font-family: var(--font-mono);
  padding: 1px 6px; border-radius: 999px; border: 1px solid var(--line-strong);
  color: var(--muted); vertical-align: middle; margin-left: 6px; white-space: nowrap;
}
.rep-badge.ok { color: var(--c-best); border-color: var(--c-best); }
.rep-badge.soft { color: var(--c-inaccuracy); border-color: var(--c-inaccuracy); }
.rep-badge.bad { color: var(--c-blunder); border-color: var(--c-blunder); }
.rep-issue {
  border: 0; background: transparent; padding: 0; text-align: left; font: inherit;
  color: var(--c-inaccuracy); cursor: pointer; text-decoration: underline dotted;
}
.rep-issue:hover { color: var(--accent); }

.opp-nums { display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 12px; }
.opp-nums span { display: flex; flex-direction: column; gap: 2px; }
.opp-nums b { font-family: var(--font-display); font-size: 24px; font-weight: 500; line-height: 1; }
.opp-nums small { font-size: 11px; color: var(--muted); text-transform: uppercase; letter-spacing: 0.06em; }

/* ---------- one thing to work on ---------- */
.goal-set { display: flex; gap: 8px; align-items: center; padding: 10px 14px 14px; flex-wrap: wrap; }
.goal-set select { flex: 1 1 180px; min-width: 0; background: var(--bg-2); border: 1px solid var(--line); border-radius: 8px; padding: 8px 10px; color: var(--text); font-size: 13px; }
.goal { padding: 12px 14px 14px; display: flex; flex-direction: column; gap: 10px; }
.goal-nums { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; }
.goal-nums span { display: flex; flex-direction: column; gap: 2px; font-family: var(--font-display); font-size: 22px; line-height: 1; }
.goal-nums small { font-family: var(--font-ui); font-size: 11px; color: var(--muted); text-transform: uppercase; letter-spacing: 0.06em; }
.goal-nums .now { color: var(--text); }
.goal-nums .from, .goal-nums .target { color: var(--text-2); }
.goal-nums .target { text-align: right; }
.goal-nums .now { text-align: center; }
.goal-bar { height: 8px; border-radius: 5px; background: var(--panel-2); overflow: hidden; }
.goal-bar i { display: block; height: 100%; border-radius: 5px; background: var(--accent); transition: width .3s; }
.goal.better .goal-bar i, .goal.done .goal-bar i { background: var(--c-best); }
.goal.worse .goal-bar i { background: var(--c-blunder); }
.goal.done .goal-nums .now { color: var(--c-best); }
.weak .work-on { align-self: center; white-space: nowrap; }

/* ---------- converting ---------- */
.conv-row { display: grid; grid-template-columns: 130px 1fr 46px; gap: 10px; align-items: center; font-size: 12.5px; padding: 3px 0; }
.conv-row .k { color: var(--text-2); }
.conv-row .bar { height: 7px; border-radius: 4px; background: var(--panel-2); overflow: hidden; }
.conv-row .bar i { display: block; height: 100%; background: var(--c-best); border-radius: 4px; }
.conv-row .v { font-family: var(--font-mono); text-align: right; color: var(--muted); }

/* ---------- the story of the game ---------- */
.story { padding: 4px 14px 14px; display: flex; flex-direction: column; gap: 2px; border-bottom: 1px solid var(--line); }
.story .narr { margin: 0 0 10px; color: var(--text-2); font-size: 14px; line-height: 1.6; max-width: 62ch; }
.story .narr:last-child { margin-bottom: 0; }
.turn-head { font-size: 11px; text-transform: uppercase; letter-spacing: 0.08em; color: var(--muted); margin: 10px 0 4px; }
.turn {
  display: grid; grid-template-columns: minmax(72px, auto) 1fr auto; align-items: baseline; gap: 10px;
  padding: 7px 8px; border-radius: 8px; border-left: 2px solid transparent; font-size: 13px;
}
.turn:hover { background: var(--panel-2); }
.turn.mine { border-left-color: var(--c-blunder); }
.turn.theirs { border-left-color: var(--c-best); }
.turn.missed { border-left-color: var(--c-inaccuracy); }
.turn .mv { font-family: var(--font-mono); font-size: 12.5px; color: var(--text); }
.turn .what { color: var(--text-2); }
.turn .clk { font-family: var(--font-mono); font-size: 11.5px; font-style: normal; color: var(--muted); margin-left: 8px; white-space: nowrap; }
.turn .clk.hot { color: var(--c-inaccuracy); }
.turn .swing { font-family: var(--font-mono); font-size: 12px; color: var(--muted); white-space: nowrap; }
.story .pats { margin: 10px 0 0; padding-left: 18px; color: var(--text-2); font-size: 13px; }
.story .pats li { margin-bottom: 3px; }
.seg.sm button { padding: 4px 9px; font-size: 12px; }

.rep-tree { display: flex; flex-direction: column; max-height: 46vh; overflow-y: auto; overflow-x: hidden; }
.rep-node {
  display: grid; grid-template-columns: 16px minmax(0, auto) minmax(0, 1fr) auto; gap: 8px; align-items: baseline;
  padding: 6px 12px 6px 0; border-top: 1px solid var(--line); font-size: 13px; cursor: pointer;
}
.rep-node:hover { background: var(--panel-2); }
.rep-node .tw { color: var(--muted); font-size: 11px; }
.rep-node .mv { font-family: var(--font-mono); font-size: 12.5px; color: var(--text); min-width: 0; }
.rep-node .meta { color: var(--muted); font-size: 11.5px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.rep-node .meta b { color: var(--accent); font-weight: 600; }
.rep-node.leaf .mv { color: var(--text-2); }
.rep-node .kill { border: 0; background: transparent; color: var(--muted); padding: 2px 6px; border-radius: 6px; font-size: 11px; }
.rep-node .kill:hover { color: var(--danger); background: var(--panel); }

/* ---------- blindfold ---------- */
.bf-line { font-family: var(--font-mono); font-size: 14px; line-height: 1.9; color: var(--text); padding-bottom: 10px; }
.bf-q { font-family: var(--font-display); font-size: 19px; padding-bottom: 10px; }
.bf-palette { display: grid; grid-template-columns: repeat(7, 1fr); gap: 6px; }
.bf-piece {
  aspect-ratio: 1; border: 1px solid var(--line); border-radius: 8px; background: var(--bg-2);
  display: grid; place-items: center; padding: 4px;
}
.bf-piece:hover { border-color: var(--accent); }
.bf-piece i { display: block; width: 100%; height: 100%; background-size: contain; background-repeat: no-repeat; background-position: center; }
.bf-empty { color: var(--muted); font-size: 18px; }
.bf-verdict { font-size: 14px; padding: 8px 0; }
.bf-verdict.ok { color: var(--c-best); }
.bf-verdict.no { color: var(--c-blunder); }

/* ---------- puzzle rush ---------- */
/* The HUD sits above the board because on a phone the panel is below the fold
   while you are solving, and a clock you cannot see is not a clock. */
.rush-hud { display: flex; align-items: center; gap: 12px; padding: 6px 4px; }
.rush-hud .t { font-family: var(--font-display); font-size: 26px; line-height: 1; font-variant-numeric: tabular-nums; }
.rush-hud .t.low { color: var(--danger); }
.rush-hud .sc { color: var(--muted); font-size: 13px; }
.rush-hud .sc b { color: var(--text); font-family: var(--font-mono); font-size: 16px; margin-right: 3px; }
.rush-hud .strikes { display: flex; gap: 5px; margin-left: auto; }
.rush-hud .strikes i { width: 11px; height: 11px; border-radius: 50%; border: 1.5px solid var(--line-strong); }
.rush-hud .strikes i.x { background: var(--danger); border-color: var(--danger); }
.rush-score { display: flex; align-items: baseline; gap: 9px; padding-bottom: 6px; }
.rush-score b { font-family: var(--font-display); font-size: 40px; line-height: 1; font-weight: 500; }
.rush-score span { color: var(--muted); font-size: 13px; }
.rush-fill { display: flex; align-items: center; gap: 8px; color: var(--muted); font-size: 13px; }
.rush-misses { display: flex; flex-direction: column; gap: 2px; margin-bottom: 10px; max-height: 30vh; overflow: auto; }
.rush-miss { display: grid; grid-template-columns: 42px 1fr auto; align-items: center; gap: 8px; padding: 7px 8px; border-radius: 8px; font-size: 13px; }
.rush-miss:hover { background: var(--panel-2); }
.rush-miss .n { font-family: var(--font-mono); font-size: 12px; color: var(--muted); }
.rush-miss .st { font-size: 11px; color: var(--muted); text-transform: uppercase; letter-spacing: 0.06em; }

/* ---------- side panel ---------- */
.panel { display: flex; flex-direction: column; gap: 12px; min-width: 0; }
.card { background: var(--panel); border: 1px solid var(--line); border-radius: var(--radius); overflow: hidden; }
.card-h { display: flex; align-items: center; gap: 10px; padding: 12px 14px; border-bottom: 1px solid var(--line); flex-wrap: wrap; }
#op-train { white-space: nowrap; margin-left: 8px; }
.card-h h3 { font-family: var(--font-display); font-weight: 500; font-size: 16px; letter-spacing: -0.01em; }
.card-h .sub { color: var(--muted); font-size: 12px; }
.card-h .card-actions { display: flex; gap: 6px; align-items: center; margin-left: auto; }
.card-b { padding: 12px 14px; }

/* engine block */
.engine-top { display: grid; grid-template-columns: auto 1fr auto; align-items: center; gap: 12px; padding: 14px 14px 8px; }
.eval-big { font-family: var(--font-display); font-size: 40px; line-height: 1; font-weight: 500; letter-spacing: -0.03em; min-width: 92px; font-variant-numeric: tabular-nums; }
.eval-big.mate { color: var(--accent); }
.engine-meta { display: flex; flex-direction: column; gap: 2px; font-size: 12px; color: var(--muted); }
.engine-meta b { color: var(--text-2); font-weight: 500; }
.engine-meta .cloud { color: var(--c-brilliant); }
.engine-ctl { display: flex; gap: 4px; }
.icon-btn { width: 32px; height: 32px; border-radius: 9px; border: 1px solid var(--line); background: transparent; color: var(--text-2); display: grid; place-items: center; }
.icon-btn:hover { background: var(--panel-2); color: var(--text); }
.icon-btn.active { color: var(--accent); border-color: var(--accent); }
.icon-btn svg { width: 15px; height: 15px; }
.depth-track { height: 3px; background: var(--line); margin: 0 14px 8px; border-radius: 2px; overflow: hidden; }
.depth-track i { display: block; height: 100%; width: 0; background: var(--accent); transition: width 0.3s; }
.lines { display: flex; flex-direction: column; }
.line {
  display: grid; grid-template-columns: 56px 1fr; gap: 10px; align-items: baseline;
  padding: 7px 14px; border-top: 1px solid var(--line); cursor: pointer; font-size: 13px;
}
.line:hover { background: var(--panel-2); }
.line .sc { font-family: var(--font-mono); font-weight: 600; font-size: 12px; padding: 2px 6px; border-radius: 6px; text-align: center; background: var(--panel-2); }
.line .sc.w { background: #efe9dc; color: #111; }
.line .sc.b { background: #2a2a2e; color: #eee; }
.line .pv { color: var(--text-2); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; font-family: var(--font-mono); font-size: 12px; }
.line .pv b { color: var(--text); font-weight: 600; }
.engine-settings { display: none; padding: 10px 14px; border-top: 1px solid var(--line); gap: 12px; flex-wrap: wrap; font-size: 12px; color: var(--text-2); }
.engine-settings.open { display: flex; }
.engine-settings label { display: flex; align-items: center; gap: 6px; }
.engine-settings select, .engine-settings input[type=number] { background: var(--panel-2); border: 1px solid var(--line); border-radius: 6px; padding: 3px 6px; }

/* tabs */
.tabs { display: flex; border-bottom: 1px solid var(--line); }
.tab { flex: 1; padding: 10px 6px; border: 0; background: transparent; color: var(--muted); font-weight: 500; font-size: 13px; position: relative; }
.tab.active { color: var(--text); }
.tab.active::after { content: ''; position: absolute; left: 12px; right: 12px; bottom: -1px; height: 2px; background: var(--accent); border-radius: 2px; }
.tab-pane { display: none; }
.tab-pane.active { display: block; }

/* move list */
.movelist { max-height: 44vh; overflow: auto; padding: 6px 8px; font-family: var(--font-mono); font-size: 13px; }
.mv-row { display: grid; grid-template-columns: 36px 1fr 1fr; align-items: stretch; }
.mv-num { color: var(--muted); padding: 5px 6px; font-size: 11px; }
.mv { padding: 4px 8px; border-radius: 6px; cursor: pointer; display: flex; align-items: center; gap: 6px; }
.mv:hover { background: var(--panel-2); }
.mv.cur { background: var(--accent-soft); color: var(--accent); box-shadow: inset 0 0 0 1px var(--accent); }
.mv .g { font-size: 10px; font-weight: 700; min-width: 16px; text-align: center; font-family: var(--font-ui); }
.mv.c-brilliant .g { color: var(--c-brilliant); } .mv.c-best .g { color: var(--c-best); } .mv.c-excellent .g { color: var(--c-excellent); }
.mv.c-good .g { color: var(--c-good); } .mv.c-book .g { color: var(--c-book); } .mv.c-inaccuracy .g { color: var(--c-inaccuracy); }
.mv.c-mistake .g { color: var(--c-mistake); } .mv.c-blunder .g { color: var(--c-blunder); } .mv.c-forced .g { color: var(--muted); }
.mv.c-blunder { color: var(--c-blunder); } .mv.c-mistake { color: var(--c-mistake); } .mv.c-brilliant { color: var(--c-brilliant); }
.variation-bar { display: flex; align-items: center; gap: 8px; padding: 8px 12px; background: var(--accent-soft); color: var(--accent); font-size: 12px; }
.empty { padding: 26px 14px; color: var(--muted); text-align: center; font-size: 13px; }
.empty b { color: var(--text-2); font-weight: 500; }

/* move detail / coach */
.coach { padding: 12px 14px; border-top: 1px solid var(--line); display: flex; gap: 12px; align-items: flex-start; }
.coach-pos { margin: 6px 0 0; padding-left: 16px; font-size: 12.5px; color: var(--text-2); }
.coach-pos li { margin-bottom: 2px; }
.coach-pos li.good::marker { color: var(--c-best); }
.coach-pos li.bad::marker { color: var(--c-inaccuracy); }

.coach .badge { font-family: var(--font-mono); font-weight: 700; font-size: 12px; padding: 4px 8px; border-radius: 7px; background: var(--panel-2); white-space: nowrap; }
.coach p { margin: 0; color: var(--text-2); font-size: 13px; }
.coach p b { color: var(--text); font-weight: 600; }
.coach .best { font-family: var(--font-mono); font-size: 12px; color: var(--muted); margin-top: 4px; }

/* report */
.report-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; padding: 12px 14px; }
.acc-card { background: var(--panel-2); border-radius: 10px; padding: 12px; display: flex; flex-direction: column; gap: 2px; }
.acc-card .who { font-size: 12px; color: var(--muted); display: flex; align-items: center; gap: 6px; }
.acc-card .who i { width: 10px; height: 10px; border-radius: 3px; display: inline-block; border: 1px solid var(--line-strong); }
.acc-card .val { font-family: var(--font-display); font-size: 34px; font-weight: 500; letter-spacing: -0.03em; line-height: 1.05; }
.acc-card .val small { font-size: 14px; color: var(--muted); margin-left: 2px; }
.acc-card .est { font-size: 11px; color: var(--muted); }
.acc-card .est b { color: var(--text-2); font-family: var(--font-mono); font-weight: 500; }
.cls-table { padding: 0 14px 12px; display: grid; gap: 4px; }
.cls-row { display: grid; grid-template-columns: 34px 1fr 34px; align-items: center; gap: 8px; font-size: 13px; }
.cls-row .n { font-family: var(--font-mono); text-align: center; font-weight: 600; }
.cls-row .lab { display: flex; align-items: center; gap: 8px; color: var(--text-2); }
.cls-row .lab i { width: 8px; height: 8px; border-radius: 50%; display: inline-block; }
.phase-row { display: grid; grid-template-columns: 90px 1fr 1fr; gap: 8px; align-items: center; font-size: 12px; padding: 3px 0; }
.phase-row .bar { height: 6px; background: var(--line); border-radius: 3px; overflow: hidden; position: relative; }
.phase-row .bar i { position: absolute; top: 0; bottom: 0; left: 0; border-radius: 3px; }
.phase-row .bar.w i { background: #efe9dc; } .phase-row .bar.b i { background: #6b6f7a; }
.graph { display: block; width: 100%; height: 110px; cursor: pointer; }
.key-moments { padding: 6px 8px 10px; display: flex; flex-direction: column; gap: 4px; }
.km { display: grid; grid-template-columns: 52px 1fr auto auto; gap: 10px; align-items: center; padding: 7px 8px; border-radius: 8px; cursor: pointer; font-size: 13px; }
.km:hover { background: var(--panel-2); }
.km .san { font-family: var(--font-mono); font-weight: 600; }
.km .cls { font-size: 11px; font-weight: 600; text-transform: uppercase; letter-spacing: 0.06em; }
.km .why { color: var(--muted); font-size: 12px; }
.progress { height: 6px; background: var(--line); border-radius: 3px; overflow: hidden; margin: 8px 14px 12px; }
.progress i { display: block; height: 100%; background: var(--accent); width: 0; transition: width 0.2s; }

/* opening / explorer */
.opening-name { font-family: var(--font-display); font-size: 17px; padding: 12px 14px 4px; }
.opening-name small { display: block; font-family: var(--font-mono); color: var(--muted); font-size: 11px; margin-top: 2px; }
.book-moves { display: flex; flex-direction: column; }
.bm { display: grid; grid-template-columns: 70px 1fr auto; gap: 10px; align-items: center; padding: 7px 14px; border-top: 1px solid var(--line); cursor: pointer; font-size: 13px; }
.bm:hover { background: var(--panel-2); }
.bm .san { font-family: var(--font-mono); font-weight: 600; }
.bm .nm { color: var(--text-2); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.bm .wdl { display: flex; width: 120px; height: 8px; border-radius: 4px; overflow: hidden; background: var(--line); }
.bm .wdl i { display: block; height: 100%; }
.bm .wdl .w { background: #efe9dc; } .bm .wdl .d { background: #8a8f9d; } .bm .wdl .b { background: #2a2a2e; }
.bm .games { font-family: var(--font-mono); font-size: 11px; color: var(--muted); }
.token-row { display: flex; gap: 6px; padding: 10px 14px; border-top: 1px solid var(--line); }
.token-row input { flex: 1; background: var(--panel-2); border: 1px solid var(--line); border-radius: 8px; padding: 6px 9px; font-size: 12px; }
.hint { padding: 8px 14px 12px; color: var(--muted); font-size: 12px; line-height: 1.5; }

/* guess mode */
.guess-box { padding: 12px 14px; display: flex; flex-direction: column; gap: 10px; }
.guess-score { display: flex; gap: 18px; font-family: var(--font-mono); font-size: 12px; color: var(--muted); }
.guess-score b { color: var(--text); font-size: 20px; font-family: var(--font-display); }
.guess-msg { padding: 10px 12px; border-radius: 10px; background: var(--panel-2); font-size: 13px; min-height: 40px; }
.guess-msg.good { border-left: 3px solid var(--c-best); }
.guess-msg.bad { border-left: 3px solid var(--c-blunder); }

/* modal */
.modal-bg { position: fixed; inset: 0; background: rgba(4, 5, 8, 0.7); backdrop-filter: blur(6px); display: none; place-items: center; z-index: 50; padding: 20px; }
.modal-bg.open { display: grid; }
.modal-bg { align-items: center; }
.modal { width: min(680px, 100%); background: var(--panel); border: 1px solid var(--line-strong);
  border-radius: 18px; box-shadow: var(--shadow); animation: pop 0.2s cubic-bezier(.2,.8,.2,1);
  /* Stay scrollable so the actions remain reachable when the on-screen
     keyboard shrinks the viewport. */
  max-height: 100%; overflow-y: auto; overscroll-behavior: contain; }
@keyframes pop { from { transform: translateY(10px) scale(0.98); opacity: 0; } to { transform: none; opacity: 1; } }
.modal-h { display: flex; align-items: center; justify-content: space-between; padding: 16px 18px 0; }
.modal-h h2 { font-family: var(--font-display); font-weight: 500; font-size: 22px; }
.modal-b { padding: 14px 18px 18px; }
textarea.paste { width: 100%; min-height: 150px; resize: vertical; background: var(--bg-2); border: 1px solid var(--line); border-radius: 10px; padding: 10px 12px; font-family: var(--font-mono); font-size: 12px; }
textarea.paste:focus, input:focus, select:focus { outline: 2px solid var(--accent); outline-offset: -1px; }
.row { display: flex; gap: 8px; align-items: center; flex-wrap: wrap; }
.row.end { justify-content: flex-end; }
.err { color: var(--danger); font-size: 12px; }
.field { display: flex; flex-direction: column; gap: 5px; font-size: 12px; color: var(--muted); }
.field.dimmed { opacity: 0.45; }
label.mini { display: flex; align-items: center; gap: 6px; font-size: 12px; color: var(--muted); }
label.mini input { width: 74px; background: var(--bg-2); border: 1px solid var(--line); border-radius: 8px; padding: 6px 8px; color: var(--text); font-size: 13px; }

.field input, .field select { background: var(--bg-2); border: 1px solid var(--line); border-radius: 8px; padding: 8px 10px; color: var(--text); font-size: 13px; max-width: 100%; }
/* A setting with its own explanation under it, rather than a bare tick box. */
.field.check { flex-direction: row; align-items: flex-start; gap: 9px; cursor: pointer; }
.field.check input { width: auto; margin: 2px 0 0; flex: none; padding: 0; }
.field.check > span { display: flex; flex-direction: column; gap: 2px; color: var(--text); font-size: 13px; }
.field.check small { color: var(--muted); font-size: 11.5px; line-height: 1.45; }

/* The measured-level readout: a range, because a point estimate would be a lie. */
.level-row { display: flex; align-items: baseline; gap: 10px; flex-wrap: wrap; }
.level-row .band { font-family: var(--font-display); font-size: 34px; line-height: 1.05; letter-spacing: -0.03em; font-variant-numeric: tabular-nums; }
.level-row .pm { font-family: var(--font-mono); font-size: 12px; color: var(--muted); }

/* ---------- the ghost ---------- */
.ghost-card { border: 1px solid var(--line); border-radius: 12px; background: var(--panel-2); padding: 12px 13px; display: flex; flex-direction: column; gap: 7px; }
.ghost-card .gh-top { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; }
.ghost-card .gh-name { font-weight: 600; font-size: 13.5px; color: var(--text); }
.ghost-card .gh-from { font-family: var(--font-mono); font-size: 10.5px; color: var(--muted); }
.ghost-card ul { margin: 0; padding-left: 16px; display: flex; flex-direction: column; gap: 4px; }
.ghost-card li { color: var(--text-2); font-size: 12.5px; line-height: 1.5; }
.ghost-card .gh-warn { color: var(--c-inaccuracy); font-size: 12px; }
.ghost-card .row { margin-top: 2px; }

/* ---------- the player you were ---------- */
.ghost-card.thin-era { color: var(--muted); font-size: 12px; line-height: 1.5; }
.era-card select { width: 100%; }
.era-diff { width: 100%; border-collapse: collapse; font-size: 12px; font-variant-numeric: tabular-nums; }
.era-diff th { text-align: right; font-weight: 500; color: var(--muted); font-size: 10.5px; text-transform: uppercase; letter-spacing: 0.06em; padding-bottom: 3px; }
.era-diff th:first-child { text-align: left; }
.era-diff td { padding: 3px 0; color: var(--text-2); border-top: 1px solid var(--line); text-align: right; }
.era-diff td:first-child { text-align: left; color: var(--muted); }
.era-diff td.up { color: var(--c-best); }
.era-diff td.down { color: var(--c-blunder); }
.era-open { font-size: 12px; color: var(--text-2); line-height: 1.5; }
.era-run { display: flex; align-items: center; gap: 7px; font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.era-result { display: flex; flex-direction: column; gap: 5px; font-size: 12.5px; color: var(--text-2); }
.era-result b { color: var(--text); font-size: 13.5px; }
.era-result.won b { color: var(--c-best); }
.era-result.lost b { color: var(--c-inaccuracy); }
.era-result .era-note, .era-result .era-when { color: var(--muted); font-size: 11.5px; }
.era-games { margin: 2px 0 0; padding: 0; list-style: none; display: flex; flex-direction: column; gap: 3px; }
.era-games li { display: grid; grid-template-columns: 38px 1fr auto; align-items: center; gap: 8px; font-size: 11.5px; color: var(--muted); }
.era-games .era-g { font-weight: 600; color: var(--text-2); }

.game-row .res.win { color: var(--c-best); } .game-row .res.loss { color: var(--c-blunder); } .game-row .res.draw { color: var(--muted); }
.game-row .row-end { display: flex; align-items: center; gap: 8px; }
.game-row .x { border: 0; background: transparent; color: var(--muted); cursor: pointer; padding: 2px 6px; border-radius: 6px; font-size: 11px; }
.game-row .x:hover { color: var(--danger); background: var(--panel); }
.games-list { max-height: 44vh; overflow: auto; display: flex; flex-direction: column; gap: 4px; margin-top: 10px; }
.game-row { display: grid; grid-template-columns: 1fr auto; gap: 8px; padding: 8px 10px; border-radius: 10px; border: 1px solid var(--line); cursor: pointer; }
.game-row:hover { background: var(--panel-2); }
.game-row .players { font-weight: 600; font-size: 13px; }
.game-row .meta { color: var(--muted); font-size: 11px; }
.game-row .res { font-family: var(--font-mono); font-weight: 600; }

/* toasts */
.toast-wrap { position: fixed; left: 50%; bottom: 22px; transform: translateX(-50%); display: flex; flex-direction: column; gap: 6px; z-index: 60; pointer-events: none; }
.toast { background: var(--panel); border: 1px solid var(--line-strong); color: var(--text); padding: 10px 14px; border-radius: 10px; font-size: 13px; box-shadow: var(--shadow); animation: pop 0.2s; }
.toast.err { border-color: var(--danger); }

/* ---------- puzzles ---------- */
.puzzle-head { display: flex; align-items: center; gap: 14px; padding: 14px; }
.stat { display: flex; flex-direction: column; }
.stat .k { color: var(--muted); font-size: 11px; text-transform: uppercase; letter-spacing: 0.08em; }
.stat .v { font-family: var(--font-display); font-size: 26px; line-height: 1.1; }
.turn-banner { display: flex; align-items: center; gap: 10px; padding: 12px 14px; font-size: 15px; font-weight: 500; border-top: 1px solid var(--line); }
.turn-banner i { width: 14px; height: 14px; border-radius: 4px; border: 1px solid var(--line-strong); }
.turn-banner.win { color: var(--c-best); } .turn-banner.fail { color: var(--c-blunder); }
.theme-select { padding: 10px 14px; border-top: 1px solid var(--line); display: flex; gap: 8px; align-items: center; font-size: 12px; color: var(--muted); }
.theme-select select { flex: 1; background: var(--panel-2); border: 1px solid var(--line); border-radius: 8px; padding: 6px 8px; }
.drill-list { display: flex; flex-direction: column; }
.drill { display: grid; grid-template-columns: auto minmax(0, 1fr) auto auto; gap: 10px; align-items: center; padding: 8px 14px; border-top: 1px solid var(--line); font-size: 13px; cursor: pointer; }
.drill:hover { background: var(--panel-2); }
.drill .n { font-family: var(--font-mono); color: var(--muted); }
.drill .st { font-size: 11px; font-family: var(--font-mono); }

/* ---------- play ---------- */
.play-setup { padding: 14px; display: flex; flex-direction: column; gap: 14px; }
.rating-pick { display: flex; flex-direction: column; gap: 6px; }
.rating-pick .val { font-family: var(--font-display); font-size: 42px; line-height: 1; letter-spacing: -0.03em; }
.rating-pick .val small { font-size: 13px; color: var(--muted); font-family: var(--font-ui); margin-left: 8px; letter-spacing: 0; }
input[type=range] { width: 100%; accent-color: var(--accent); }
.seg { display: inline-flex; background: var(--panel-2); border-radius: 10px; padding: 3px; gap: 2px; }
.seg.wrap { flex-wrap: wrap; }
.seg button { border: 0; background: transparent; color: var(--muted); padding: 6px 12px; border-radius: 8px; font-weight: 500; }
.seg button.active { background: var(--panel); color: var(--text); box-shadow: 0 1px 2px rgba(0,0,0,0.3); }
.seg button:disabled { opacity: 0.55; cursor: default; }
.persona { display: grid; grid-template-columns: 44px 1fr; gap: 10px; align-items: center; padding: 10px; border-radius: 10px; background: var(--panel-2); }
.persona .av { width: 44px; height: 44px; border-radius: 12px; display: grid; place-items: center; font-family: var(--font-display); font-size: 22px; background: var(--accent-soft); color: var(--accent); }
.persona .nm { font-weight: 600; }
.persona .desc { font-size: 12px; color: var(--muted); }
.clock { font-family: var(--font-mono); font-size: 22px; padding: 4px 10px; border-radius: 8px; background: var(--panel-2); }
.clock.active { background: var(--accent); color: var(--accent-ink); }
.play-status { padding: 12px 14px; font-size: 14px; border-top: 1px solid var(--line); }
.play-status b { color: var(--accent); }

/* ---------- setup ---------- */
.palette { display: grid; grid-template-columns: repeat(6, 1fr); gap: 6px; padding: 12px 14px; }
.pal { aspect-ratio: 1; border-radius: 10px; border: 1px solid var(--line); background: var(--panel-2) center / 80% no-repeat; cursor: pointer; }
.pal:hover { border-color: var(--line-strong); }
.pal.active { border-color: var(--accent); box-shadow: 0 0 0 2px var(--accent-soft); }
.pal.trash { display: grid; place-items: center; color: var(--danger); }
.setup-opts { padding: 0 14px 12px; display: flex; flex-direction: column; gap: 10px; font-size: 13px; }
.setup-opts label { display: flex; gap: 8px; align-items: center; }
.setup-opts input[type=text] { width: 100%; background: var(--bg-2); border: 1px solid var(--line); border-radius: 8px; padding: 8px 10px; font-family: var(--font-mono); font-size: 12px; }
.chk-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 6px; }

/* shortcuts footer */
.kbd-hint { color: var(--muted); font-size: 11px; padding: 4px 6px; }
kbd { font-family: var(--font-mono); font-size: 10px; background: var(--panel-2); border: 1px solid var(--line-strong); border-radius: 4px; padding: 1px 5px; }

.spin { display: inline-block; width: 12px; height: 12px; border: 2px solid var(--line-strong); border-top-color: var(--accent); border-radius: 50%; animation: spin 0.8s linear infinite; }
@keyframes spin { to { transform: rotate(360deg); } }
::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-thumb { background: var(--line-strong); border-radius: 5px; border: 2px solid transparent; background-clip: padding-box; }

/* ---------- my games ---------- */
.workspace.single { grid-template-columns: minmax(300px, 780px); }
.games-list.tall { max-height: none; padding: 8px; display: flex; flex-direction: column; gap: 4px; }
.acct-row { display: flex; gap: 8px; flex-wrap: wrap; }
.acct-chip { display: inline-flex; align-items: center; gap: 8px; padding: 6px 8px 6px 12px; border: 1px solid var(--line); border-radius: 999px; background: var(--panel-2); font-size: 13px; }
.acct-chip .site { color: var(--muted); font-size: 11px; }
.acct-chip .x { border: 0; background: transparent; color: var(--muted); cursor: pointer; padding: 2px 6px; border-radius: 999px; font-size: 11px; }
.acct-chip .x:hover { color: var(--danger); background: var(--panel); }
.game-row .res { font-family: var(--font-mono); font-weight: 700; align-self: center; min-width: 22px; text-align: center; }
.game-row .res.win { color: var(--c-best); }
.game-row .res.loss { color: var(--c-blunder); }
.game-row .res.draw { color: var(--muted); }


/* ---------- insights ---------- */
.game-row .row-end { display: flex; align-items: center; gap: 10px; }
.game-row .done { color: var(--c-best); font-size: 13px; font-weight: 700; }

/* Both users of this grid hold exactly four tiles, so auto-fit's three-across
   step leaves the fourth alone in a row next to an empty cell. Four or two,
   never three. */
.stat-grid { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 1px; background: var(--line); border-bottom: 1px solid var(--line); }
@media (max-width: 900px) { .stat-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.stat-tile { background: var(--panel); padding: 14px; display: flex; flex-direction: column; gap: 2px; }
.stat-tile .k { color: var(--muted); font-size: 11px; text-transform: uppercase; letter-spacing: 0.07em; }
.stat-tile .v { font-family: var(--font-display); font-size: 30px; line-height: 1.05; letter-spacing: -0.03em; font-variant-numeric: tabular-nums; }
.stat-tile .v small { font-size: 13px; color: var(--muted); margin-left: 2px; }
.stat-tile .d { font-size: 11.5px; color: var(--muted); font-variant-numeric: tabular-nums; }
.stat-tile .d.up { color: var(--c-best); }
.stat-tile .d.down { color: var(--c-mistake); }

.panel-block { padding: 14px; border-bottom: 1px solid var(--line); display: flex; flex-direction: column; gap: 12px; }
.bar-title { font-size: 11px; text-transform: uppercase; letter-spacing: 0.07em; color: var(--muted); }
.bar-title small { text-transform: none; letter-spacing: 0; }
.spark { width: 100%; height: 64px; display: block; }
.bar-group { display: flex; flex-direction: column; gap: 5px; }
.bar-row { display: grid; grid-template-columns: 86px 1fr 46px 34px; gap: 8px; align-items: center; font-size: 12.5px; }

/* the clock block: same shape as the accuracy bars, but the bar means "how
   often this goes wrong", so it runs warm rather than accent-coloured */
/* earlier vs recent: a row is two numbers and an arrow. Green and red are
   reserved for measures that actually cleared their threshold. */
.prog-headline { margin: 0 0 10px; font-size: 13.5px; color: var(--text-2); }
.prog { display: grid; grid-template-columns: 1fr auto 14px auto 66px; gap: 8px; align-items: baseline; padding: 5px 0; font-size: 12.5px; border-top: 1px solid var(--line); }
.prog:first-of-type { border-top: 0; }
.prog .k { color: var(--text-2); }
.prog .was { font-family: var(--font-mono); color: var(--muted); }
.prog .arrow { color: var(--muted); text-align: center; }
.prog .now { font-family: var(--font-mono); color: var(--text); }
.prog .delta { font-family: var(--font-mono); font-size: 11.5px; text-align: right; color: var(--muted); }
.prog.better .now, .prog.better .delta { color: var(--c-best); font-weight: 600; }
.prog.worse .now, .prog.worse .delta { color: var(--c-blunder); font-weight: 600; }
.prog-legend { margin-top: 10px; font-size: 11.5px; color: var(--muted); line-height: 1.5; }

.clock-row { display: grid; grid-template-columns: 86px 1fr 46px 34px; gap: 8px; align-items: center; font-size: 12.5px; padding: 2px 0; }
.clock-row .k { color: var(--text-2); }
.clock-row .bar { height: 7px; border-radius: 4px; background: var(--panel-2); overflow: hidden; }
.clock-row .bar i { display: block; height: 100%; background: var(--c-inaccuracy); border-radius: 4px; }
.clock-row .v { font-family: var(--font-mono); text-align: right; }
.clock-row .n { font-family: var(--font-mono); color: var(--muted); text-align: right; font-size: 11px; }
.clock-row.hot .bar i { background: var(--c-blunder); }
.clock-row.hot .k, .clock-row.hot .v { color: var(--c-blunder); font-weight: 600; }
.clock-legend { white-space: nowrap; display: grid; grid-template-columns: 86px 1fr 46px 34px; gap: 8px; padding-top: 6px; font-size: 10px; text-transform: uppercase; letter-spacing: 0.06em; color: var(--muted); }
.clock-legend span:nth-child(3), .clock-legend span:nth-child(4) { text-align: right; }
.bar-row .k { color: var(--text-2); }
.bar-row .bar { height: 7px; background: var(--line); border-radius: 4px; overflow: hidden; }
.bar-row .bar i { display: block; height: 100%; background: var(--accent); border-radius: 4px; }
.bar-row .v { font-family: var(--font-mono); text-align: right; font-variant-numeric: tabular-nums; }
.bar-row .n { font-family: var(--font-mono); color: var(--muted); font-size: 11px; text-align: right; }

.weak-list { display: flex; flex-direction: column; }
.weak { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; gap: 14px; align-items: center; padding: 13px 14px; border-top: 1px solid var(--line); }
.weak:first-child { border-top: 0; }
.weak .metric { font-family: var(--font-display); font-size: 24px; color: var(--accent); letter-spacing: -0.02em; min-width: 52px; text-align: center; font-variant-numeric: tabular-nums; }
.weak .t { font-weight: 600; font-size: 14.5px; }
.weak .d { color: var(--text-2); font-size: 13px; }

.moment-list { display: flex; flex-direction: column; padding-bottom: 6px; }
.moment { display: grid; grid-template-columns: 84px minmax(0, 1fr) auto auto; gap: 10px; align-items: center; padding: 9px 14px; border-top: 1px solid var(--line); cursor: pointer; font-size: 13px; }
.moment:hover { background: var(--panel-2); }
.moment .mv { font-family: var(--font-mono); font-weight: 600; }
.moment .why { color: var(--muted); font-size: 12px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.moment .date { font-family: var(--font-mono); font-size: 11px; color: var(--muted); }
/* A conversion is labelled with a phrase ("move 41, before Rd1"), not a move
   number, so it needs the room the 84px move column does not have. */
.moment.conv { grid-template-columns: minmax(150px, 1.4fr) minmax(0, 1fr) auto auto; }
.moment.conv .mv { font-family: var(--font-ui); font-weight: 500; }

/* ---------- drill scheduling ---------- */
/* the report that runs the moment a bot game ends */
.pl-sum-load { padding: 12px 14px; font-size: 13px; color: var(--muted); display: flex; align-items: center; gap: 8px; }
.pl-sum-top { display: grid; grid-template-columns: repeat(3, 1fr); gap: 1px; background: var(--line); border-top: 1px solid var(--line); border-bottom: 1px solid var(--line); }
.pl-sum-top .acc { background: var(--panel); padding: 10px 12px; display: flex; flex-direction: column; gap: 2px; }
.pl-sum-top .acc b { font-family: var(--font-display); font-size: 20px; font-weight: 500; }
.pl-sum-top .acc small { color: var(--muted); font-size: 11px; }
.pl-turns { display: flex; flex-direction: column; }
.pl-turn { display: grid; grid-template-columns: 74px 1fr auto; gap: 10px; align-items: baseline; padding: 8px 14px; border-bottom: 1px solid var(--line); cursor: pointer; font-size: 13px; }
.pl-turn:hover { background: var(--panel-2); }
.pl-turn .mv { font-family: var(--font-mono); font-weight: 600; }
.pl-turn .why { font-size: 12px; }
.pl-turn .best { font-family: var(--font-mono); font-size: 12px; color: var(--c-best); }
.pl-clean { padding: 12px 14px; font-size: 13px; color: var(--text-2); border-bottom: 1px solid var(--line); }

.remind-row { display: flex; align-items: center; gap: 14px; flex-wrap: wrap; padding: 12px 14px 4px; font-size: 13px; }
.remind-row label { display: flex; align-items: center; gap: 7px; color: var(--text-2); }
.remind-row input[type="time"] {
  background: var(--bg-2); border: 1px solid var(--line); color: var(--text);
  border-radius: 8px; padding: 5px 8px; font-family: var(--font-mono); font-size: 13px;
}
.remind-row input[type="checkbox"] { accent-color: var(--accent); }
.remind-at { opacity: 0.5; pointer-events: none; transition: opacity .15s; }
.remind-row.on .remind-at { opacity: 1; pointer-events: auto; }

.drill-stats { display: flex; gap: 6px; flex-wrap: wrap; padding: 10px 14px 2px; }
.drill-stats .chip { font-size: 11.5px; color: var(--muted); border: 1px solid var(--line); border-radius: 999px; padding: 3px 9px; }
.drill-stats .chip b { color: var(--text-2); font-family: var(--font-mono); font-weight: 600; }
.drill-stats .chip.hot { border-color: var(--accent); color: var(--accent); }
.drill-stats .chip.hot b { color: var(--accent); }
.drill-stats .chip.muted { opacity: 0.7; }
.drill.due { box-shadow: inset 2px 0 0 var(--accent); }
.drill.cur { background: var(--panel-2); }
.drill .hint { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.drill .st.new { color: var(--muted); }
.drill .st.learning { color: var(--c-inaccuracy); }
.drill .st.learned { color: var(--c-best); }
.drill.due .st { color: var(--accent); font-weight: 600; }

/* ---------- openings ---------- */
.op-crumb { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; padding: 12px 14px 8px; }
.crumb { border: 1px solid var(--line); background: var(--panel-2); color: var(--text-2); border-radius: 999px; padding: 4px 11px; font-family: var(--font-mono); font-size: 12px; }
.crumb:hover { border-color: var(--line-strong); color: var(--text); }
.crumb.active { border-color: var(--accent); color: var(--accent); background: var(--accent-soft); }
.crumb-score { margin-left: auto; font-size: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.op-moves { display: flex; flex-direction: column; }
.op-move { display: grid; grid-template-columns: 62px 1fr 34px 44px 46px; gap: 10px; align-items: center; padding: 9px 14px; border-top: 1px solid var(--line); cursor: pointer; }
.op-move:hover { background: var(--panel-2); }
.op-move .san { font-family: var(--font-mono); font-weight: 600; font-size: 13.5px; }
.op-move .share { height: 7px; background: var(--line); border-radius: 4px; overflow: hidden; }
.op-move .share i { display: block; height: 100%; background: var(--accent); border-radius: 4px; }
.op-move .n, .op-move .sc, .op-move .acc { font-family: var(--font-mono); font-size: 12px; text-align: right; font-variant-numeric: tabular-nums; }
.op-move .n { color: var(--muted); }
.op-move .sc.good { color: var(--c-best); } .op-move .sc.bad { color: var(--c-blunder); }
.op-move .acc { color: var(--muted); }
.op-legend { display: grid; grid-template-columns: 62px 1fr 34px 44px 46px; gap: 10px; padding: 6px 14px 12px; font-size: 10px; text-transform: uppercase; letter-spacing: 0.06em; color: var(--muted); border-top: 1px solid var(--line); }
.op-legend span:nth-child(n+3) { text-align: right; }
/* The scout has no accuracy to report — nobody analyses an opponent's games. */
.op-moves.four .op-move, .op-legend.four { grid-template-columns: 62px 1fr 34px 52px; }

/* One prep sentence per row, with the evidence behind it kept in view. */
.brief-list { display: flex; flex-direction: column; }
.brief-row { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 4px 14px; align-items: baseline; padding: 11px 14px; border-top: 1px solid var(--line); }
.brief-row .t { font-size: 13.5px; line-height: 1.5; }
.brief-row .n { font-family: var(--font-mono); font-size: 10.5px; color: var(--muted); white-space: nowrap; }
@media (max-width: 560px) {
  .brief-row { grid-template-columns: minmax(0, 1fr); }
  .brief-row .n { white-space: normal; }
}
.dev-list { display: flex; flex-direction: column; }
.dev { padding: 11px 14px; border-top: 1px solid var(--line); cursor: pointer; display: flex; flex-direction: column; gap: 4px; }
.dev:hover { background: var(--panel-2); }
/* NOT .line — that class belongs to the engine's PV rows, which are a 56px
   grid, and reusing it squeezed every move list into that first column. */
.dev .dev-line { font-family: var(--font-mono); font-size: 12.5px; color: var(--text-2); line-height: 1.45; }
.dev .cmp { display: flex; align-items: center; gap: 10px; font-size: 13px; flex-wrap: wrap; }
.dev .cmp b { font-family: var(--font-mono); }
.dev .cmp small { color: var(--muted); font-size: 11px; }
.dev .main { color: var(--c-best); }
.dev .alt { color: var(--c-mistake); }
.dev .arrow { color: var(--muted); font-size: 11px; }

/* ---------- first run ---------- */
.first-run { padding: 18px 16px; display: flex; flex-direction: column; gap: 10px; }
.first-run h4 { font-family: var(--font-display); font-weight: 500; font-size: 17px; }
.first-run p { margin: 0; color: var(--text-2); font-size: 13.5px; }
.first-run .row { gap: 8px; }
.drill .kill { border: 0; background: transparent; color: var(--muted); padding: 2px 6px; border-radius: 6px; font-size: 11px; }
.drill .kill:hover { color: var(--danger); background: var(--panel); }

/* ---------- board palettes ---------- */
:root[data-board="forest"] { --sq-light: #eaead2; --sq-dark: #779455; }
:root[data-board="ocean"]  { --sq-light: #dee3e6; --sq-dark: #6f8fb0; }
:root[data-board="slate"]  { --sq-light: #d8d8d4; --sq-dark: #7d7f84; }

/* Between phone and desktop the board had no height limit at all: on a tablet it
   grew to the full column width, overflowed the screen and pushed the evaluation

/* Wide but short — a phone on its side, or a tablet in landscape. There is plenty
   of room to put the panel beside the board here; what there is not room for is a
   board sized by width. Size it by height instead and the two fit side by side,

/* Your own words about a move. */
.note-box { padding: 8px 14px 10px; border-top: 1px solid var(--line); display: flex; flex-direction: column; gap: 6px; align-items: flex-start; }
.note-box.empty-note { opacity: 0.65; }
.note-box.empty-note:hover { opacity: 1; }
.note-text { margin: 0; font-size: 13px; line-height: 1.5; color: var(--text-2); white-space: pre-wrap; }
.note-input {
  width: 100%; background: var(--bg-2); color: var(--text); font: inherit; font-size: 13px;
  border: 1px solid var(--line); border-radius: 8px; padding: 8px 10px; resize: vertical;
}
.note-box .row.end { width: 100%; display: flex; justify-content: flex-end; gap: 6px; }
.mv .has-note { display: inline-block; width: 5px; height: 5px; border-radius: 50%; background: var(--accent); vertical-align: middle; margin-left: 4px; }

/* Every line tried from this game, so a second idea does not erase the first. */
.branch-list { display: flex; flex-direction: column; }
.branch { display: grid; grid-template-columns: 46px minmax(0, 1fr) auto auto; gap: 8px; align-items: baseline; padding: 8px 14px; border-top: 1px solid var(--line); cursor: pointer; font-size: 12.5px; }
.branch:hover { background: var(--panel-2); }
.branch.cur { box-shadow: inset 2px 0 0 var(--accent); background: var(--panel-2); }
.branch .at { font-family: var(--font-mono); color: var(--muted); }
.branch .sans { font-family: var(--font-mono); color: var(--text-2); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.branch.cur .sans { color: var(--text); }
.branch .bname { font-family: var(--font-ui); color: var(--accent); font-weight: 600; }
.branch .kill, .branch .rename { border: 0; background: transparent; color: var(--muted); padding: 2px 6px; border-radius: 6px; font-size: 11px; }
.branch .rename:hover { color: var(--accent); background: var(--panel); }
.branch .kill:hover { color: var(--danger); background: var(--panel); }

/* The concrete half of a coach note: what the position actually did. */
.coach-why { margin: 4px 0 0; color: var(--text); font-size: 13px; line-height: 1.5; }

/* ---------- reachable without a mouse ---------- */

/* Present to a screen reader, absent to everyone else. */
.sr-only {
  position: absolute; width: 1px; height: 1px; margin: -1px; padding: 0;
  overflow: hidden; clip: rect(0 0 0 0); clip-path: inset(50%); white-space: nowrap; border: 0;
}

.skip-link {
  position: absolute; left: 8px; top: -60px; z-index: 100;
  background: var(--accent); color: var(--accent-ink);
  padding: 10px 14px; border-radius: 10px; font-weight: 600; font-size: 13px;
  transition: top .15s;
}
.skip-link:focus { top: 8px; }

/* One visible focus treatment for everything, including the rows that only look
   like buttons. :focus-visible keeps it off pointer clicks. */
:where(a, button, input, select, textarea, [tabindex]):focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
  border-radius: 8px;
}
.pboard:focus-visible { outline-offset: 4px; }

/* The square the keyboard is standing on. */
.psq.hl-cursor { box-shadow: inset 0 0 0 3px var(--accent); }

@media (prefers-reduced-motion: reduce) {
  .ppiece { transition: none !important; }
  .skip-link { transition: none; }
  *, *::before, *::after { animation-duration: .001ms !important; animation-iteration-count: 1 !important; }
}

/* ---------------------------------------------------------------------------
   Responsive overrides live at the end, all of them.
   A media query adds no specificity, so a breakpoint rule placed before the
   component it overrides silently loses — which had quietly killed a dozen
   declarations here, including the phone board-height cap and the tablet
   width cap. Widest range first, so narrower ones win.
   --------------------------------------------------------------------------- */

@media (max-width: 1080px) {
  .workspace { grid-template-columns: 1fr; }
  .board-col { max-width: 720px; margin: 0 auto; width: 100%; }
}

@media (max-width: 720px) {
  .shell { grid-template-columns: 1fr; grid-template-rows: 1fr auto; }
  .rail { flex-direction: row; order: 2; padding: 4px 6px; gap: 0; border-right: 0; border-top: 1px solid var(--line); }
  .brand, .rail-spacer, .rail-foot { display: none; }
  .rail-nav { flex-direction: row; padding: 0; gap: 2px; }
  .rail-btn { padding: 8px 4px; font-size: 11px; }
  .workspace { padding: 10px 10px 4px; gap: 10px; }
  /* Cap the board so the eval / setup panel sits within reach, not a full screen down. */
  .board-col { gap: 8px; }
  .board-frame { max-width: min(100%, 64vh); margin: 0 auto; width: 100%; }
  .player-strip, .rush-hud { max-width: min(100%, 64vh); margin: 0 auto; width: 100%; }
  /* Toolbar: keep the move nav on its own line, wrap actions cleanly (no orphans). */
  .board-tools { gap: 6px; }
  .board-tools .nav-group { flex: 1 1 100%; }
  .board-tools .nav-group button { flex: 1; padding: 11px 0; }
  .board-tools .btn { flex: 1 1 auto; justify-content: center; }
  .board-tools .btn.sm { padding: 9px 10px; font-size: 13px; }
  .tool-spacer { display: none; }
  /* Roomier tap targets on controls and rows. */
  .icon-btn { width: 38px; height: 38px; }
  .mv { padding: 7px 8px; }
  .tab { padding: 13px 6px; }
  .eval-big { font-size: 34px; min-width: 74px; }
  .movelist { max-height: 38vh; }
  .kbd-hint { display: none; }
  /* Keep bottom-anchored content clear of the tab bar. */
  .stage { padding-bottom: 4px; }
}

@media (max-width: 620px) {
  .prog { grid-template-columns: 1fr auto 12px auto 54px; gap: 6px; font-size: 12px; }
}

@media (max-width: 620px) {
  .clock-row, .clock-legend { grid-template-columns: 74px 1fr 40px 30px; gap: 6px; }
}

@media (max-width: 620px) {
  /* the openings header carries a title, a colour switch and an action: on a
     phone the action gets its own row rather than wrapping to three words */
  #op-train { margin: 0; width: 100%; }

  .moment { grid-template-columns: 76px 1fr auto; }
  .moment .date { display: none; }
  .weak .metric { font-size: 20px; min-width: 44px; }
}

@media (max-width: 620px) {
  .pl-turn { grid-template-columns: 66px 1fr auto; gap: 7px; }
}

@media (max-width: 620px) {
  .op-move, .op-legend { grid-template-columns: 54px 1fr 30px 40px 42px; gap: 7px; }
}

@media (max-height: 620px) {
  textarea.paste { min-height: 92px; }
  .modal-h h2 { font-size: 19px; }
}

/* Between phone and desktop the board had no height limit at all: on a tablet it
   grew to the full column width, overflowed the screen and pushed the evaluation
   panel entirely below the fold. Cap it by what is actually on screen. */
@media (min-width: 721px) and (max-width: 1080px) {
  .board-col { max-width: min(720px, calc(100dvh - 190px)); }
}

/* Wide but short — a phone on its side, or a tablet in landscape. There is plenty
   of room to put the panel beside the board here; what there is not room for is a
   board sized by width. Size it by height instead and the two fit side by side,
   which is the whole reason to turn a device sideways. */
@media (min-width: 700px) and (max-width: 1080px) and (orientation: landscape) {
  .workspace {
    /* the panel's minimum is what stops a tall screen giving the board so much
       width that the evaluation header has to wrap onto four lines */
    grid-template-columns: minmax(200px, calc(100dvh - 104px)) minmax(340px, 1fr);
    gap: 14px; padding: 12px 16px 14px;
    align-items: start;
  }
  .board-col { max-width: none; margin: 0; gap: 8px; }
  .board-tools { gap: 6px; }
  .board-tools .btn { padding: 6px 9px; font-size: 12px; }
  /* The eval header is three columns in a narrow panel; shrink the outer two so
     the engine's own line has somewhere to go. */
  .engine-top { gap: 8px; padding: 10px 12px 6px; }
  .eval-big { font-size: 30px; min-width: 58px; }
  .engine-ctl .icon-btn { width: 32px; height: 32px; }
}
