/*
 * CasinoPer — channel 2.
 *
 * Loaded after landing.css. Two jobs:
 *
 *   1. Repalette. The whole design keys off --red, so redefining that flips
 *      every badge, chip, button and ring to teal in one move.
 *   2. Relayout. index2 and this page share one stylesheet and one script, and
 *      a recolour alone reads as the same site with a filter on it. So the
 *      header, the schedule panel and the scoreboard are all rebuilt here:
 *      utility strip and icon nav above, CANLI / YAYINLANACAKLAR with a search
 *      box and a sport column, and the board in two columns of cards.
 *
 * Everything is scoped under body.cper so nothing here can reach index2.
 */

body.cper {
  /* CasinoPer teal, sampled from the logo artwork. */
  --red: #16d99a;
  --red-dim: #0fae7b;
  --red-glow: rgba(22, 217, 154, .22);

  /*
   * Neutral near-black surfaces, teal reserved for the accent.
   *
   * These were green-tinted, on the theory that the panels should belong to the
   * same picture as the green skin. In practice a wide dark-green panel next to
   * a full-colour illustration reads as murky rather than as tinted - the green
   * is too desaturated to look deliberate and too present to look neutral, and
   * it made the player surround in particular look dirty.
   *
   * Going fully neutral fixed the murk but overshot - flat black next to this
   * artwork looked like a hole rather than a panel. These sit between: clearly
   * green, but dark enough that the colour reads as depth instead of as a wash.
   * Teal still means one thing only - interactive, or CasinoPer.
   */
  /*
   * Two tones, not one. Panels sit at --surface, the controls inside them a
   * shade lighter at --surface-2 - that step is what gives a panel depth. A
   * single flat colour is why the previous pass read as a slab however dark or
   * light it was set.
   */
  --bg: #0b1210;
  --surface: #0f1715;
  --surface-2: #162320;
  --surface-3: #1d2e29;
  --line: #223330;
  --line-soft: #17231f;

  --fg: #eef6f3;
  /*
   * Effectively white. Two earlier passes lifted these part-way and both still
   * read as grey next to full-strength text - including inside the match modal,
   * where the stat labels, coach lines and shirt numbers all sit on --fg-mute.
   * There is no lightness gap left to carry hierarchy here; size and weight do
   * it instead.
   */
  --fg-dim: #eef6f3;
  --fg-mute: #e2eeea;
}

/*
 * The backdrop.
 *
 * No scrim: the artwork is shown at full strength, the way index2 shows its
 * own. It went through two worse versions first - a gradient that faded to
 * flat, which left a hard band across the page where it ran out, then a
 * constant wash, which was even but muddied the artwork for no gain.
 *
 * What makes bare artwork safe here is that nothing on this page sits directly
 * on it any more. Every surface carries its own translucent panel - the utility
 * strip, the header, the player, the schedule rail, the live-scores card and
 * the footer - so the skin only ever shows through in the outer gutters, which
 * is exactly where its own promotional artwork lives. That was not true while
 * the CANLI SKOR TABLOSU board was here: its heading, league chips and pager
 * had no backdrop of their own and needed the wash to stay legible. Removing
 * the board is what made this possible. If a bare-text surface is ever added
 * back outside a panel, it will need either a panel or the wash returned.
 */
body.cper {
  background: #0b1210 url('/pageskin-cper.jpg') no-repeat center top;
  background-size: cover;
  background-attachment: fixed;
}

