/* ══════════════════════════════════════════════════════════════════════════
   The public searchable leaderboard page (/leaderboard/, leaderboard.html).

   Loaded LAST, after the base stylesheet set and the Tabulator theme, and it needs to win
   against both. Two jobs:

     1. Put the board in the grid's slot, under the whole top chrome, and unlock
        THAT BOX ONLY. The page extends index.html, so the sky/billboard/ant-line/grass
        chrome is shared; 00-core.css's document lockdown (overflow:hidden,
        touch-action:manipulation, user-select:none, -webkit-touch-callout:none)
        is what pins that chrome in place and is deliberately KEPT. A stat table
        needs the opposite of all four, so #leaderboard_shell — and nothing
        above it — undoes them for itself. Scoping is via
        <body class="leaderboard_page">, never a class on <html>: a document
        -level reset would let the horizon scroll away.

     2. Skin Tabulator in wood. Tabulator's prebuilt themes compile their SCSS
        variables down to literal hex — there are NO CSS custom properties to
        hook a palette onto — so this is override-by-class-name. RE-CHECK THIS
        BLOCK ON ANY TABULATOR UPGRADE: a renamed internal class silently
        reverts to grey, with no error anywhere.

   Wood technique on this page: the big variable-size containers use 9-slice
   border-image (WOOD-UI.md §4.1) so nothing is stretched far off its native
   aspect; near-native-aspect elements (the search well) keep the
   stretch-to-fit convention. Every one of them writes `/ 1 /` in the
   border-image width slot — the unitless multiplier of the computed
   border-width, which is also the property's initial value — so the art tracks
   whatever border-width says and the two can never drift apart. No exporter run
   is needed: every image this page uses was already a served asset in
   static/img/.

   THERE IS NO MOBILE MODE, and there must never be one again (2026-08). This
   file carries no @media query and no viewport unit: a clamp(...vw...) ramp is
   just a breakpoint with the stairs sanded off, and either way the page ends up
   measuring the window instead of laying itself out. Width is handled by the
   layout primitives — flex + flex-wrap on the toolbar and the pager, flex on the
   static top ten, max-width + margin:auto on the reading column, and
   Tabulator's own fitColumns plus the tableholder's overflow on the table. The
   chrome has ONE size everywhere, in em where it should track the text.
   ══════════════════════════════════════════════════════════════════════════ */

/* ── 1. The slot ─────────────────────────────────────────────────────────── */

/* Exactly where #thegrid sits on the game page: pinned below the grass line and
   filling the rest of the window. 144px = .grass top (128px) + its height (16px)
   — the horizon.

   z-index 50 puts the board UNDER THE ENTIRE TOP CHROME, which is the rung
   #about has always had (it is position:absolute with no z-index at all). It
   was 60 while the board still slid in on a translateY(-100%): that dragged a
   viewport-tall box up through y=0..144 and back for the whole animation, and at
   60 it painted OVER the mist, the billboard sign and the sky ad on the way in
   and on the way out. The board cross-fades in place now (15-view-swap.css), so
   nothing travels above the horizon and this rung is the belt to that braces —
   keep it, because it is what makes re-introducing any kind of movement safe.

   Above it: .sky .back (51 — position:relative + z-index is a STACKING CONTEXT,
   so the mist, the billboard faces, #preview_ribbon, #billboard_link and
   #sky_ad_slot all ride at 51 with it no matter what their own local z-index
   says; #sky_ad_slot's 60 is one of those and never reached the root ladder),
   then .grass (110), .ant-line (120) and #top_buttons (200), which keep painting
   over the board as they do over the canvas.

   Level with it, and beaten on DOCUMENT ORDER because leaderboard_content.html
   renders after game_content.html: #leaderboard_backdrop (50 — its own dim,
   which must stay under it), #control_panel (50) and #top_HUD (50). The tie is
   deliberate rather than a gap: dropping to 45 would let an open control panel
   float over a board whose shell has no background of its own. Nothing else in
   the ladder lives between 50 and 60, so this rung flips the board against the
   sky subtree and against nothing else.

   touch-action is pan-x AS WELL AS pan-y, and the pan-x is load-bearing:
   touch-action resolves as the INTERSECTION up the ancestor chain, so a pan-y
   shell vetoes horizontal panning inside .tabulator-tableholder however that
   element declares itself (§3 sets pan-x pan-y there). The table is wider than
   the frame on a phone, and without this the columns past the fold are
   unreachable by finger. A narrow DESKTOP window can never catch this
   regressing — wheel, trackpad and scrollbar all work regardless.

   overflow-x stays hidden: it clips this element's OWN box and has no effect on
   a descendant that is itself a scroll container, and it is what stops the whole
   page gaining a horizontal scrollbar if the table box ever measures wider.

   This is also the ONLY scroller on the page, and the only element that undoes
   the game's document lockdown — html/body stay locked, which is what keeps the
   scenery above from scrolling away. */
