/* Palette carried over from the Streamlit app's theme, so the two look related
   while both are up. FDR colours are the FPL-community convention and are not
   ours to invent. */
:root {
  --purple: #37003c;
  --purple-soft: #f4f0f8;
  --ink: #1a1a2e;
  --muted: #6b6b7b;
  --line: #e4e0ea;
  --bg: #fff;
  --page: #f3f1f6;

  /* A second, lighter purple. The modal opens on top of the card head, and a
     head in the same colour as the band behind it has no edge; this one is the
     same hue carried up in lightness, so the two read as one family. */
  --purple-lift: #7a1a6d;
  --purple-lift-mid: #9c2a82;
  --purple-lift-far: #b93f95;

  /* The Points band, and the pair of colours every actual-vs-expected bar
     uses — solid for what happened, pale for what was expected. */
  --band: #f6f1f9;
  --actual: #4a1750;
  --expected: #d9c9e2;

  /* Minutes pills: the fill is green past the 60' point, amber under it. */
  --pill-start: #12b981;
  --pill-sub: #f59e0b;

  /* How long a pointer has to rest on something before its tooltip appears.
     One value for the whole app: a tooltip on a stat cell should not feel
     different from a tooltip on the info icon. The browser's own delay on a
     `title` attribute is about a second and cannot be set, which is why
     tooltips here are `data-tip` instead. */
  --tip-delay: 200ms;

  --fdr-1-bg: darkgreen;   --fdr-1-fg: #fff;
  --fdr-2-bg: #09fc7b;     --fdr-2-fg: #000;
  --fdr-3-bg: #e7e7e8;     --fdr-3-fg: #000;
  --fdr-4-bg: #ff1651;     --fdr-4-fg: #fff;
  --fdr-5-bg: #80072d;     --fdr-5-fg: #fff;
}

* { box-sizing: border-box; }

body {
  margin: 0;
  background: var(--page);
  color: var(--ink);
  font: 14px/1.45 system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
}

/* ── Chrome ─────────────────────────────────────────────────────────────── */