/* Teal is bright; white-on-teal loses the contrast red carried. */
body.cper .cta-btn.primary { color: #04140d; }
body.cper .cta-btn.primary:hover { background: #23f0ab; box-shadow: 0 4px 18px rgba(22,217,154,.4); }
body.cper .rtab.on,
body.cper .btab.on,
body.cper .mtab.on,
body.cper .pgr-n.on { color: #04140d; }
body.cper .btab u.lv { color: #04140d; }

/* "On air" is not a brand colour. Live stays red on both pages - recolouring it
   teal here would make it read as one more accent on an already teal page. */
body.cper .livetag { background: rgba(225, 29, 72, .92); }
body.cper .hh-live, body.cper .lh-live { background: #e11d48; color: #fff; }
body.cper .mrow2.islive { box-shadow: inset 2px 0 0 #e11d48; background: rgba(225,29,72,.07); }
body.cper .mrow2.islive:hover { background: rgba(225,29,72,.12); }
body.cper .st-form .fp.l { background: #e11d48; }
body.cper .q.live { background: #e11d48; border-color: #e11d48; color: #fff; }

/* ---- utility strip -------------------------------------------------------- */

.topbar {
  background: rgba(3, 14, 11, .82);
  backdrop-filter: blur(8px);
  border-bottom: 1px solid var(--line-soft);
  font-size: 12px;
}
.topbar-in {
  max-width: var(--max); margin: 0 auto; padding: 0 16px;
  height: 28px; display: flex; align-items: center; gap: 16px;
}
.topbar .addr { color: var(--fg-mute); letter-spacing: .01em; }
.topbar .addr a {
  color: var(--red); font-weight: 700; text-decoration: none;
  letter-spacing: .04em;
}
.topbar .addr a:hover { text-decoration: underline; }
/* Socials move up here out of the header, which the icon nav now fills. */
.topbar .social { margin-left: auto; display: flex; gap: 4px; }
.topbar .social a {
  width: 26px; height: 26px; border: 0; background: none;
  display: grid; place-items: center; border-radius: 6px;
  color: var(--fg-mute);
}
.topbar .social a svg { width: 15px; height: 15px; }
.topbar .social a:hover { color: var(--red); background: rgba(22,217,154,.12); }

/* ---- header -------------------------------------------------------------- */

body.cper .hdr { background: rgba(5, 22, 17, .78); }
/* 76px put the header's bottom edge across the page skin's own "ÖZEL
   BONUSLAR" / "CANLI BAHİSLER" headline in the right gutter, which read as a
   rendering fault rather than two layers. 60px clears it. */
body.cper .hdr-in {
  height: 60px; gap: 22px;
}
/* Scaled down from the 40px this replaced, in step with the shorter header;
   the logo is a 210x44 PNG so it keeps its proportions. */
body.cper .logo img { height: 32px; width: auto; display: block; }

/* Icon over label, as on the main site. */
.iconnav {
  margin-left: auto;
  display: flex; align-items: center; gap: 4px;
}
.iconnav a {
  display: grid; justify-items: center; gap: 5px;
  /* Tightened from 7px 13px along with the shorter header, so the icon and
     its label still clear the top and bottom edges instead of touching them. */
  padding: 4px 12px; border-radius: 9px;
  text-decoration: none; color: var(--fg-dim);
  font-size: 10px; font-weight: 700; letter-spacing: .05em;
  white-space: nowrap;
  transition: color .12s, background .12s;
}
.iconnav a svg { width: 19px; height: 19px; }
.iconnav a:hover { color: var(--red); background: rgba(22,217,154,.1); }

/* Sign-up sits inside the header here, not in a band of its own. */
body.cper .hdr-in .cta {
  max-width: none; margin: 0; padding: 0; width: auto;
  gap: 7px; flex: 0 0 auto;
}
body.cper .hdr-in .cta-btn { padding: 9px 17px; font-size: 12px; }

@media (max-width: 1100px) {
  .iconnav a span { display: none; }
  .iconnav a { padding: 8px 10px; }
}
@media (max-width: 820px) {
  body.cper .hdr-in { height: auto; padding: 10px 14px; flex-wrap: wrap; gap: 12px; }
  .iconnav { order: 3; margin-left: 0; width: 100%; overflow-x: auto; }
  body.cper .hdr-in .cta { margin-left: auto; }
  .topbar .addr { font-size: 11px; }
}

/* ---- schedule panel ------------------------------------------------------ */

/* Wider than index2's 290px: this panel now carries a sport column and a search
   box as well as the list. */
/* margin-top: with the broadcaster strip removed, .app centres hero-in in
   whatever space is left, which can be none on a short window - hero-in would
   then sit flush against the header with its top border touching the
   header's bottom border. A small fixed gap guarantees they never meet. */
/*
 * 320, not 372.
 *
 * The content column is pinned at 1076px because that is the width of the page
 * skin's central dark panel - anything wider covers the artwork in the gutters,
 * which has to stay visible. So the only width left to give the video is the
 * rail's, and the rail had spare: its sport column hides itself when there is
 * nothing to filter, and fixture rows ellipsise long names either way.
 */
body.cper .hero-in { grid-template-columns: minmax(0, 1fr) 320px; }

body.cper .rail-hd { gap: 2px; }
body.cper .rtab { font-size: 11px; letter-spacing: .06em; }

.mpanel { display: flex; flex-direction: column; min-height: 0; flex: 1 1 auto; }
/* A class selector outranks the UA [hidden] rule, so without this #mpanel kept
   its flex layout while hidden - landing.js swaps it out for SIRALAMA, and the
   sub-tabs and search box stayed on screen with the standings table rendering
   into whatever space was left, which is what threw its sticky header off. */
.mpanel[hidden] { display: none; }

/* CANLI / YAYINLANACAKLAR. index2 runs live and upcoming together in one
   chronological list on purpose; splitting them is one of the things that makes
   this page read as its own. */
.mtabs {
  /* Three views now, not two: SIRALAMA was moved down out of the MAÇLAR /
     SOHBET row so that live, upcoming and the table sit in one bar. CANLI is
     the shortest label and YAYINLANACAKLAR much the longest, so the columns are
     weighted rather than equal thirds - equal thirds wrapped the long one. */
  display: grid; grid-template-columns: 0.85fr 1.4fr 0.9fr;
  border-bottom: 1px solid var(--line);
}
/* A class selector outranks the UA [hidden] rule, so without this the bar would
   keep its grid layout and stay on screen when SOHBET is selected - the same
   trap #mpanel fell into. */
.mtabs[hidden] { display: none; }
.mtb {
  display: flex; align-items: center; justify-content: center; gap: 6px;
  padding: 11px 4px; border: 0; background: none; cursor: pointer;
  /* Three labels in a 372px rail leaves little room; the type is a shade
     smaller and the tracking tighter than the two-tab version needed. */
  font-family: inherit; font-size: 10.5px; font-weight: 800; letter-spacing: .04em;
  color: var(--fg-mute);
  border-bottom: 2px solid transparent;
  transition: color .12s, border-color .12s, background .12s;
}
.mtb:hover { color: var(--fg-dim); background: rgba(255,255,255,.03); }
.mtb.on { color: var(--fg); border-bottom-color: var(--red); }
.mtb u {
  text-decoration: none; font-size: 10px; font-weight: 700;
  padding: 1px 6px; border-radius: 20px;
  background: var(--surface-3); color: var(--fg-dim);
}
.mtb u:empty { display: none; }
.mtb.on u { background: var(--red); color: #04140d; }
/*
 * The CANLI pip is red whether or not the tab is selected.
 *
 * It used to dim to --fg-mute when unselected, which on the old green palette
 * came out as a green dot - so the one element on the page that means "on air"
 * changed colour depending on which tab you happened to be looking at. The tab
 * itself already shows selection through its label and underline; the pip is
 * stating a fact about the fixtures, not about the tab.
 */
.mtb .pip { width: 6px; height: 6px; border-radius: 50%; background: #e11d48; }

.rsearch {
  position: relative;
  padding: 9px 10px;
  border-bottom: 1px solid var(--line-soft);
}
.rsearch svg {
  position: absolute; left: 21px; top: 50%; transform: translateY(-50%);
  width: 14px; height: 14px; color: var(--fg-mute); pointer-events: none;
}
.rsearch input {
  width: 100%; padding: 8px 10px 8px 30px;
  /* On the palette, one step below the panel so the field reads as inset. */
  background: var(--bg);
  border: 1px solid var(--line); border-radius: 8px;
  color: var(--fg); font: inherit; font-size: 12.5px;
  -webkit-appearance: none; appearance: none;
}
.rsearch input::placeholder { color: var(--fg-mute); }
.rsearch input:focus {
  outline: none; border-color: var(--red-dim);
  box-shadow: 0 0 0 3px var(--red-glow);
}
/* Chrome draws its own clear button in the wrong colour on a dark field. */
.rsearch input::-webkit-search-cancel-button { -webkit-appearance: none; }

/* List plus the sport column beside it. */
.mbody { display: flex; min-height: 0; flex: 1 1 auto; }

.sportrail {
  flex: 0 0 auto;
  width: 52px;
  display: flex; flex-direction: column;
  border-right: 1px solid var(--line-soft);
  overflow-y: auto;
  scrollbar-width: none;
}
.sportrail::-webkit-scrollbar { width: 0; }
.sportrail[hidden] { display: none; }
.sp {
  position: relative;
  flex: 0 0 auto;
  height: 46px;
  display: grid; place-items: center;
  border: 0; background: none; cursor: pointer;
  color: var(--fg-mute);
  border-bottom: 1px solid var(--line-soft);
  border-left: 2px solid transparent;
  transition: color .12s, background .12s, border-color .12s;
}
.sp:hover { color: var(--fg-dim); background: rgba(255,255,255,.03); }
.sp.on { color: var(--red); border-left-color: var(--red); background: rgba(22,217,154,.08); }
.sp svg { width: 20px; height: 20px; }
.sp .sp-all { font-size: 9px; font-weight: 800; letter-spacing: .05em; }
/* Count in the corner, small enough not to compete with the icon. */
.sp u {
  position: absolute; top: 5px; right: 5px;
  text-decoration: none; font-size: 9px; font-weight: 700;
  color: var(--fg-mute);
}
.sp.on u { color: var(--red); }

body.cper .rail-body { flex: 1 1 auto; min-width: 0; }

/*
 * The crest pair is left exactly as landing.css draws it: home crest, "v", away
 * crest, together at the front of the row.
 *
 * An earlier version here tried to push the two crests out to opposite edges of
 * the row, score-style. It hid the away crest and the "v" to do it - but never
 * actually repositioned the away crest, so the second team's badge simply
 * vanished from every fixture. Splitting that pair needs the row rebuilt in the
 * markup, not a column tweak, and it is not worth losing a badge over.
 */

@media (max-width: 980px) {
  body.cper .hero-in { grid-template-columns: minmax(0, 1fr); }
}

/* ---- featured live match ------------------------------------------------- */

.feat {
  margin: 10px 0 0;
  background: rgba(11, 38, 32, .82);
  backdrop-filter: blur(6px);
  border: 1px solid var(--line);
  border-radius: var(--r);
  padding: 12px 14px 13px;
}
.feat[hidden] { display: none; }

.ft-hd {
  display: flex; align-items: center; gap: 8px;
  padding-bottom: 10px; margin-bottom: 11px;
  border-bottom: 1px solid var(--line-soft);
}
.ft-lg {
  font-size: 11.5px; font-weight: 700; letter-spacing: .04em;
  color: var(--fg-dim); text-transform: uppercase;
}
.ft-round {
  font-style: normal; font-size: 11px; color: var(--fg-mute);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.ft-min {
  margin-left: auto; flex: 0 0 auto;
  font-size: 11px; font-weight: 800; letter-spacing: .04em;
  padding: 3px 9px; border-radius: 20px;
  background: #e11d48; color: #fff;
}

.ft-row {
  display: grid; grid-template-columns: minmax(0,1fr) auto minmax(0,1fr);
  align-items: center; gap: 12px;
}
.ft-team { display: flex; align-items: center; gap: 10px; min-width: 0; }
.ft-team.r { flex-direction: row-reverse; }
.ft-team img { width: 38px; height: 38px; object-fit: contain; flex: 0 0 auto; }
.ft-team b {
  font-size: 14px; font-weight: 700; color: var(--fg);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.ft-score { display: grid; justify-items: center; gap: 2px; flex: 0 0 auto; }
.ft-score b {
  font-size: 26px; font-weight: 800; letter-spacing: -.02em;
  font-variant-numeric: tabular-nums;
}
.ft-score span { font-size: 10.5px; color: var(--fg-mute); }

.ft-venue {
  margin: 9px 0 0; text-align: center;
  font-size: 11px; color: var(--fg-mute);
}

.ft-stats { margin-top: 12px; display: grid; gap: 9px; }
.ft-st-top {
  display: flex; align-items: center; gap: 8px;
  font-size: 11px; margin-bottom: 4px;
}
.ft-st-top b { font-variant-numeric: tabular-nums; color: var(--fg); }
.ft-st-top span { flex: 1 1 auto; text-align: center; color: var(--fg-mute); }
.ft-st-bar { display: flex; height: 4px; border-radius: 3px; overflow: hidden; gap: 2px; }
.ft-st-bar i.h { background: var(--red); }
.ft-st-bar i.a { background: var(--surface-3); }

.ft-more {
  margin-top: 13px; width: 100%;
  padding: 9px; border-radius: 9px;
  background: rgba(22, 217, 154, .1);
  border: 1px solid var(--red-dim); color: var(--red);
  font: inherit; font-size: 12px; font-weight: 700; letter-spacing: .04em;
  cursor: pointer;
  transition: background .12s;
}
.ft-more:hover { background: rgba(22, 217, 154, .2); }

@media (max-width: 560px) {
  .ft-team b { font-size: 12px; }
  .ft-team img { width: 30px; height: 30px; }
  .ft-score b { font-size: 21px; }
}

/* ---- live scores (inside .feat, under the featured match) ---------------- */

.lsc {
  margin-top: 13px; padding-top: 12px;
  border-top: 1px solid var(--line-soft);
}

.lsc-hd {
  display: flex; align-items: center; gap: 8px;
  margin-bottom: 6px;
}
/* Same weight as .board-hd h2, so the two headers read as one system. */
.lsc-hd h3 {
  display: flex; align-items: center; gap: 8px; margin: 0;
  font-size: 12px; font-weight: 800; letter-spacing: .11em; color: var(--fg-dim);
}
.lsc-n { margin-left: auto; font-size: 11px; color: var(--fg-mute); }

/* Scrollbar approach copied from .chat-log in landing.css: touching any single
   ::-webkit-scrollbar part makes Chrome drop its overlay scrollbar for the
   legacy widget, which draws a pale track and stepper arrows unless every
   part - track, thumb, hover, buttons and corner - is accounted for here. */
.lsc-list {
  max-height: 300px; overflow-y: auto;
  scrollbar-width: thin; scrollbar-color: #303e4e transparent;
}
.lsc-list::-webkit-scrollbar { width: 10px; height: 10px; }
.lsc-list::-webkit-scrollbar-track { background: transparent; }
.lsc-list::-webkit-scrollbar-thumb {
  background: #303e4e; border-radius: 999px;
  border: 3px solid transparent; background-clip: content-box;
}
.lsc-list::-webkit-scrollbar-thumb:hover { background: #45596e; background-clip: content-box; }
.lsc-list::-webkit-scrollbar-button { display: none; width: 0; height: 0; }
.lsc-list::-webkit-scrollbar-corner { background: transparent; }

/* A row that behaves like a table row, not a button - no chrome, no default
   button font, the grid does the alignment. */
.lsc-row {
  width: 100%; display: grid;
  grid-template-columns: 32px minmax(0, 1fr) 58px minmax(0, 1fr);
  align-items: center; gap: 8px;
  padding: 8px 10px; margin: 0;
  border: 0; border-bottom: 1px solid var(--line-soft); border-radius: 0;
  background: none; color: inherit;
  font: inherit; text-align: left; cursor: pointer;
  transition: background .12s;
}
.lsc-row:last-child { border-bottom: 0; }
.lsc-row:hover { background: rgba(255, 255, 255, .03); }

/* <u> for the minute, so it needs its underline stripped explicitly. */
.lsc-min {
  text-decoration: none; text-align: center;
  font-size: 10.5px; font-weight: 700; color: var(--fg-mute);
  font-variant-numeric: tabular-nums;
}

/* Crest-and-name pair. The two sides are mirror images of each other in the
   markup (h: crest then name, a: name then crest) rather than sharing one DOM
   order and a reversing class - same idea as .ft-team/.ft-team.r, just spelt
   out in the HTML instead of in a modifier, because the row is built by a
   template rather than by hand. */
.lsc-side { display: flex; align-items: center; gap: 6px; min-width: 0; }
/*
 * Both sides pack against the score with the crest innermost, so the two mirror
 * each other and the score reads as the pivot.
 *
 * `order` on the crest, not `row-reverse`. The home markup is crest-then-name,
 * so reversing the axis did put the crest by the score - but it also reverses
 * what `justify-content` means, and the `flex-end` paired with it therefore
 * packed the home team to the LEFT of its column. Its distance from the score
 * then varied with every team-name length and nothing lined up vertically.
 */
.lsc-side.h { justify-content: flex-end; text-align: right; }
.lsc-side.h .lsc-c { order: 2; }
.lsc-side.a { justify-content: flex-start; text-align: left; }
.lsc-side b {
  min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
  font-size: 12px; font-weight: 600; color: var(--fg);
}
.lsc-c { width: 16px; height: 16px; flex: 0 0 16px; object-fit: contain; }

.lsc-sc {
  text-align: center; font-size: 13px; font-weight: 700;
  font-variant-numeric: tabular-nums; color: var(--fg);
}

@media (max-width: 560px) {
  .lsc-row {
    grid-template-columns: 26px minmax(0, 1fr) 44px minmax(0, 1fr);
    gap: 6px; padding: 7px 8px;
  }
  .lsc-min { font-size: 9.5px; }
  .lsc-side b { font-size: 11px; }
  .lsc-sc { font-size: 12px; }
}

/* ---- scoreboard ---------------------------------------------------------- */

body.cper .board-hd h2 { text-shadow: 0 1px 3px rgba(0, 0, 0, .7); }

/* League picker leads the row here and trails it on index2. */
body.cper .board-filters .lgdd { order: -1; flex: 0 0 auto; }

/*
 * Two columns of cards rather than one full-width list.
 *
 * The panel border moves onto the cells, because a two-column grid inside one
 * bordered panel leaves an unresolved seam down the middle - and the rows draw
 * their own separators, which would only line up in a single column.
 */
body.cper .board-list {
  background: none; backdrop-filter: none;
  border: 0; border-radius: 0; overflow: visible;
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 8px;
}
body.cper .board-list .board-empty,
body.cper .board-list .board-note { grid-column: 1 / -1; }

body.cper .mrow2 {
  background: rgba(11, 38, 32, .8);
  backdrop-filter: blur(6px);
  border: 1px solid var(--line);
  border-radius: 10px;
  border-bottom: 1px solid var(--line);
  padding: 10px 12px;
  transition: background .12s, border-color .12s, transform .12s;
}
body.cper .mrow2:hover {
  background: rgba(22, 217, 154, .08);
  border-color: var(--red-dim);
  transform: translateY(-1px);
}
body.cper .mrow2.islive {
  box-shadow: inset 3px 0 0 #e11d48;
  border-color: rgba(225, 29, 72, .4);
}

@media (max-width: 860px) {
  body.cper .board-list { grid-template-columns: minmax(0, 1fr); }
}

/* ---- footer -------------------------------------------------------------- */

body.cper .ftr { background: rgba(3, 14, 11, .8); }
body.cper .ftr img { height: 22px; width: auto; opacity: .75; }

/* Recent goals and cards, shown when the API has no statistics for the fixture
   - which is the norm for reserve and youth football. */
.ft-flow { margin-top: 12px; display: grid; gap: 1px; }
.ft-fl {
  /* The team column is given a share of the row rather than `auto`: with auto
     the player column claimed the slack first and every club name ended up
     truncated to three letters. */
  display: grid; grid-template-columns: 30px 18px minmax(0, 1fr) minmax(0, 44%);
  align-items: center; gap: 8px;
  padding: 6px 2px;
  border-top: 1px solid var(--line-soft);
  font-size: 12px;
}
.ft-fl u {
  text-decoration: none; color: var(--fg-mute);
  font-size: 11px; font-variant-numeric: tabular-nums;
}
.ft-fl-i { display: grid; place-items: center; }
.ft-fl-i svg { width: 14px; height: 14px; }
.ft-fl b {
  font-weight: 600; color: var(--fg);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.ft-fl i {
  font-style: normal; font-size: 11px; color: var(--fg-mute);
  text-align: right;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}

/* ---- player sizing ------------------------------------------------------- */

/*
 * --chrome is everything above and below the video that is not the video, and
 * landing.css sizes the player as (100vh - chrome) * 16/9. Its 356px was
 * measured on index2: header 55, two CTA bars at 47 each, provider strip 48,
 * caption bar 58, footer 49, plus padding.
 *
 * This page has none of that middle section - the CTA pair moved into the
 * header and the provider strip is gone - and its header stack is shorter. So
 * 356 was subtracting ~140px of chrome that does not exist here, and on a short
 * window the player was shrinking below the width of the column it sits in for
 * no reason. Remeasured for this layout: topbar 28 + header 60 + caption 58 +
 * footer 49 + padding.
 */
body.cper { --chrome: 215px; }

/* ---- standings panel ----------------------------------------------------- */

/*
 * The team-cell and opaque-sticky-header fixes moved into landing.css: both were
 * bugs on index2 as well, not CasinoPer quirks. Only the colour belongs here -
 * the shared value is a blue-grey that reads as foreign on a green page.
 */


/* Hover needs to sit on the green scale too, and be strong enough to read
   against panels that are already translucent over the skin. */
body.cper .stbl tbody tr:hover { background: rgba(22, 217, 154, .1); }

/*
 * SIRALAMA lives in the sub-tab bar now, so it is an .mtb rather than an .rtab
 * - but unlike the other two it has no count badge, and the standings panel it
 * opens sits directly below this bar. It also has to stay lit while its own
 * panel is showing, which is why landing.js gates the CANLI / YAYINLANACAKLAR
 * highlight on #mpanel being the visible panel.
 */
body.cper .mtabs #tab-table { letter-spacing: .05em; }

/* With SIRALAMA gone from the top row, MAÇLAR and SOHBET have room to breathe. */
body.cper .rail-hd { gap: 4px; }

/* The standings panel now opens under the sub-tab bar instead of directly under
   the rail tabs, so its own dropdown no longer needs a top border of its own -
   the bar above already provides the separation. */
body.cper .stand-hd { border-top: 0; }

/* ---- the rail keeps the player's height ---------------------------------- */

/*
 * The rail stays stretched to the player, as landing.css draws it - `.rail-wrap`
 * is a stretched grid item with `.rail` absolutely positioned to fill it.
 *
 * It was briefly made to hug its rows instead, to close the empty area under a
 * two-fixture list. That was the wrong trade: with the panel short, the space
 * beside the player became bare page skin rather than an empty panel, and the
 * artwork showing through a hole in the layout looked far worse than the gap it
 * replaced. An empty panel reads as "nothing scheduled"; a hole reads as broken.
 *
 * Closing that gap properly means giving the rail something to fill it with, not
 * shrinking the rail.
 */

/* ---- modal tabs with no data --------------------------------------------- */

/*
 * Tabs for sections the API has nothing for are now shown rather than dropped.
 * Hiding them made İLK 11 look unimplemented, when in fact the fixture was a
 * youth match for which the upstream API publishes no lineup at all - the panel
 * behind the tab says so ("Kadrolar maçtan ~1 saat önce açıklanır"), which is
 * the answer the reader wanted and could not reach.
 *
 * Dimmed, but deliberately still clickable: the explanation is the content.
 */
/*
 * Full opacity. Three passes tried to dim an empty tab and be readable at once
 * (.45, .72, then .72 again because this rule outranks the one in landing.css)
 * and every one came out grey next to its neighbour - white text at 72% IS
 * grey. The tab says what section it is; the panel behind it says whether there
 * is anything in it. Dimming the label only hid the first to imply the second.
 */
/* No weight override either. The 700 was here to compensate for the dimming;
   with that gone it only made empty tabs lighter than their neighbours, which
   is the same "one is bold, one is not" problem from the other direction. All
   three tabs now inherit one weight from .mtab. */
body.cper .mtab.empty,
.mtab.empty {
  opacity: 1;
}
body.cper .mtab.empty:hover,
.mtab.empty:hover { opacity: 1; }
/* A selected empty tab must still read as selected, so the accent wins over
   the dimming rather than being averaged with it. */
body.cper .mtab.empty.on,
.mtab.empty.on { opacity: 1; }

/* Footer wordmark. Sits tight against the logo so the two read as one lockup -
   "CASINOPER TV" - rather than a logo with a stray caption next to it. */
body.cper .ftr { gap: 7px; }
body.cper .ftr-tv {
  font-size: 15px; font-weight: 800; letter-spacing: .04em;
  color: var(--fg-dim);
}

/* ---- live-scores rows: which competition ---------------------------------- */

/*
 * Without the competition, this list is unreadable. The API's worldwide in-play
 * feed is overwhelmingly youth, reserve and women's football - 104 of the 105
 * fixtures live as I write this - so the rows were "Maldives U20", "Stanway
 * Rovers", "Viking FK W" with nothing to say what any of it was. The league now
 * sits on its own line under the teams, quiet enough not to compete with the
 * score but present on every row.
 */
.lsc-row { row-gap: 3px; }
/*
 * Centred under the match, not under the whole row. Spanning from column 1 put
 * it beneath the minute, hanging off the left edge with nothing above it;
 * starting at the home column centres it on the teams and score - the block it
 * actually describes.
 */
.lsc-lg {
  grid-column: 2 / -1;
  display: flex; align-items: center; justify-content: center;
  gap: 5px; min-width: 0;
}
.lsc-lgb { width: 14px; height: 14px; flex: 0 0 14px; object-fit: contain; opacity: .8; }
.lsc-ln {
  font-size: 10px; letter-spacing: .03em; color: var(--fg-mute);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}

/* The heading pip is red for live scores. On the upcoming fallback that would
   claim these matches are on air, so it drops to the neutral scale. */
.lsc-hd .pip.soon { background: var(--fg-mute); box-shadow: none; }

/* Kickoff time in the minute slot reads as a time, not a clock count; a
   cancelled fixture in that set is struck through like the board rows. */
.lsc-min.off {
  text-decoration: line-through; text-decoration-thickness: 1px;
  color: var(--fg-mute); letter-spacing: 0;
}

/*
 * Win / draw / loss stay hidden here too, exactly as on index2.
 *
 * They were briefly shown because this rail was 372px. It is 340 now - the
 * difference went to the video - and nine columns in that width crushed the
 * header into an unreadable "O G B M AV P FORM" run with the team names
 * squeezed behind it. Played, goal difference and points still justify the
 * ordering, which is the whole job of the extra columns; the other three were
 * the ones worth losing.
 */

/* ---- no dead space around the player ------------------------------------ */

/*
 * The empty bands above and below the video, removed - without widening the
 * page.
 *
 * Widening was the wrong fix and got reverted: --max stays at 1076 and the rail
 * at 372 precisely so the page skin's artwork keeps showing in the left and
 * right gutters. Covering it with a wider content column made the player bigger
 * by hiding the thing the skin is there for.
 *
 * What actually created the bands is vertical, not horizontal:
 *
 * 1. .app centres its children. Whenever the page is shorter than the window
 *    that inserts blank space above the player whose height depends on the
 *    window - which is why it read as a broken empty block rather than as
 *    deliberate spacing. Top-aligned, the header is followed by the player.
 * 2. .player-col carried its own top inset, adding to the same strip.
 * 3. --chrome told the 16:9 cap to reserve room for a header stack and CTA
 *    bars this page does not have, so the video was sized smaller than its
 *    column for space that was never used. Remeasured for this layout, the
 *    video grows to fill the column it already had.
 */
body.cper .app { justify-content: flex-start; }

/*
 * The page fills the window instead of leaving slack.
 *
 * landing.css sizes .hero-in by its content (`flex: 0 0 auto`) because index2
 * has a scoreboard below it that wants the rest of the page. This page does
 * not, so on a tall window the content stopped short and the leftover height
 * piled up as a dead band above the footer - a couple of hundred pixels of
 * nothing. Centring it, which is what .app did originally, only split the same
 * emptiness into two smaller bands above and below.
 *
 * So the row grows, and the growth goes to the live-scores card: its list was
 * capped at 300px and scrolling while blank space sat underneath it. Now the
 * card takes the slack and shows more matches, which is what the space is
 * worth. Nothing is stretched that would look wrong stretched - the video keeps
 * its aspect ratio and the rail already scrolls internally.
 */
/* padding-top:0 as well as margin: landing.css gives .hero-in 10px all round,
   and that top 10 was the last of the strip between the header and the video. */
body.cper .hero-in {
  /*
   * No padding at all. landing.css gives this 10px all round; padding-top was
   * the strip under the header, and padding-bottom was the last one - 10px of
   * page background showing beneath the scores card, with the skin's own
   * wordmark visible through it. The sides go too, so the player and the rail
   * run edge to edge against the artwork instead of floating on it.
   */
  margin-top: 0; flex: 1 1 auto; min-height: 0;
  padding: 0;
}

/*
 * Rounded on the outer edge, square where it meets the rail.
 *
 * .screen carried a 10px radius on all four corners while the rail's left edge
 * is square, and the two touch exactly - so the video's rounded top-right cut a
 * visible notch out of the seam. This mirrors what the rail already does on its
 * own outer side, so the pair reads as one panel split down the middle rather
 * than two tiles that do not quite meet.
 */
body.cper .screen { border-radius: var(--r) 0 0 var(--r); }
body.cper .player-col { padding-top: 0; justify-content: flex-start; min-height: 0; }

/*
 * The video takes the leftover height, and the card takes only what it needs.
 *
 * The slack used to go to the live-scores card, which worked only when the
 * list was long. With two matches on the board the card stretched and left
 * blank space under its rows - the same dead area, moved inside a panel.
 *
 * So .screen grows instead, and drops its 16:9 lock to do it. That is a real
 * trade: the box becomes taller than 16:9, so `object-fit: cover` fills it by
 * scaling up and cropping the left and right edges of the picture rather than
 * letterboxing. `contain` would put the empty space straight back, this time
 * as black bars inside the player. On a football feed the crop costs a sliver
 * of pitch width, which is the price of the fill.
 */
body.cper .screen {
  /*
   * flex-grow AND a 16:9 ratio, not one or the other.
   *
   * `aspect-ratio: auto` was wrong: before the first segment arrives the video
   * element has no intrinsic size, so the box collapsed to the height of the
   * "Yayın hazırlanıyor" overlay and left the rest of the column empty - the
   * player looked broken for the two seconds that matter most, on first load.
   *
   * Keeping the ratio gives the box a floor derived from its own width, so it
   * is correctly sized with no video at all; flex-grow then stretches it into
   * whatever height is left over. Never smaller than 16:9, never a gap.
   */
  /*
   * min-height, not 0. The ratio is the PREFERRED size, not a hard floor:
   * with `min-height: 0` the box refused to give anything back, so on a
   * 768-tall window the column needed 779px and the page overflowed by 150 -
   * a scrollbar and a footer pushed below the fold. It may now shrink under
   * pressure, down to a size where the picture is still worth watching.
   */
  /*
   * flex-grow 0, and a low shrink priority. The video holds 16:9.
   *
   * Letting it take the leftover height did remove every gap, but at a cost
   * that was worse than the gap: the box became 735x611 on a 1080 window
   * (ratio 1.20) and 735x315 on a 720 one (ratio 2.33), and `object-fit: cover`
   * fills those by cropping - about a third of the picture's width lost on the
   * big screen, a quarter of its height on the small one.
   *
   * So the slack goes to the scores card instead (see .feat below): it grows to
   * absorb spare height and shrinks first when there is not enough. That keeps
   * the video at exactly 16:9 across the whole 720-1080 range with no gap
   * anywhere, because the card has enough range to cover the difference. The
   * min-height is a last resort for windows shorter than the card can absorb.
   */
  flex: 0 1 auto; min-height: 240px;
  aspect-ratio: 16 / 9;
  width: 100%;
}
body.cper #video { object-fit: cover; }

/*
 * Content height, so the card cannot manufacture a gap of its own - but
 * shrinkable, so it is not the reason the page overflows either. On a short
 * window the list gives up rows before the video gives up size, which is the
 * right order: someone came for the stream.
 */
/*
 * The card is the elastic element: it takes all spare height and gives it up
 * first. Growing it is not padding - it shows more matches, which is what the
 * space is worth. The high shrink factor is what lets the video keep its ratio
 * on a short window.
 */
body.cper .feat { flex: 1 100 auto; min-height: 0; display: flex; flex-direction: column; }
body.cper .lsc { flex: 1 1 auto; min-height: 0; display: flex; flex-direction: column; }
body.cper .lsc-list { max-height: none; flex: 1 1 auto; min-height: 84px; }

/* The 13px of panel either side of the video was .player-col's own inset - the
   dark strips flanking the picture. The video spans the full column now. */
body.cper .player-col { padding-left: 0; padding-right: 0; }
body.cper .under { padding-left: 4px; padding-right: 4px; }
body.cper { --chrome: 196px; }

/* ---- footer -------------------------------------------------------------- */

/*
 * No dark band under the player.
 *
 * The footer painted an opaque strip across the bottom of the page, and with
 * the skin's own CASINOPER artwork sitting directly behind it the result was
 * two logos stacked in a black box. Transparent, it reads as the page ending
 * rather than as another panel, and the height it was reserving goes to the
 * video above it.
 *
 * The mark keeps a shadow because what is behind it is now artwork rather than
 * a flat colour, and that varies.
 */
/*
 * No footer at all on this page.
 *
 * It was a dark band carrying a second CASINOPER mark directly over the skin's
 * own CASINOPER artwork - two logos in a box, at the bottom of a page whose
 * header already says who this is. Removing it hands its height to the player,
 * which is what the space is worth here. The mark and the "TV" wordmark go with
 * it; index2 keeps its own footer untouched.
 */
body.cper .ftr { display: none; }

/*
 * One screen, no scrollbar - which is what finally makes "no gaps" possible.
 *
 * body is `min-height: 100%`, so the flex chain was free to grow past the
 * window and nothing ever applied shrink pressure: the player held its 16:9
 * height, the card held its rows, and the page simply overflowed - 150px at
 * 768 tall, with a scrollbar and the footer pushed below the fold. Pinning the
 * height bounds the chain, so the leftover space is distributed instead of
 * invented, and .screen / .lsc-list give a little back when there is not
 * enough.
 *
 * Desktop only. Below the 980px breakpoint the layout stacks into one column
 * and genuinely needs to scroll, so it must keep its natural height there.
 */
@media (min-width: 981px) {
  body.cper { height: 100%; overflow: hidden; }
  body.cper .app { min-height: 0; }
  /*
   * minmax(0, 1fr) on the row, not the default `auto`.
   *
   * This was the piece that made the rest of the chain inert. A grid row sized
   * `auto` is as tall as its tallest item's content, so bounding .hero-in from
   * above changed nothing - the row simply overflowed and, with body clipped,
   * the bottom of the scores card was cut off and unreachable. minmax(0, 1fr)
   * lets the row be smaller than its content, which is what finally gives
   * .screen and .lsc-list something to shrink against.
   */
  body.cper .hero-in { grid-template-rows: minmax(0, 1fr); }
  /*
   * align-self: stretch is the fix. landing.css sets `align-self: start` on
   * this column so index2's player sits at the top of a taller row; here that
   * made the column opt out of the row's height entirely - it sized to its
   * content at 783px inside a correctly-bounded 668px row and spilled past the
   * window. Stretched, it takes the row height and the flex children below can
   * finally shrink into it.
   */
  body.cper .player-col { min-height: 0; align-self: stretch; }
  body.cper .rail-wrap { min-height: 0; align-self: stretch; }
}

/*
 * The rail's total-fixture counter is dropped on this page.
 *
 * It rendered as a small empty pill in the top-right of the rail header - a
 * grey slab with nothing in it whenever the count was zero, which reads as a
 * broken control rather than a number. It is also redundant here: the CANLI and
 * YAYINLANACAKLAR sub-tabs each carry their own count, so the combined total
 * answers a question nobody asked. index2 keeps it; it has no sub-tabs.
 */
body.cper .rail-n { display: none; }

/* ---- live-scores card: no rule, no dead space, red pip ------------------- */

/*
 * The .lsc block carried margin-top, padding-top and a border-top, which made
 * sense while it sat below a featured-match block inside the same card and
 * needed separating from it. That block is gone, so all three were decorating
 * the top of an otherwise empty card: ~37px of space and a horizontal line
 * above "CANLI SKORLAR" with nothing above them to divide it from.
 */
body.cper .lsc {
  margin-top: 0;
  padding-top: 0;
  border-top: 0;
}
/* The card's own inset shrinks to match - the heading is the top of the panel
   now, so it does not need to be held away from an edge it is already at. */
body.cper .feat { padding-top: 9px; margin-top: 8px; }

/*
 * The pip goes red, not the brand teal.
 *
 * `.pip` takes --red, which on this page is the CasinoPer teal - so the dot
 * beside CANLI SKORLAR came out green and read as decoration. It means "on
 * air", which is the one thing on this page that stays red on both brands, for
 * the same reason .livetag and .q.live do: it is a state, not a brand colour.
 * The upcoming variant stays neutral, since kickoff times are not on air.
 */
body.cper .lsc-hd .pip { background: #e11d48; box-shadow: 0 0 0 3px rgba(225, 29, 72, .18); }
body.cper .lsc-hd .pip.soon { background: var(--fg-mute); box-shadow: none; }

/* The featured group's heading carries the live pip, so it takes the same red
   as the rest of the on-air indicators rather than the brand teal. */
body.cper .rgrp-t .pip { background: #e11d48; box-shadow: 0 0 0 3px rgba(225, 29, 72, .18); }
/*
 * No per-row marker at all on this page.
 *
 * These rows already sit under an ÖNE ÇIKANLAR heading that names exactly what
 * they are, so the wash and the star were a second and third way of saying it -
 * and the gold read as a warning colour against the teal palette rather than as
 * emphasis. index2 needs them because it has no heading: one combined list in
 * kickoff order, where a featured fixture has to announce itself in place.
 */
body.cper .ritem.featured,
body.cper .ritem.featured:hover { background: none; }
body.cper .ritem.featured .ritem-t span::after { content: none; }

/* ---- panels stay opaque over the artwork --------------------------------- */

/*
 * landing.css paints these at rgba(17, 22, 29, .93) - a blue-grey at 93%, which
 * works over index2's muted skin. This page's artwork is a busy full-colour
 * casino illustration, and 7% of it came through: faces and shapes were
 * legible inside the rail's empty area, which reads as a rendering fault rather
 * than as translucency.
 *
 * Near-opaque rather than fully flat, so the panels still sit *on* the artwork
 * instead of looking pasted over it, but nothing recognisable survives.
 */
body.cper .rail,
body.cper .player-col,
body.cper .feat {
  background: #0f1715;
}
/* The board list and modal share the same treatment where they exist. */
body.cper .board-list,
body.cper .mdl-box { background: #0f1715; }

/* The standings' sticky header was matched to the old green surface. */
body.cper .stbl th { background: #0f1715; }

/*
 * Square corners on the live-scores card.
 *
 * It carried the shared 10px radius, which rounded the top and bottom of a
 * panel that butts directly against the player above it and the window edge
 * below - so the rounding read as two stray notches in an otherwise straight
 * column rather than as a card. The player keeps its outer-left radius, which
 * is the one corner that actually sits against the artwork.
 */
body.cper .feat { border-radius: 0; }

/*
 * Square throughout on this page.
 *
 * The player column runs edge to edge against the artwork with no gutter, so
 * every rounded corner it had was meeting something flat - the rail on one
 * side, the scores card underneath, the header above. Each one read as a notch
 * rather than as a curve. Square is the honest shape for a flush block.
 */
body.cper .player-col,
body.cper .screen,
body.cper .rail { border-radius: 0; }

/*
 * Anything in the modal still pinned to a literal grey, lifted with it.
 * These were written before the palette moved and hold their own colours.
 */
body.cper .bm-none,
body.cper .lu2-gt,
body.cper .lu-coach,
body.cper .st-top span,
body.cper .lu2-p i,
body.cper .tl-min,
body.cper .mdl-sub { color: var(--fg-dim); }

/* Unselected modal tabs use the same white as everything else; only the pill
   and the accent mark which one is open. */
body.cper .mtab { color: var(--fg); }
body.cper .mtab.on { color: #04140d; }