#leaderboard_shell {
    position: absolute;
    top: 144px;
    right: 0;
    bottom: 0;
    left: 0;
    z-index: 50;
    box-sizing: border-box;
    /* The bottom gutter is scroll clearance under a footer that wraps to two
       lines on a phone; it used to be 40px on narrow screens and ZERO otherwise,
       which left the pager flush to the viewport edge on desktop. */
    padding: 8px 6px 48px;
    overflow-y: auto;
    overflow-x: hidden;
    touch-action: pan-x pan-y;
    -webkit-user-select: text;
    user-select: text;
    -webkit-touch-callout: default;
    font-family: 'Arvo', 'Courier New', Courier, monospace;
    color: #fff;
}

/* ── 2. Page furniture ───────────────────────────────────────────────────── */

/* The centered column. The shell itself must span the full width (it is the
   scroll box), so the measure lives one level in. */
#leaderboard_inner {
    max-width: 650px;
    margin: 0 auto;
}

/* The closer, #about_close_button's geometry (70-auth-chrome.css) with two changes:
   it is an ANCHOR, so it needs display:block to take a box at all; and it
   sticks to the TOP OF THE SHELL rather than to 148px, because the shell is
   already positioned at the horizon and is its own scroll container. Sticky is
   the point — it stays reachable however far down a long table you have read,
   exactly as About's rides About's scroll.

   Lives here rather than in the base set: it is pure page furniture, needed only
   once the board is open, so it has nothing to say to the game page and the
   lazy-injection hazard that pins the view rules next door does not apply. */
#leaderboard_close_button {
    display: block;
    position: sticky;
    top: 8px;
    float: right;
    width: 50px;
    height: 50px;
    text-align: center;
    background: transparent;
    z-index: 200;
    margin-right: -5px;
}

#leaderboard_close_button:active {
    top: 10px;
    margin-left: -2px;
}

/* 9-sliced frame (WOOD-UI.md §4.1): slices in served-file pixels of the
   1922x328 strip — 40 top (margin+outline), 80 ends (chips), 60 bottom
   (26px shadow band with clearance). The flat background is the underlay
   that paints while the lazily-injected CSS/image loads. */
/* FLEX, not floats, and that is the whole responsive story for this bar: the
   title and the well sit on one line while there is room and the well drops to
   its own line when there is not. A float pair (title left, well pulled up by a
   negative margin onto a fixed-height bar) looks identical wide and simply
   OVERLAPS below ~340px, because a float has no way to say "wrap when you must".
   justify-content puts the well hard right, which is the arrangement floats were
   reaching for. */
#leaderboard_toolbar {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    gap: 8px;
    align-items: center;
    border: solid transparent;
    border-width: 8px 16px 12px;
    border-image: url('../img/panel_dark_wood_horizontal_strip.png') 40 80 60 80 fill / 1 / 0 stretch;
    background: transparent;
}

/* One 44px control baseline across the toolbar: the title and the search
   well. 44px is the touch target — the in-game pager's 32px is too small
   for a page that is read on a phone. */

/* The page title, which lives in this bar rather than on a headboard of its
   own (2026-08, when the Columns/Reset/CSV buttons left and freed the room).
   No background: the toolbar's plank IS its board. It never shrinks; the well
   beside it is the elastic one, and flex-wrap drops that well onto its own line
   before either can be squashed. */
#leaderboard_toolbar_title {
    flex: 0 0 auto;
    padding-right: 6px;
    line-height: 44px;
    font-size: 14pt;
    color: #fff;
    text-shadow: #0a0a0a 2px 2px 3px;
}

/* Grows into whatever the title leaves and wraps below it when that is under
   its 180px floor. max-width keeps it from becoming a comically wide trough on
   a desktop board. */
#leaderboard_toolbar .hs_search_input {
    flex: 1 1 180px;
    min-width: 180px;
    max-width: 320px;
    height: 38px;
    box-sizing: border-box;
    padding-left: 25px;
    font-size: .9em;
    color: white;
}