header.top {
  display: flex;
  align-items: baseline;
  gap: 1.5rem;
  padding: 0.75rem 1.25rem;
  background: var(--purple);
  color: #fff;
}
header.top .brand { font-weight: 700; letter-spacing: -0.01em; }
header.top nav { display: flex; gap: 1rem; }
header.top nav a {
  color: #cfc3d6;
  text-decoration: none;
  padding-bottom: 2px;
  border-bottom: 2px solid transparent;
}
header.top nav a:hover { color: #fff; }
header.top nav a[aria-current="page"] { color: #fff; border-bottom-color: #09fc7b; }
/* Pushed to the far right, away from the two links that switch between the
   pages a manager actually reads. */
header.top nav.aside { margin-left: auto; }

main { padding: 1rem 1.25rem 3rem; }

h1 { font-size: 1.35rem; margin: 0 0 0.15rem; }
.caption { color: var(--muted); font-size: 0.85rem; margin: 0 0 1rem; }

/* ── Controls ───────────────────────────────────────────────────────────── */

.controls {
  display: flex;
  flex-wrap: wrap;
  gap: 0.9rem;
  align-items: flex-end;
  padding: 0.85rem 1rem;
  background: var(--purple-soft);
  border-radius: 8px;
  margin-bottom: 1rem;
}
.field { display: flex; flex-direction: column; gap: 0.25rem; }
.field label { font-size: 0.75rem; font-weight: 600; color: var(--muted); }
.field select,
.field input {
  font: inherit;
  padding: 0.35rem 0.5rem;
  border: 1px solid var(--line);
  border-radius: 6px;
  background: #fff;
  color: inherit;
}
.field.check { flex-direction: row; align-items: center; gap: 0.4rem; }
.field.check label { font-size: 0.85rem; font-weight: 400; color: var(--ink); }

/* Segmented control for Total / Per Game / Per 90. */
.segmented { display: inline-flex; border: 1px solid var(--line); border-radius: 6px; overflow: hidden; }
.segmented button {
  font: inherit;
  border: 0;
  padding: 0.35rem 0.8rem;
  background: #fff;
  color: var(--muted);
  cursor: pointer;
}
.segmented button + button { border-left: 1px solid var(--line); }
.segmented button[aria-pressed="true"] { background: var(--purple); color: #fff; }

/* ── Tables ─────────────────────────────────────────────────────────────── */

.table-wrap { overflow: auto; max-height: 74vh; border: 1px solid var(--line); border-radius: 8px; background: var(--bg); }

table { border-collapse: separate; border-spacing: 0; width: 100%; font-variant-numeric: tabular-nums; }
th, td { padding: 0.35rem 0.55rem; text-align: right; white-space: nowrap; }
th:first-child, td:first-child,
th.text, td.text { text-align: left; }

thead th {
  position: sticky;
  top: 0;
  z-index: 2;
  background: var(--purple-soft);
  border-bottom: 1px solid var(--line);
  font-size: 0.75rem;
  text-transform: uppercase;
  letter-spacing: 0.03em;
  color: var(--muted);
  cursor: pointer;
  user-select: none;
}
thead th:hover { color: var(--ink); }
thead th .arrow { opacity: 0.45; font-size: 0.7em; }

tbody tr { border-bottom: 1px solid #f1eef5; }
tbody tr:hover { background: #faf8fc; }
tbody td { border-bottom: 1px solid #f1eef5; }

.shirt { width: 22px; height: 22px; vertical-align: middle; display: block; }
.pos { font-size: 0.7rem; font-weight: 700; color: var(--muted); }

.empty { padding: 2rem; text-align: center; color: var(--muted); }

/* ── FDR ────────────────────────────────────────────────────────────────── */

/* The cell is only the gutter: its padding is the whitespace, and the colour
   sits on the box inside it. Colouring the cell itself ran two fixtures of the
   same difficulty together into one wide block, with nothing to say where one
   gameweek ended and the next began. */
td.fdr { text-align: center; font-size: 0.8rem; font-weight: 600; padding: 3px; }
td.fdr .box { display: block; padding: 0.3rem 0.4rem; border-radius: 5px; }
td.fdr .fx { display: block; }
.fdr-1 { background: var(--fdr-1-bg); color: var(--fdr-1-fg); }
.fdr-2 { background: var(--fdr-2-bg); color: var(--fdr-2-fg); }
.fdr-3 { background: var(--fdr-3-bg); color: var(--fdr-3-fg); }
.fdr-4 { background: var(--fdr-4-bg); color: var(--fdr-4-fg); }
.fdr-5 { background: var(--fdr-5-bg); color: var(--fdr-5-fg); }
.fdr-blank { background: #fafafa; color: #bbb; }

td.team-cell { font-weight: 600; }

/* The horizontal strip of upcoming fixtures inside the player modal. */
.fdr-strip { display: flex; flex-wrap: wrap; gap: 4px; margin: 0.5rem 0 0; }
.fdr-strip .cell { text-align: center; }
.fdr-strip .gw { font-size: 0.7rem; color: var(--muted); }
.fdr-strip .box {
  padding: 6px 10px;
  border-radius: 6px;
  font-size: 0.8rem;
  font-weight: 600;
  min-width: 76px;
}

/* ── Tooltips ───────────────────────────────────────────────────────────── */

/* Anything with a data-tip says it on hover, or on keyboard focus when the
   element itself takes focus. Below the element rather than above it, so a
   row near the top of a scrolling table is not clipped by its own wrapper. */
[data-tip] { position: relative; }
[data-tip]::after {
  content: attr(data-tip);
  position: absolute;
  top: calc(100% + 6px);
  /* Anchored to the element's near edge and growing away from it, rather than
     centred: centred on a 17px icon in the leftmost column, the label hangs off
     the side of the table and the wrapper cuts it in half. Columns near the
     right edge want the other anchor — data-tip-align="end". */
  left: 0;
  z-index: 5;
  padding: 0.3rem 0.45rem;
  border-radius: 5px;
  background: var(--ink);
  color: #fff;
  font-size: 0.72rem;
  font-weight: 400;
  line-height: 1.2;
  text-transform: none;
  letter-spacing: 0;
  white-space: nowrap;
  opacity: 0;
  /* Invisible until the delay has passed, and gone the moment the pointer
     leaves — a tooltip that lingers on the way out reads as a stuck one. */
  pointer-events: none;
  transition: opacity 90ms ease;
}
[data-tip][data-tip-align="end"]::after { left: auto; right: 0; }
[data-tip]:hover::after,
[data-tip]:focus-visible::after { opacity: 1; transition-delay: var(--tip-delay); }

/* ── Identity ───────────────────────────────────────────────────────────── */

/* Badge, name and a line of context under it — one block, used by a stats row
   and by the modal head. Sizes are the defaults a table row wants; the head
   overrides them where it wants them bigger. */
.ident { display: flex; align-items: center; gap: 0.55rem; }
.ident .badge { width: 26px; height: 26px; border-radius: 6px; flex: none; object-fit: contain; }
.ident .who { display: flex; flex-direction: column; line-height: 1.15; }
.ident .name { font-weight: 600; }
.ident .meta { font-size: 0.68rem; color: var(--muted); text-transform: uppercase; letter-spacing: 0.02em; }

/* ── Sparkline ──────────────────────────────────────────────────────────── */

.spark { display: inline-flex; align-items: flex-end; gap: 1px; height: 18px; }
.spark i { width: 5px; background: var(--purple); border-radius: 1px 1px 0 0; display: block; }

/* ── Modal ──────────────────────────────────────────────────────────────── */

dialog {
  border: 0;
  border-radius: 10px;
  /* The head is a colour band to the edges, so the corners have to clip it. */
  overflow: hidden;
  padding: 0;
  width: min(1100px, 94vw);
  max-height: 92vh;
  box-shadow: 0 12px 40px rgba(0, 0, 0, 0.25);
}
dialog::backdrop { background: rgba(26, 26, 46, 0.45); }
/* The head is the page's card head (see below), so the modal opens on the same
   purple band the table sits under. The player's identity and his summary tiles
   share that one line — the name reads as the label on the numbers. */
.modal-head {
  display: flex;
  align-items: center;
  gap: 1.1rem;
  position: sticky;
  top: 0;
  z-index: 3;
}
.modal-head .ident { flex: none; }
.modal-head .badge { width: 44px; height: 44px; border-radius: 8px; }
.modal-head .name { font-size: 1.25rem; font-weight: 700; letter-spacing: -0.01em; }
.modal-head .meta { font-size: 0.8rem; color: #f7e9f3; }
/* The tiles take the rest of the line; the close button keeps the corner. */
.modal-head .metrics { flex: 1; margin: 0; }
.modal-head button.close {
  flex: none;
  align-self: flex-start;
  border: 0;
  background: transparent;
  font-size: 1.5rem;
  line-height: 1;
  cursor: pointer;
  color: #e7d8ee;
}
.modal-head button.close:hover { color: #fff; }
/* Both classes, so it outranks the .card-head gradient declared further down:
   the modal takes the lighter band, the page keeps the deep one. */
.card-head.modal-head {
  background: linear-gradient(
    105deg,
    var(--purple-lift) 0%,
    var(--purple-lift-mid) 55%,
    var(--purple-lift-far) 100%
  );
}
.modal-body { padding: 0.25rem 1.25rem 1.5rem; overflow: auto; }
/* Shorter than a page's table: the fixtures above it should stay in view. */
.modal-body .table-wrap { max-height: 46vh; }

/* On the purple band the tiles are translucent white, the way the mode pills
   on the stats card are, rather than the pale panel they were on a white head. */
.metrics { display: flex; flex-wrap: wrap; gap: 0.5rem; }
.metric {
  flex: 1 1 78px;
  background: rgba(255, 255, 255, 0.18);
  border-radius: 8px;
  padding: 0.4rem 0.7rem;
}
.metric .k { font-size: 0.7rem; text-transform: uppercase; color: #f7e9f3; letter-spacing: 0.03em; }
.metric .v { font-size: 1.15rem; font-weight: 700; color: #fff; }

h3.section { font-size: 0.95rem; margin: 1.25rem 0 0.5rem; }

/* Match result, coloured the way a results table colours a W/D/L. */
.res-W { background: #00a651; color: #fff; }
.res-D { background: #e7e7e8; color: #333; }
.res-L { background: #e00030; color: #fff; }

/* ── MCP page ────────────────────────────────────────────────────────────── */

.mcp { padding: 2.75rem 1.35rem 3.25rem; text-align: center; }
.mcp .lede {
  max-width: 44rem;
  margin: 0 auto 2rem;
  font-size: 1rem;
  line-height: 1.65;
  color: var(--muted);
}
.mcp .lede p { margin: 0 0 0.85rem; }
.mcp .lede p:last-child { margin-bottom: 0; }

/* The URL is the reason the page exists, so it gets the middle and a border
   around it rather than sitting in a paragraph. */
.endpoint {
  display: inline-flex;
  align-items: center;
  gap: 0.75rem;
  /* Wraps rather than overflowing: the URL and the button stack on a phone. */
  flex-wrap: wrap;
  justify-content: center;
  padding: 0.7rem 0.7rem 0.7rem 1.15rem;
  border: 1px solid var(--line);
  border-radius: 12px;
  background: var(--purple-soft);
}
.endpoint code {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 1.05rem;
  color: var(--purple);
  word-break: break-all;
}
.endpoint button {
  flex: none;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 34px;
  height: 34px;
  padding: 0;
  border: 0;
  border-radius: 8px;
  background: var(--purple);
  color: #fff;
  cursor: pointer;
}
.endpoint button svg { width: 17px; height: 17px; display: block; }
/* The tick replaces the clipboard rather than joining it, so the button never
   changes size mid-click. */
.endpoint button .tick,
.endpoint button.done .clip { display: none; }
.endpoint button.done .tick { display: block; }
.endpoint button:hover { background: var(--purple-lift); }
.endpoint button.done { background: var(--pill-start); }
.endpoint button:focus-visible {
  outline: 2px solid var(--purple-lift-mid);
  outline-offset: 2px;
}

.mcp .endpoint-note { margin: 1rem 0 0; }

/* ── Stats card ──────────────────────────────────────────────────────────── */

.card {
  background: var(--bg);
  border: 1px solid var(--line);
  border-radius: 14px;
  overflow: hidden;
  box-shadow: 0 1px 3px rgba(26, 26, 46, 0.06);
}

/* The deep-purple band: title, live caption and mode switch on top, the
   filters below — everything that steers the table lives on the colour. */
.card-head {
  padding: 1.1rem 1.35rem;
  background: linear-gradient(105deg, #37003c 0%, #4a1050 55%, #6a1a54 100%);
  color: #fff;
}
.card-head h1 { font-size: 1.5rem; margin: 0; letter-spacing: -0.01em; }
.card-head .sub { margin: 0.3rem 0 0; font-size: 0.85rem; color: #d9c3e0; }
.card-head .segmented { margin-left: auto; }

/* On the band the control is translucent; the active mode is a solid white pill. */
.segmented.on-dark {
  border: 0;
  background: transparent;
  border-radius: 0;
  overflow: visible;
  gap: 0.5rem;
  /* Sits on the filter row, so it lines up with the inputs, not their labels. */
  align-self: flex-end;
  flex: none;
}
/* Each mode is its own outlined pill; the active one fills solid white. */
.segmented.on-dark button {
  background: transparent;
  color: #e7d8ee;
  border: 1px solid rgba(255, 255, 255, 0.3);
  border-radius: 999px;
  padding: 0.35rem 0.95rem;
}
.segmented.on-dark button + button { border-left: 1px solid rgba(255, 255, 255, 0.3); }
.segmented.on-dark button[aria-pressed="true"] {
  background: #fff;
  border-color: #fff;
  color: var(--purple);
  font-weight: 600;
}

/* Filters sit on the band, so they drop the light panel and read on the dark:
   pale labels over solid white inputs that stand out against the purple. */
.controls.in-band {
  background: transparent;
  padding: 0;
  margin: 0.9rem 0 0;
  gap: 0.75rem 0.9rem;
}
.controls.in-band .field label { color: #e7d8ee; }
.controls.in-band .field select,
.controls.in-band .field input {
  border: 0;
  background: #fff;
  color: var(--ink);
}

/* The card owns the frame, so the table inside it drops its own border. */
.card .table-wrap { border: 0; border-radius: 0; max-height: 72vh; }

/* ── Stats table ────────────────────────────────────────────────────────── */

/* The sum of the column widths declared below. Under that, the browser stops
   honouring them and compresses each column by its own content, which pulls the
   two bar columns to different widths; the wrapper scrolls instead. */
table.stats { font-size: 0.82rem; min-width: 1343px; }
table.stats th,
table.stats td { padding: 0.45rem 0.6rem; border-bottom: 1px solid #f1eef5; }

/* Two header rows: a group band over the columns it spans, then the columns. */
table.stats thead th { position: sticky; background: #fbfafc; }
table.stats thead tr.groups th {
  top: 0;
  height: 26px;
  font-size: 0.65rem;
  letter-spacing: 0.08em;
  color: #9a90a6;
  text-align: center;
  border-bottom: 0;
  cursor: default;
}
table.stats thead tr.groups th:first-child { background: #fbfafc; }
table.stats thead tr.cols th { top: 26px; }
table.stats thead tr.cols th.text { text-align: left; }

table.stats tbody tr:hover { background: #faf8fc; }
table.stats tbody tr:hover td.band { background: #f0e6f6; }

/* The Points group runs as a tinted band down the whole table. */
table.stats .band { background: var(--band); }
/* A light rule opens each group, header and body alike, so the bands read as
   one column each. The Points group's right edge is the next group's rule. */
table.stats .gstart { border-left: 1px solid var(--line); }

/* Every plain stat column is the same width, so the spacing stays even; the
   slack a 100%-wide table hands out is shared equally between them. */
table.stats .stat { width: 68px; }

/* A pair is as wide as a plain stat — the two numbers stack into the row height
   the points column already forces, so the pairing costs no space. The bar that
   closes the returns group gets a column of its own to grow in. */
table.stats .pair { width: 68px; }
/* Both bar columns share one width, so a bar of a given length means the same
   thing in either group and the two read as one instrument. */
table.stats .barcol { width: 160px; }

/* The FDR matrix borrows the same table style; its colour cells stay dense and
   centred, which the shared padding would otherwise loosen. */
table.stats td.fdr { padding: 3px; text-align: center; }

/* Rank and identity. */
table.stats td.rank,
table.stats th.rank { text-align: left; color: #b3a9bd; width: 1%; padding-right: 0.2rem; }
/* The cell stays a table-cell — flexing the td itself drops it out of table
   layout and its bottom border stops lining up with the rest of the row. A
   fixed width keeps it from soaking up the slack a 100%-wide table hands to
   its widest auto column, which grew the gap after the name on every larger
   screen; the slack now spreads across the stat columns instead. A longer name
   still widens the column rather than clipping. */
table.stats td.player { text-align: left; width: 190px; }
/* The icon and the identity on one line inside one button, the icon first,
   where the eye enters the row. The button has to be stripped back to its
   contents: it is a cell's worth of text, not a control that looks like one. */
table.stats .who-cell {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  width: 100%;
  padding: 0;
  border: 0;
  background: transparent;
  font: inherit;
  color: inherit;
  text-align: left;
  cursor: pointer;
}
table.stats .info { flex: none; display: flex; color: #b3a9bd; }
table.stats .info svg { width: 17px; height: 17px; display: block; }
/* Hovering anywhere in the block lights the whole block, so it is obvious that
   the name opens the same thing the icon does. */
table.stats .who-cell:hover .info,
table.stats .who-cell:hover .name { color: var(--purple-lift-mid); }
/* Keyboard focus has to be visible: the button carries no border of its own. */
table.stats .who-cell:focus-visible { outline: 2px solid var(--purple-lift-mid); outline-offset: 2px; border-radius: 6px; }


/* Price, ownership and minutes read as one strip under the player's name, on
   the spacing the returns columns keep: a plain stat here is exactly as wide as
   a G, an A or a GI, and centred. Minutes is the exception, and only by as much
   as five pills need — a 68px column would leave them 8px each. */
table.stats td.avail,
table.stats th.avail { width: 68px; text-align: center; }
table.stats td.mins,
table.stats th.mins { width: 108px; }
/* The pill strip's height, left empty under the two plain figures. Without it
   the minutes cell is the taller of the three and its figure centres higher
   than theirs; with it, all three sit on one line and the pills hang below. */
table.stats td.avail:not(.mins)::after { content: ""; display: block; height: 11px; }

/* Progress towards a price change: a chip in its own column, so the price
   beside it stays a plain centred figure. One min-width for every chip, filled
   or not, so the column reads as one straight run rather than a ragged one.
   The fills are the FDR classes above — reused, not restated. */
table.stats .chg {
  display: inline-block;
  min-width: 46px;
  padding: 1px 4px;
  border-radius: 4px;
  font-size: 0.8rem;
  font-weight: 600;
}
/* No expected change takes no fill: the colour is the signal, so spending it on
   the 600-odd players who are not moving would leave nothing to notice. The
   figure still reads as one of the table's numbers, so it inherits their colour
   and weight rather than being dimmed into a second class of its own. */
table.stats .chg.flat { font-weight: 400; }

/* Minutes: the figure over one pill per fixture, centred under it. Five pills
   and no more, so the column is a fixed size whatever window is selected. */
table.stats .mins-v { display: block; }
table.stats .pills { display: flex; justify-content: center; gap: 2px; margin-top: 3px; }
/* Each pill outlines a full 90; the fill inside is the minutes played, so the
   empty part of the outline is the minutes missed. */
table.stats .pill {
  width: 16px;
  height: 8px;
  border-radius: 999px;
  background: #e6e2ec;
  display: flex;
  overflow: hidden;
}
/* The grey capsule is the full 90; the coloured fill is the minutes played —
   from the left for a start, from the right for a sub. */
table.stats .pill.from-bench { justify-content: flex-end; }
table.stats .pill .fill { align-self: stretch; flex: 0 0 auto; max-width: 100%; border-radius: 999px; }
table.stats .pill .fill.hi { background: var(--pill-start); }
table.stats .pill .fill.lo { background: var(--pill-sub); }

/* Pushed to the right so a bar-less pair lines up under its own heading; a pair
   with a bar has the track claiming the slack, so this changes nothing there. */
table.stats .pair-row { display: flex; align-items: center; justify-content: flex-end; gap: 0.5rem; }
table.stats .pair-row + .pair-row { margin-top: 3px; }
/* The gap is the divider: a bar drawn in two parts reads as goals then assists
   without needing a second colour to say so. */
table.stats .pair-row .track { flex: 1; height: 12px; display: flex; align-items: center; gap: 2px; }
table.stats .pair-row .bar { height: 100%; border-radius: 3px; min-width: 2px; }
table.stats .pair-row .bar.act { background: var(--actual); }
table.stats .pair-row .bar.exp { background: var(--expected); }
/* A minimum, not a width: a fixed one is overrun by a four-character figure,
   which then hangs out to the left of the column it belongs to. */
table.stats .pair-row .v { min-width: 3ch; text-align: right; flex: none; }
table.stats .pair-row .v.muted { color: var(--muted); font-size: 0.76rem; }
