/* Site styles. One family (Bricolage Grotesque), a slate-and-river palette taken from the
   redrawn map, team blue/red, and gold for the player you searched. Keep the colour tokens in
   sync with crates/player/src/color.rs. Built into public/build/style-<hash>.css by web/build.mjs. */

:root {
  --bg: #0d1215;
  --panel: #121a1e;
  --raise: #18232a;
  --line: #24323a;
  --line-soft: #1b262c;
  --ink: #e8e4da;
  --ink-2: #b4b9b2;
  --muted: #7d8984;
  --blue: #4c9be8;
  --blue-deep: #1d3550;
  --red: #e5534b;
  --red-deep: #4a2427;
  --gold: #f3c969;
  --river: #2c7d93;
  --up: #46b97c;
  --focus-ring: 0 0 0 2px var(--bg), 0 0 0 4px var(--gold);
  --font: "Bricolage Grotesque", ui-sans-serif, system-ui, -apple-system, "Segoe UI", sans-serif;
  --r-lg: 14px;
  --r-md: 8px;
  --r-sm: 5px;
  color-scheme: dark;
}

*, *::before, *::after { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; }
/* Sticky footer: the page is a column at least the viewport tall, the shown main grows, and the
   footer comes last, so a short page puts it at the bottom and a long one after the content. */
body {
  margin: 0;
  display: flex; flex-direction: column;
  min-height: 100svh;
  min-height: 100dvh;
  background: var(--bg);
  color: var(--ink);
  font-family: var(--font);
  font-size: 15px;
  line-height: 1.5;
  font-optical-sizing: auto;
  font-variant-numeric: tabular-nums;
  -webkit-font-smoothing: antialiased;
}
button, input, select { font: inherit; color: inherit; }
button { cursor: pointer; }
:focus-visible { outline: none; box-shadow: var(--focus-ring); border-radius: var(--r-sm); }
img { display: block; }
[hidden] { display: none !important; }
.visually-hidden {
  position: absolute !important; width: 1px; height: 1px; overflow: hidden;
  clip-path: inset(50%); white-space: nowrap;
}

/* ---- Top bar ---------------------------------------------------------------------------- */
/* Pinned while the page scrolls: opaque enough to read over rows, the notch area inside its own
   padding so nothing shows above it. Above page content (z <= 5), below the fixed hovercards,
   toast, fullscreen player and drop veil (50-100); its menus are top-layer popovers. */
.topbar {
  display: flex; align-items: center; gap: 20px;
  padding: max(14px, env(safe-area-inset-top)) max(16px, env(safe-area-inset-left)) 14px max(16px, env(safe-area-inset-right));
  min-height: 64px;
  position: sticky; top: 0; z-index: 40;
  background: color-mix(in srgb, var(--bg) 92%, transparent);
  -webkit-backdrop-filter: blur(10px); backdrop-filter: blur(10px);
  box-shadow: 0 1px 0 var(--line-soft);
}
/* Scrolling to something (a focused field, a restored row) keeps it clear of the bar. */
html { scroll-padding-top: calc(var(--topbar-h, 64px) + 8px); }
.mark {
  display: inline-flex; align-items: center; gap: 8px;
  color: var(--ink); text-decoration: none;
  font-weight: 700; font-size: 19px; letter-spacing: -0.02em;
}
.mark svg { width: 26px; height: 26px; fill: none; stroke: var(--gold); stroke-width: 3; stroke-linecap: round; }