/* The server-rendered top ten, on the same one-solid-board treatment as the
   table below (§3): a 9-sliced dark square panel replaces the old PORTRAIT
   panel_dark_wood_mobile_vertical stretched landscape. Slice 100 covers the
   art's measured corner-chip band (~80-100px); vertical `round` tiles the
   plank-course fill instead of stretching the grain. */
#leaderboard_static_top {
    padding: 14px 10px;
    margin-bottom: 10px;
    border: 14px solid transparent;
    border-image: url('../img/panel_dark_wood_large_square.png') 100 fill / 1 / 0 stretch round;
    background: transparent;
}

#leaderboard_static_top .hs_static_sign {
    position: static;
    display: inline-block;
    float: none;
    margin: 0 0 12px;
    font-size: 13pt;
}

/* Rows are flat alternating tints over the board's grain fill — no per-row
   plank PNGs (their notched/tapered end art clipped rank medals and numbers
   at row height). The board is one piece of furniture; rows just shade it.

   A row is a FLEX row: a fixed rank chip, an elastic name, and a sugar figure
   sized to its digits. It used to be three inline-blocks held apart by a
   min-width on the name, which is exactly the kind of magic number that then
   needs a breakpoint to shrink it — the row simply distributes now, at any
   width. */
#leaderboard_static_top .high_score {
    display: flex;
    align-items: baseline;
    gap: 8px;
    background: rgba(0, 0, 0, 0.10);
    border-bottom: 1px solid rgba(0, 0, 0, 0.35);
    padding: 8px 10px;
    cursor: default;
    filter: none;
}

#leaderboard_static_top .high_score:nth-child(even) {
    background: rgba(0, 0, 0, 0.28);
}

#leaderboard_static_top .hs_rank {
    flex: 0 0 44px;
    text-align: center;
    font-size: 12pt;
}

/* min-width:0 is load-bearing: a flex item defaults to min-width:auto, which
   refuses to shrink below its content and would defeat the ellipsis. */
#leaderboard_static_top .hs_ant {
    flex: 1 1 auto;
    min-width: 0;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

#leaderboard_static_top .hs_sugar {
    flex: 0 0 auto;
}

/* ── 3. Tabulator, in wood ───────────────────────────────────────────────── */

/* EVERY selector below is prefixed `#leaderboard_shell`, never
   `body.leaderboard_page`, and that is a bug fix rather than a style choice
   (2026-08).

   The body class is VIEW STATE: showGame() removes it in the first frame of the
   close. While the skin hung off it, that one line un-skinned the entire table
   instantly — and the vendor theme underneath paints .tabulator, -header,
   -table, -footer and -row-even all #fff — so the board spent its whole 260ms
   fade-out cross-fading a WHITE table over the world. That is the white flash.
   A widget's skin must not depend on which view is showing.

   #leaderboard_shell is the table's own always-present ancestor, so the skin
   holds whatever the body class is doing. It also scores 1,0,0 against the old
   0,1,0, so every override below got MORE specific against the vendor, never
   less — the (0,7,0)/(0,8,0) specificity notes further down are now one ID
   higher and still win. */

/* One solid board: the same 9-sliced dark square panel as the top-ten box.
   The 14px frame also insets the header/rows inside the panel outline
   (Tabulator sizes rows from the holder's clientWidth, so the border-box
   inset needs no JS cooperation). It is 14 rather than the old 22 because 22
   was only ever the wide half of a breakpoint pair — and the 8px it gives back
   on each side is 16px more table, which this board can use. If the vertical
   `round` tiling ever shows band/middle seams after a Tabulator or art change,
   plain `stretch` is the sanctioned fallback (WOOD-UI.md §4.1). */
#leaderboard_shell .tabulator {
    border: 14px solid transparent;
    border-image: url('../img/panel_dark_wood_large_square.png') 100 fill / 1 / 0 stretch round;
    background: transparent;
    border-radius: 0;
    font-family: inherit;
    font-size: 10pt;
    color: #fff;
}

/* Transparent, so the container's one-solid-board fill reads straight through;
   the box-shadow is the only rule that separates the header from the rows.
   There is no plank art of its own here — the 3-slice header/footer planks went
   when the one-solid-board treatment landed. Keep `border: 0`: a side border
   would inset this element's contents without insetting .tabulator-tableholder,
   and every header cell would sit off its column by the border width. */
#leaderboard_shell .tabulator .tabulator-header {
    border: 0 solid transparent;
    background: transparent;
    color: #fff;
    font-weight: bold;
    text-shadow: #0a0a0a -1px 1px 1px;
    box-shadow: 0 2px 0 rgba(0, 0, 0, 0.35);
}

#leaderboard_shell .tabulator .tabulator-header .tabulator-col {
    background: transparent;
    border-right: 1px solid rgba(0, 0, 0, 0.25);
}

/* The vendor paints a #e6e6e6 hover on every sortable header, from a rule
   carrying the .tabulator-col-sorter-element class (specificity 0,6,0) — one
   step above what the plain .tabulator-col:hover here can reach. Matching its
   class list and keeping the #leaderboard_shell prefix wins at 1,6,0. */
#leaderboard_shell .tabulator .tabulator-header .tabulator-col:hover,
#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable.tabulator-col-sorter-element:hover {
    background: rgba(255, 255, 255, 0.08);
}

#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable[aria-sort='ascending'],
#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable[aria-sort='descending'] {
    background: rgba(255, 255, 255, 0.14);
}

/* Clearance for the sort arrow, which the vendor parks absolutely at right: 4px
   and which is 12px wide — so 16px is the least that keeps a title off it. The
   vendor reserves 25px; those 9px are what several one-word headers needed. */
#leaderboard_shell .tabulator .tabulator-header .tabulator-col .tabulator-col-title {
    padding-right: 16px;
}

/* The sort arrows are the vendor's CSS triangles, coloured #bbb unsorted and
   #666 active — near-invisible on dark wood, and the active state reads as the
   DIMMER of the two. Recoloured to the page's cream, with the unsorted state
   held back so the sorted column is the one that stands out. Each selector
   mirrors the vendor's own (0,8,0) chain plus the #leaderboard_shell prefix. */
#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable[aria-sort='none'] .tabulator-col-content .tabulator-col-sorter .tabulator-arrow {
    border-bottom-color: rgba(232, 220, 200, 0.5);
}

#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable[aria-sort='ascending'] .tabulator-col-content .tabulator-col-sorter .tabulator-arrow {
    border-bottom-color: #e8dcc8;
}

#leaderboard_shell .tabulator .tabulator-header .tabulator-col.tabulator-sortable[aria-sort='descending'] .tabulator-col-content .tabulator-col-sorter .tabulator-arrow {
    border-top-color: #e8dcc8;
}

/* Rows are semi-transparent tints over the container's border-image fill, so
   the wood grain reads through both shades (same treatment as the static
   top ten). The old per-row plank PNGs — and the "load-bearing right
   padding" that dodged their tapered ends — are gone: there is no end art
   anywhere near the cells now, so padding is symmetric. */
#leaderboard_shell .tabulator-row {
    background: rgba(0, 0, 0, 0.10);
    border: 0;
    border-bottom: 1px solid rgba(0, 0, 0, 0.35);
    color: #fff;
}

#leaderboard_shell .tabulator-row.tabulator-row-even {
    background: rgba(0, 0, 0, 0.28);
}

#leaderboard_shell .tabulator-row:hover {
    background: rgba(255, 255, 255, 0.08);
    filter: none;
}

/* em, not px: the padding tracks the 10pt cell text, so it is the TYPE that
   sets the row's breathing room rather than a number keyed to how wide the
   window happens to be. (0.5em/0.75em ≈ 6.7px/10px here.) */
#leaderboard_shell .tabulator-row .tabulator-cell {
    border-right: 1px solid rgba(0, 0, 0, 0.18);
    padding: 0.5em 0.75em;
}

/* Padding only. The divider belongs to .tabulator-col above; drawing it here
   too put two lines a few pixels apart down every header, which boxed each
   title and its arrow into what looked like its own separate tab.

   Tighter side padding than the body cells because a header carries a word and
   a sort arrow in the width a cell gives to a number: at 10px the one-word
   titles that cannot wrap (Online, Sapphire, Emerald) still lost their last
   letters on their narrowest columns. 0.45em ≈ 6px is that floor, and it is a
   floor at EVERY width now — the old narrow-screen rule swept this selector in
   with the body cells and pushed it back up to 8px on exactly the screens that
   could least afford it. */
#leaderboard_shell .tabulator .tabulator-header .tabulator-col .tabulator-col-content {
    padding: 0.5em 0.45em;
}

/* Transparent for the same reason as the header: the container's board shows
   through. white-space returns to normal so the row below can wrap. */
#leaderboard_shell .tabulator-footer {
    border: 0 solid transparent;
    background: transparent;
    color: #fff;
    white-space: normal;
}