.search { position: relative; display: flex; gap: 6px; align-items: stretch; flex: 1; max-width: 560px; min-width: 0; }
.search input, .search select {
  background: var(--panel); border: 1px solid var(--line); border-radius: var(--r-md);
  padding: 9px 12px; min-width: 0;
}
.search input { flex: 1; width: 100%; }
.search button, .search select { flex: none; }
.search input::placeholder { color: var(--muted); }
.search select { padding-right: 6px; }
.search button {
  border: 0; border-radius: var(--r-md); padding: 9px 16px; font-weight: 650;
  background: var(--ink); color: var(--bg); white-space: nowrap;
}
.search button:hover { background: #fff; }
.search button[disabled] { opacity: 0.6; cursor: progress; }

/* On the landing page the search lives in the intro, at a larger size. */
body[data-view="landing"] .topbar .search { display: none; }
.search-slot .search { display: flex; max-width: none; }
.search-slot .search input, .search-slot .search select, .search-slot .search button { padding: 13px 16px; font-size: 17px; }
/* Riot ID suggestions under the input: recent searches first, then the players index. */
.suggest {
  position: absolute; left: 0; top: calc(100% + 4px); z-index: 30; margin: 0; padding: 4px; list-style: none;
  background: var(--panel); border: 1px solid var(--line); border-radius: var(--r-md);
  box-shadow: 0 10px 28px rgba(0, 0, 0, 0.45); max-height: 340px; overflow-y: auto;
}
.suggest[hidden] { display: none; }
.suggest li {
  display: flex; padding: 7px 10px; border-radius: var(--r-sm); cursor: pointer; font-size: 15px;
  color: var(--ink-2);
}
.suggest li .n { min-width: 0; white-space: normal; overflow-wrap: break-word; }
.suggest li .tag { color: var(--muted); flex: none; }
.suggest li.mine { color: var(--ink); }
.suggest li.mine + li:not(.mine) { margin-top: 5px; box-shadow: 0 -3px 0 -2px var(--line-soft); }
.suggest li[aria-selected="true"], .suggest li:hover { background: var(--raise); color: var(--ink); }
.search-slot .suggest li { padding: 9px 14px; font-size: 16px; }

/* ---- Landing ------------------------------------------------------------------------------ */
.landing {
  display: grid; grid-template-columns: minmax(0, 0.85fr) minmax(0, 1.2fr);
  gap: clamp(24px, 4vw, 64px); align-items: start;
  padding: clamp(8px, 4vh, 48px) max(16px, 4vw) 48px;
  max-width: 1440px; margin: 0 auto; align-content: center;
}
.intro { padding-top: clamp(0px, 6vh, 64px); min-width: 0; }
h1 {
  font-size: clamp(2.6rem, 6vw, 4.6rem); line-height: 0.98; letter-spacing: -0.035em;
  font-weight: 760; margin: 0 0 18px; font-variation-settings: "opsz" 96;
}
.lede { font-size: 18px; line-height: 1.55; color: var(--ink-2); max-width: 34em; margin: 0 0 28px; }
.sample-line { color: var(--muted); margin: 14px 0 0; }

/* Drop zone: the main way in. */
.drop {
  display: grid; justify-items: center; text-align: center; gap: 2px; cursor: pointer;
  padding: 26px 20px 22px; border: 1.5px dashed #3a4d56; border-radius: var(--r-lg);
  background: linear-gradient(180deg, rgba(243, 201, 105, 0.05), rgba(243, 201, 105, 0) 70%), var(--panel);
  transition: border-color 0.15s, background-color 0.15s;
}
.drop:hover, .drop:focus-visible { border-color: var(--gold); }
.drop svg { width: 40px; height: 40px; fill: none; stroke: var(--gold); stroke-width: 2.2; stroke-linecap: round; stroke-linejoin: round; margin-bottom: 6px; }
.drop-title { margin: 0; font-size: 19px; font-weight: 650; letter-spacing: -0.01em; }
.drop-title b { color: var(--gold); font-weight: 700; }
.drop-sub { margin: 0; }
.drop-hint { margin: 8px 0 0; font-size: 12.5px; color: var(--muted); }
.drop-hint code { font-family: inherit; color: var(--ink-2); }
.or { margin: 26px 0 10px; color: var(--ink-2); font-weight: 600; }
.drop-veil {
  position: fixed; inset: 0; z-index: 100; display: grid; place-items: center; pointer-events: none;
  background: rgba(13, 18, 21, 0.82); border: 3px dashed var(--gold);
}
.drop-veil p { font-size: 28px; font-weight: 700; letter-spacing: -0.02em; }
/* Replay / game card with the decoder status. */
.card { background: var(--panel); border: 1px solid var(--line); border-radius: var(--r-lg); padding: 14px 16px; margin: 0 0 14px; }
.card-head { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 12px; margin-bottom: 10px; }
.card-head h2 { margin: 0; font-size: 18px; letter-spacing: -0.01em; }
.card-head .sub { color: var(--muted); font-size: 13px; }
.card-teams { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin-bottom: 10px; }
.card-team-head { margin: 0 0 4px; font-size: 12.5px; font-weight: 650; color: var(--team); }
.card-player { display: grid; grid-template-columns: 28px minmax(0, 1fr) auto; align-items: center; gap: 8px; padding: 2px 0; font-size: 13px; }
.card-player img { width: 28px; height: 28px; border-radius: 50%; box-shadow: 0 0 0 1.5px var(--team); }
.card-name { min-width: 0; overflow-wrap: break-word; }
.card-kda { color: var(--ink-2); font-weight: 600; }
.card-status .status { margin: 0; }
.upload { display: grid; gap: 6px; color: var(--ink-2); font-size: 14px; font-variant-numeric: tabular-nums; }
.upload-bar { height: 4px; border-radius: 2px; background: var(--raise); overflow: hidden; }
.upload-bar i { display: block; height: 100%; width: 0; background: var(--gold); transition: width 0.2s linear; }
.status.busy::before {
  content: ""; display: inline-block; width: 10px; height: 10px; margin-right: 8px; vertical-align: -1px;
  border-radius: 50%; border: 2px solid var(--muted); border-top-color: var(--gold); animation: spin 0.8s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }
.badge {
  display: inline-block; vertical-align: 1px; font-size: 11px; font-weight: 650; padding: 1px 7px; border-radius: 999px;
  background: var(--raise); color: var(--muted); margin-left: 4px;
}
.badge.decoded { background: #2a2414; color: var(--gold); }
.badge.file { color: var(--ink-2); }
/* Row layout rules are scoped to their parent (`.game-row > .gr-…`, `.game-card > .gr-strip`) so
   another element reusing a class name can't take a row's layout (a team wrapper once did).
   The row's right strip: the analysis square on top (Analyze button, progress ring with percent,
   Analyzed, Can't analyze, Retry), the scoreboard chevron below; each half the row's height. */
.game-card > .gr-strip { display: grid; grid-template-rows: repeat(2, 1fr); border-left: 1px solid var(--line-soft); min-height: 0; }
.game-card > .gr-strip > .expand { border-left: 0; border-top: 1px solid var(--line-soft); }
.game-card > .gr-strip > .az-sq, .game-card > .gr-strip > .az-slot { min-height: 30px; }
.az-slot { display: grid; min-height: 0; }
.az-sq {
  position: relative; display: grid; place-items: center; width: 100%; height: 100%; min-height: 36px;
  padding: 0; border: 0; background: transparent; color: var(--gold);
}
button.az-sq:hover { background: var(--raise); }
button.az-sq:focus-visible { box-shadow: inset 0 0 0 2px var(--gold); border-radius: 0; }
.az-sq.busy { color: var(--ink-2); cursor: default; }
.az-sq.busy:hover { background: transparent; }
.az-sq.failed { color: #f2a19b; }
.az-sq.done { color: var(--gold); }
.az-sq.cant { color: var(--muted); }
.az-glyph { width: 20px; height: 20px; fill: none; stroke: currentColor; stroke-width: 1.7; stroke-linecap: round; stroke-linejoin: round; }
.az-pct { position: absolute; inset: 0; display: grid; place-items: center; font-size: 8.5px; font-weight: 700; color: var(--ink); font-variant-numeric: tabular-nums; letter-spacing: -0.02em; }
.az-ring { width: 28px; height: 28px; transform: rotate(-90deg); }
.az-ring circle { fill: none; stroke-width: 2.4; }
.az-ring .track { stroke: var(--line); }
.az-ring .arc { stroke: var(--gold); stroke-linecap: round; transition: stroke-dasharray 0.4s linear; }
.az-ring.spin { animation: az-turn 1s linear infinite; }
@keyframes az-turn { from { transform: rotate(-90deg); } to { transform: rotate(270deg); } }
@media (prefers-reduced-motion: reduce) { .az-ring.spin { animation: none; } .az-ring .arc { transition: none; } }
.az-tags { display: contents; }
.az-note { font-size: 12.5px; color: var(--muted); margin-top: 2px; overflow-wrap: anywhere; }
.az-note.error { color: #f2a19b; }

/* Early-game tags: outlined pills, blue for the searched player's team, red for the enemy's (the
   row's filled stripe is win/loss). */
/* A wrapping group in the wrapping name line: on a narrow row the group takes its own line(s). */
.etags { display: flex; flex-wrap: wrap; gap: 2px 4px; }
.etag {
  font-size: 11px; font-weight: 650; padding: 0 6px; border-radius: 999px; border: 1px solid currentColor;
  white-space: nowrap;
}
@media (max-width: 480px) { .etag { font-size: 10px; padding: 0 5px; } }
.etag.us { color: var(--blue); }
.etag.them { color: var(--red); }
.recent { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 14px; }
.recent[hidden] { display: none; }
.recent button {
  border: 1px solid var(--line); background: var(--panel); border-radius: 999px; padding: 4px 12px; font-size: 13px; color: var(--ink-2);
}
.recent button:hover { color: var(--ink); border-color: #33454e; }
.recent button small { color: var(--muted); margin-left: 4px; }
.link {
  background: none; border: 0; padding: 0; color: var(--gold);
  text-decoration: underline; text-underline-offset: 3px; text-decoration-thickness: 1px;
}
.showcase {
  margin: 0; position: sticky; top: 16px; aspect-ratio: 1; width: 100%; contain: strict;
  border-radius: var(--r-lg); overflow: hidden; background: var(--panel);
}
.showcase canvas { position: absolute; inset: 0; width: 100%; height: 100%; display: block; }

.results { margin-top: 28px; }
.results .status { color: var(--ink-2); }
.results .status.error { color: #f2a19b; }
.results .status button { margin-left: 8px; }
.who { display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 10px; margin: 0 0 10px; }
.cur-rank { display: inline-flex; align-items: baseline; gap: 6px; font-size: 13px; color: var(--ink-2); font-variant-numeric: tabular-nums; }
.cur-rank .rank { align-self: center; }
/* A player page's Refresh, at the header's right end, with when it last ran. */
.who-refresh-wrap { margin-left: auto; display: inline-flex; align-items: center; gap: 8px; align-self: center; }
.who-updated { color: var(--muted); font-size: 12px; }
.who-updated:empty { display: none; }
/* After a Refresh, a game that wasn't listed slides in. */
.match-list > li.fresh-in { animation: fresh-in 420ms cubic-bezier(0.2, 0.7, 0.2, 1); }
@keyframes fresh-in { from { opacity: 0; transform: translateY(-8px); } to { opacity: 1; transform: none; } }
@media (prefers-reduced-motion: reduce) { .match-list > li.fresh-in { animation: none; } }
.cur-rank-slot { display: inline-flex; align-items: baseline; gap: 10px; flex-wrap: wrap; }
.ladder { font-size: 13px; color: var(--ink-2); font-variant-numeric: tabular-nums; }
.cur-label { color: var(--muted); font-size: 11px; font-weight: 650; text-transform: uppercase; letter-spacing: 0.04em; }
.who h2 { font-size: 20px; margin: 0; letter-spacing: -0.01em; }
.who .tag { color: var(--muted); }
.match-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 6px; }
.match-row {
  display: grid; grid-template-columns: 4px 44px minmax(0, 1fr) auto; align-items: center; gap: 12px;
  width: 100%; text-align: left; padding: 8px 14px 8px 0; border: 1px solid var(--line-soft);
  border-radius: var(--r-md); background: var(--panel); overflow: hidden;
}
.match-row:hover { border-color: var(--line); background: var(--raise); }
div.match-row:not(.pending) { cursor: pointer; }
.match-row.off { cursor: not-allowed; opacity: 0.55; }
/* The row's name is its open button (the row's click opens too); the row shows its focus. */
.match-row .open { background: none; border: 0; padding: 0; font-weight: inherit; text-align: left; }
.match-row .open:focus-visible { box-shadow: none; }
.match-row.off .open { cursor: not-allowed; }
.match-row .stripe { align-self: stretch; margin: -8px 0; }
.match-row.win .stripe { background: var(--blue); }
.match-row.loss .stripe { background: var(--red); }
.match-row img { width: 44px; height: 44px; border-radius: 50%; }
.match-row .main { min-width: 0; }
.match-row .champ { font-weight: 650; display: flex; flex-wrap: wrap; align-items: center; gap: 2px 4px; }
.match-row .champ .badge { margin-left: 0; }
.match-row .meta { color: var(--muted); font-size: 13px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.match-row .kda { text-align: right; font-weight: 600; }
.match-row .kda small { display: block; color: var(--muted); font-weight: 400; font-size: 12px; }
.match-row.pending { opacity: 0.6; }

/* A game row: outcome + queue/duration/age, champion vs lane opponent, K/D/A + CS, the analysis
   badge and early tags, both teams. Stacked on a narrow card; columns from 640 px of card. */
.game-row {
  grid-template-columns: 4px auto minmax(0, 1fr);
  grid-template-areas:
    "stripe result result"
    "stripe champs stats"
    "stripe items items"
    "stripe mid mid"
    "stripe teams teams";
  align-items: center; gap: 4px 12px; padding: 10px 14px 10px 0; font-variant-numeric: tabular-nums;
}
.game-row .stripe { grid-area: stripe; grid-row: 1 / -1; margin: -10px 0; }
.gr-tags .badge { margin-left: 0; }
.game-row > .gr-result { grid-area: result; min-width: 0; display: flex; flex-wrap: wrap; align-items: baseline; gap: 0 10px; }
.game-row > .gr-result .open { font-weight: 700; font-size: 15px; justify-self: start; }
.game-row.win .open { color: var(--blue); }
.game-row.loss .open { color: var(--red); }
.game-row.remake .open { color: var(--muted); }
.gr-outcome { display: flex; flex-wrap: wrap; align-items: baseline; gap: 0 6px; }
.gr-ff { font-size: 12px; font-weight: 600; color: var(--ink-2); white-space: nowrap; }
.game-row > .gr-items { grid-area: items; display: flex; align-items: center; gap: 2px; }
/* `.game-row` beats `.match-row img` (the old row's 44 px portrait). */
.game-row .gr-item { width: 22px; height: 22px; border-radius: 4px; flex: none; }
.game-row .gr-item.empty { background: rgba(255, 255, 255, 0.025); box-shadow: inset 0 0 0 1px var(--line); }
.game-row .gr-item.trinket { margin-left: 6px; border-radius: 50%; }
.game-row .gr-item.quest, .sb-items .quest { margin-left: 4px; border-radius: 50%; box-shadow: 0 0 0 1px var(--gold); }
.gr-meta { display: flex; flex-wrap: wrap; gap: 0 8px; color: var(--muted); font-size: 12.5px; }
.game-row > .gr-champs { grid-area: champs; display: flex; align-items: flex-start; gap: 6px; }
/* A champion circle: its rank badge in the bottom-right corner (the viewer's attribution-badge
   pattern, ringed in the panel colour) and the LP under it. */
.gr-cc { display: grid; justify-items: center; row-gap: 3px; }
.gr-cci { position: relative; display: block; }
.gr-cc .cb { position: absolute; right: -6px; bottom: -3px; line-height: 0; }
.gr-cc .cb .rank { box-shadow: 0 0 0 2px var(--panel); }
.gr-cc .cb .rank.now { background: var(--panel); box-shadow: inset 0 0 0 1px var(--rank, #9aa5ad), 0 0 0 2px var(--panel); }
.gr-cc .clp { min-height: 12px; font-size: 10px; line-height: 12px; color: var(--muted); font-variant-numeric: tabular-nums; }
.gr-vs { align-self: center; margin-top: -14px; }
.game-row .gr-champs img { border-radius: 50%; }
.game-row .gr-me { width: 44px; height: 44px; }
.game-row .gr-opp { width: 30px; height: 30px; opacity: 0.9; }
.gr-vs { color: var(--muted); font-size: 11px; font-weight: 600; }
.game-row > .gr-stats { grid-area: stats; display: grid; justify-items: end; gap: 1px; }
.gr-kda { font-weight: 650; white-space: nowrap; }
.gr-cs { color: var(--muted); font-size: 12px; white-space: nowrap; }
.game-row > .gr-mid { grid-area: mid; display: grid; gap: 2px; min-width: 0; }
.gr-tags { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 4px; min-width: 0; }
.gr-tags:empty, .gr-mid:empty { display: none; }
.game-row > .gr-mid > .az-note { margin: 0; }
.game-row > .gr-teams { grid-area: teams; display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); gap: 8px 16px; min-width: 0; margin-top: 6px; }
/* Each team: five players a few px apart; each player is the champion beside two lines, rank and
   LP on top (kept, empty, when there's none, so names line up) and the full Riot ID below. */
.gr-team { list-style: none; margin: 0; padding: 0; display: grid; gap: 4px; min-width: 0; }
.gr-team li { display: grid; grid-template-columns: 34px minmax(0, 1fr); align-items: center; column-gap: 7px; min-width: 0; font-size: 12px; line-height: 16px; color: var(--ink-2); }
.game-row .gr-team img { width: 34px; height: 34px; border-radius: 4px; }
.gr-team .pc { display: grid; row-gap: 2px; min-width: 0; }
/* The rank line is the quiet one: small badge, muted LP; the name line carries the weight. */
.gr-team .pr { display: flex; align-items: center; gap: 4px; height: 13px; opacity: 0.9; }
.gr-team .pr .lp { color: var(--muted); font-size: 10.5px; line-height: 1; font-weight: 400; font-variant-numeric: tabular-nums; }
.gr-name { display: flex; align-items: baseline; gap: 3px; background: none; border: 0; padding: 0; color: inherit; min-width: 0; text-align: left; white-space: nowrap; }
/* Team columns fit a 16-letter name and a 5-letter tag; a wider ID (full-width glyphs) breaks
   rather than clips. */
.gr-name .n { min-width: 0; overflow-wrap: anywhere; white-space: normal; }
.gr-name .t { flex: none; color: var(--muted); font-size: 10.5px; font-weight: 400; }
/* Tight rank badges (team lists, the row's rank chip, the header): 12 px tall, hugging the text. */
.gr-team .rank, .gr-cc .rank, .cur-rank .rank {
  display: inline-flex; align-items: center; height: 12px; padding: 0 3px; margin-left: 0; border-radius: 2px;
  font-size: 9px; line-height: 1; font-weight: 750; letter-spacing: 0.03em; font-variant-numeric: tabular-nums; vertical-align: middle;
}
/* A current rank (from today's ladder, on rows not analyzed) is outlined; a game-time rank is filled. */
.rank.now { background: transparent; color: var(--rank, #9aa5ad); box-shadow: inset 0 0 0 1px var(--rank, #9aa5ad); }
a.gr-name { color: inherit; text-decoration: none; }
a.gr-name:hover .n, a.gr-name:focus-visible .n { color: var(--gold); text-decoration: underline; text-underline-offset: 2px; }
.who-icon:empty { display: none; }
.who-icon { align-self: center; }
.who-avatar { width: 40px; height: 40px; border-radius: 50%; box-shadow: 0 0 0 1px var(--line); }
.suggest .s-picon { width: 20px; height: 20px; border-radius: 50%; flex: none; margin-right: 8px; align-self: center; }
.gr-team li.me { color: var(--gold); font-weight: 650; }
.gr-tside { min-width: 0; }
/* Medium cards: the outcome line, champions + K/D/A, items and the middle block on the left, both
   teams on the right. */
@container gcard (min-width: 560px) and (max-width: 1039.98px) {
  .game-row {
    /* Fixed detail columns so every row's K/D/A and teams line up. */
    grid-template-columns: 4px 100px 100px minmax(180px, 1fr);
    grid-template-rows: 1fr auto auto auto auto 1fr;
    grid-template-areas:
      "stripe . . teams"
      "stripe result result teams"
      "stripe champs stats teams"
      "stripe items items teams"
      "stripe mid mid teams"
      "stripe . . teams";
  }
  .game-row > .gr-stats { justify-items: start; }
  .game-row > .gr-teams { margin-top: 0; grid-row: 1 / -1; align-self: center; justify-self: end; width: min(100%, 424px); grid-template-columns: minmax(0, 204px) minmax(0, 204px); }
}

/* Columns: outcome, champions + K/D/A over the items, the middle (rank, analysis, tags; centred,
   wrapping, the one flexible column), both teams. */
@container gcard (min-width: 1040px) {
  .game-row {
    /* One fixed template, so every column starts at the same x in every row: outcome, champions
       over the items, K/D/A, the middle (rank and tags; the only flexible column, empty when a row
       has none), both teams at fixed widths against the right strip. */
    grid-template-columns: 4px 132px 100px 112px minmax(0, 1fr) 424px;
    /* Spacer rows above and below keep champions, K/D/A and items one centred block. */
    grid-template-rows: 1fr auto auto 1fr;
    grid-template-areas:
      "stripe result . . mid teams"
      "stripe result champs stats mid teams"
      "stripe result items items mid teams"
      "stripe result . . mid teams";
  }
  .game-row > .gr-mid { align-self: center; justify-items: center; text-align: center; padding: 0 4px; }
  .gr-tags { justify-content: center; }
  .game-row > .gr-result { display: grid; align-self: stretch; align-content: center; gap: 3px; }
  /* The surrender, when there is one, always on its own line under the outcome. */
  .gr-outcome { display: grid; }
  .gr-meta { display: grid; gap: 1px; }
  .game-row > .gr-stats { justify-items: start; }
  /* Each team a fixed 204 px, the widest realistic cell measured in this font: champion 34 + 7 +
     16 bold capitals and a 5-capital tag (AGURININASKERIXY #QUACK); real lists top out near 177.
     A wider ID (W-heavy or full-width glyphs) wraps rather than clips. The middle takes the rest. */
  .game-row > .gr-teams { margin-top: 0; grid-row: 1 / -1; align-self: center; justify-self: end; width: 424px; grid-template-columns: 204px 204px; gap: 0 16px; }
}

/* Phones: the two teams one above the other, full width. */
@container gcard (max-width: 559.98px) {
  .game-row > .gr-teams { grid-template-columns: minmax(0, 1fr); }
}

/* A game card: the row opens the replay, the chevron unfolds the scoreboard under it. */
/* A player's page: the list without the hero, drop zone, sample and showcase; search in the top bar. */
body[data-view="player"] .topbar .search { display: flex; }
body[data-view="player"] .intro > :not(.results), body[data-view="player"] .showcase { display: none; }
body[data-view="player"] .landing { grid-template-columns: minmax(0, 1fr); max-width: 1240px; align-content: start; padding-top: 4px; }
body[data-view="player"] .intro { padding-top: 0; }
body[data-view="player"] .results { margin-top: 8px; }

.game-card {
  container: gcard / inline-size;
  display: grid; grid-template-columns: minmax(0, 1fr) 44px;
  border: 1px solid var(--line-soft); border-radius: var(--r-md); background: var(--panel); overflow: hidden;
}
.game-card:hover, .game-card.open { border-color: var(--line); }
.game-card > .match-row { border: 0; border-radius: 0; background: transparent; }
.game-card > .match-row:hover { background: var(--raise); }
.game-card > .match-row:has(.open:focus-visible), .expand:focus-visible { box-shadow: inset 0 0 0 2px var(--gold); border-radius: var(--r-md); }
.expand {
  display: grid; place-items: center; padding: 0; border: 0; border-left: 1px solid var(--line-soft);
  background: transparent; color: var(--muted);
}
.expand:hover { background: var(--raise); color: var(--ink); }
.expand svg { fill: none; stroke: currentColor; stroke-width: 1.8; stroke-linecap: round; stroke-linejoin: round; transition: transform 220ms ease; }
.expand[aria-expanded="true"] { color: var(--gold); }
.expand[aria-expanded="true"] svg { transform: rotate(180deg); }
.sb-wrap {
  grid-column: 1 / -1; display: grid; grid-template-rows: 0fr;
  transition: grid-template-rows 260ms cubic-bezier(0.2, 0.7, 0.2, 1);
}
.game-card.open .sb-wrap { grid-template-rows: 1fr; }
.sb-inner { min-height: 0; overflow: hidden; container: sb / inline-size; }
.game-card.open .sb-inner { border-top: 1px solid var(--line-soft); }
@media (prefers-reduced-motion: reduce) { .sb-wrap, .expand svg { transition: none; } }
.sb-note { margin: 0; padding: 12px 14px; color: var(--muted); font-size: 13px; }
.sb-note.error { color: #f2a19b; }

.sb-team { --team: var(--blue); padding: 4px 0 6px; }
.sb-team.red { --team: var(--red); }
.sb-team + .sb-team { border-top: 1px solid var(--line-soft); }
.sb-rows { list-style: none; margin: 0; padding: 0; }
.sb-head, .sb-row {
  display: grid; align-items: center; column-gap: 10px;
  grid-template-columns: 34px 34px minmax(0, 1fr) 78px 52px auto 46px;
  grid-template-areas: "champ sums name kda cs items gold";
  padding: 4px 12px 4px 10px; border-left: 3px solid transparent;
}
.sb-head { padding-top: 6px; padding-bottom: 6px; font-size: 13px; color: var(--ink-2); }
.sb-result { grid-column: 1 / 4; font-weight: 700; color: var(--team); }
.sb-result small { margin-left: 8px; font-weight: 500; color: var(--muted); font-size: 12px; }
.sb-champ { grid-area: champ; position: relative; }
.sb-champ img { width: 34px; height: 34px; border-radius: 50%; box-shadow: 0 0 0 1.5px var(--team); }
.sb-champ .lvl {
  position: absolute; right: -4px; bottom: -3px; min-width: 16px; padding: 0 3px; border-radius: 8px;
  background: var(--bg); color: var(--ink-2); font-size: 10px; font-weight: 650; line-height: 15px; text-align: center;
}
/* Summoner spells (left column) and runes (keystone over the secondary tree, right column). */
.sb-sums { grid-area: sums; display: grid; grid-template-columns: 16px 16px; grid-template-rows: 16px 16px; grid-auto-flow: column; gap: 2px; }
.sb-sums img, .sb-sums .slot { width: 16px; height: 16px; border-radius: 3px; }
.sb-runes, .sb-rune-slot { grid-row: 1 / 3; display: grid; grid-template-rows: 16px 16px; gap: 2px; padding: 0; border: 0; background: none; cursor: help; }
.sb-sums .sb-runes img { border-radius: 50%; background: #0b0f12; }
.sb-sums .sb-runes .tree { padding: 2px; }
.sb-runes:focus-visible { border-radius: 4px; }
.rune-pop {
  position: fixed; inset: auto; margin: 0; padding: 10px 12px; width: max-content; max-width: min(320px, calc(100vw - 16px));
  background: var(--panel); color: var(--ink); border: 1px solid var(--line); border-radius: var(--r-md);
  box-shadow: 0 10px 28px rgba(0, 0, 0, 0.45); font-size: 12.5px; line-height: 1.35;
}
.rune-pop:popover-open { display: grid; gap: 8px; }
.rp-tree { display: grid; gap: 5px; }
.rp-tree-name { display: flex; align-items: center; gap: 6px; font-weight: 700; color: var(--ink-2); font-size: 11.5px; text-transform: uppercase; letter-spacing: 0.04em; }
.rp-ti { width: 16px; height: 16px; }
.rp-rune { display: grid; grid-template-columns: 22px minmax(0, 1fr); align-items: center; gap: 8px; }
.rp-rune.key { grid-template-columns: 30px minmax(0, 1fr); }
.rp-ri { width: 22px; height: 22px; border-radius: 50%; background: #0b0f12; }
.rp-rune.key .rp-ri { width: 30px; height: 30px; }
.rp-rune b { display: block; font-weight: 650; }
.rp-rune small { display: block; color: var(--muted); font-size: 11.5px; font-variant-numeric: tabular-nums; }
.rp-rune.key small { color: var(--gold); }
.rp-shards { color: var(--muted); font-size: 11.5px; border-top: 1px solid var(--line-soft); padding-top: 6px; }
.sb-name { grid-area: name; min-width: 0; display: grid; line-height: 1.25; }
.sb-name small { color: var(--muted); font-size: 12px; overflow-wrap: break-word; }
.sb-who {
  justify-self: start; max-width: 100%; padding: 0; border: 0; background: none; text-align: left;
  font-size: 14px; font-weight: 600; overflow-wrap: break-word;
}
a.sb-who { color: inherit; text-decoration: none; }
a.sb-who:hover .n, a.sb-who:focus-visible .n { color: var(--gold); text-decoration: underline; text-underline-offset: 3px; text-decoration-thickness: 1px; }
.sb-who .tag { color: var(--muted); font-weight: 400; margin-left: 2px; }
.sb-kda { grid-area: kda; text-align: right; font-size: 13px; font-weight: 600; white-space: nowrap; }
.sb-cs { grid-area: cs; text-align: right; font-size: 13px; white-space: nowrap; }
.sb-kda small, .sb-cs small { display: block; color: var(--muted); font-weight: 400; font-size: 11px; line-height: 1.2; }
.sb-items { grid-area: items; display: flex; align-items: center; gap: 2px; }
.sb-items img, .sb-items .slot { width: 22px; height: 22px; border-radius: 4px; flex: none; }
.sb-items .slot { background: var(--raise); }
.sb-items .trinket { margin-left: 5px; border-radius: 50%; }
.sb-objs { gap: 10px; flex-wrap: wrap; }
.sb-obj { display: inline-flex; align-items: center; gap: 3px; font-weight: 600; color: var(--ink-2); }
.sb-obj img { width: 14px; height: 14px; }
.sb-gold { grid-area: gold; text-align: right; font-size: 13px; color: var(--gold); font-weight: 600; }
.sb-head .sb-kda, .sb-head .sb-cs { font-weight: 600; color: var(--ink-2); }
.sb-row.me { background: color-mix(in srgb, var(--gold) 8%, transparent); border-left-color: var(--gold); }
.sb-row.me .sb-who .n { color: var(--gold); }

/* Numbers with the game's gold / CS icon (text label until the pack has them). The class is not
   `.glyph`: that is the feed's team-coloured structure marker. */
.num { display: inline-flex; align-items: center; gap: 3px; font-variant-numeric: tabular-nums; }
.num .hud-icon { height: 1.1em; width: auto; object-fit: contain; vertical-align: -0.15em; }
.num .unit { color: var(--muted); font-size: 11px; }

/* While a search's games are listed, the list gets the room and the showcase steps back. */
/* :where keeps it at .landing's specificity, so the one-column breakpoints below still win. */
.landing:where(:has(.match-list)) { grid-template-columns: minmax(0, 1.9fr) minmax(0, 0.7fr); max-width: 1640px; }

/* Side by side: one grid for the whole card, every row a subgrid, lane matchups per row. Both
   teams use the same layout (no mirroring): champion, summoners, name, K/D/A over CS, gold, items. */
.sb-stack { display: none; }
.sb-duo {
  --it: 20px;
  display: grid; padding: 4px 0 8px; column-gap: 8px;
  grid-template-columns:
    34px 34px minmax(0, 1fr) auto auto calc(var(--it) * 8 + 31px)
    auto
    34px 34px minmax(0, 1fr) auto auto calc(var(--it) * 8 + 31px);
}
.sb-duo .sb-gold { display: none; }
.sb-duo-head, .sb-pairs, .sb-pair { grid-column: 1 / -1; display: grid; grid-template-columns: subgrid; }
/* Each team's bans, a quiet row under its header: dimmed champion icons in turn order. */
.sb-bans { display: flex; align-items: center; gap: 4px; padding: 3px 10px 5px; }
.sb-bans-label { color: var(--muted); font-size: 11px; margin-right: 4px; }
.sb-bans img, .sb-bans .slot { width: 20px; height: 20px; border-radius: 4px; }
.sb-bans img { filter: grayscale(0.6); opacity: 0.8; }
.sb-bans .slot { box-shadow: inset 0 0 0 1px var(--line); }
.sb-duo-bans { grid-column: 1 / -1; display: grid; grid-template-columns: subgrid; }
.sb-duo-bans .blue { grid-column: 1 / 7; }
.sb-duo-bans .red { grid-column: 8 / 14; }
.sb-pairs { list-style: none; margin: 0; padding: 0; }
.sb-side { display: grid; grid-template-columns: subgrid; grid-template-rows: auto auto; align-items: center; padding: 4px 8px; border-left: 3px solid transparent; }
.sb-side.blue { grid-column: 1 / 7; }
.sb-side.red { grid-column: 8 / 14; }
.sb-side.me { background: color-mix(in srgb, var(--gold) 8%, transparent); border-color: var(--gold); }
.sb-side.me .sb-who .n { color: var(--gold); }
.sb-side > * { grid-row: 1 / 3; }
.sb-side .sb-kda { grid-row: 1; align-self: end; }
.sb-side .sb-cs { grid-row: 2; align-self: start; color: var(--ink-2); }
.sb-side .sb-kda small, .sb-side .sb-cs small { display: none; }
.sb-side .sb-champ { grid-column: 1; } .sb-side .sb-sums { grid-column: 2; } .sb-side .sb-name { grid-column: 3; }
.sb-side .sb-kda, .sb-side .sb-cs { grid-column: 4; } .sb-side .sb-gold { grid-column: 5; } .sb-side .sb-items { grid-column: 6; }
.sb-duo .sb-items img, .sb-duo .sb-items .slot { width: var(--it); height: var(--it); }
.sb-duo .sb-champ img { box-shadow: 0 0 0 1.5px var(--team, var(--line)); }
.sb-side.blue { --team: var(--blue); } .sb-side.red { --team: var(--red); }
.sb-role { grid-column: 7; align-self: center; text-align: center; color: var(--muted); font-size: 11px; padding: 0 2px; min-width: 34px; }
.sb-pair + .sb-pair { border-top: 1px solid var(--line-soft); }
.sb-pair:hover .sb-side { background: color-mix(in srgb, var(--ink) 3%, transparent); }
.sb-pair:hover .sb-side.me { background: color-mix(in srgb, var(--gold) 11%, transparent); }

.sb-duo-head { padding: 6px 0 8px; border-bottom: 1px solid var(--line-soft); font-size: 13px; color: var(--ink-2); }
.sb-duo-head .sb-side { grid-template-rows: auto; padding-top: 2px; padding-bottom: 2px; }
.sb-duo-head .sb-side > * { grid-row: 1; }
.sb-duo-head .sb-result { grid-column: 1 / 4; color: var(--team); font-weight: 700; }
.sb-duo-head .sb-kda { grid-column: 4; }
.sb-duo-head .sb-cs { display: none; }
.sb-duo-head .sb-gold { grid-column: 5; }
.sb-duo-head .sb-objs { grid-column: 6; }

@container sb (min-width: 900px) { .sb-duo .sb-gold { display: block; } }
@container sb (max-width: 760px) {
  .sb-duo { --it: 15px; column-gap: 5px; grid-template-columns: 30px 0 minmax(0, 1fr) auto auto calc(var(--it) * 8 + 22px) auto 30px 0 minmax(0, 1fr) auto auto calc(var(--it) * 8 + 22px); }
  .sb-duo .sb-sums { display: none; }
  .sb-duo .sb-champ img { width: 30px; height: 30px; }
  .sb-duo .sb-items { gap: 1px; }
  .sb-duo .sb-role { min-width: 0; font-size: 0; padding: 0; }
  .sb-side { padding-left: 5px; padding-right: 5px; }
  .sb-duo .sb-name small { display: none; }
}
@container sb (max-width: 699px) { .sb-duo { display: none; } .sb-stack { display: block; } }

@container sb (max-width: 520px) {
  .sb-head, .sb-row {
    grid-template-columns: 34px 34px minmax(0, 1fr) auto auto;
    /* The build gets a row of its own: eight icons don't fit beside the CS and gold. */
    grid-template-areas: "champ sums name kda kda" "champ sums name cs gold" "items items items items items";
    row-gap: 3px; padding-right: 10px; column-gap: 8px;
  }
  .sb-head { grid-template-areas: "result result result kda kda" "items items items cs gold"; }
  .sb-row .sb-items { margin-top: 2px; }
  .sb-result { grid-area: result; }
  .sb-items img, .sb-items .slot { width: 19px; height: 19px; }
  .sb-items .trinket { margin-left: 3px; }
  .sb-kda small { display: inline; margin-left: 4px; }
  .sb-cs small { display: none; }
}
.more { margin-top: 10px; }
.ghost {
  background: transparent; border: 1px solid var(--line); border-radius: var(--r-md); padding: 7px 14px; color: var(--ink-2);
}
.ghost:hover { border-color: var(--muted); color: var(--ink); }

/* ---- Viewer ------------------------------------------------------------------------------- */
body[data-view="viewer"] .landing { display: none; }
.viewer {
  display: grid;
  /* Columns: the feed, the rest of the player, and the right half; the bottom row splits evenly
     (blue over the feed and part of the player, red under the rest). */
  --feed: clamp(260px, 19vw, calc(400px * var(--uiz))); --gap: 8px;
  grid-template-columns: var(--feed) minmax(0, 1fr) calc((100% - var(--gap)) / 2);
  grid-template-rows: auto minmax(0, 1fr) auto;
  grid-template-areas: "head head head" "feed player player" "blue blue red";
  gap: var(--gap); padding: 0 12px 10px;
  height: calc(100dvh - var(--topbar-h, 64px));
}
.viewer[hidden] { display: none; }
/* The player: the map (the largest square that fits, sized by Viewer.fitMap) over the playback bar,
   one element that goes fullscreen on its own. */
.player { grid-area: player; display: flex; flex-direction: column; align-items: center; gap: 10px; min-width: 0; min-height: 0; }
.player > .stage { width: var(--map, 100%); height: var(--map, 100%); flex: none; }
.player > .transport { align-self: stretch; }
.player:fullscreen { background: var(--bg); padding: 12px; }
.player.fs { position: fixed; inset: 0; z-index: 50; background: var(--bg); padding: 12px; }
.view-tabs, .feed-toggle, .feed-head { display: none; }

.match-head { grid-area: head; display: flex; flex-wrap: wrap; align-items: baseline; gap: 4px 14px; padding: 0 4px; }
.match-head h2 { font-size: 17px; margin: 0; letter-spacing: -0.01em; }
.match-head .sub { color: var(--muted); font-size: 13px; }
.match-head .back { margin-left: auto; }

.panel { background: var(--panel); border: 1px solid var(--line-soft); border-radius: var(--r-lg); }

/* Under the feed and the player: blue's team card on the left half, red's on the right, laid out
   identically (no mirroring) except that each team's totals sit on its inner side (blue's on its
   right edge, red's on its left), so the scores meet in the middle. Each player: portrait, name,
   Riot ID, K/D/A and summoners; Q W E R as lettered tiles; gold and CS; the items in a tray. */
.team-panel {
  min-width: 0; min-height: 0; overflow: hidden; display: flex;
  background: var(--panel); border: 1px solid var(--line-soft); border-radius: var(--r-lg);
  box-shadow: inset 0 3px 0 var(--team);
}
.team-panel.blue { grid-area: blue; }
.team-panel.red { grid-area: red; }
.tp-head {
  flex: none; width: 104px; display: flex; flex-direction: column; gap: 5px; padding: 10px 10px 8px;
  border-right: 1px solid var(--line-soft);
}
.team-panel.blue .tp-head { order: 2; border-right: 0; border-left: 1px solid var(--line-soft); text-align: right; align-items: flex-end; }
.tp-name { display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px; font-size: 13px; font-weight: 700; color: var(--team); }
.tp-name .result { color: var(--gold); font-size: 12px; font-weight: 650; }
.tp-kills { display: flex; align-items: baseline; gap: 5px; color: var(--team); font-variant-numeric: tabular-nums; }
.tp-kills b { font-size: 30px; font-weight: 780; line-height: 1; letter-spacing: -0.02em; }
.tp-kills small { font-size: 11px; color: var(--muted); font-weight: 600; }
.tp-gold { display: flex; flex-wrap: wrap; align-items: center; gap: 2px 6px; font-size: 12.5px; color: var(--ink-2); font-variant-numeric: tabular-nums; }
.team-panel.blue .tp-gold, .team-panel.blue .tp-objs, .team-panel.blue .tp-name { justify-content: flex-end; }
.tp-gold .lead { color: var(--gold); font-weight: 650; }
.tp-objs { display: flex; flex-wrap: wrap; align-items: center; gap: 3px 8px; font-size: 12px; color: var(--ink-2); font-weight: 600; }
.tp-obj { display: inline-flex; align-items: center; gap: 3px; }
.tp-obj img { width: 15px; height: 15px; }
.tp-rows { list-style: none; margin: 0; padding: 4px; flex: 1; min-width: 0; display: flex; gap: 3px; }
.tp-rows > li { flex: 1 1 0; min-width: 0; display: flex; container: pl / inline-size; }
.pl {
  width: 100%; display: grid; grid-template-columns: 34px minmax(0, 1fr);
  grid-template-areas: "face who" "face stats" "face more" "abil abil" "items items";
  column-gap: 6px; row-gap: 5px; align-content: start; padding: 6px; text-align: left; overflow: hidden;
  background: transparent; border: 1px solid transparent; border-radius: var(--r-md);
}
.pl:hover { background: var(--raise); }
.pl.following { border-color: var(--line); background: var(--raise); }
.pl .face { grid-area: face; position: relative; width: 34px; height: 34px; }
.pl .face img { width: 34px; height: 34px; border-radius: 50%; box-shadow: 0 0 0 2px var(--team); }
.pl.focus .face img { box-shadow: 0 0 0 2px var(--gold); }
.pl.dead .face img { filter: grayscale(1) brightness(0.6); }
.pl .lvl {
  position: absolute; right: -4px; bottom: -3px; font-size: 10px; line-height: 1; font-weight: 700;
  background: var(--bg); border-radius: 6px; padding: 2px 3px; min-width: 15px; text-align: center;
}
.pl .respawn { position: absolute; inset: 0; display: grid; place-items: center; font-weight: 750; font-size: 14px; text-shadow: 0 1px 3px #000; }
/* Champion on the first line, the Riot ID on its own line under it: neither is ever dropped; the
   Riot ID ellipsizes (full name in its tooltip), the champion name stays whole. */
.pl .who { grid-area: who; min-width: 0; margin: 0; display: flex; flex-direction: column; align-items: stretch; gap: 1px; white-space: nowrap; overflow: hidden; }
.pl .who .champ { display: flex; align-items: baseline; min-width: 0; }
.pl .who b { flex: none; font-size: 13px; font-weight: 650; }
.pl.dead .who b { color: var(--muted); }
/* Ranked tier (when the replay carries it): a small chip in the tier's colour. */
.rank {
  display: inline-block; flex: none; margin-left: 4px; padding: 0 4px; border-radius: 4px; font-size: 10px; font-weight: 750;
  line-height: 14px; letter-spacing: 0.02em; color: var(--bg); background: var(--rank, #9aa5ad); vertical-align: 1px;
}
.r-iron { --rank: #8d8178; } .r-bronze { --rank: #b0785a; } .r-silver { --rank: #a9b4bb; } .r-gold { --rank: #e1b85a; }
.r-platinum { --rank: #5fc4b7; } .r-emerald { --rank: #4fc77f; } .r-diamond { --rank: #7f9cff; } .r-master { --rank: #c27ef0; }
.r-grandmaster { --rank: #ef6f6f; } .r-challenger { --rank: #f3d27a; }
.pl .who .id { display: block; min-width: 0; overflow-wrap: break-word; color: var(--ink-2); font-size: 11px; font-weight: 500; line-height: 1.2; }
.pl .who .id .tag { color: var(--muted); font-weight: 400; }
.pl .who .id.search { cursor: pointer; }
.pl .who .id.search:hover .n { text-decoration: underline; text-underline-offset: 2px; }
/* K/D/A and gold, then the lead and CS: short wrapping runs beside the portrait, each number whole. */
.pl .pl-stats, .pl .pl-more { min-width: 0; display: flex; flex-wrap: wrap; align-items: center; gap: 1px 8px; font-variant-numeric: tabular-nums; }
.pl .pl-stats { grid-area: stats; }
.pl .pl-more { grid-area: more; margin-top: -4px; }
.pl .kda { font-size: 12.5px; font-weight: 700; white-space: nowrap; }
.pl .gold, .pl .diff, .pl .cs { font-size: 11.5px; white-space: nowrap; }
.pl .gold { color: var(--ink-2); }
.pl .diff:empty { display: none; }
.pl .diff.up { color: #6fd28a; } .pl .diff.down { color: #ff7a6e; }
.pl .cs, .pl .wards { color: var(--muted); }
.pl .wards { display: none; }
.pl .items {
  grid-area: items; display: flex; gap: 2px; padding: 3px; border-radius: 6px;
  background: rgba(6, 9, 11, 0.55); box-shadow: inset 0 0 0 1px var(--line-soft);
}
.pl .it { display: block; width: 15px; height: 15px; border-radius: 2px; background: var(--raise); }
.pl .it.empty { background: transparent; box-shadow: inset 0 0 0 1px var(--line-soft); }
.pl .it.trinket { margin-left: auto; border-radius: 50%; }
/* Role-quest and quest-reward items (slots 7-8), after the trinket. */
.it.quest { border-radius: 50%; box-shadow: 0 0 0 1px var(--gold); }
/* Abilities (when skill-ups are decoded) then the summoner spells: rounded tiles with the slot
   letter, ability rank as pips. */
.pl .abil { grid-area: abil; display: flex; gap: 4px; }
.viewer:not(.has-skills) .pl .ab-slot:not(.sum-slot) { display: none; }
.pl .sum-slot[data-key="D"] { margin-left: 4px; }
.viewer:not(.has-skills) .pl .sum-slot[data-key="D"] { margin-left: 0; }
.pl .ab-slot { position: relative; display: flex; flex-direction: column; align-items: center; gap: 2px; }
/* Corners, the same on every tile (map pops too): charges top-left, the slot key bottom-right, a
   form champion's other-form inset top-right. */
.pl .sum.ab[data-key]::before {
  content: attr(data-key); position: absolute; right: -2px; bottom: -1px; z-index: 3; font-size: 8.5px; font-weight: 800; line-height: 1;
  padding: 1px 2px; border-radius: 3px; background: var(--bg); color: var(--ink-2);
}
.pl .sum.ab { width: 22px; height: 22px; border-radius: 6px; }
.pl .sum.ab img { width: 20px; height: 20px; border-radius: 5px; }
.pl .sum.ab.down::after { transform: rotate(var(--a)) translateY(-11px); }
.pl .sum.ab.unlearned img { filter: grayscale(1) brightness(0.45); }
.pl .pips, .pcard .pips { display: flex; justify-content: center; gap: 2px; width: 0; min-width: 100%; }
/* Pips never widen their tile: up to 6 ranks (Udyr, Jayce) shrink to fit it. */
/* A base visit's new items in the inventory: a gold glow at the shop row's opacity, one pulse. */
.it.fresh {
  box-shadow: 0 0 0 1.5px rgba(255, 215, 94, var(--fresh, 1)), 0 0 6px 1px rgba(255, 215, 94, calc(var(--fresh, 1) * 0.7));
  animation: fresh-pulse 0.7s ease-out 1;
}
@keyframes fresh-pulse { 0% { box-shadow: 0 0 0 1.5px #ffd75e, 0 0 12px 4px rgba(255, 215, 94, 0.9); } }
@media (prefers-reduced-motion: reduce) { .it.fresh { animation: none; } }
/* The other form's ability still on cooldown (form champions): a small inset in the tile's top-right
   corner with its own sweep. */
.sum.hid { position: absolute; z-index: 4; width: 11px; height: 11px; top: -4px; right: -4px; padding: 1px;
  border-radius: 3px; box-shadow: 0 0 0 1px var(--bg); pointer-events: auto; }
.sum.hid img { width: 9px; height: 9px; border-radius: 2px; }
.sum.hid img.lit { inset: 1px; }
.sum.hid.down::after { width: 3px; height: 3px; margin: -1.5px 0 0 -1.5px; transform: rotate(var(--a)) translateY(-5.5px); }
.pcard .sum.hid { width: 14px; height: 14px; top: -5px; right: -5px; }
.pcard .sum.hid img { width: 12px; height: 12px; }
.pcard .sum.hid.down::after { transform: rotate(var(--a)) translateY(-7px); }
.pl .pips i { flex: 0 1 3px; min-width: 1px; height: 3px; border-radius: 50%; background: var(--line); }
.pl .pips i.on { background: var(--gold); }
/* Narrow player columns: smaller tiles so Q W E R D F stay on one line. */
@container pl (max-width: 180px) {
  /* No room for the quest slots beside six items and the trinket: the player card shows them. */
  .pl .it.quest { display: none; }
  .pl .abil { gap: 3px; } .pl .sum-slot[data-key="D"] { margin-left: 3px; }
  .pl .sum.ab { width: 19px; height: 19px; } .pl .sum.ab img { width: 17px; height: 17px; }
  .pl .sum.ab.down::after { transform: rotate(var(--a)) translateY(-9.5px); }
}
@container pl (max-width: 156px) {
  .pl .abil { gap: 2px; } .pl .sum-slot[data-key="D"] { margin-left: 2px; }
  .pl .sum.ab { width: 16px; height: 16px; border-radius: 5px; } .pl .sum.ab img { width: 14px; height: 14px; border-radius: 4px; }
  .pl .sum.ab.down::after { transform: rotate(var(--a)) translateY(-8px); }
}
@container pl (max-width: 131px) {
  .pl .sum.ab { width: 13px; height: 13px; border-radius: 4px; } .pl .sum.ab img { width: 11px; height: 11px; border-radius: 3px; }
  .pl .sum.ab.down::after { transform: rotate(var(--a)) translateY(-6.5px); }
  .pl .pips { gap: 1px; } .pl .pips i { flex-basis: 2px; height: 2px; }
  .pl .pl-stats, .pl .pl-more { column-gap: 6px; }
  /* A five-digit gold with its coin still fits beside the portrait at the narrowest tiles (98 px). */
  .pl .gold, .pl .diff, .pl .cs { font-size: 11px; }
  .pl .num .hud-icon { width: 10px; height: 10px; margin-right: 2px; }
  .pl .items { gap: 1px; padding: 2px; }
  .pl .it { width: 11px; height: 11px; }
}
/* Very narrow: the names take a full-width row under the portrait and K/D/A. */
@container pl (max-width: 130px) {
  .pl { grid-template-areas: "face stats" "more more" "who who" "abil abil" "items items"; }
  .pl .face { margin-bottom: -2px; }
}
/* Wide columns: two lines per player. */
@container pl (min-width: 290px) {
  .pl {
    grid-template-columns: 34px auto minmax(0, 1fr) auto;
    grid-template-areas: "face who who abil" "face stats more items";
    align-items: center; row-gap: 4px; padding: 5px 6px;
  }
  .pl .abil { justify-self: end; }
  .pl .items { justify-self: end; }
  .pl .pl-more { margin-top: 0; padding-left: 6px; }
}
@container pl (min-width: 290px) and (max-width: 399px) { .pl .diff { display: none; } }

.blue { --team: var(--blue); }
.red { --team: var(--red); }

/* Stage */
.stage { grid-area: stage; position: relative; min-height: 0; min-width: 0; border-radius: var(--r-lg); overflow: hidden; background: var(--bg); touch-action: none; }
.stage canvas { position: absolute; inset: 0; width: 100%; height: 100%; display: block; cursor: grab; }
.stage #map-under { pointer-events: none; }
.stage canvas.hovering { cursor: pointer; }
.stage canvas.dragging { cursor: grabbing; }
/* The map's top-right corner: its tools over the fog switch, kept clear of the centred clock (the
   tools wrap onto more rows when the map is too narrow for one). */
.map-corner {
  position: absolute; top: 10px; right: 10px; max-width: calc(50% - 96px);
  display: flex; flex-direction: column; align-items: flex-end; gap: 8px; pointer-events: none;
}
.map-corner > * { pointer-events: auto; }
.map-tools { display: flex; flex-wrap: wrap; justify-content: flex-end; gap: 4px; }
.map-tools button {
  min-width: 34px; height: 34px; padding: 0 9px; border-radius: var(--r-md); border: 1px solid var(--line);
  background: rgba(18, 26, 30, 0.86); font-weight: 600; font-size: 15px;
}
.map-tools button:hover { background: var(--raise); }
.map-tools button[hidden] { display: none; }
.map-tools button[aria-pressed="true"] { background: var(--raise); color: var(--gold); border-color: var(--gold); }
.fog-tools {
  display: flex; align-items: center; gap: 2px; padding: 3px;
  border-radius: var(--r-md); border: 1px solid var(--line); background: rgba(18, 26, 30, 0.86); font-size: 12px;
}
.fog-tools[hidden] { display: none; }
.fog-tools span { color: var(--muted); padding: 0 6px 0 4px; }
.fog-tools button { border: 0; background: transparent; border-radius: var(--r-sm); padding: 4px 8px; font-weight: 600; color: var(--ink-2); }
.fog-tools button[aria-pressed="true"] { background: var(--raise); color: var(--ink); }
.fog-tools button[data-fog="100"][aria-pressed="true"] { color: var(--blue, #6fb6ff); }
.fog-tools button[data-fog="200"][aria-pressed="true"] { color: var(--red, #ff7a66); }
.source-note {
  position: absolute; left: 12px; bottom: 8px; margin: 0; max-width: min(520px, 72%);
  font-size: 12px; color: var(--muted); cursor: help; line-height: 1.35;
  text-decoration: underline dotted rgba(125, 137, 132, 0.6); text-underline-offset: 3px;
}
.source-note[data-source="timeline"] { color: var(--ink-2); }
.map-clock {
  position: absolute; top: 10px; left: 50%; transform: translateX(-50%); pointer-events: none;
  display: flex; align-items: baseline; gap: 8px; padding: 4px 14px 5px; border-radius: var(--r-md);
  background: rgba(13, 18, 21, 0.78); border: 1px solid var(--line);
  font-size: 28px; font-weight: 700; font-variant-numeric: tabular-nums; letter-spacing: 0.02em; color: var(--ink);
}
.map-clock small { display: none; font-size: 11px; font-weight: 650; text-transform: uppercase; letter-spacing: 0.08em; color: var(--gold); }
.map-clock.paused small { display: inline; }
.stage-status {
  position: absolute; inset: 0; display: grid; place-items: center; text-align: center; padding: 24px;
  background: rgba(13, 18, 21, 0.72); color: var(--ink-2);
}
.stage-status[hidden] { display: none; }
.tip {
  position: absolute; z-index: 3; pointer-events: none; min-width: 180px; max-width: 260px;
  background: rgba(18, 26, 30, 0.96); border: 1px solid var(--line); border-radius: var(--r-md);
  padding: 9px 11px; font-size: 13px; line-height: 1.4; box-shadow: 0 8px 24px rgba(0, 0, 0, 0.45);
}
.tip[hidden] { display: none; }
.tip .t-name { font-weight: 700; font-size: 14px; }
.tip .t-id { color: var(--muted); }
.tip .t-grid { display: grid; grid-template-columns: auto 1fr; gap: 1px 12px; margin-top: 6px; }
.tip .t-grid dt { color: var(--muted); }
.tip .t-grid dd { margin: 0; text-align: right; font-weight: 600; }
.tip .t-dead { color: #f2a19b; margin-top: 4px; }

/* Player card: a glance card over the hovered champion, a pinned full card that follows it. */
.pcard {
  --team: var(--blue);
  position: absolute; left: 0; top: 0; z-index: 4; width: 228px;
  background: color-mix(in srgb, var(--panel) 90%, transparent);
  -webkit-backdrop-filter: blur(6px); backdrop-filter: blur(6px);
  border: 1px solid color-mix(in srgb, var(--team) 45%, var(--line)); border-radius: var(--r-md);
  padding: 9px 10px 10px; font-size: 12.5px; line-height: 1.35; color: var(--ink);
  box-shadow: 0 10px 28px rgba(0, 0, 0, 0.5); will-change: transform; contain: layout style;
}
.pcard.red { --team: var(--red); }
.pcard.glance { pointer-events: none; width: 210px; }
.pcard.full { width: 284px; }
.pcard[hidden] { display: none; }
.pc-arrow {
  position: absolute; left: 0; top: 0; width: 12px; height: 7px; pointer-events: none;
  background: color-mix(in srgb, var(--team) 80%, var(--line));
  clip-path: polygon(0 0, 100% 0, 50% 100%);
}
.pc-head { display: flex; align-items: center; gap: 9px; }
.pc-face { position: relative; flex: none; }
.pc-face img { width: 40px; height: 40px; border-radius: 50%; box-shadow: 0 0 0 2px var(--team); }
.pc-lvl {
  position: absolute; right: -5px; bottom: -4px; min-width: 18px; padding: 0 4px; border-radius: 9px;
  background: var(--bg); border: 1px solid var(--line); font-size: 11px; font-weight: 700; line-height: 15px; text-align: center;
}
.pc-who { display: grid; min-width: 0; flex: 1; }
.pc-who b { font-size: 14px; color: var(--team); }
.pc-who small { color: var(--muted); overflow-wrap: break-word; }
.pc-btn {
  flex: none; border: 1px solid var(--line); background: transparent; color: var(--ink-2); border-radius: var(--r-sm);
  font-size: 11.5px; padding: 2px 7px; line-height: 1.5;
}
.pc-btn:hover { color: var(--ink); border-color: var(--muted); }
.pc-follow[aria-pressed="true"] { color: var(--gold); border-color: var(--gold); }
.pc-close { font-size: 16px; padding: 0 7px; line-height: 1.3; }
.pc-xp { height: 3px; margin: 8px 0 6px; border-radius: 2px; background: var(--line-soft); overflow: hidden; }
.pc-xpfill { display: block; height: 100%; background: #b48cf0; transform-origin: left; }
.pc-bar {
  position: relative; height: 15px; margin-top: 3px; border-radius: 3px; overflow: hidden;
  background: rgba(6, 9, 11, 0.8);
}
.pc-fill, .pc-ghost, .pc-extra { position: absolute; inset: 0; transform-origin: left; will-change: transform; }
/* The "damage taken" segment: holds after a hit, then drains to the bar. */
.pc-ghost { background: rgba(255, 236, 214, 0.55); }
.pc-bar.res .pc-ghost { background: rgba(255, 255, 255, 0.28); }
.pc-bar.hp .pc-fill { background: linear-gradient(#5fc66d, #3f9a4c); }
.pcard.red .pc-bar.hp .pc-fill { background: linear-gradient(#e86a5f, #b9473e); }
.pc-bar.hp .pc-extra { background: #ece6d6; }
.pc-bar.res .pc-fill { background: var(--res, #4f8fe0); }
.pc-bar.res .pc-extra { display: none; }
.pc-val {
  position: relative; display: block; text-align: center; font-size: 10.5px; font-weight: 650; line-height: 15px;
  color: #fff; text-shadow: 0 1px 2px rgba(0, 0, 0, 0.9); font-variant-numeric: tabular-nums;
}
.pc-dead { margin-top: 5px; color: #f2a19b; font-weight: 650; }
body[data-view="viewer"] .pc-attach { display: flex; align-items: center; gap: 6px; margin-top: 5px; color: #cfe3ff; font-weight: 650; }
body[data-view="viewer"] .pc-attach[hidden] { display: none; }
body[data-view="viewer"] .pc-attach img { width: 18px; height: 18px; border-radius: 50%; border: 2px solid; box-sizing: content-box; }
.pcard.is-dead .pc-face img { filter: grayscale(1) brightness(0.6); }
.pc-abil { display: flex; align-items: flex-start; gap: 4px; margin-top: 9px; }
.pc-slot { position: relative; display: flex; flex-direction: column; align-items: center; gap: 2px; }
.pc-sumslot { margin-left: auto; }
.pc-sumslot + .pc-sumslot { margin-left: 0; }
body[data-view="viewer"] .pc-runeslot { margin-left: 2px; cursor: help; }
body[data-view="viewer"] .pc-rune { display: grid; place-items: center; width: 28px; height: 28px; border-radius: 50%; background: #0b0f12; box-shadow: inset 0 0 0 1px var(--line); }
body[data-view="viewer"] .pc-rune img { width: 26px; height: 26px; border-radius: 50%; }
body[data-view="viewer"] .pc-rtree { width: 12px; height: 12px; }
body[data-view="viewer"] .pc-runepage { display: grid; gap: 8px; margin-top: 2px; }
.pcard .sum { width: 28px; height: 28px; }
.pcard .sum img { width: 26px; height: 26px; }
.pcard .sum.down::after { transform: rotate(var(--a)) translateY(-14px); }
.pcard .sum.ab.unlearned img { filter: grayscale(1) brightness(0.45); }
.pcard .pips i { flex: 0 1 4px; min-width: 1px; height: 4px; border-radius: 50%; background: var(--line); }
.pcard .pips i.on { background: var(--gold); }
.pc-items { display: flex; gap: 3px; margin-top: 8px; }
.pc-items .it { width: 24px; height: 24px; border-radius: 4px; background: var(--raise); }
.pc-items .trinket { margin-left: 5px; border-radius: 50%; }
.pc-econ { display: flex; justify-content: space-between; gap: 8px; margin-top: 8px; font-weight: 650; font-variant-numeric: tabular-nums; }
.pc-gold { color: var(--gold); }
.pc-gold small { color: var(--muted); font-weight: 500; }
.pc-buffs { display: flex; flex-wrap: wrap; gap: 4px; margin-top: 8px; }
.pc-buffs[hidden] { display: none; }
.pc-buff {
  --p: 1; --ring: color-mix(in srgb, var(--ink) 70%, transparent);
  position: relative; display: grid; place-items: center; width: 26px; height: 26px; border-radius: 50%; flex: none;
  background: conic-gradient(var(--ring) calc(var(--p) * 360deg), rgba(255, 255, 255, 0.08) 0);
}
.pc-buff img, .pc-buff .pc-glyph { width: 22px; height: 22px; border-radius: 50%; background: var(--bg); }
.pc-buff .pc-glyph { display: grid; place-items: center; font-size: 11px; font-weight: 700; color: var(--ink-2); }
.pc-buff.cc { --ring: #ff6b5e; }
.pc-buff.cc img { filter: sepia(0.5) saturate(2.2) hue-rotate(-30deg); }
.pc-buff.obj { --ring: var(--gold); box-shadow: 0 0 8px color-mix(in srgb, var(--gold) 55%, transparent); }
.pc-stacks {
  position: absolute; right: -4px; bottom: -3px; min-width: 14px; padding: 0 3px; border-radius: 7px;
  background: var(--bg); border: 1px solid var(--line); font-size: 9.5px; font-weight: 700; line-height: 12px; text-align: center;
}
.pcard.full .pc-buffs { display: grid; grid-template-columns: 26px minmax(0, 1fr) auto; gap: 4px 7px; align-items: center; }
.pc-bwrap { display: contents; }
.pc-bname { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; color: var(--ink-2); }
.pc-bleft { color: var(--muted); font-variant-numeric: tabular-nums; font-size: 11.5px; }
.pc-stats { display: grid; grid-template-columns: repeat(3, auto 1fr); gap: 2px 8px; margin: 9px 0 0; padding-top: 8px; border-top: 1px solid var(--line-soft); }
.pc-stats[hidden] { display: none; }
.pc-stats dt { color: var(--muted); }
.pc-stats dd { margin: 0; text-align: right; font-weight: 650; font-variant-numeric: tabular-nums; }
.pl.carded { box-shadow: inset 0 0 0 1px var(--gold); }
/* Hovercards: rich panels for card elements, nesting up to three deep (fixed, so the map edge
   can't clip them), sized with the map (--ui-dom). A pinned one has a gold edge. */
.hc {
  position: fixed; left: 0; top: 0; z-index: 60; width: max-content; max-width: 24em;
  font-size: calc(12.5px * var(--ui-dom, 1)); line-height: 1.42;
  background: rgba(14, 20, 23, 0.97); border: 1px solid var(--line); border-radius: var(--r-md);
  padding: 0.65em 0.8em; box-shadow: 0 10px 28px rgba(0, 0, 0, 0.55); cursor: default;
}
.hc.pinned { border-color: var(--gold); box-shadow: 0 0 0 1px var(--gold), 0 10px 28px rgba(0, 0, 0, 0.55); }
.hc-head { display: flex; align-items: center; gap: 0.6em; }
.hc-icon { width: 2.6em; height: 2.6em; border-radius: 6px; flex: none; background: var(--bg); }
.hc-titles { min-width: 0; }
.hc-title { font-weight: 700; font-size: 1.08em; }
.hc-sub { color: var(--muted); font-size: 0.92em; margin-top: 1px; overflow-wrap: anywhere; }
.hc-rows { display: grid; grid-template-columns: auto 1fr; gap: 2px 1em; margin: 0.5em 0 0; }
.hc-rows dt { color: var(--muted); }
.hc-rows dd { margin: 0; text-align: right; font-weight: 600; font-variant-numeric: tabular-nums; }
.hc-body { margin-top: 0.55em; padding-top: 0.55em; border-top: 1px solid var(--line-soft); color: var(--ink-2); font-size: 0.96em; line-height: 1.5; }
.hc-body > .tt-ability { margin: 0; padding: 0; border: 0; font-size: 1em; }
.hc-ref { text-decoration: underline dotted color-mix(in srgb, currentColor 60%, transparent); text-underline-offset: 3px; cursor: help; }
.hc-ref:hover { text-decoration-style: solid; color: var(--ink); }
.hc-path { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 10px; margin-top: 0.5em; }
.hc-path .hc-ref { display: inline-flex; align-items: center; gap: 4px; }
.hc-path img { width: 1.6em; height: 1.6em; border-radius: 3px; }
.hc-k { color: var(--muted); }
.tt-text .tt-section { display: block; }
.tt-text .tt-section + .tt-section { margin-top: 0.4em; }
.tt-attention { color: var(--ink); font-weight: 650; }
.tt-flavortext { display: block; font-style: italic; color: var(--muted); }
.tt-rules { display: block; color: var(--muted); font-size: 0.92em; }
.tt-keyword { color: var(--gold); }
.pcard [data-tip] { cursor: help; }
/* The in-game ability detail. */
.tt-ability { margin-top: 7px; padding-top: 7px; border-top: 1px solid var(--line-soft); font-size: 12px; line-height: 1.5; color: var(--ink-2); }
.tt-meta { margin-bottom: 6px; color: var(--ink-2); }
.tt-k { color: var(--muted); margin-right: 4px; }
.tt-ability b { color: var(--ink); }
.tt-val { color: var(--ink); }
.tt-calc { color: var(--muted); font-size: 11px; }
.tt-physicaldamage { color: #ff8c4a; } .tt-magicdamage { color: #7fb0ff; } .tt-truedamage { color: #f2efe8; }
.tt-status { color: #e6c86e; } .tt-keywordmajor, .tt-spellname { color: var(--gold); } .tt-healing { color: #6fd28a; } .tt-shield { color: #d8e2ea; }
.tt-speed { color: #9fd3c7; } .tt-recast, .tt-active, .tt-passive { color: #c79bff; }
.pc-bgroup { grid-column: 1 / -1; margin-top: 4px; font-size: 10.5px; font-weight: 700; color: var(--muted); letter-spacing: 0.02em; }
.pc-bwrap.internal .pc-bname, .pc-bwrap.internal .pc-bleft { opacity: 0.62; }
.pc-buff.internal { opacity: 0.7; }
.pcard.full .pc-buffs { max-height: 260px; overflow-y: auto; overscroll-behavior: contain; }
.pcard.medium .pc-bgroup, .pcard.medium .pc-buff.internal, .pcard.medium .pc-bwrap.internal { display: none; }
/* All cards: every player's card at once, a team-coloured edge so the sides read at a glance; a
   card pushed away from its champion gets a thin leader line. */
.pcard.full { box-shadow: inset 3px 0 0 var(--team), 0 10px 28px rgba(0, 0, 0, 0.5); }
.pcard.hovered { opacity: 0.97; }
.pcard.all.front { z-index: 5; }
.pcard.all .pc-follow, .pcard.all .pc-close { display: none; }
.pcard.medium { width: 214px; padding: 7px 8px 8px; }
.pcard.medium .pc-stats, .pcard.medium .pc-bname, .pcard.medium .pc-bleft, .pcard.medium .pc-who small, .pcard.medium .pc-xp { display: none; }
.pcard.full.medium .pc-buffs { display: flex; }
.pcard.medium .pc-bwrap:nth-child(n + 5) { display: none; }
.pcard.medium .pc-head { gap: 7px; }
.pcard.medium .pc-face img { width: 32px; height: 32px; }
.pcard.medium .pc-abil { margin-top: 6px; }
.pcard.medium .sum { width: 24px; height: 24px; }
.pcard.medium .sum img { width: 22px; height: 22px; }
.pcard.medium .pc-items .it { width: 21px; height: 21px; }
svg.leaders { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; z-index: 3; overflow: visible; }
svg.leaders line { stroke-width: 1.2; stroke-dasharray: 3 3; }
svg.leaders line.blue { stroke: var(--blue); }
svg.leaders line.red { stroke: var(--red); }
svg.leaders line.neutral { stroke: #c79bff; }
/* Monster cards: the player card's frame in the neutral monsters' violet. */
.pcard.mcard { --team: #c79bff; width: 214px; }
.mcard .mc-face img { border-radius: 8px; box-shadow: 0 0 0 2px var(--team); }
.mc-body { display: grid; gap: 3px; margin-top: 7px; }
.mc-body:empty { display: none; }
.mc-line { display: flex; align-items: center; gap: 5px; min-width: 0; }
.mc-line .hc-ref { display: inline-flex; align-items: center; gap: 4px; min-width: 0; }
.mc-ic { width: 18px; height: 18px; border-radius: 50%; flex: none; }
.mc-num { margin-left: auto; font-weight: 650; font-variant-numeric: tabular-nums; }
.mc-sub { margin-top: 4px; font-size: 11px; font-weight: 650; color: var(--muted); }
.mc-dmg { display: grid; gap: 2px; }
.mc-grant { display: flex; align-items: center; gap: 6px; margin-top: 8px; padding-top: 7px; border-top: 1px solid var(--line-soft); color: var(--ink-2); }
.mc-grant img { width: 20px; height: 20px; border-radius: 4px; }
.mc-grant b { color: var(--ink); font-weight: 650; }
@media (max-width: 520px) {
  .pcard.full { width: 236px; font-size: 12px; padding: 7px 8px 8px; }
  .pcard.full .pc-stats, .pcard.full .pc-bname, .pcard.full .pc-bleft { display: none; }
  .pcard.full .pc-buffs { display: flex; }
  .pcard .sum { width: 24px; height: 24px; }
  .pcard .sum img { width: 22px; height: 22px; }
  body[data-view="viewer"] .pc-rune { width: 24px; height: 24px; }
  body[data-view="viewer"] .pc-rune img { width: 22px; height: 22px; }
  .pcard .sum.down::after { transform: rotate(var(--a)) translateY(-12px); }
  .pc-items .it { width: 21px; height: 21px; }
}

/* Feed */
.feed { grid-area: feed; display: flex; flex-direction: column; min-height: 0; background: var(--panel); border: 1px solid var(--line-soft); border-radius: var(--r-lg); overflow: hidden; }
.feed-head { align-items: center; justify-content: space-between; padding: 10px 12px 4px 16px; }
.feed-head h3 { margin: 0; font-size: 14px; }
.feed-close { font-size: 20px; line-height: 1; padding: 2px 10px; }
.filters { display: flex; gap: 6px; padding: 10px 12px; flex-wrap: wrap; border-bottom: 1px solid var(--line-soft); }
.filters button {
  border: 1px solid var(--line); background: transparent; border-radius: 999px; padding: 3px 11px; font-size: 13px; color: var(--muted);
}
.filters button[aria-pressed="true"] { background: var(--raise); color: var(--ink); border-color: #33454e; }
/* The feed column's two panes: the event feed and the lane graphs (lane.ts). */
body[data-view="viewer"] .feed-panes { display: flex; gap: 4px; margin: 10px 12px 0; padding: 3px; border: 1px solid var(--line-soft); border-radius: var(--r-md); background: var(--bg); }
body[data-view="viewer"] .feed-panes button { flex: 1; border: 0; background: transparent; border-radius: var(--r-sm); padding: 5px 8px; font-size: 13px; font-weight: 650; color: var(--muted); }
body[data-view="viewer"] .feed-panes button[aria-selected="true"] { background: var(--raise); color: var(--ink); }
body[data-view="viewer"] .feed[data-pane="lane"] .filters, body[data-view="viewer"] .feed[data-pane="lane"] .events { display: none; }
body[data-view="viewer"] .feed:not([data-pane="lane"]) .lane-pane { display: none; }
body[data-view="viewer"] .lane-pane { flex: 1; min-height: 0; overflow-y: auto; overscroll-behavior: contain; scrollbar-gutter: stable; padding: 10px 12px 16px; position: relative; }
body[data-view="viewer"] .lane-graphs { min-height: 100%; }
body[data-view="viewer"] .ln-top { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
body[data-view="viewer"] .ln-pick { flex: 1 1 120px; min-width: 0; max-width: 100%; font-size: 13px; font-weight: 650; padding: 4px 6px; }
body[data-view="viewer"] .ln-vs { display: flex; align-items: center; gap: 6px; font-size: 13px; min-width: 0; }
body[data-view="viewer"] .ln-vs-w { color: var(--muted); font-size: 12px; }
body[data-view="viewer"] .ln-face { display: inline-flex; align-items: center; gap: 5px; min-width: 0; }
body[data-view="viewer"] .ln-face img { width: 22px; height: 22px; border-radius: 50%; box-shadow: 0 0 0 1.5px var(--team); flex: none; }
body[data-view="viewer"] .ln-none { color: var(--muted); font-size: 12.5px; margin: 8px 0 0; }
body[data-view="viewer"] .ln-leads {
  display: grid; grid-template-columns: auto repeat(3, minmax(0, 1fr)); gap: 3px 10px; margin: 12px 0 4px; padding: 7px 9px;
  border: 1px solid var(--line-soft); border-radius: var(--r-md); font-size: 12.5px; font-variant-numeric: tabular-nums; text-align: right;
}
body[data-view="viewer"] .ln-leads[hidden] { display: none; }
body[data-view="viewer"] .ln-lh { color: var(--muted); font-size: 11px; font-weight: 650; }
body[data-view="viewer"] .ln-lt { color: var(--ink-2); text-align: left; }
body[data-view="viewer"] .ln-leads > :first-child { text-align: left; }
body[data-view="viewer"] .ln-leads .future { opacity: 0.38; }
body[data-view="viewer"] .ln-chart { margin: 10px 0 0; }
body[data-view="viewer"] .ln-chart figcaption { display: flex; align-items: baseline; justify-content: space-between; gap: 8px; font-size: 12.5px; margin-bottom: 2px; }
body[data-view="viewer"] .ln-val { font-variant-numeric: tabular-nums; font-weight: 650; font-size: 12px; }
body[data-view="viewer"] .ln-svg { display: block; max-width: 100%; cursor: pointer; touch-action: pan-y; user-select: none; }
body[data-view="viewer"] .ln-grid line { stroke: var(--line-soft); stroke-width: 1; }
body[data-view="viewer"] .ln-grid line.zero { stroke: var(--muted); stroke-opacity: 0.7; }
body[data-view="viewer"] .ln-grid line.v { stroke-dasharray: 2 3; }
body[data-view="viewer"] .ln-grid text { fill: var(--muted); font-size: 10px; font-variant-numeric: tabular-nums; }
body[data-view="viewer"] .ln-mark line { stroke: var(--ink-2); stroke-opacity: 0.55; stroke-dasharray: 4 3; }
body[data-view="viewer"] .ln-mark circle { stroke: var(--panel); stroke-width: 1.5; }
body[data-view="viewer"] .ln-dim { fill: var(--panel); fill-opacity: 0.6; }
body[data-view="viewer"] .ln-cursor { stroke: var(--gold); stroke-width: 1.5; }
body[data-view="viewer"] .ln-hover { stroke: var(--ink-2); stroke-width: 1; stroke-opacity: 0.6; }
body[data-view="viewer"] .ln-axis { margin: 4px 0 0; text-align: center; color: var(--muted); font-size: 11px; }
.events { position: relative; list-style: none; margin: 0; padding: 6px 6px 40px; overflow-y: auto; overflow-x: hidden; flex: 1; min-height: 0; overscroll-behavior: contain; }
.ev {
  display: grid; grid-template-columns: 42px minmax(0, 1fr); gap: 8px; align-items: center;
  padding: 6px 8px; border-radius: var(--r-md); cursor: pointer; border-left: 3px solid transparent;
}
.ev:hover { background: var(--raise); }
/* Rows after the playhead dim, except one the user opened. */
.ev.future:not([aria-expanded="true"]) { opacity: 0.38; }
/* A row stays highlighted only when the user opened it. */
.ev[aria-expanded="true"] { background: var(--raise); }
/* The playhead: a thin line between the rows, labelled with the time. */
.events > .now { display: flex; align-items: center; gap: 8px; height: 0; margin: 4px 0 4px 8px; pointer-events: none; }
.events > .now time { flex: none; margin-top: -1px; padding: 0 6px; border-radius: 4px; background: var(--gold); color: var(--bg); font-size: 10.5px; font-weight: 750; line-height: 15px; font-variant-numeric: tabular-nums; }
.events > .now::after { content: ""; flex: 1; height: 1px; background: var(--gold); opacity: 0.7; }
.ev .ic-me { position: relative; display: inline-flex; flex: none; }
.ev .me-dot { position: absolute; right: -2px; bottom: -2px; width: 8px; height: 8px; border-radius: 50%; background: var(--gold); box-shadow: 0 0 0 1.5px var(--panel); }
.ev time { color: var(--muted); font-size: 12.5px; }
.t-stolen { color: #ff9a7a; font-weight: 800; }
.t-invaded { color: var(--muted); font-weight: 700; }
.ev.expandable > time { cursor: pointer; }
.ev.expandable > time:hover { color: var(--ink); text-decoration: underline; text-underline-offset: 2px; }
.ev .body { display: flex; align-items: center; gap: 6px; min-width: 0; }
.ev .ic { width: 24px; height: 24px; border-radius: 50%; box-shadow: 0 0 0 1.5px var(--team, var(--line)); flex: none; }
.ev .ic.sm { width: 17px; height: 17px; box-shadow: none; opacity: 0.85; }
.ev .ic.sq { border-radius: var(--r-sm); box-shadow: none; }
.ev .ic.obj { box-shadow: none; border-radius: 0; }
.glyph { display: inline-block; flex: none; width: 13px; height: 13px; margin: 0 5.5px; background: var(--team); }
.glyph.turret { border-radius: 2px; }
.glyph.inhib { transform: rotate(45deg); width: 12px; height: 12px; }
.glyph.plate { width: 12px; height: 7px; border-radius: 1px; margin: 0 6px; opacity: 0.75; }
.glyph.ace { width: 14px; height: 14px; border-radius: 50%; background: none; border: 2px solid var(--ink); }
.ev .arrow { color: var(--muted); font-size: 12px; }
.ev .txt { font-size: 13.5px; min-width: 0; flex: 1; line-height: 1.35; }
.ev .txt b { font-weight: 650; }
/* Summoner spells in the roster. On cooldown the icon is a soft fade; the recovered part comes
   back in full colour through a feathered edge, a thin border fills clockwise around the icon
   and a glint shimmers at its leading point. */
.sum {
  --a: calc((1 - var(--cd, 0)) * 360deg);
  position: relative; width: 22px; height: 22px; padding: 1px; border-radius: 4px; background: transparent;
}
.sum img { display: block; width: 20px; height: 20px; border-radius: 3px; transition: filter 0.25s; }
.sum img.lit {
  position: absolute; inset: 1px; display: none;
  -webkit-mask: conic-gradient(#000 calc(var(--a) - 14deg), transparent calc(var(--a) + 14deg));
  mask: conic-gradient(#000 calc(var(--a) - 14deg), transparent calc(var(--a) + 14deg));
}
.sum.down { background: conic-gradient(#ffe9a0 var(--a), rgba(10, 14, 16, 0.85) 0); }
.sum.down img:not(.lit) { filter: saturate(0.25) brightness(0.6); }
.sum.down img.lit { display: block; }
.sum.down::after {
  content: ""; position: absolute; left: 50%; top: 50%; width: 5px; height: 5px; margin: -2.5px 0 0 -2.5px;
  border-radius: 50%; pointer-events: none; z-index: 1;
  background: radial-gradient(circle, #fffbe8 0 18%, rgba(255, 233, 160, 0.75) 32%, rgba(255, 233, 160, 0) 70%);
  transform: rotate(var(--a)) translateY(-11px);
}
/* Ammo abilities: the charge count in the top-left corner; while a charge comes back with some left, a
   ring fills without fading the icon. */
.sum.charging { background: conic-gradient(#ffe9a0 var(--a), rgba(10, 14, 16, 0.85) 0); }
.sum .chg {
  position: absolute; left: -3px; top: -3px; z-index: 2; min-width: 11px; padding: 0 2px; border-radius: 6px;
  background: var(--bg); border: 1px solid var(--line); color: var(--ink); font-size: 9px; font-weight: 700;
  line-height: 10px; text-align: center; pointer-events: none;
}
.sum.down .chg { color: var(--muted); }
/* Switched on (Ashe Q, Anivia R, forms, shields): a bright, steady border glow. */
.sum.on { box-shadow: 0 0 0 1.5px #7ff0ff, 0 0 7px 1px rgba(127, 240, 255, 0.65); border-radius: 4px; }
.sum.ready { animation: sum-ready 0.5s ease-out; }
@keyframes sum-ready {
  0% { transform: scale(1); box-shadow: 0 0 0 0 rgba(255, 233, 160, 0.9); }
  35% { transform: scale(1.25); box-shadow: 0 0 0 4px rgba(255, 233, 160, 0.55); }
  100% { transform: scale(1); box-shadow: 0 0 0 7px rgba(255, 233, 160, 0); }
}
@media (prefers-reduced-motion: reduce) { .sum.ready { animation: none; } }
.ev .pill {
  display: inline-block; vertical-align: 1px; white-space: nowrap;
  font-size: 11px; font-weight: 650; padding: 1px 7px; border-radius: 999px; background: #2a2414; color: var(--gold);
}
.ev .pill.shutdown { background: #2b1c1c; color: #f2a19b; }
/* Expandable kills and fights. */
.ev:focus-visible { outline: none; box-shadow: var(--focus-ring); }
.ev .chev { flex: none; width: 16px; height: 16px; margin-left: auto; position: relative; opacity: 0.55; }
.ev .chev::before {
  content: ""; position: absolute; left: 5px; top: 3px; width: 6px; height: 6px;
  border-right: 1.5px solid var(--ink-2); border-bottom: 1.5px solid var(--ink-2); transform: rotate(45deg); transition: transform 0.15s;
}
.ev[aria-expanded="true"] .chev::before { transform: translate(0, 3px) rotate(225deg); }
.ev.expandable:hover .chev, .ev.fight:hover .chev { opacity: 1; }
/* A fight: its header, then its kills behind a bracket. */
.ev.fight { margin-top: 6px; }
.ev.fight .txt { font-size: 13px; color: var(--ink-2); }
.ev.fight .txt b { color: var(--ink); }
.ev .down.blue { color: var(--blue); font-weight: 650; }
.ev .down.red { color: var(--red); font-weight: 650; }
.glyph.fight { width: 24px; height: 24px; flex: none; position: relative; }
.glyph.ping {
  width: 18px; height: 18px; margin: 0 3px; flex: none; display: grid; place-items: center; border-radius: 50%;
  border: 1.5px solid var(--line); font-size: 12px; font-weight: 800; line-height: 1; color: var(--ink);
}
.glyph.ward { width: 12px; height: 12px; margin: 0 6px; flex: none; transform: rotate(45deg); border-radius: 2px; }
.glyph.ward.w1 { background: #ff5fa8; }
.glyph.ward.w2 { background: #5fb4ff; }
.glyph.ward.w0 { background: #7ee08a; }
.glyph.ward.w3 { background: #ffe066; }
.filters button[hidden] { display: none; }
.tip .t-cc { margin-top: 6px; color: var(--gold); font-weight: 650; font-size: 12.5px; }
.t-ward { display: flex; align-items: center; gap: 2px; }
.t-ward .glyph.ward { margin: 0 8px 0 3px; }
.t-by { display: flex; align-items: center; gap: 6px; margin: 4px 0 2px; font-weight: 650; }
.t-by .ic { border-radius: 50%; border: 2px solid; }
.glyph.fight::before, .glyph.fight::after {
  content: ""; position: absolute; left: 11px; top: 3px; width: 2px; height: 18px; border-radius: 1px; background: var(--gold);
}
.glyph.fight::before { transform: rotate(40deg); }
.glyph.fight::after { transform: rotate(-40deg); }
.ev.in-fight { margin-left: 12px; border-left: 2px solid rgba(243, 201, 105, 0.35); border-radius: 0 var(--r-md) var(--r-md) 0; }
.ev.in-fight.fight-end { border-bottom-left-radius: 6px; margin-bottom: 6px; }

.ev > .recap { grid-column: 1 / -1; cursor: default; min-width: 0; }
.recap {
  --phys: #e9935b; --magic: #8aa8ff; --true: #efe9dc;
  margin: 4px -2px 2px; padding: 10px 10px 8px; border-radius: var(--r-md);
  background: var(--bg); border: 1px solid var(--line-soft); font-size: 12.5px;
}
.recap-tabs { display: inline-flex; gap: 2px; padding: 2px; border-radius: var(--r-sm); background: var(--panel); margin: 0 6px 8px 0; }
.recap-tabs button { border: 0; background: transparent; padding: 3px 8px; border-radius: 4px; font-size: 12px; font-weight: 600; color: var(--muted); }
.recap-tabs button[aria-pressed="true"] { background: var(--raise); color: var(--ink); }
.recap-total { margin: 0 0 8px; color: var(--ink-2); line-height: 1.5; }
.recap-total b { color: var(--ink); font-size: 14px; font-variant-numeric: tabular-nums; }
.recap-total .legend { display: inline-flex; flex-wrap: wrap; gap: 8px; margin-left: 8px; font-size: 11.5px; }
.recap-total .legend span::before { content: ""; display: inline-block; width: 8px; height: 8px; border-radius: 2px; margin-right: 4px; vertical-align: 0; }
.legend .p { color: var(--phys); } .legend .p::before { background: var(--phys); }
.legend .m { color: var(--magic); } .legend .m::before { background: var(--magic); }
.legend .t { color: var(--true); } .legend .t::before { background: var(--true); }
.recap-groups { list-style: none; margin: 0; padding: 0; display: grid; gap: 9px; }
.rg-head { display: flex; align-items: center; gap: 7px; }
.rg-head .ic { width: 20px; height: 20px; border-radius: 50%; box-shadow: 0 0 0 1.5px var(--line); }
.rg.blue .rg-head .ic { box-shadow: 0 0 0 1.5px var(--blue); }
.rg.red .rg-head .ic { box-shadow: 0 0 0 1.5px var(--red); }
.rg-name { font-weight: 650; color: var(--ink); flex: 1; min-width: 0; overflow-wrap: break-word; }
.rg-amt { font-variant-numeric: tabular-nums; font-weight: 650; }
.rg-pct { color: var(--muted); font-variant-numeric: tabular-nums; min-width: 34px; text-align: right; }
.dbar { display: flex; height: 5px; margin: 5px 0 5px 27px; max-width: calc(100% - 27px); border-radius: 3px; overflow: hidden; background: var(--panel); }
.dbar i { display: block; min-width: 2px; }
.dbar .p { background: var(--phys); } .dbar .m { background: var(--magic); } .dbar .t { background: var(--true); }
.hits { list-style: none; margin: 0 0 0 27px; padding: 0; display: flex; flex-wrap: wrap; gap: 4px 6px; }
.hit { display: inline-flex; align-items: center; gap: 4px; padding: 1px 6px 1px 1px; border-radius: 4px; background: var(--panel); font-variant-numeric: tabular-nums; font-size: 11.5px; cursor: help; }
.hit img { width: 18px; height: 18px; border-radius: 3px; display: block; }
.hit.p span { color: var(--phys); } .hit.m span { color: var(--magic); } .hit.t span { color: var(--true); }
.recap .g { width: 18px; height: 18px; border-radius: 3px; display: inline-block; flex: none; background: var(--raise) center / 12px no-repeat; }
.recap .g.src { width: 20px; height: 20px; border-radius: 50%; }
.recap .g.basic { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M3 13l7-7M10 3h3v3l-6 6-3-3z' fill='none' stroke='%23e8e4da' stroke-width='1.4' stroke-linejoin='round'/%3E%3C/svg%3E"); }
.recap .g.burn { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M8 2c1 3 4 4 4 8a4 4 0 0 1-8 0c0-2 1-3 2-4 0 2 1 3 2 3 0-3-1-4 0-7z' fill='%23e9935b'/%3E%3C/svg%3E"); }
.recap .g.tower { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M4 14h8l-1-8h1V3h-2v1H9V3H7v1H6V3H4v3h1z' fill='%23b4b9b2'/%3E%3C/svg%3E"); }
.recap .g.minion { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Ccircle cx='8' cy='8' r='4' fill='%23b4b9b2'/%3E%3C/svg%3E"); }
.recap .g.monster { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M3 6l2-3 1 3h4l1-3 2 3v4a5 5 0 0 1-10 0z' fill='%23c79bff'/%3E%3C/svg%3E"); }
.recap .g.other { background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath d='M8 3l5 5-5 5-5-5z' fill='none' stroke='%23b4b9b2' stroke-width='1.4'/%3E%3C/svg%3E"); }
/* Decoded recap: the killing blow, and every hit in order. */
.recap-kb { display: flex; flex-wrap: wrap; align-items: center; gap: 4px 6px; margin: 8px 0 4px; font-size: 12.5px; color: var(--ink-2); }
.recap-kb img { width: 18px; height: 18px; border-radius: 3px; }
.kb-tag { font-size: 10.5px; font-weight: 800; padding: 1px 6px; border-radius: 999px; background: #ff6b5e; color: #160807; }
.recap-timeline { list-style: none; margin: 8px 0 0; padding: 0; display: grid; gap: 2px; font-size: 12px; }
.recap-timeline .tl { display: grid; grid-template-columns: 48px 18px auto minmax(0, 1fr) auto auto; align-items: center; gap: 6px; padding: 2px 4px; border-radius: 4px; }
.recap-timeline .tl > img:nth-of-type(2) { width: 18px; height: 18px; border-radius: 3px; }
.recap-timeline .tl:not(:has(> img:nth-of-type(2))) { grid-template-columns: 48px 18px minmax(0, 1fr) auto auto; }
.recap-timeline time { color: var(--muted); font-variant-numeric: tabular-nums; text-align: right; }
.recap-timeline .tl-what { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; color: var(--ink-2); }
.recap-timeline .tl-amt { font-weight: 700; font-variant-numeric: tabular-nums; text-align: right; }
.recap-timeline .tl-amt.p { color: #ff8c4a; } .recap-timeline .tl-amt.m { color: #7fb0ff; } .recap-timeline .tl-amt.t { color: #f2efe8; }
.recap-timeline .tl.kb { background: color-mix(in srgb, #ff6b5e 14%, transparent); }
.recap-empty { margin: 9px 0 0; color: var(--muted); font-size: 11.5px; line-height: 1.4; }

/* Transport */
.transport {
  grid-area: transport; display: grid; grid-template-columns: auto auto auto minmax(0, 1fr) auto auto;
  align-items: center; gap: 12px; background: var(--panel); border: 1px solid var(--line-soft);
  border-radius: var(--r-lg); padding: 8px 12px;
}
.play {
  width: 46px; height: 46px; border-radius: 50%; border: 0; background: var(--ink); color: var(--bg);
  display: grid; place-items: center;
}
.play svg { width: 22px; height: 22px; fill: currentColor; }
.play .i-pause { display: none; }
.play.is-playing .i-play { display: none; }
.play.is-playing .i-pause { display: block; }
.clock { font-size: 15px; font-weight: 650; min-width: 92px; }
.clock .of { color: var(--muted); margin: 0 4px; font-weight: 400; }
.clock #total { color: var(--muted); font-weight: 400; }
#speed { background: var(--raise); border: 1px solid var(--line); border-radius: var(--r-md); padding: 6px 8px; }
.scrub { position: relative; height: 72px; cursor: pointer; touch-action: none; border-radius: var(--r-md); }
.scrub canvas { position: absolute; inset: 0; width: 100%; height: 100%; display: block; }
.scrub-tip {
  position: absolute; top: -30px; transform: translateX(-50%); padding: 3px 8px; font-size: 12px; font-weight: 650;
  background: var(--raise); border: 1px solid var(--line); border-radius: var(--r-sm); pointer-events: none; white-space: nowrap;
}
.scrub-tip[hidden] { display: none; }
.icon-btn {
  width: 40px; height: 40px; border-radius: var(--r-md); border: 1px solid var(--line); background: transparent;
  display: grid; place-items: center; font-weight: 700;
}
.icon-btn:hover { background: var(--raise); }
.icon-btn svg { width: 20px; height: 20px; fill: none; stroke: currentColor; stroke-width: 2; stroke-linecap: round; stroke-linejoin: round; }

.keys {
  background: var(--panel); color: var(--ink); border: 1px solid var(--line); border-radius: var(--r-lg);
  padding: 20px 24px; max-width: 420px;
}
.keys::backdrop { background: rgba(0, 0, 0, 0.55); }
.keys h2 { margin: 0 0 10px; font-size: 18px; }
.keys { max-width: min(860px, calc(100vw - 32px)); max-height: calc(100dvh - 48px); overflow-y: auto; }
.keys-grid { columns: 2 340px; column-gap: 28px; margin-bottom: 16px; }
.keys-group { break-inside: avoid; margin-bottom: 14px; }
.keys-group h3 { margin: 0 0 6px; font-size: 13px; color: var(--muted); font-weight: 650; }
.keys-group dl { margin: 0; }
.keys-row { display: grid; grid-template-columns: 9.5em 1fr; gap: 10px; padding: 3px 0; align-items: baseline; }
.keys-row dt { display: flex; flex-wrap: wrap; gap: 3px; }
.keys-row dd { margin: 0; color: var(--ink-2); font-size: 13px; }
.keys kbd {
  font: 600 11.5px/1 system-ui, sans-serif; padding: 3px 6px; border-radius: 5px; color: var(--ink);
  background: var(--raise); border: 1px solid var(--line); box-shadow: inset 0 -1px 0 var(--line);
}
.keys-league { margin-left: 8px; font-size: 11px; color: var(--gold); white-space: nowrap; }
/* Panels hidden (H): the player takes the whole viewer. */
.viewer.hud-off { grid-template-areas: "head head head" "player player player"; grid-template-rows: auto minmax(0, 1fr); }
.viewer.hud-off .feed, .viewer.hud-off .team-panel { display: none; }
.toast {
  position: fixed; left: 50%; bottom: 28px; transform: translateX(-50%); z-index: 70; pointer-events: none;
  padding: 8px 14px; border-radius: var(--r-md); background: rgba(14, 20, 23, 0.96); border: 1px solid var(--line);
  font-size: 13px; font-weight: 600; box-shadow: 0 8px 22px rgba(0, 0, 0, 0.5);
}
.toast[hidden] { display: none; }
.keys button { background: var(--ink); color: var(--bg); border: 0; border-radius: var(--r-md); padding: 7px 16px; font-weight: 650; }
.noscript { padding: 24px; }

/* ---- Responsive --------------------------------------------------------------------------- */
@media (min-width: 2200px) {
  body { font-size: 16px; }
  .viewer { gap: 14px; padding: 0 18px 18px; }
  .ev .txt { font-size: 14.5px; }
}
/* Very wide viewports (a 1440p or 4K monitor at 100%): the panels around the map scale up with the
   screen instead of staying laptop-sized beside a huge map. Only DOM without canvases is zoomed
   (the map, its tooltip and the scrubber size themselves from their own boxes); the feed column
   widens by the same factor. */
:root { --uiz: 1; }
@media (min-width: 2400px) { :root { --uiz: 1.2; } }
@media (min-width: 2880px) { :root { --uiz: 1.4; } }
@media (min-width: 3400px) { :root { --uiz: 1.6; } }
.topbar, .match-head, .feed, .team-panel, .map-tools, .fog-tools { zoom: var(--uiz); }



/* Small laptops: a narrower event column. */
@media (max-width: 1279px) {
  .viewer { --feed: 240px; }
}

@media (max-width: 760px), (max-width: 1180px) and (orientation: portrait) {
  .card-teams { grid-template-columns: minmax(0, 1fr); }
  .topbar { gap: 12px; padding-top: max(10px, env(safe-area-inset-top)); padding-bottom: 10px; flex-wrap: wrap; }
  body[data-view="viewer"] .topbar .search, body[data-view="player"] .topbar .search { order: 3; flex-basis: 100%; max-width: none; }
  .landing { grid-template-columns: minmax(0, 1fr); padding-top: 0; }
  .showcase { position: relative; top: 0; order: -1; max-width: 520px; margin: 0 auto; }
  /* The search comes right after the headline; the drop zone (a file picker on phones) follows. */
  .intro { padding-top: 0; display: flex; flex-direction: column; }
  .intro .drop { order: 2; margin-top: 18px; }
  .intro .results { order: 3; }
  .search-slot .search { flex-wrap: wrap; }
  .search-slot .search input { flex-basis: 100%; }
  .search-slot .search select { flex: 0 0 auto; }
  .search-slot .search button { flex: 1; }
  /* Phone: the player (map + playback), then the teams side by side or the feed, by tab. */
  .viewer {
    height: auto; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    grid-template-rows: auto auto auto auto auto;
    grid-template-areas: "head head" "player player" "tabs tabs" "blue red" "feed feed";
    padding: 0 8px 16px; gap: 8px;
  }
  .player > .stage { width: 100%; height: auto; aspect-ratio: 1; }
  .player:fullscreen > .stage, .player.fs > .stage { width: auto; height: 100%; max-width: 100%; aspect-ratio: 1; flex: 1 1 0; min-height: 0; }
  .feed, .viewer.feed-open .feed { position: static; transform: none; visibility: visible; width: auto; box-shadow: none; border-radius: var(--r-lg); transition: none; }
  .feed-toggle, .feed-head { display: none; }
  .view-tabs { grid-area: tabs; display: flex; gap: 4px; padding: 3px; border: 1px solid var(--line-soft); border-radius: var(--r-md); background: var(--panel); }
  .view-tabs button { flex: 1; border: 0; background: transparent; border-radius: var(--r-sm); padding: 8px; font-weight: 650; color: var(--ink-2); }
  .view-tabs button[aria-selected="true"] { background: var(--raise); color: var(--ink); }
  .viewer:not([data-tab="teams"]) .team-panel { display: none; }
  .viewer[data-tab="teams"] .feed { display: none; }
  body[data-view="viewer"] .feed-panes { display: none; }
  .team-panel { flex-direction: column; }
  .tp-head, .team-panel.blue .tp-head { order: 0; width: auto; border: 0; border-bottom: 1px solid var(--line-soft); text-align: left; align-items: stretch; }
  .team-panel.blue .tp-gold, .team-panel.blue .tp-objs, .team-panel.blue .tp-name { justify-content: flex-start; }
  .tp-rows { flex-direction: column; padding: 3px; }
  .pl { grid-template-columns: 32px minmax(0, 1fr); grid-template-areas: "face who" "face stats" "face more" "abil abil" "items items"; padding: 5px; column-gap: 7px; }
  .pl .face, .pl .face img { width: 32px; height: 32px; }
  .feed { height: 60vh; }
  .transport { grid-template-columns: auto auto 1fr auto; grid-template-areas: "play clock speed fs" "scrub scrub scrub scrub"; gap: 8px 10px; }
  .play { grid-area: play; width: 42px; height: 42px; }
  .clock { grid-area: clock; }
  #speed { grid-area: speed; justify-self: end; }
  #fullscreen { grid-area: fs; }
  #help { display: none; }
  .scrub { grid-area: scrub; height: 56px; }
  .map-clock { left: 8px; top: 8px; transform: none; font-size: 20px; padding: 2px 10px 3px; gap: 6px; }
  .source-note { font-size: 11px; right: 12px; max-width: none; bottom: 6px; background: rgba(13, 18, 21, 0.75); padding: 2px 6px; border-radius: var(--r-sm); left: 6px; }
  .topbar .search button { padding: 9px 12px; }
  .map-tools button { min-width: 32px; height: 32px; }
  .map-corner { max-width: calc(100% - 120px); }
}

/* Room for Fit, Minions and Pings beside the clock: pinch and the wheel zoom here. */
@media (max-width: 520px) {
  #zoom-in, #zoom-out { display: none; }
}

@media (prefers-reduced-motion: reduce) {
  * { scroll-behavior: auto !important; }
  .status.busy::before { animation: none; }
}

/* "Analyzing game": the decoder pipeline at work, over the dimmed map. */
.analyzing {
  position: absolute; inset: 0; z-index: 4; display: grid; place-items: center; padding: 16px;
  background: rgba(13, 18, 21, 0.6); overflow: hidden; transition: opacity 0.6s ease;
}
.analyzing[data-state="done"] { opacity: 0; pointer-events: none; }
.az-sweep {
  position: absolute; inset: -60%; pointer-events: none;
  background: linear-gradient(135deg, transparent 46%, rgba(76, 155, 232, 0.05) 48.8%, rgba(243, 201, 105, 0.13) 50%, rgba(229, 83, 75, 0.05) 51.2%, transparent 54%);
  animation: az-sweep 3.8s cubic-bezier(0.45, 0, 0.25, 1) infinite;
}
@keyframes az-sweep { from { transform: translate(-28%, 28%); } to { transform: translate(28%, -28%); } }
.analyzing[data-state="ended"] .az-sweep, .analyzing[data-state="waiting"] .az-sweep { animation-play-state: paused; opacity: 0; transition: opacity 0.4s; }
.az-panel {
  position: relative; width: min(400px, 100%); display: grid; gap: 14px; padding: 16px 18px 18px;
  background: rgba(18, 26, 30, 0.94); border: 1px solid var(--line); border-radius: var(--r-lg);
  box-shadow: 0 24px 70px rgba(0, 0, 0, 0.5);
}
.az-team { display: flex; justify-content: center; gap: 8px; }
.az-team img {
  width: 40px; height: 40px; border-radius: 50%; box-shadow: 0 0 0 2px var(--team-c), 0 0 0 4px var(--panel);
  animation: az-in 0.5s calc(var(--k) * 60ms) both ease-out;
}
.az-team.blue img { --team-c: var(--blue); }
.az-team.red img { --team-c: var(--red); animation-delay: calc(300ms + var(--k) * 60ms); }
@keyframes az-in { from { opacity: 0; transform: translateY(4px) scale(0.92); } }
.az-title { margin: 0; font-size: 22px; font-weight: 700; letter-spacing: -0.01em; }
.az-sub { margin: 2px 0 12px; color: var(--muted); font-size: 13px; }
.az-stages { list-style: none; margin: 0; padding: 0; display: grid; gap: 9px; }
.az-stage { display: grid; grid-template-columns: 18px 1fr auto; align-items: center; column-gap: 8px; font-size: 14px; color: var(--muted); transition: color 0.3s; }
.az-dot { width: 10px; height: 10px; border-radius: 50%; border: 1.5px solid var(--line); justify-self: center; position: relative; transition: background 0.3s, border-color 0.3s; }
.az-stage[data-state="done"] { color: var(--ink-2); }
.az-stage[data-state="done"] .az-dot { background: var(--gold); border-color: var(--gold); }
.az-stage[data-state="active"] { color: var(--ink); font-weight: 600; }
.az-stage[data-state="active"] .az-dot { border-color: var(--gold); }
.az-stage[data-state="active"] .az-dot::after {
  content: ""; position: absolute; inset: -5px; border-radius: 50%; border: 1.5px solid var(--gold);
  animation: az-pulse 1.4s ease-out infinite;
}
@keyframes az-pulse { from { opacity: 0.9; transform: scale(0.6); } to { opacity: 0; transform: scale(1.5); } }
.az-stage[data-state="stopped"] { color: var(--ink); }
.az-stage[data-state="stopped"] .az-dot { border-color: var(--red); background: var(--red); }
.az-detail { font-size: 12.5px; color: var(--ink-2); font-variant-numeric: tabular-nums; font-weight: 500; }
.az-bar { grid-column: 2 / -1; height: 3px; margin-top: 5px; border-radius: 2px; background: var(--raise); overflow: hidden; }
.az-bar[hidden] { display: none; }
.az-bar i { display: block; height: 100%; width: 0; background: var(--gold); transition: width 0.6s ease; }
.az-status:empty { display: none; }
.az-msg { margin: 14px 0 0; color: var(--ink-2); font-size: 14px; line-height: 1.45; }
.az-why { margin: 6px 0 0; color: var(--muted); font-size: 12px; overflow-wrap: anywhere; }
.az-actions { display: flex; flex-wrap: wrap; gap: 8px; margin-top: 12px; }
.az-btn { border: 0; border-radius: var(--r-md); padding: 8px 14px; font-weight: 650; background: var(--ink); color: var(--bg); }
.az-btn.ghost { background: transparent; color: var(--ink-2); border: 1px solid var(--line); }
@media (prefers-reduced-motion: reduce) {
  .az-sweep { display: none; }
  .az-team img, .az-stage[data-state="active"] .az-dot::after { animation: none; }
  .analyzing { transition: none; }
}
@media (max-width: 760px) {
  /* The map is a square here: drop the decorative portraits and let the panel scroll. */
  .analyzing { place-items: start center; overflow-y: auto; padding: 10px; }
  .az-team { display: none; }
  .az-panel { padding: 12px 14px 14px; gap: 8px; }
  .az-title { font-size: 18px; }
  .az-sub { margin-bottom: 8px; }
  .az-stages { gap: 6px; }
  .az-stage { font-size: 13px; }
  .az-msg { margin-top: 8px; font-size: 13px; }
}
.source-note[hidden] { display: none; }

/* The two size cycles: a portrait (round) for champions, a tile (square) for every other icon. */
.size-btn { display: inline-flex; align-items: center; gap: 4px; }
.size-btn .sz { width: 9px; height: 9px; border: 1.5px solid currentColor; border-radius: 2px; opacity: 0.8; }
.size-btn .sz.round { border-radius: 50%; }

/* ---- Rankings ------------------------------------------------------------------------------ */
.nav-link { flex: none; color: var(--ink-2); text-decoration: none; font-weight: 650; font-size: 14.5px; padding: 6px 2px; border-radius: var(--r-sm); }
.nav-link:hover { color: var(--ink); }
body[data-view="rankings"] .nav-link { color: var(--gold); }
body[data-view="rankings"] .topbar .search { display: flex; }
.rankings { max-width: 1040px; margin: 0 auto; padding: 4px max(16px, 4vw) 48px; }
.rk-head { display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 14px; margin: 4px 0 14px; }
.rk-head h1 { margin: 0; font-size: 26px; letter-spacing: -0.02em; }
.rk-region { background: var(--panel); border: 1px solid var(--line); border-radius: var(--r-md); padding: 6px 8px; align-self: center; }
.rk-sub { color: var(--muted); font-size: 13px; }
.rk-tools { display: flex; flex-wrap: wrap; align-items: center; gap: 10px 16px; margin-bottom: 10px; }
.rk-search { flex: 1 1 220px; max-width: 320px; background: var(--panel); border: 1px solid var(--line); border-radius: var(--r-md); padding: 8px 12px; }
.rk-search::placeholder { color: var(--muted); }
.rk-jumps { display: flex; flex-wrap: wrap; gap: 4px 14px; }
.rk-jump { display: inline-flex; align-items: center; gap: 5px; color: var(--ink-2); text-decoration: none; font-size: 13.5px; }
.rk-jump:hover, .rk-jump[aria-current="page"] { color: var(--ink); }
.rk-jump .n { color: var(--muted); font-variant-numeric: tabular-nums; }
.rk-table { width: 100%; table-layout: fixed; border-collapse: collapse; font-variant-numeric: tabular-nums; background: var(--panel); border: 1px solid var(--line-soft); border-radius: var(--r-lg); overflow: hidden; }
.rk-table th { text-align: left; font-size: 12px; font-weight: 600; color: var(--muted); padding: 9px 12px; border-bottom: 1px solid var(--line); }
.rk-table td { padding: 7px 12px; border-bottom: 1px solid var(--line-soft); font-size: 14px; white-space: nowrap; }
.rk-table tbody tr:last-child td { border-bottom: 0; }
.rk-table tbody tr:hover td { background: var(--raise); }
.rk-table .rk-pos { width: 104px; text-align: right; color: var(--ink-2); padding-left: 4px; padding-right: 6px; }
/* The mover's previous place: dim, small, in a fixed slot after the rank on every row. */
.rk-prev { display: inline-block; width: 5ch; margin-left: 5px; text-align: left; font-size: 11px; color: var(--muted); font-variant-numeric: tabular-nums; }
/* The move since the previous snapshot, in a fixed slot left of the rank: green up, red down, a
   green dot for new. Only players who changed themselves (their LP or games) get one. */
.rk-mv { display: inline-block; width: 8px; margin-right: 4px; text-align: right; font-size: 9px; line-height: 1; vertical-align: 1px; }
.rk-mv.up { color: var(--up); }
.rk-mv.down { color: var(--red); }
.rk-mv.new::before { content: ""; display: inline-block; width: 6px; height: 6px; border-radius: 50%; background: var(--up); vertical-align: 1px; }
.rk-mv:not(:empty), .rk-mv.new { animation: rk-mv-in 0.4s ease-out; }
@keyframes rk-mv-in { from { opacity: 0; transform: translateY(2px); } to { opacity: 1; transform: none; } }
.rk-table td.rk-who { white-space: normal; overflow-wrap: break-word; line-height: 1.3; }
.rk-table .rk-tier { width: 52px; }
.rk-table .rk-lp { width: 96px; }
.rk-table .rk-wl { width: 128px; }
.rk-table .rk-wr { width: 84px; }
.rk-table .rk-lp, .rk-table .rk-wl, .rk-table .rk-wr { text-align: right; }
.rk-table td.rk-wl { color: var(--ink-2); font-size: 13px; }
.rk-table td.rk-wr { color: var(--ink-2); }
/* Tight rank badges, as in the game list. */
.rk-table .rank, .rk-jump .rank {
  display: inline-flex; align-items: center; height: 14px; padding: 0 4px; margin-left: 0; border-radius: 2px;
  font-size: 10px; line-height: 1; font-weight: 750; letter-spacing: 0.03em; vertical-align: middle;
}
a.rk-name { color: var(--ink); text-decoration: none; }
a.rk-name:hover .n { text-decoration: underline; text-underline-offset: 2px; }
a.rk-name .t { color: var(--muted); margin-left: 1px; }
.rk-unknown { display: inline-flex; align-items: center; gap: 8px; background: none; border: 0; padding: 0; color: var(--muted); font: inherit; cursor: pointer; max-width: 100%; }
.rk-unknown[disabled] { cursor: progress; }
.rk-lookup { display: inline-flex; align-items: center; justify-content: center; min-width: 54px; height: 20px; padding: 0 8px; border: 1px solid var(--line); border-radius: 999px; font-size: 11.5px; font-weight: 600; color: var(--ink-2); }
.rk-unknown:hover:not([disabled]) .rk-lookup { background: var(--raise); color: var(--ink); border-color: var(--muted); }
/* Looking up: the pill turns into a spinner, then the name fades in. */
.rk-unknown.busy .rk-lookup::after { content: ""; width: 10px; height: 10px; border: 2px solid var(--line); border-top-color: var(--ink-2); border-radius: 50%; animation: rk-spin 0.7s linear infinite; }
a.rk-name.rk-fade { animation: rk-in 0.5s ease-out; }
@keyframes rk-in { from { opacity: 0; } to { opacity: 1; } }
.rk-status { color: var(--muted); margin: 14px 2px; }
.rk-status:empty { display: none; }
.rk-pager { display: flex; justify-content: center; align-items: center; gap: 18px; margin-top: 14px; font-size: 14px; }
.rk-page { color: var(--ink); text-decoration: none; padding: 7px 14px; border: 1px solid var(--line); border-radius: var(--r-md); background: var(--panel); }
a.rk-page:hover { background: var(--raise); }
.rk-page.off { color: var(--muted); opacity: 0.6; }
.rk-of { color: var(--ink-2); font-variant-numeric: tabular-nums; }
@media (max-width: 520px) {
  .nav-link { font-size: 13.5px; }
  .rk-table th, .rk-table td { padding: 7px 8px; }
  .rk-table .rk-wl { display: none; }
  .rk-table .rk-pos { width: 86px; }
  .rk-prev { margin-left: 4px; font-size: 10px; }
  .rk-table .rk-tier { width: 36px; }
  .rk-table .rk-lp { width: 56px; }
  /* No truncation on phones: names wrap between words or before the #tag (mid-word only when one word is too long), "Unknown player" is
     "Unknown" with its Look up pill under it when they don't fit, LP drops its unit (the header has it). */
  .rk-table td.rk-who { white-space: normal; overflow: visible; text-overflow: clip; overflow-wrap: break-word; line-height: 1.3; }
  .rk-unknown { flex-wrap: wrap; gap: 4px 8px; text-align: left; }
  .rk-wide { display: none; }
  .rk-table .rk-wr { width: 46px; }
  .rk-table th.rk-wr { font-size: 0; }
  .rk-table th.rk-wr::after { content: "WR"; font-size: 12px; }
  .rk-head h1 { font-size: 22px; }
}
@media (max-width: 360px) {
  .rk-table .rk-pos { width: 80px; }
}
/* Phones and portrait tablets: the search takes its own row, as on the player page. */
@media (max-width: 760px), (max-width: 1180px) and (orientation: portrait) {
  body[data-view="rankings"] .topbar .search { order: 3; flex-basis: 100%; max-width: none; }
}
/* The owner's Refresh: spins while Riot answers, then counts down to the next one. */
.rk-refresh { display: inline-flex; align-items: center; gap: 6px; align-self: center; padding: 5px 10px; border: 1px solid var(--line); border-radius: var(--r-md); background: var(--panel); color: var(--ink-2); font: inherit; font-size: 13px; font-variant-numeric: tabular-nums; cursor: pointer; }
.rk-refresh[hidden] { display: none; }
.rk-refresh:hover:not([disabled]) { background: var(--raise); color: var(--ink); }
.rk-refresh[disabled] { cursor: default; opacity: 0.75; }
.rk-refresh svg { width: 14px; height: 14px; fill: none; stroke: currentColor; stroke-width: 2.2; stroke-linecap: round; stroke-linejoin: round; }
.rk-refresh.busy { cursor: progress; }
.rk-refresh.busy svg { animation: rk-spin 0.8s linear infinite; }
@keyframes rk-spin { to { transform: rotate(360deg); } }
/* A row a refresh moved (place or LP) flashes once. */
.rk-table tbody tr.rk-changed td { animation: rk-flash 2.4s ease-out; }
@keyframes rk-flash { from { background: color-mix(in srgb, var(--gold) 22%, transparent); } to { background: transparent; } }
@media (prefers-reduced-motion: reduce) {
  .rk-unknown.busy .rk-lookup::after { animation: none; }
  a.rk-name.rk-fade { animation: none; }
  .rk-mv:not(:empty), .rk-mv.new { animation: none; }
  .rk-refresh.busy svg { animation: none; opacity: 0.5; }
  .rk-table tbody tr.rk-changed td { animation: none; background: color-mix(in srgb, var(--gold) 10%, transparent); }
}

/* ---- Footer: Riot's legal notice and the legal links, on every page but /admin -------------- */
/* Flex items with auto side margins shrink to their content: the centred columns keep full width. */
body > main, body > .site-foot { width: 100%; }
body > main { flex: 1 0 auto; }
body > .viewer { flex: none; }
.site-foot {
  display: flex; align-items: baseline; gap: 8px 24px; flex-wrap: wrap;
  max-width: 1440px; margin: 0 auto;
  padding: 18px max(16px, env(safe-area-inset-left)) max(18px, env(safe-area-inset-bottom)) max(16px, env(safe-area-inset-right));
  border-top: 1px solid var(--line-soft); color: var(--muted); font-size: 11.5px; line-height: 1.5;
}
.site-foot p { margin: 0; flex: 1 1 32em; max-width: 72em; }
.site-foot nav { display: flex; gap: 16px; flex: none; }
.site-foot a { color: var(--ink-2); text-decoration: none; }
.site-foot a:hover { color: var(--ink); text-decoration: underline; }

/* ---- /terms, /privacy ----------------------------------------------------------------------- */
.legal { max-width: 720px; margin: 0 auto; padding: 8px 16px 56px; }
.legal h1 { font-size: 34px; line-height: 1.15; letter-spacing: -0.02em; margin: 16px 0 4px; }
.legal h2 { font-size: 18px; margin: 30px 0 8px; }
.legal p, .legal li { color: var(--ink-2); line-height: 1.65; }
.legal p { margin: 0 0 12px; }
.legal ul { margin: 0 0 12px; padding-left: 20px; }
.legal li { margin: 0 0 4px; }
.legal a { color: var(--ink); }
.legal code { font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: 0.88em; color: var(--ink); overflow-wrap: anywhere; }
.legal-date { color: var(--muted) !important; font-size: 13px; margin-bottom: 20px !important; }

/* Estimated numbers (gold and CS between Riot's minute frames, a timeline-only respawn): a ~ mark. */
body[data-view="viewer"] .num.est::before, body[data-view="viewer"] .respawn.est:not(:empty)::before { content: "~"; opacity: 0.7; }
body[data-view="viewer"] .mastery-b {
  display: inline-block; margin-left: 4px; padding: 0 4px; border-radius: 4px; font-size: 10px; font-weight: 700; line-height: 14px;
  color: #d9c27a; box-shadow: inset 0 0 0 1px rgba(217, 194, 122, 0.55); vertical-align: 1px; font-variant-numeric: tabular-nums;
}