/* Eight 44px buttons and a select do not fit a phone on one line, and the
   vendor lays them out in a nowrap flex row that simply clips. Wrapping turns
   the overflow into a second line. */
#leaderboard_shell .tabulator-footer .tabulator-footer-contents {
    flex-wrap: wrap;
    gap: 4px;
}

/* The vendor sets color on .tabulator-paginator itself, so the footer's white
   never reaches any text the paginator renders directly — it lands dark grey on
   dark wood. Nothing does today (the page-size label went with the selector and
   the numbered buttons are off), which is exactly why this stays: it is the
   catch-all for whatever a vendor upgrade puts back there. */
#leaderboard_shell .tabulator-footer .tabulator-paginator {
    color: #fff;
}

/* The numbered page buttons are gone (paginationButtonCount: 0), so this is
   the empty container they used to fill — hidden so it stops contributing two
   flex gaps between Prev and Next, and so a vendor upgrade that changes the
   button-range arithmetic can't bring the digits back unstyled. */
#leaderboard_shell .tabulator-footer .tabulator-pages {
    display: none;
}

/* Which wood the pager buttons wear. Held in a custom property so the one rule
   below can paint it at a specificity that survives :hover — see there.
   First/Prev/Next/Last are all that remain, and they carry words, not digits:
   they render about twice as wide as they are tall, so the round art stretched
   into ovals. The short button is 472x203, which is the shape these are.

   76px, not the old wide-screen 96: the four word buttons plus the page-size
   select crowd a phone once the labels wrap, and 76 is the width the words
   still fit. .tabulator-footer-contents wraps them to a second line, which is
   what handles a footer with nowhere left to go. */
#leaderboard_shell .tabulator-footer .tabulator-page {
    --loa-pager-art: url('../img/short_wooden_button_grey.png');
    min-width: 76px;
    min-height: 44px;
    margin: 2px;
    padding: 2px 10px;
    border: 0;
    border-radius: 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    color: #fff;
    font-family: inherit;
    text-shadow: #0a0a0a 1px 1px 1px;
}

/* THE hover fix. The vendor's hover rule uses the `background` SHORTHAND, so
   it does not merely tint the button — it resets background-image to none and
   the wood disappears into a flat dark rectangle. Its selector scores (0,4,1);
   listing :hover here alongside the base state scores (0,5,0) and wins, which
   is why the art has to be re-asserted rather than just recoloured. The
   vendor's guard is :not(disabled) — an element type, never true — so it fires
   on the greyed-out buttons too; both states are covered here. */
#leaderboard_shell .tabulator .tabulator-footer .tabulator-page,
#leaderboard_shell .tabulator .tabulator-footer .tabulator-page:hover {
    background: var(--loa-pager-art) no-repeat;
    background-size: 100% 100%;
}

#leaderboard_shell .tabulator .tabulator-footer .tabulator-page:not(:disabled):hover {
    filter: brightness(1.15);
    cursor: pointer;
}

#leaderboard_shell .tabulator-footer .tabulator-page:disabled {
    opacity: 0.45;
}

/* The page-size <select> and its "Page Size" label are gone (2026-08): the
   footer is First/Prev/Next/Last and nothing else. Omitting
   paginationSizeSelector in leaderboard_page.js is what removes them, so there
   is no element left here to skin. Bringing the option back means bringing back
   its wood WELL skin too — a raw native select on dark wood is the one control
   on this page the vendor theme would render unstyled. */

#leaderboard_shell .tabulator-placeholder,
#leaderboard_shell .tabulator-placeholder-contents {
    color: #e8dcc8;
    font-family: inherit;
}

/* Tabulator's virtual scroller owns this element. It needs no
   -webkit-overflow-scrolling: momentum scrolling has been the default since
   iOS 13 and the property is obsolete everywhere. What it DOES need is the
   touch-action the reset above restores — without it the game's
   touch-action: manipulation swallows the scroll gesture. The transparent
   backgrounds (here and on .tabulator-table) undo the vendor theme's white
   table body so the container's wood fill shows through the row tints —
   the whole point of the one-solid-board treatment. */
#leaderboard_shell .tabulator .tabulator-tableholder {
    touch-action: pan-x pan-y;
    background: transparent;
    scrollbar-width: thin;
    scrollbar-color: #8a5a3a transparent;
}

#leaderboard_shell .tabulator .tabulator-tableholder .tabulator-table {
    background: transparent;
}
