/* AUTO-GENERATED by deploy.sh — concatenation of:
     assets/css/branding.css
     assets/css/blocks.css
     assets/css/chess.css
     assets/css/home.css
   Edit the source files, not this one. */

/* === branding.css === */
/* Lichfield branding — logo sizing and title-next-to-logo in nav and footer.
   Loaded globally from default.hbs. */

/* Self-hosted Cinzel (Bold, 700) — used by the site title in nav + footer.
   Latin subset only; the title is "Lichfield Chess Club" — pure ASCII. */
@font-face {
    font-family: "Cinzel";
    font-style: normal;
    font-weight: 700;
    font-display: swap;
    src: url("../fonts/cinzel-700-latin.woff2") format("woff2");
    unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+20AC, U+2122, U+FEFF, U+FFFD;
}

.gh-navigation-logo,
.gh-footer-logo {
    display: inline-flex !important;
    align-items: center;
    gap: 0.15em;
    text-decoration: none;
}

/* Logo image — bumped from Source's default ~30px to a more presentable 56px.
   Uses !important because Source ships hard-coded sizing on these selectors. */
.gh-navigation-logo img {
    height: 80px !important;
    width: auto !important;
    max-height: 80px;
    /* Nudge the logo up a few px relative to the title text. transform
       doesn't take part in layout, so the inline-flex alignment between
       logo and title isn't disturbed — just the logo's painted position
       is shifted. */
    transform: translateY(-4px);
}
.gh-footer-logo img {
    height: 40px !important;
    width: auto !important;
    max-height: 40px;
}

/* "Chess Club" line — 10% smaller than "Lichfield" so the first word
   reads as the dominant element of the wordmark. */
.lc-nav-title-sub {
    font-size: 0.84em;
}

/* Club name text next to the logo */
.lc-nav-title {
    font-family: "Cinzel", Georgia, serif;
    font-size: 2rem;
    font-weight: 700;
    color: inherit;
    line-height: 1;
    /* Cinzel is a wide all-caps serif; a touch of positive tracking
       suits it better than the negative letter-spacing the previous
       sans had. Kept modest. */
    letter-spacing: 0.005em;
    white-space: nowrap;
}
/* Nudge the navigation title 2px down relative to the logo. transform
   doesn't take part in layout so the inline-flex alignment isn't
   disturbed. Scoped to the nav only — footer title stays as-is. */
.gh-navigation-logo .lc-nav-title {
    transform: translateY(2px);
}

.gh-footer-logo .lc-nav-title {
    font-size: 1.7rem;
    font-weight: 600;
}

/* Mobile nav: keep the site title visible but in single-line form like
   the footer (no <br>, both words same size). Logo shrinks to 56px to
   leave room for the title alongside the search + hamburger buttons.
   Breakpoint matches Source's hamburger-menu cutoff (767px in
   dropdown.js). */
@media (max-width: 767px) {
    /* Same two-line layout as desktop, just sized down. The 0.84em
       ratio between the two lines (set on .lc-nav-title-sub) is
       inherited automatically because we only change the parent
       font-size here. */
    .gh-navigation-logo .lc-nav-title {
        font-size: 1.8rem;
    }
    .gh-navigation-logo img {
        height: 56px !important;
        max-height: 56px;
    }
}

/* Current-page indicator in the primary nav. Ghost's {{navigation}} helper
   tags the active <li> with `nav-current` — we paint a thick accent-coloured
   underline beneath that link via an absolutely-positioned ::after so the
   surrounding nav layout is unaffected (no padding/border shift). */
/* Tighten the gap between primary-nav items. Source ships 28px which
   reads loose for our short labels (Home / News / Match Reports etc.). */
.gh-navigation .nav {
    gap: 22px;
}

/* Inactive nav links: soften the near-black to a slightly lighter grey
   so the active link (kept at full near-black + green underline) stands
   out more by contrast. */
.gh-navigation .nav > li > a { color: #444; }

.gh-navigation .nav > li.nav-current > a {
    position: relative;
    /* Active link rendered as pure black for max contrast against the
       softer #333 inactive items. Locks against hover/visited tint too.
       Selector matches the depth of the inactive rule above (3 classes,
       2 elements) so it wins specificity. */
    color: #000;
}
.gh-navigation .nav-current > a::after {
    content: "";
    position: absolute;
    left: 0;
    right: 0;
    bottom: -8px;
    height: 4px;
    background: var(--ghost-accent-color, #2e7d32);
    border-radius: 2px;
}
/* The dropdown ("..." overflow menu) lays its links out as full-width rows,
   so the underline pseudo above stretches edge-to-edge and looks like a
   misplaced separator between items. Suppress it inside the dropdown and
   use a coloured + bold treatment instead — clearer indication that the
   current page lives in the overflow menu. */
.gh-navigation .gh-dropdown .nav-current > a::after {
    content: none;
}
.gh-navigation .gh-dropdown .nav-current > a {
    /* !important needed: Source's screen.css declares
       `.gh-dropdown li a { color: #15171a !important }` so we have to
       match its priority to recolour the active item. */
    color: var(--ghost-accent-color, #2e7d32) !important;
    font-weight: 700;
}

/* When the active page is hidden inside the overflow ("...") menu, tint
   the toggle button green so it visually pairs with the green+bold
   styling of the active item inside the dropdown. Source's dropdown.js
   nests the .gh-dropdown markup INSIDE the .gh-more-toggle <button>
   itself, so :has(.nav-current) on the toggle correctly matches when any
   item inside its dropdown is the current page.
   No underline here — the "..." glyph is too small for an underline to
   look right, and a colour change reads cleanly on its own. */
.gh-navigation .gh-more-toggle:has(.nav-current) {
    color: var(--ghost-accent-color, #2e7d32);
}

/* "Read more →" cue inside post cards on listing pages (news, match-reports,
   tag, author). Inline at the end of the excerpt so the ellipsis runs
   straight into it. Coloured + bold for affordance; the whole card is a
   single anchor (.gh-card-link) so this is just a visual CTA — clicks are
   captured by the wrapping link, not a nested one. */
.gh-card-readmore {
    color: var(--ghost-accent-color, #2e7d32);
    font-weight: 600;
    white-space: nowrap;
    /* Dotted underline matching the body-link treatment defined further
       down — visually flags the cue as a link affordance. */
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
    transition: text-decoration-style 0.15s, color 0.15s;
}
.gh-card-link:hover .gh-card-readmore {
    text-decoration-style: solid;
    color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 80%, #000);
}

/* Source defaults .gh-card-excerpt to 1.45rem, smaller than the 1.6rem
   body size. Match body so list pages read with consistent typography.
   Also disable Source's 2-line -webkit-line-clamp: our template already
   truncates the excerpt to a fixed word count, and an additional CSS
   clamp hides the trailing "… Read more →" cue when excerpts run past
   2 lines (which 40-word excerpts routinely do). */
.gh-card-excerpt {
    font-size: 1.6rem;
    display: block;
    -webkit-line-clamp: none;
    overflow: visible;
}

/* Card title hover: switch from Source's opacity-fade to a green tint,
   matching the homepage feed-item titles (.lc-feed-title). The whole
   card is wrapped in .gh-card-link so the hover triggers on any part of
   the card, not just the title text. */
.gh-card-link:hover .gh-card-title {
    color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 80%, #000);
    opacity: 1;
    transition: color 0.15s;
}

/* Horizontal dividers — Source has no explicit margin so they sit too close
   to surrounding paragraphs. Give them moderate breathing room.
   Lists trim their own bottom margin so HRs after a <ul> end up tighter
   than after a <p>; bump the HR's own top-margin a bit more to compensate. */
/* Blockquote typography: italic and slightly larger than body so quoted
   passages read as deliberate asides. Layout (full width, accent
   left-border, top/bottom margins) stays at Source's defaults. */
.gh-content blockquote:not([class]) {
    font-style: italic;
    font-size: 1.15em;
    line-height: 1.45;
}

/* Tighten the gap above and below bulleted / numbered lists in post and
   page bodies. Source's default 28px sibling spacing reads loose when a
   list belongs to its surrounding paragraph; we want them visually
   grouped. Targets both the list's own top margin and the following
   element's top margin (since Source applies all gap-margins as
   margin-top via `.gh-content > * + *`). */
/* Above the list: 0.8em — keeps the list visually attached to the
   intro paragraph that often precedes it. */
.gh-content > ul,
.gh-content > ol {
    margin-top: 0.8em !important;
}
/* Below the list: clear separation before whatever follows, since the
   list usually opens a new thought. Implemented as margin-top on the
   next sibling because Source applies all gap-margins that way
   (.gh-content > * + *). */
.gh-content > ul + *,
.gh-content > ol + * {
    margin-top: 1.6em !important;
}

/* Tighten heading-after-heading. Source applies a 56px top margin to
   every heading-with-id that isn't the first element (a clean break
   before each new section), but when an h3 sits *immediately* under an
   h2 (as in "Key Historical Milestones" → "Early Years") that 56px
   reads as wasted space — the two are conceptually one block. Drop it
   to a small subhead-style gap for that case only; standalone headings
   still get the 56px breathing room. */
.gh-content > [id] + [id] {
    margin-top: 0.8em;
}

/* Override Source's "+ * { margin-top: 48px !important }" rule that
   forces the element after hr to claim 48px above itself, which margin-
   collapses with our hr's bottom margin and wins. With this we control
   the below-hr gap directly. */
.gh-content > hr + * {
    margin-top: 1.5rem !important;
}
.gh-content hr {
    /* Asymmetric: full break above (3rem), tighter below (1.5rem) so the
       following content doesn't feel detached from the section opener. */
    margin: 3rem 0 1.5rem !important;
    /* Dotted 1px line in mid-grey. Source's default uses background-color
       on a 1px-tall block, which can only render as solid; switching to
       border-top lets us use border-style: dotted. height:0 collapses the
       block so the visible line is purely the border. */
    /* Wider-spaced dots than the browser default `border: dotted` allows.
       radial-gradient draws a 1px-radius dot per `background-size` tile;
       set tile width to control spacing (here ~10px between dots). */
    height: 2px;
    border: 0;
    background: radial-gradient(circle at center, #888 1px, transparent 1.5px) repeat-x;
    background-size: 8px 2px;
}
.gh-content ul + hr,
.gh-content ol + hr {
    margin-top: 4rem !important;
}

/* Feature images at the top of posts/pages — Ghost has no native crop UI,
   and Source renders feature images at full intrinsic height which blows
   up the layout for tall photos. Cap as a 16:7 banner that crops centrally
   via object-fit. The full-resolution image is still uploaded; we just
   constrain the rendered shape. .gh-article scope keeps author avatars
   (which also use .gh-article-image) untouched. */
.gh-article .gh-article-image {
    aspect-ratio: 16 / 7;
    max-height: 420px;
    overflow: hidden;
    border-radius: 8px;
}
.gh-article .gh-article-image img {
    width: 100% !important;
    height: 100% !important;
    object-fit: cover !important;
    display: block;
}

/* Listing-page banner — used by /match-reports/, /news/ when the
   corresponding tag has a feature_image. Sits above the post list as a
   slimmer cousin of the home hero. */
/* Tone H3 inside post / page body down to body-text size, weight 500,
   with a small margin below. Source's default 1.3em + heading-weight is
   too shouty for how Lichfield uses H3 (typically a small sub-section
   label).
   - Selector chains the three classes Ghost always emits on the post
     body wrapper (.gh-content .gh-canvas .is-body) for high specificity
     so the rule wins against Source's `.gh-content h3` and any future
     :is()/:where() block that tries to retarget headings.
   - !important is belt-and-braces — verified locally that without it
     the rule wasn't visibly winning on /contact/ even from a fresh
     private window.
   - :not() exclusions preserve the larger styling intentionally given
     to the PGN viewer's title and the league-table title. */
/* Match .lc-feed-title (homepage news / match-report card titles) so that
   sub-section H3s in post / page bodies feel consistent with the cards on
   the homepage. Only the bottom margin is set — the top margin falls back
   to whatever Source's content-flow rules dictate (typically the 28px gap
   that .gh-content > * + * applies between siblings). */
.gh-content.gh-canvas.is-body h3:not(.chess-game-title):not(.league-table-title):not(.lc-fixtures-month-title) {
    font-size: 1.9rem !important;
    font-weight: 600 !important;
    line-height: 1.3 !important;
    letter-spacing: 0 !important;
    margin-bottom: 0.3em !important;
}

.lc-page-hero {
    background: var(--ghost-accent-color, #2e7d32);
    color: #fff;
    padding: 4.5rem 0 4rem;
    text-align: center;
    position: relative;
}
/* Source's screen.css zeros .gh-container's top-margin on tag and author
   templates because Source's stock tag.hbs renders the heading INSIDE the
   container. Our custom tag.hbs / match-reports.hbs / news.hbs instead put
   a full-bleed banner ABOVE the container — without spacing here, the
   first post card jams against the bottom of the banner on /tag/<slug>/
   pages. Restoring the default 64px margin only when our hero is the
   immediate predecessor leaves Source's other layouts untouched. */
.lc-page-hero + .gh-container {
    /* Same clamp as the page-template gh-content rule below so that
       listing pages (news, match-reports, tag) and full pages both
       have identical breathing room below the hero. */
    margin-top: clamp(28px, 2.7vw + 17px, 52px);
}

/* Posts with a feature-image hero — collapse the gap between the hero
   banner and the author meta below to match the gap on regular pages.
   Two stacking margins are at play: .gh-article-header margin-top
   (default 72px) AND .gh-article-meta margin-top (default 20px). We
   trim the header to clamp(28-52px) and zero out the meta margin so
   the meta sits directly at the top of the article header. */
.lc-page-hero + main .gh-article-header {
    margin-top: clamp(28px, 2.7vw + 17px, 52px);
}
.lc-page-hero + main .gh-article-header .gh-article-meta {
    margin-top: 0;
}

/* On a Ghost Page that has a feature image, the title moves into the
   .lc-page-hero banner and page.hbs deliberately skips the
   .gh-article-header wrapper. That wrapper normally provides Source's
   ~40–72 px top breathing room above the article body, so without it
   the post body butts right up against the hero. Restore some gap —
   but smaller than Source's full clamp because the hero already has
   its own padding-bottom (~64 px), so 72 px on top of that totals to
   ~135 px of dead space which reads as too much. ~24-44 px scales
   nicely from phone to desktop. */
.page-template .lc-page-hero + main .gh-content {
    margin-top: clamp(28px, 2.7vw + 17px, 52px);
}
/* Force a clean zero margin on whatever the first child of an article
   body happens to be. Without this, different first-child types (ul,
   ol, p, h2…) interact differently with margin-collapse against the
   surrounding hero and our own list-margin rules — producing
   inconsistent gaps between visually similar pages. The .gh-content's
   own margin-top above is now the *only* source of spacing. */
.gh-content > *:first-child {
    margin-top: 0 !important;
}
.lc-page-hero.has-bg-image {
    background-size: cover;
    background-position: center;  /* default; overridable per-post via internal tag */
    background-repeat: no-repeat;
}
.lc-page-hero.lc-crop-top { background-position: top center; }
.lc-page-hero.lc-crop-bottom { background-position: bottom center; }
.lc-page-hero.has-bg-image::before {
    content: "";
    position: absolute;
    inset: 0;
    background: linear-gradient(180deg, rgba(0, 0, 0, 0.42), rgba(0, 0, 0, 0.62));
    pointer-events: none;
    z-index: 0;
}

/* Ghost's "Header" card (the one editors insert via /header in Koenig)
   carries a background image but Ghost's stock CSS only adds a faint
   20%-bottom gradient and only when class kg-style-image is set. Cards
   in kg-style-accent that ALSO carry an image (as on /about/) get no
   overlay at all, so the white heading + button copy can be unreadable.
   Mirror our own .lc-page-hero treatment: a 42→62% black gradient over
   the image, with the content text z-stacked on top.
   Requires BOTH an image AND some text content (heading/button) — an
   image-only header card is just a banner photo and shouldn't be
   dimmed. */
.kg-header-card.kg-v2:has(.kg-header-card-image):has(:is(h2, h3, h4, .kg-header-card-button))::before {
    content: "";
    position: absolute;
    inset: 0;
    background: linear-gradient(180deg, rgba(0, 0, 0, 0.42), rgba(0, 0, 0, 0.62));
    pointer-events: none;
    z-index: 1;
}
.kg-header-card.kg-v2 .kg-header-card-content {
    position: relative;
    z-index: 2;
}
/* Header-card button hover. Ghost's stock CSS dims the button to
   opacity:.85 on hover, which on a transparent-button-on-image
   background reads as the button "disappearing". Replace with the
   subtle 1px lift used by the homepage CTAs (.lc-btn:hover) and keep
   full opacity. */
.kg-header-card.kg-v2 .kg-header-card-button {
    transition: transform 0.15s, background 0.15s, color 0.15s;
}
.kg-header-card.kg-v2 .kg-header-card-button:hover {
    opacity: 1;
    transform: translateY(-1px);
}
.lc-page-hero-inner {
    max-width: 820px;
    margin: 0 auto;
    padding: 0 2rem;
    position: relative;
    z-index: 1;
}
.lc-page-hero-title {
    font-size: clamp(3rem, 4.6vw, 4.4rem);
    line-height: 1.15;
    margin: 0 0 0.4em;
    color: #fff;
    letter-spacing: -0.005em;
}
.lc-page-hero-tagline {
    font-size: clamp(1.5rem, 1.7vw, 1.8rem);
    line-height: 1.5;
    margin: 0 auto;
    max-width: 640px;
    opacity: 0.95;
}
.lc-page-hero-eyebrow {
    display: inline-block;
    font-size: 1.3rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.06em;
    color: #fff;
    text-decoration: none;
    opacity: 0.85;
    margin-bottom: 0.6em;
    padding: 0.3em 0.8em;
    border: 1px solid rgba(255, 255, 255, 0.5);
    border-radius: 4px;
}
.lc-page-hero-eyebrow:hover {
    opacity: 1;
    background: rgba(255, 255, 255, 0.15);
}
@media (max-width: 600px) {
    .lc-page-hero { padding: 3rem 0 2.6rem; }
}

/* Body-text links — green with dotted underline.
   Scoped to article content (.gh-content), the home welcome strip, and the
   editable footer panel. Navigation, buttons, tag chips, pagination, post-nav
   cards etc. all live outside these wrappers and keep their existing styles. */
.gh-content a,
.lc-welcome-inner a,
.lc-footer-panel-inner a {
    color: var(--ghost-accent-color, #2e7d32);
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
    transition: color 0.15s, text-decoration-style 0.15s;
}
.gh-content a:hover,
.lc-welcome-inner a:hover,
.lc-footer-panel-inner a:hover {
    text-decoration-style: solid;
    color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 80%, #000);
}

/* Site-wide footer panel — content edited in Pages → "Footer panel".
   Sits above the footer on every page, centre-aligned, with a soft tint
   so it reads as ancillary content rather than competing with the page. */
.lc-footer-panel {
    background: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 6%, #fff);
    border-top: 1px solid color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 12%, #fff);
    padding: 3rem 0 3.2rem;
    text-align: center;
}
/* On mobile the surrounding whitespace shrinks and the page content
   sits flush against the top of the panel band (which starts where its
   background colour starts). Add some breathing room above the band by
   pushing it down with margin-top, so there's white space between the
   last bit of body content and the start of the panel's green tint. */
@media (max-width: 600px) {
    /* Skip the bump on the homepage — its hero+meet+feeds layout
       already provides plenty of breathing room above the panel. */
    body:not(.home-template) .lc-footer-panel {
        margin-top: 2.8rem;
    }
    /* Bump the gap above page / listing body content on phones — the
       desktop clamp's floor of 28px reads tight on a small screen.
       Already a no-op on the homepage (no .lc-page-hero there). */
    .lc-page-hero + .gh-container,
    .page-template .lc-page-hero + main .gh-content {
        margin-top: 36px;
    }
}
.lc-footer-panel-inner {
    max-width: 760px;
    margin: 0 auto;
    padding: 0 2rem;
}
.lc-footer-panel-inner > :first-child { margin-top: 0; }
.lc-footer-panel-inner > :last-child { margin-bottom: 0; }
.lc-footer-panel-inner h1,
.lc-footer-panel-inner h2,
.lc-footer-panel-inner h3 {
    color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 80%, #000);
}

/* Source's .gh-footer carries margin-top: 12vw on non-page templates, which
   leaves a large white gap between our footer panel and the site footer.
   The panel already provides its own visual separation, so collapse the
   margin whenever the panel sits directly above the footer. */
.lc-footer-panel + .gh-footer {
    margin-top: 0;
}

/* Editor / admin shortcut links in the footer menu (helper pages and the
   Ghost admin) — fade them so they're visibly secondary to the public
   nav (Contact Us etc.) sitting alongside. Targets by href rather than
   slugified li-class so the rule survives an editor renaming the label. */
.gh-footer-menu a[href*="/assets/fen-helper.html"],
.gh-footer-menu a[href*="/assets/league-helper.html"],
.gh-footer-menu a[href*="/assets/pgn-helper.html"],
.gh-footer-menu a[href*="/ghost/"],
.gh-footer-menu a[href$="/ghost"] {
    opacity: 0.5;
}

/* The whole footer sits in a white closing band — a single 1px top
   border provides the visual separation from page content above
   (matches the old sponsor-strip pattern, just without the grey). */
.gh-footer {
    background: #fff;
    border-top: 1px solid #e8e8e8;
}

/* Source's .gh-footer-bar has margin-bottom: 100px AND a bottom border.
   We drop both and add roomy padding inside the band so the copyright
   row has breathing room above the bottom of the grey region rather
   than sitting tight against either edge. The wider column-gap means
   the row needs more horizontal space — counter-balance by stacking
   the bar earlier (≤1200px). */
.gh-footer-bar {
    margin-bottom: 0;
    padding-bottom: 40px;
    border-bottom: 0;
    column-gap: 80px;
}
@media (max-width: 1200px) {
    .gh-footer-bar {
        display: flex;
        flex-direction: column;
        gap: 20px;
    }
}

/* Sponsor strip — appears below the footer when @custom.sponsor_image is set.
   Styled as a quiet, secondary-content band so it doesn't compete with the
   main page. Image is capped at 320px tall (240px on phones) and centred,
   with a small "Sponsored by" label above so its role reads cleanly. */
.lc-sponsor {
    background: #fff;
    border-top: 1px solid #e8e8e8;
    padding: 2.6rem 0 2.8rem;
    text-align: center;
}
.lc-sponsor-inner {
    max-width: 760px;
    margin: 0 auto;
    padding: 0 2rem;
}
.lc-sponsor-label {
    display: block;
    font-size: 1.2rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: #888;
    margin-bottom: 1.1rem;
    font-weight: 600;
}
.lc-sponsor a {
    display: inline-block;
    text-decoration: none;
    line-height: 0;  /* trims phantom whitespace under the inline image */
    cursor: pointer;
}
.lc-sponsor a img {
    cursor: pointer;  /* some browsers don't inherit the anchor's pointer
                         cursor onto the inner image; force it explicitly */
}
.lc-sponsor img {
    max-width: 100%;
    width: auto;
    height: auto;
    border-radius: 6px;
    box-shadow: 0 2px 10px rgba(0, 0, 0, 0.07);
    transition: transform 0.15s, box-shadow 0.15s;
}
/* External-link marker. JS in default.hbs adds .lc-external-link to any
   <a> inside post / page body or the footer panel whose origin differs
   from the current page. A small superscript "↗" glyph is appended so
   visitors can see at a glance which clicks leave the site. */
a.lc-external-link::after {
    content: " \2197";  /* ↗ NORTH EAST ARROW */
    font-size: 0.8em;
    margin-left: 0.1em;
    /* Don't underline the glyph — keep the dotted underline scoped to
       the visible text only. */
    text-decoration: none;
    display: inline-block;
}

/* Links inside the sponsor label — match the body's dotted-underline
   treatment so they read consistently as click affordances. The sponsor
   logo's own <a> wrapper is styled separately below and unaffected. */
.lc-sponsor-label a {
    color: var(--ghost-accent-color, #2e7d32);
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
    transition: color 0.15s, text-decoration-style 0.15s;
}
.lc-sponsor-label a:hover {
    text-decoration-style: solid;
}

/* Size variants — set via @custom.sponsor_size in admin. Medium is default. */
.lc-sponsor-small  img { max-height: 100px; }
.lc-sponsor-medium img { max-height: 320px; }
.lc-sponsor-large  img { max-height: 480px; }

.lc-sponsor a:hover img {
    transform: translateY(-1px);
    box-shadow: 0 4px 14px rgba(0, 0, 0, 0.12);
}
@media (max-width: 600px) {
    .lc-sponsor { padding: 2rem 0 2.2rem; }
    .lc-sponsor-small  img { max-height: 80px; }
    .lc-sponsor-medium img { max-height: 240px; }
    .lc-sponsor-large  img { max-height: 340px; }
}

/* Numbered pagination — Ghost's {{pagination}} helper renders:
       <nav class="pagination" role="navigation">
         <a class="newer-posts" href="…">Newer Posts</a>
         <span class="page-number">Page 2 of 12</span>
         <a class="older-posts" href="…">Older Posts</a>
       </nav>
   Source ships no styling for this since it uses infinite-scroll. */
.pagination {
    display: flex;
    justify-content: center;
    align-items: center;
    gap: 1.6rem;
    margin: 4rem auto 5rem;
    max-width: 720px;
    padding: 0 2rem;
    font-size: 1.6rem;
}
.pagination .page-number {
    color: #6b6b6b;
    flex: 1;
    text-align: center;
    font-variant-numeric: tabular-nums;
}
.pagination a {
    text-decoration: none;
    color: var(--ghost-accent-color, #2e7d32);
    font-weight: 600;
    padding: 0.7rem 1.4rem;
    border: 1px solid var(--ghost-accent-color, #2e7d32);
    border-radius: 6px;
    transition: background 0.15s, color 0.15s;
}
.pagination a:hover {
    background: var(--ghost-accent-color, #2e7d32);
    color: #fff;
}
.pagination .newer-posts { order: 1; }
.pagination .page-number { order: 2; }
.pagination .older-posts { order: 3; }

/* Tag chips at the foot of each post. Uses Ghost's {{foreach tags}} which
   skips internal (`#`-prefixed) tags by default, so #imported-from-wp etc.
   stay hidden. */
.lc-post-tags {
    display: flex;
    flex-wrap: wrap;
    gap: 0.6rem;
    margin: 3rem 0 1rem;
    padding-top: 1.6rem;
    border-top: 1px solid #e8e8e8;
}
.lc-post-tag {
    display: inline-block;
    padding: 0.4rem 1rem;
    font-size: 1.4rem;
    font-weight: 500;
    text-decoration: none;
    color: var(--ghost-accent-color, #2e7d32);
    background: rgba(46, 125, 50, 0.08);
    border-radius: 999px;
    transition: background 0.15s, color 0.15s;
}
.lc-post-tag:hover {
    background: var(--ghost-accent-color, #2e7d32);
    color: #fff;
}

/* Prev/next within the same primary tag, rendered at the bottom of a post.
   Width and horizontal alignment come from the parent gh-canvas wrapper,
   which Source uses to place children in the 720px main column. */
.lc-post-nav {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1.6rem;
    margin: 4rem 0 5rem;
}
.lc-post-nav:empty { display: none; }
.lc-post-nav-link {
    display: block;
    padding: 1.6rem 1.8rem;
    border: 1px solid #dde1e3;
    border-radius: 8px;
    text-decoration: none;
    color: inherit;
    transition: border-color 0.15s, transform 0.15s, background 0.15s;
}
.lc-post-nav-link:hover {
    border-color: var(--ghost-accent-color, #2e7d32);
    transform: translateY(-2px);
}
.lc-post-nav-direction {
    display: block;
    font-size: 1.3rem;
    font-weight: 600;
    color: var(--ghost-accent-color, #2e7d32);
    text-transform: uppercase;
    letter-spacing: 0.04em;
    margin-bottom: 0.4em;
}
.lc-post-nav-title {
    display: block;
    font-size: 1.7rem;
    font-weight: 600;
    line-height: 1.3;
    color: #2a2a2a;
}
.lc-post-nav-prev { grid-column: 1; }
.lc-post-nav-next {
    grid-column: 2;
    text-align: right;
}
@media (max-width: 600px) {
    .lc-post-nav { grid-template-columns: 1fr; }
    .lc-post-nav-prev,
    .lc-post-nav-next {
        grid-column: 1;
        text-align: left;
    }
}

/* Featured posts — same layout as a regular post, but boxed inside a
   soft-green border with a "★ Featured post" banner at the top. The
   horizontal divider between posts stays in place (between the box
   and the next post), separated from the box by a small gap. */

/* Shared banner appearance — used for both the listing card and the
   homepage feed card. Default state is dark grey; the green accent
   flips in on hover (see hover rules below). The transition smooths
   the colour change. */
.lc-featured-banner,
.lc-feed-featured-badge {
    display: block;
    background: #555;
    color: #fff;
    font-size: 1.2rem;
    font-weight: 600;
    letter-spacing: 0.04em;
    padding: 0.4rem 1rem;
    text-align: left;
    border-radius: 6px 6px 0 0;
    transition: background-color 0.15s;
}

/* Listing cards (Match Reports / News / tag archives). Border wraps
   the whole article; banner sits flush at the top. NO overflow:hidden
   here — Source draws the inter-card horizontal divider via
   .gh-card::before placed in the gap above the NEXT card, which a
   clipping ancestor would hide. The banner's own top border-radius
   handles the rounded corners. The .gh-card-link below the banner
   gets explicit padding so content doesn't butt against the border;
   the banner stays edge-to-edge because it's a SIBLING of the link,
   not inside it. */
.gh-card.featured {
    border: 1px solid #777;
    border-radius: 6px;
    margin-bottom: 1.2rem;        /* gap before the next-card divider */
    transition: border-color 0.15s;
}
.gh-card.featured .gh-card-link {
    padding: 1.4rem;
}
.gh-card.featured:hover { border-color: #4caf50; }
.gh-card.featured:hover .lc-featured-banner { background: var(--ghost-accent-color, #2e7d32); }

/* Homepage feed cards. The .lc-feed-item base style applies
   border-bottom (the divider between regular cards). For featured
   items we put the box on the inner <a> and add padding-bottom to the
   <li> so the divider is offset from the box by a small gap. The
   compound `.lc-feed-item.lc-feed-item-featured` selector lifts
   specificity above home.css's `.lc-feed-item a` so our padding wins
   over the base shorthand. */
.lc-feed-item.lc-feed-item-featured > a {
    border: 1px solid #777;
    border-radius: 6px;
    padding: 1.4rem;
    transition: border-color 0.15s;
}
.lc-feed-item.lc-feed-item-featured > a:hover { border-color: #4caf50; }
.lc-feed-item.lc-feed-item-featured > a:hover .lc-feed-featured-badge {
    background: var(--ghost-accent-color, #2e7d32);
}
.lc-feed-item.lc-feed-item-featured {
    padding-top: 0.8rem;
    padding-bottom: 2rem;
}
.lc-feed-item.lc-feed-item-featured .lc-feed-featured-badge {
    margin: -1.4rem -1.4rem 0.9rem;
}

/* Single post page — small "★ Featured post" marker shown inline next
   to the post's tag eyebrow (e.g. "NEWS  ★ Featured post"). The tag
   and the mark are siblings inside an .lc-eyebrow-row wrapper so they
   share a single grid row inside .gh-canvas. The mark itself is plain
   inline text — no border, no badge styling. */
.lc-eyebrow-row {
    display: block;
    margin-bottom: 12px;
}
.lc-featured-mark {
    margin-left: 1.4em;          /* breathing room from tag */
    font-size: 1.3rem;
    font-weight: 500;
    letter-spacing: 0.01em;
    text-transform: uppercase;
    color: #777;
}
.lc-featured-mark-star {
    margin-right: 0.25em;        /* tighter gap before "Featured post" */
}
/* Over a feature-image hero the surrounding tag eyebrow is white. Match
   the mark to that, slightly muted so it doesn't compete with the tag. */
.lc-page-hero .lc-featured-mark { color: rgba(255, 255, 255, 0.85); }

/* Listings (Match Reports, News, tag archives) — narrow the body grid to
   the same width as standard pages so the post cards don't feel
   stretched. Source's container is a 16-col grid where the main column
   takes cols 3-14, so capping the OUTER width alone leaves the actual
   content at only 12/16 of that. We do both: cap the inner container
   to --content-width AND override .gh-main to fill the full container
   so the post list ends up at exactly --content-width (matches body
   text on regular pages). The page hero stays full-bleed (outside
   this selector). */
.gh-container.is-list .gh-container-inner {
    max-width: var(--content-width, 720px);
}
.gh-container.is-list:not(.has-sidebar) :is(.gh-main, .gh-more, .gh-container-title) {
    grid-column: 1 / -1;
}

/* Author avatar bubble.
   Source's source.css sizes .gh-article-author-image > a as a 56x56
   round bubble (img/svg are position:absolute inset:0 inside it).
   We removed the <a> when disabling author archive pages, replacing
   it with a <span>. This mirrors source.css's `a` rule onto `span`
   so the bubble keeps its shape. */
.gh-article-author-image span {
    background-color: var(--color-light-gray);
    border: 3px solid var(--background-color);
    border-radius: 50%;
    height: 56px;
    margin: 0 -8px;
    overflow: hidden;
    position: relative;
    width: 56px;
}
.gh-article-author-image span:first-child { z-index: 10; }
.gh-article-author-image span:nth-child(2) { z-index: 9; }
.gh-article-author-image span:nth-child(3) { z-index: 8; }

/* Bookmark card: thumbnails for internal links are shown when the
   linked post has a real feature_image, and hidden when Ghost falls back
   to the author's profile_image (i.e. when feature_image is null).
   Detection runs at page load via the Content API — see the inline
   script in default.hbs. CSS just provides the hidden state. */
.kg-bookmark-card.lc-no-feature-image .kg-bookmark-thumbnail { display: none; }

/* Bookmark card: hide the human author name. Counter-intuitively, the
   author of the linked post lives in .kg-bookmark-publisher (Ghost uses
   .kg-bookmark-author for the *site* name). Hiding the whole span
   also removes the "·" separator that's a ::before pseudo on it. */
.kg-bookmark-card .kg-bookmark-publisher { display: none; }

/* Inline bold in post / page body content. Default <strong>/<b> render
   at 700 which reads too heavy against Inter's regular 400. Drop to
   650 — between semibold (600) and bold (700). Inter is loaded as a
   variable font (weight range 100–900) so non-integer steps render
   precisely. */
.gh-content :is(strong, b) { font-weight: 650; }

/* File-upload card (Ghost "File" content type): darken and thicken the
   border so the card reads as a distinct download affordance rather than
   fading into the page. Koenig's bundled CSS uses a near-invisible 1px
   border at ~8% black; we replace it with a 2px medium-grey. */
.kg-file-card.kg-card .kg-file-card-container {
    border: 1px solid #666;
}
/* Source injects 48px of top margin above any .kg-card following a
   paragraph; that's too much breathing room above a file download
   block. Trim to a tighter value. !important is needed because
   Source's adjacent-sibling selector has higher specificity than a
   single-class override. */
.gh-content .kg-file-card { margin-top: 2.4rem !important; }

/* Gallery card: by default Ghost gives it `kg-width-wide`, which puts it
   in Source's wider-than-content grid column (~960px on a 720px content
   column). We want galleries to match body width — same column as
   paragraphs and other in-flow content. */
.gh-content .kg-gallery-card.kg-width-wide,
.gh-content .kg-gallery-card.kg-width-full {
    grid-column: main;
}

/* Custom 404 page (error-404.hbs). Sits inside the default layout
   so the visitor keeps the full nav + footer. */
.lc-error-404 {
    padding: clamp(20px, 3vw + 8px, 48px) 0 clamp(28px, 4vw + 12px, 64px);
}
.lc-error-inner {
    max-width: var(--content-width, 720px);
    margin: 0 auto;
    padding: 0 2rem;
    text-align: center;
}
.lc-error-logo {
    display: block;
    width: 120px;
    height: auto;
    margin: 0 auto 2rem;
}
.lc-error-eyebrow {
    font-size: clamp(4rem, 8vw + 1rem, 8rem);
    font-weight: 700;
    line-height: 1;
    color: var(--ghost-accent-color, #2e7d32);
    margin: 0 0 0.4em;
}
.lc-error-title {
    font-size: clamp(2.6rem, 3vw + 1rem, 3.6rem);
    font-weight: 700;
    margin: 0 0 1rem;
}
.lc-error-body {
    font-size: 1.7rem;
    line-height: 1.55;
    color: #555;
    margin: 0 0 1.6rem;
}
.lc-error-links {
    list-style: none;
    padding: 0;
    margin: 0 0 2rem;
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: 0.6rem 1.4rem;
}
.lc-error-links a {
    color: var(--ghost-accent-color, #2e7d32);
    font-weight: 600;
    font-size: 1.55rem;
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
}
.lc-error-links a:hover { text-decoration-style: solid; }
.lc-error-search {
    font-size: 1.4rem;
    color: #777;
    margin: 0;
}

/* Post action button group (Send + Copy link). Sits at the right edge
   of the .gh-article-meta byline row. Class names deliberately avoid
   the word "share" so privacy/ad-blocker extensions don't strip them. */
.lc-post-actions {
    display: inline-flex;
    align-items: center;
    gap: 0.6rem;
    margin-left: auto;            /* push to right edge of meta flex row */
}
.lc-post-action {
    display: inline-flex;
    align-items: center;
    gap: 0.45em;
    padding: 0.45em 0.9em;
    border: 1px solid #666;
    border-radius: 100px;
    background: transparent;
    font-size: 1.2rem;
    font-weight: 600;
    color: #333;
    cursor: pointer;
    transition: background-color 0.15s, color 0.15s, border-color 0.15s;
    font-family: inherit;
    white-space: nowrap;
    /* These are rendered as <a> elements (not <button>) so password
       managers don't hijack the click. Reset anchor-specific defaults
       so they still look like buttons. */
    text-decoration: none;
}
.lc-post-action:hover { text-decoration: none; }
.lc-post-action:hover,
.lc-post-action-done {
    background: var(--ghost-accent-color, #2e7d32);
    border-color: var(--ghost-accent-color, #2e7d32);
    color: #fff;
}
.lc-post-action .icon {
    width: 14px;
    height: 14px;
    flex-shrink: 0;
}

/* On narrow viewports (portrait mobile) the byline row gets tight
   and the action group can crowd the author info or clip the icons.
   Wrap it onto its own line below the author + date instead. */
@media (max-width: 600px) {
    .gh-article-meta { flex-wrap: wrap; }
    .lc-post-actions {
        margin-left: 0;
        margin-top: 0.6rem;
        flex-basis: 100%;
    }
}

/* Toggle card (collapsible content): make the chevron clearly visible.
   Source / Koenig default to a thin 1px stroke in a near-transparent
   grey, which makes the affordance easy to miss. Bigger button, fatter
   stroke, body-text colour. The path-level selector wins specificity
   over Koenig's `.cls-1` rule so stroke-width actually takes effect. */
.kg-toggle-card .kg-toggle-card-icon { width: 24px; height: 24px; }
.kg-toggle-card .kg-toggle-card-icon svg {
    width: 100%;
    height: 100%;
    fill: none;
}
.kg-toggle-card .kg-toggle-card-icon svg path,
.kg-toggle-card .kg-toggle-card-icon svg path.cls-1 {
    stroke: var(--color-darker-gray, #15171a);
    stroke-width: 2;
    stroke-linecap: round;
    stroke-linejoin: round;
    fill: none;
}

/* ──── /join-us/ FAQ section ──────────────────────────────────────────
   Appears below the Ghost-authored page content via page-join-us.hbs.
   Each question is a collapsed <details> accordion so the section is
   visually unobtrusive — readers scan the question list, click to
   expand any that interest them. Content remains visible-by-default
   enough to back the FAQPage JSON-LD. */
.lc-faq {
    margin-top: 3em;
}
.lc-faq > h2 { margin-bottom: 0.8em; }

.lc-faq-item {
    border-bottom: 1px solid var(--lc-border, rgba(0, 0, 0, 0.08));
    padding: 0.6em 0;
}
.lc-faq-item > summary {
    cursor: pointer;
    list-style: none;             /* hide default disclosure triangle */
    font-weight: 600;
    padding: 0.2em 0 0.2em 1.4em;
    position: relative;
    transition: color 0.15s;
}
.lc-faq-item > summary::-webkit-details-marker { display: none; }
.lc-faq-item > summary::before {
    /* Custom chevron pointing right when closed, down when open. */
    content: '';
    position: absolute;
    left: 0;
    top: 0.55em;
    width: 0.55em;
    height: 0.55em;
    border-right: 2px solid currentColor;
    border-bottom: 2px solid currentColor;
    transform: rotate(-45deg);
    transition: transform 0.15s;
}
.lc-faq-item[open] > summary::before { transform: rotate(45deg); top: 0.45em; }
.lc-faq-item > summary:hover { color: var(--lc-accent-dark, #1b5e20); }
.lc-faq-item > p {
    margin: 0.6em 0 0.2em;
    padding-left: 1.4em;
}

/* === blocks.css === */
/* Layout helpers for use inside Ghost posts and pages.
   Drop one of these wrappers into an HTML card in the Koenig editor.
   Children flow into equal columns; on narrow screens they stack. */

.lc-cols-2,
.lc-cols-3,
.lc-cols-4 {
    display: grid;
    gap: 2.4rem;
    margin: 2.4rem 0;
    text-align: left;  /* reset any inherited center-align (e.g. inside home-welcome strip) */
}

.lc-cols-2 { grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)); }
.lc-cols-3 { grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); }
.lc-cols-4 { grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); }

/* Each direct child is a column. min-width: 0 prevents long words from
   forcing the grid wider than the container. */
.lc-cols-2 > *,
.lc-cols-3 > *,
.lc-cols-4 > * {
    min-width: 0;
}

/* Trim the first/last child's vertical margin so column tops and bottoms
   line up cleanly regardless of which heading or paragraph they start with. */
.lc-cols-2 > * > :first-child,
.lc-cols-3 > * > :first-child,
.lc-cols-4 > * > :first-child { margin-top: 0; }

.lc-cols-2 > * > :last-child,
.lc-cols-3 > * > :last-child,
.lc-cols-4 > * > :last-child { margin-bottom: 0; }

/* Embedded maps (Google Maps / OpenStreetMap iframes).
   Wrap the iframe in <div class="lc-map">…</div> so it's responsive
   and matches the rest of the post styling. */
.lc-map {
    margin: 2rem 0;
    aspect-ratio: 16 / 10;
    overflow: hidden;
    border-radius: 8px;
    border: 1px solid #dde1e3;
}
.lc-map iframe {
    width: 100%;
    height: 100%;
    border: 0;
    display: block;
}

/* === chess.css === */
/* Lichfield chess components — diagrams, puzzles, league tables.
   Loaded unconditionally by default.hbs; the matching JS bails early
   when no .chess-diagram / .chess-puzzle / .league-table is on the page. */

.chess-diagram-wrapper,
.chess-puzzle-wrapper {
    margin: 1.5em auto;
    width: 100%;
    max-width: 480px;
    /* Defensively reset min-width: grid items default to min-content which
       can collapse the wrapper when aspect-ratio is set on a child. */
    min-width: 0;
}

/* --- Board themes -------------------------------------------------------- */
/* The default brown theme comes from chessground.brown.css. Each named
   theme below overrides cg-board with a 2×2 tiled SVG of two squares
   (one transparent, one filled). 25% tile size ⇒ tiled 4× = 8×8 squares.
   Apply via class chess-theme-<name> on the wrapper (set by chess.js
   from the data-theme attribute). */
.chess-theme-blue cg-board {
    background-color: #dee3e6;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 2 2' shape-rendering='crispEdges'%3E%3Cpath fill='%238ca2ad' d='M1 0h1v1H1zM0 1h1v1H0z'/%3E%3C/svg%3E");
    background-size: 25% 25%;
}
.chess-theme-green cg-board {
    background-color: #ffffdd;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 2 2' shape-rendering='crispEdges'%3E%3Cpath fill='%23769656' d='M1 0h1v1H1zM0 1h1v1H0z'/%3E%3C/svg%3E");
    background-size: 25% 25%;
}
.chess-theme-grey cg-board {
    background-color: #ebebeb;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 2 2' shape-rendering='crispEdges'%3E%3Cpath fill='%23808080' d='M1 0h1v1H1zM0 1h1v1H0z'/%3E%3C/svg%3E");
    background-size: 25% 25%;
}
.chess-theme-wood cg-board {
    background-color: #d8b074;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 2 2' shape-rendering='crispEdges'%3E%3Cpath fill='%237a4a1f' d='M1 0h1v1H1zM0 1h1v1H0z'/%3E%3C/svg%3E");
    background-size: 25% 25%;
}
.chess-theme-pink cg-board {
    background-color: #fde6f1;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 2 2' shape-rendering='crispEdges'%3E%3Cpath fill='%23c75d8e' d='M1 0h1v1H1zM0 1h1v1H0z'/%3E%3C/svg%3E");
    background-size: 25% 25%;
}

/* --- Piece sets ---------------------------------------------------------- */
/* Default pieces (Cburnett) come from chessground.cburnett.css. Each named
   set below pulls SVGs from Lichess's CDN. Apply via class
   chess-pieces-<name> on the wrapper (set by chess.js from data-pieces). */
.chess-pieces-alpha .cg-wrap piece.pawn.white   { background-image: url('https://lichess1.org/assets/piece/alpha/wP.svg'); }
.chess-pieces-alpha .cg-wrap piece.pawn.black   { background-image: url('https://lichess1.org/assets/piece/alpha/bP.svg'); }
.chess-pieces-alpha .cg-wrap piece.knight.white { background-image: url('https://lichess1.org/assets/piece/alpha/wN.svg'); }
.chess-pieces-alpha .cg-wrap piece.knight.black { background-image: url('https://lichess1.org/assets/piece/alpha/bN.svg'); }
.chess-pieces-alpha .cg-wrap piece.bishop.white { background-image: url('https://lichess1.org/assets/piece/alpha/wB.svg'); }
.chess-pieces-alpha .cg-wrap piece.bishop.black { background-image: url('https://lichess1.org/assets/piece/alpha/bB.svg'); }
.chess-pieces-alpha .cg-wrap piece.rook.white   { background-image: url('https://lichess1.org/assets/piece/alpha/wR.svg'); }
.chess-pieces-alpha .cg-wrap piece.rook.black   { background-image: url('https://lichess1.org/assets/piece/alpha/bR.svg'); }
.chess-pieces-alpha .cg-wrap piece.queen.white  { background-image: url('https://lichess1.org/assets/piece/alpha/wQ.svg'); }
.chess-pieces-alpha .cg-wrap piece.queen.black  { background-image: url('https://lichess1.org/assets/piece/alpha/bQ.svg'); }
.chess-pieces-alpha .cg-wrap piece.king.white   { background-image: url('https://lichess1.org/assets/piece/alpha/wK.svg'); }
.chess-pieces-alpha .cg-wrap piece.king.black   { background-image: url('https://lichess1.org/assets/piece/alpha/bK.svg'); }

.chess-pieces-staunty .cg-wrap piece.pawn.white   { background-image: url('https://lichess1.org/assets/piece/staunty/wP.svg'); }
.chess-pieces-staunty .cg-wrap piece.pawn.black   { background-image: url('https://lichess1.org/assets/piece/staunty/bP.svg'); }
.chess-pieces-staunty .cg-wrap piece.knight.white { background-image: url('https://lichess1.org/assets/piece/staunty/wN.svg'); }
.chess-pieces-staunty .cg-wrap piece.knight.black { background-image: url('https://lichess1.org/assets/piece/staunty/bN.svg'); }
.chess-pieces-staunty .cg-wrap piece.bishop.white { background-image: url('https://lichess1.org/assets/piece/staunty/wB.svg'); }
.chess-pieces-staunty .cg-wrap piece.bishop.black { background-image: url('https://lichess1.org/assets/piece/staunty/bB.svg'); }
.chess-pieces-staunty .cg-wrap piece.rook.white   { background-image: url('https://lichess1.org/assets/piece/staunty/wR.svg'); }
.chess-pieces-staunty .cg-wrap piece.rook.black   { background-image: url('https://lichess1.org/assets/piece/staunty/bR.svg'); }
.chess-pieces-staunty .cg-wrap piece.queen.white  { background-image: url('https://lichess1.org/assets/piece/staunty/wQ.svg'); }
.chess-pieces-staunty .cg-wrap piece.queen.black  { background-image: url('https://lichess1.org/assets/piece/staunty/bQ.svg'); }
.chess-pieces-staunty .cg-wrap piece.king.white   { background-image: url('https://lichess1.org/assets/piece/staunty/wK.svg'); }
.chess-pieces-staunty .cg-wrap piece.king.black   { background-image: url('https://lichess1.org/assets/piece/staunty/bK.svg'); }

/* --- Floated alignment --------------------------------------------------- */
/* When data-align="left|right" is set, the board floats inside the same
   HTML card so subsequent text in that card wraps around it. Ghost wraps
   each editor block in its own container, so float doesn't escape into
   later paragraph blocks — diagram + wrapping prose must share one card. */
.chess-diagram-wrapper.chess-align-left,
.chess-puzzle-wrapper.chess-align-left {
    float: left;
    margin: 0.4em 1.6em 0.8em 0;
    max-width: 360px;  /* default size when floated */
}

.chess-diagram-wrapper.chess-align-right,
.chess-puzzle-wrapper.chess-align-right {
    float: right;
    margin: 0.4em 0 0.8em 1.6em;
    max-width: 360px;
}

/* --- Explicit sizing ----------------------------------------------------- */
/* Listed after the align rules so size always wins when both are set. */
.chess-diagram-wrapper.chess-size-small,
.chess-puzzle-wrapper.chess-size-small {
    max-width: 240px;
}
.chess-diagram-wrapper.chess-size-medium,
.chess-puzzle-wrapper.chess-size-medium {
    max-width: 360px;
}
.chess-diagram-wrapper.chess-size-large,
.chess-puzzle-wrapper.chess-size-large {
    max-width: 640px;
}

/* On phones, drop the float so boards never get squashed in a narrow column. */
@media (max-width: 600px) {
    .chess-diagram-wrapper.chess-align-left,
    .chess-diagram-wrapper.chess-align-right,
    .chess-puzzle-wrapper.chess-align-left,
    .chess-puzzle-wrapper.chess-align-right {
        float: none;
        margin: 1.5em auto;
        max-width: 100%;
    }
}

/* Grid: 18px rank-label column + board, 18px file-label row below. The grid
   is square overall, so the board cell is (W-18)x(H-18) and stays square. */
.chess-board-grid {
    display: grid;
    grid-template-columns: 18px 1fr;
    grid-template-rows: 1fr 18px;
    aspect-ratio: 1 / 1;
    width: 100%;
}

.chess-board-grid .cg-wrap {
    grid-column: 2;
    grid-row: 1;
    width: 100%;
    height: 100%;
}

.chess-coords-corner {
    grid-column: 1;
    grid-row: 2;
}

.chess-coords {
    display: flex;
    align-items: center;
    justify-content: space-around;
    font-size: 11px;
    font-weight: 600;
    color: #5a5a5a;
    user-select: none;
}

.chess-coords-ranks {
    grid-column: 1;
    grid-row: 1;
    flex-direction: column;
}

.chess-coords-files {
    grid-column: 2;
    grid-row: 2;
    flex-direction: row;
}

.chess-diagram-caption,
.chess-puzzle-caption {
    text-align: center;
    font-size: 0.95em;
    color: #6b6b6b;
    margin-top: 0.5em;
    font-style: italic;
    line-height: 1.35;
}

.chess-puzzle-controls {
    display: flex;
    gap: 0.5em;
    justify-content: center;
    margin-top: 0.75em;
}

.chess-puzzle-controls button {
    font: inherit;
    padding: 0.4em 0.9em;
    border: 1px solid currentColor;
    background: transparent;
    border-radius: 4px;
    cursor: pointer;
}

.chess-puzzle-solution {
    margin-top: 0.75em;
    padding: 0.6em 0.8em;
    border-left: 3px solid #4a8;
    background: rgba(74, 136, 136, 0.06);
    font-family: ui-monospace, "SF Mono", Menlo, monospace;
    font-size: 0.9em;
}

.league-table-wrapper {
    /* Slightly bigger top margin so the table breathes away from the
       paragraph above it. Applies whether or not a title is rendered,
       since the wrapper is always the outer element. */
    margin: 1.2em 0 0.6em;
    overflow-x: auto;
}

/* Reserve space for the un-rendered <div class="league-table"> placeholder.
   Sized to match the height that a collapsed <details> renders at —
   roughly summary line-height (1.25em title × 1.2 ≈ 30px) — so chess.js
   replacing the placeholder is approximately layout-neutral. The page's
   scrollbar gutter is reserved via html { scrollbar-gutter: stable } in
   branding.css, so even minor residual shifts don't change the viewport
   width and trigger vw-based clamps in the hero. */
.league-table[data-league] {
    display: block;
    min-height: 32px;
    margin: 1.2em 0 0.6em;
}
.league-table-placeholder { color: #888; min-height: 24px; }

.league-table-wrapper table {
    /* min-width (not width) so the table can grow wider than its wrapper on
       narrow viewports; the wrapper's overflow-x:auto then provides a
       horizontal scroll. With plain width:100% the table was being forced
       into the viewport and the team column got squeezed to single-character
       width on phones. */
    min-width: 100%;
    border-collapse: collapse;
    font-size: 0.95em;
}

.league-table-wrapper th,
.league-table-wrapper td {
    padding: 0.4em 0.6em;
    text-align: left;
    border-bottom: 1px solid rgba(0, 0, 0, 0.08);
    /* Stop cells wrapping. On narrow viewports the table grows wider than the
       wrapper and the wrapper's overflow-x:auto kicks in, giving a horizontal
       scroll. Without this, "played"/"points"/"drawn" etc. wrap one letter
       per line because the columns get squeezed below their text width. */
    white-space: nowrap;
}
/* The team column is the only one that can legitimately need to wrap (long
   club names). It's the second column in every preset, so override it back
   to normal wrapping. */
.league-table-wrapper th:nth-child(2),
.league-table-wrapper td:nth-child(2) {
    white-space: normal;
}

.league-table-wrapper th {
    font-weight: 600;
    background: rgba(0, 0, 0, 0.03);
}

.league-table-wrapper tr.is-lichfield {
    font-weight: 600;
    background: rgba(255, 200, 0, 0.08);
}

.league-table-meta {
    /* !important needed to beat Source's .gh-content content-spacing rule
       which injects 48px of top margin onto any non-card/non-table that
       follows a table. */
    margin-top: 0.6em !important;
    font-size: 0.8em;
    color: #888;
    text-align: right;
}

/* Inside the league-table block, suppress Source's 48px content-spacing
   gap between the title (summary or h3) and the table itself. We use
   !important rather than chasing specificity because the source rule
   targets the table directly with adjacent-sibling logic that's awkward
   to override otherwise. 0.6em gives a small but visible breathing room
   below the title. */
.gh-content .league-table-wrapper table { margin-top: 0.8em !important; }

.league-table-error {
    padding: 0.8em 1em;
    border-left: 3px solid #c44;
    background: rgba(196, 68, 68, 0.06);
    color: #933;
    font-size: 0.95em;
}
/* Inline retry button used by .league-table-error in the game viewer's
   failure state. */
.league-table-error .chess-game-retry {
    margin-left: 0.6em;
    padding: 0.2em 0.7em;
    font: inherit;
    font-size: 0.9em;
    background: #fff;
    border: 1px solid #c44;
    border-radius: 4px;
    color: #933;
    cursor: pointer;
}
.league-table-error .chess-game-retry:hover {
    background: #fbeaea;
}

.league-table-title {
    margin: 0 0 0.6em;
    font-size: 1.25em;
    font-weight: 600;
    color: var(--ghost-accent-color, #2e7d32);
    line-height: 1.2;
}

/* Collapsible mode — the league title is rendered as <summary> inside a
   <details> element so readers can toggle the table by clicking it.
   The default browser disclosure triangle is hidden in favour of a custom
   chevron drawn from CSS borders, which rotates 90° when the table opens. */
.league-table-collapsible > summary.league-table-title {
    cursor: pointer;
    list-style: none;          /* Firefox / standard */
    user-select: none;
    /* Spacing matches the non-collapsible h3 so layouts stay consistent. */
    display: flex;
    align-items: center;
    gap: 0.5em;
}
.league-table-collapsible > summary.league-table-title::-webkit-details-marker {
    display: none;             /* Safari / Chrome legacy */
}
.league-table-collapsible > summary.league-table-title::before {
    content: "";
    flex: 0 0 auto;
    width: 0.45em;
    height: 0.45em;
    border-right: 0.14em solid currentColor;
    border-bottom: 0.14em solid currentColor;
    transform: rotate(-45deg);
    transition: transform 0.2s ease;
    margin-bottom: 0.15em;     /* optical centring against the title cap-height */
}
.league-table-collapsible[open] > summary.league-table-title::before {
    transform: rotate(45deg);
}
/* Subtle hover treatment so the click affordance isn't only the cursor. */
.league-table-collapsible > summary.league-table-title:hover {
    color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 75%, #000);
}

.league-table-narrow {
    max-width: 420px;
    margin-left: auto;
    margin-right: auto;
}
.league-table-narrow .league-table-title {
    font-size: 1.1em;
}
.league-table-narrow table {
    font-size: 0.88em;
}
.league-table-narrow th,
.league-table-narrow td {
    padding: 0.32em 0.5em;
}

/* Ellipsis row separating top-N from a Lichfield-out-of-limit row. */
.league-table-wrapper tr.league-table-gap td {
    text-align: center;
    color: #aaa;
    border-bottom: 1px dashed rgba(0, 0, 0, 0.12);
    padding: 0.15em 0.4em;
    font-size: 0.85em;
}

/* --- Interactive PGN game viewer ---------------------------------------- */
/* Mobile-first stack; on wider viewports the move list sits beside the
   board. Variants on .chess-game-wrapper share the size/align/theme hooks
   from .chess-diagram-wrapper. */

.chess-game-wrapper {
    margin: 1.5em auto;
    width: 100%;
    max-width: 720px;
    min-width: 0;
    font-size: 0.95em;
    color: #2a2a2a;
}

.chess-game-loading {
    color: #888;
    text-align: center;
    padding: 2em 1em;
    font-style: italic;
}

.chess-game-title {
    margin: 0 0 0.4em;
    font-size: 1.25em;
    font-weight: 600;
    color: var(--ghost-accent-color, #2e7d32);
    line-height: 1.2;
}

/* Collapsible mode (mirrors the league-table-collapsible pattern). */
.chess-game-collapsible > summary.chess-game-title {
    cursor: pointer;
    list-style: none;
    user-select: none;
    display: flex;
    align-items: center;
    gap: 0.5em;
}
.chess-game-collapsible > summary.chess-game-title::-webkit-details-marker { display: none; }
.chess-game-collapsible > summary.chess-game-title::before {
    content: "";
    flex: 0 0 auto;
    width: 0.45em;
    height: 0.45em;
    border-right: 0.14em solid currentColor;
    border-bottom: 0.14em solid currentColor;
    transform: rotate(-45deg);
    transition: transform 0.2s ease;
    margin-bottom: 0.15em;
}
.chess-game-collapsible[open] > summary.chess-game-title::before {
    transform: rotate(45deg);
}

.chess-game-meta {
    color: #5a5a5a;
    font-size: 0.92em;
    margin-bottom: 0.6em;
    line-height: 1.5;
}
.chess-game-meta .chess-game-result {
    font-weight: 600;
    color: #2a2a2a;
}

.chess-game-body {
    display: grid;
    grid-template-columns: 1fr;
    gap: 0.7em;
}

.chess-game-board {
    /* Reuse the diagram aspect-ratio grid; full available width. */
    width: 100%;
    margin: 0 auto;
    max-width: 480px;
}

.chess-game-controls {
    display: flex;
    align-items: center;
    gap: 0.4em;
    flex-wrap: wrap;
    justify-content: center;
}
.chess-game-btn {
    font: inherit;
    padding: 0.35em 0.7em;
    min-width: 2.4em;
    /* Flex-centre the glyph. Without this the button uses inline-baseline
       layout, which puts ◀/▶ (centred on the baseline) and ⇤/⇥ (which sit
       lower than baseline) at visibly different vertical positions inside
       their identical-sized buttons. */
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border: 1px solid #c8c8c8;
    background: #fff;
    border-radius: 4px;
    cursor: pointer;
    line-height: 1;
    color: #2a2a2a;
    transition: background 0.12s, border-color 0.12s;
}
.chess-game-btn:hover:not(:disabled) {
    background: #f3f3f3;
    border-color: #999;
}
.chess-game-btn:disabled {
    opacity: 0.4;
    cursor: not-allowed;
}
/* Visually scale the start/end glyphs (⇤ / ⇥) without affecting the
   button's own size. transform:scale doesn't take part in layout, so
   the button box stays identical to the prev/next buttons; only the
   glyph is rendered larger. */
.chess-game-glyph-lg {
    display: inline-block;
    transform: scale(1.4);
    transform-origin: center;
    position: relative;
}
/* Mobile (iOS Safari especially) renders ⇤ / ⇥ with the ink-box
   sitting lower in the line-box than the filled triangles ◀ / ▶, so
   flex-centering puts them visually below the triangles. Desktop
   system fonts don't have this offset, so we scope the correction to
   the mobile breakpoint only — applying it everywhere knocks desktop
   out of alignment. */
@media (max-width: 600px) {
    .chess-game-glyph-lg { top: -2px; }
}
.chess-game-btn.chess-game-copy {
    /* Set apart from the playback group; nudged right via auto margin. */
    margin-left: auto;
    font-size: 0.88em;
    padding: 0.35em 0.8em;
    color: var(--ghost-accent-color, #2e7d32);
    border-color: color-mix(in srgb, var(--ghost-accent-color, #2e7d32) 35%, #ccc);
}
.chess-game-position {
    font-variant-numeric: tabular-nums;
    color: #5a5a5a;
    font-size: 0.9em;
    padding: 0 0.4em;
    min-width: 4em;
    text-align: center;
}

.chess-game-moves {
    list-style: none;
    margin: 0;
    padding: 0.4em 0;
    border-top: 1px solid #e5e5e5;
    max-height: 320px;
    overflow-y: auto;
    line-height: 1.6;
}
.chess-game-moves li {
    display: flex;
    align-items: baseline;
    gap: 0.2em;
    padding: 0.05em 0.3em;
}
.chess-game-movenum {
    color: #888;
    font-size: 0.88em;
    min-width: 2.7em;            /* fits "25…" or "100." */
    text-align: right;
    padding-right: 0.3em;
    user-select: none;
    font-variant-numeric: tabular-nums;
}
.chess-game-san {
    font: inherit;
    background: transparent;
    border: 0;
    padding: 0.05em 0.4em;
    border-radius: 3px;
    cursor: pointer;
    color: inherit;
    font-family: ui-monospace, "SF Mono", Menlo, monospace;
    font-size: 0.95em;
}
.chess-game-san:hover {
    background: rgba(0, 0, 0, 0.06);
}
.chess-game-san.is-active {
    background: var(--ghost-accent-color, #2e7d32);
    color: #fff;
    font-weight: 600;
}
.chess-game-san:focus-visible {
    outline: 2px solid var(--ghost-accent-color, #2e7d32);
    outline-offset: 1px;
}

/* Desktop: move list lives to the right of the board. */
@media (min-width: 720px) {
    .chess-game-body {
        grid-template-columns: minmax(0, 480px) minmax(0, 1fr);
        grid-template-areas:
            "meta     meta"
            "board    moves"
            "controls moves";
        column-gap: 1.4em;
        row-gap: 0.6em;
        align-items: start;
    }
    .chess-game-meta     { grid-area: meta; }
    .chess-game-board    { grid-area: board; max-width: none; }
    .chess-game-controls { grid-area: controls; justify-content: flex-start; }
    .chess-game-moves    {
        grid-area: moves;
        border-top: 0;
        border-left: 1px solid #e5e5e5;
        padding: 0 0 0 0.7em;
        max-height: 460px;
    }
    .chess-game-btn.chess-game-copy {
        /* Auto-margin pushes Copy to the right edge of the controls row. */
        margin-left: auto;
    }
}

/* Size variants, same dial as diagrams/puzzles. */
.chess-game-wrapper.chess-size-small  { max-width: 520px; }
.chess-game-wrapper.chess-size-medium { max-width: 720px; }
.chess-game-wrapper.chess-size-large  { max-width: 920px; }

/* Align variants — same float pattern as diagrams. */
.chess-game-wrapper.chess-align-left {
    float: left;
    margin: 0.4em 1.6em 0.8em 0;
    max-width: 520px;
}
.chess-game-wrapper.chess-align-right {
    float: right;
    margin: 0.4em 0 0.8em 1.6em;
    max-width: 520px;
}

@media (max-width: 600px) {
    .chess-diagram-wrapper,
    .chess-puzzle-wrapper {
        max-width: 100%;
    }
    .chess-game-wrapper,
    .chess-game-wrapper.chess-align-left,
    .chess-game-wrapper.chess-align-right {
        float: none;
        margin: 1.5em auto;
        max-width: 100%;
    }
    .chess-game-btn.chess-game-copy {
        /* Wrap Copy onto its own row on narrow screens so it doesn't sit
           awkwardly against the playback buttons. */
        flex-basis: 100%;
        margin-left: 0;
    }

    /* Mobile move list — a single horizontal-scrolling row.
       Why block + inline-flex (and not flex on the row): when the row was
       a flex container, each <li>'s baseline was determined by its own
       internal flex layout and the lis didn't align with each other —
       producing the visible up/down jitter between move pairs. As an
       inline row of inline-flex items, the lis sit on a normal text line
       and align by the standard inline baseline, which is consistent. */
    .chess-game-moves {
        display: block;
        overflow-x: auto;
        overflow-y: hidden;
        max-height: none;
        white-space: nowrap;
        padding: 0.4em 0;
        line-height: 1.9;
        /* iOS / older WebKit smooth-scroll niceties */
        -webkit-overflow-scrolling: touch;
        scroll-snap-type: x proximity;
        /* Soft fade at the right edge to hint there's more content. */
        mask-image: linear-gradient(to right, #000 calc(100% - 28px), transparent);
        -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 28px), transparent);
        /* Thinner native scrollbar where supported. */
        scrollbar-width: thin;
        scrollbar-color: rgba(0,0,0,0.25) transparent;
    }
    .chess-game-moves > li {
        display: inline-flex;
        align-items: baseline;
        gap: 0.15em;
        padding: 0;
        margin: 0 0.4em 0 0;
        scroll-snap-align: start;
    }
    .chess-game-moves > li > .chess-game-movenum {
        /* Drop the desktop's right-aligned 2.7em column — on a single
           inline row the movenum just sits next to its move. */
        min-width: 0;
        text-align: left;
        padding-right: 0.1em;
    }
    .chess-game-moves::-webkit-scrollbar { height: 4px; }
    .chess-game-moves::-webkit-scrollbar-thumb {
        background: rgba(0,0,0,0.25);
        border-radius: 2px;
    }
}

/* ============================================================
   Fixtures list (<div class="lc-fixtures">)
   Renders a chronological list of all Lichfield team fixtures
   across the leagues, grouped by month. Current month + next
   month show by default; "Show past results" toggle reveals
   earlier months.
   ============================================================ */

.lc-fixtures {
    margin: 2em 0 0;          /* slightly bigger top gap above the
                                  toggle/As-of row; no bottom margin —
                                  last month section carries that. */
}
/* Drop the last month section's bottom margin so the fixtures widget
   sits close to whatever follows it (heading / hr / next paragraph). */
.lc-fixtures .lc-fixtures-month:last-child { margin-bottom: 0.4em; }
.lc-fixtures-header {
    /* Toggle on the left, "As of" on the right, both on one row with
       their text baselines aligned. Wraps onto two rows only if the
       viewport is too narrow to fit both. */
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 1rem;
    flex-wrap: wrap;
    margin-bottom: 1.2rem;
}
.lc-fixtures-meta {
    font-size: 0.85em;
    color: #888;
}
.lc-fixtures-toggle {
    display: inline-flex;
    align-items: center;
    gap: 0.5em;
    cursor: pointer;
    user-select: none;
    font-size: 0.95em;
    color: #555;
}
.lc-fixtures-toggle input { margin: 0; }
.lc-fixtures-month {
    margin: 1.6em 0;
}
/* Same visual shape as .league-table-title above so the section headings
   on a page mixing both look consistent. */
.lc-fixtures-month-title {
    margin: 0 0 0.6em;
    font-size: 1.25em;
    font-weight: 600;
    color: var(--ghost-accent-color, #2e7d32);
    line-height: 1.2;
}
.lc-fixtures-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.95em;
}
/* Source's .gh-content adjacent-sibling rule injects 48px of top margin
   above any <table> following a non-card element. Override so the table
   sits ~0.5em under the month title. !important needed to beat the
   source selector's higher specificity. */
.gh-content .lc-fixtures-table { margin-top: 0.5em !important; }
.lc-fixtures-table th,
.lc-fixtures-table td {
    padding: 0.45em 0.6em;
    text-align: left;
    border-bottom: 1px solid rgba(0, 0, 0, 0.08);
    vertical-align: top;
    white-space: nowrap;
}
.lc-fixtures-table th {
    font-weight: 600;
    background: rgba(0, 0, 0, 0.03);
}
/* Allow the League column to wrap so long-form names
   ("Cannock & District Division 2") use two lines if needed. */
.lc-fixtures-table td.lc-fixtures-comp { white-space: normal; }
/* Score column centred. */
.lc-fixtures-table th:nth-child(4),
.lc-fixtures-table td.lc-fixtures-score {
    text-align: center;
    font-weight: 600;
}
.lc-fixtures-table td.lc-fixtures-score a {
    color: inherit;
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
}
.lc-fixtures-table td.lc-fixtures-score a:hover { text-decoration-style: solid; }
.lc-fixtures-v { color: #aaa; font-weight: 400; }
.lc-fixtures-pending { color: #c66; }
.lc-fixtures-time {
    color: #888;
    font-size: 0.85em;
    margin-left: 0.4em;
}
/* Highlight the row's Lichfield team in bold so visitors can scan
   home/away presence at a glance. */
.lc-fixtures-row.lc-fixtures-home-us td.lc-fixtures-home { font-weight: 600; }
.lc-fixtures-row.lc-fixtures-away-us td.lc-fixtures-away { font-weight: 600; }
/* Past fixtures get a slightly muted text color. */
.lc-fixtures-row-past td { color: #555; }

.lc-fixtures-loading,
.lc-fixtures-error,
.lc-fixtures-empty {
    padding: 0.8em;
    color: #888;
    text-align: center;
}
.lc-fixtures-error { color: #c44; }
.lc-fixtures-empty strong { color: #444; font-weight: 600; }

/* Desktop: show full competition name, hide the short variant. */
.lc-fixtures-comp-short { display: none; }

/* Mobile: tighten padding + allow team / competition names to wrap.
   Stack the kick-off time below the date (instead of inline beside it).
   Swap to the short competition label ("Cannock Div 2"). Tighter,
   custom column widths to give Home/Away more breathing room on small
   screens, and a smaller-but-nudged-down score font. */
@media (max-width: 600px) {
    .lc-fixtures-table td,
    .lc-fixtures-table th { padding: 0.4em 0.4em; font-size: 0.92em; }
    .lc-fixtures-table td.lc-fixtures-home,
    .lc-fixtures-table td.lc-fixtures-away,
    .lc-fixtures-table td.lc-fixtures-comp {
        white-space: normal;
    }
    .lc-fixtures-time {
        display: block;
        margin-left: 0;
    }
    .lc-fixtures-comp-full { display: none; }
    .lc-fixtures-comp-short { display: inline; }

    /* Mobile column widths: 10 + 25 + 28 + 10 + 27 = 100. */
    .lc-fixtures-table th:nth-child(1),
    .lc-fixtures-table td.lc-fixtures-date {
        width: 10%;
    }
    .lc-fixtures-table th:nth-child(2),
    .lc-fixtures-table td.lc-fixtures-comp {
        width: 25%;
    }
    .lc-fixtures-table th:nth-child(3),
    .lc-fixtures-table td.lc-fixtures-home {
        width: 28%;
    }
    .lc-fixtures-table th:nth-child(4),
    .lc-fixtures-table td.lc-fixtures-score {
        width: 10%;
        /* Smaller font so "3½ - 2½" doesn't dominate the row, plus a
           padding nudge so the smaller text doesn't hug the top of the
           cell (cells use vertical-align: top by default above). */
        font-size: 0.8em;
        padding-top: 0.7em;
    }
    .lc-fixtures-table th:nth-child(5),
    .lc-fixtures-table td.lc-fixtures-away {
        width: 27%;
    }
}

/* ---------------------------------------------------------------- */
/* Match cards                                                       */
/* ---------------------------------------------------------------- */
/* Placeholder: authors paste <div class="lc-match-card" data-fid="…">
   into a post. chess.js fills it in client-side from fixtures.json. */
.lc-match-card {
    display: block;
    margin: 1.8em 0 0.6em;
}
.lc-match-card-loading,
.lc-match-card-placeholder {
    color: #888;
    font-style: italic;
    font-size: 0.9em;
}
.lc-match-card-error {
    padding: 0.7em 0.9em;
    background: rgba(196, 68, 68, 0.07);
    border-left: 3px solid #c44;
    color: #933;
    font-size: 0.9em;
}

.lc-match-card-inner {
    border: 1px solid rgba(0, 0, 0, 0.1);
    border-radius: 6px;
    background: #fff;
    overflow: hidden;
}

/* Header bar: home  TOTAL  away + meta (league + date) */
.lc-match-card-header {
    padding: 0.8em 1em;
    background: rgba(46, 125, 50, 0.06);   /* hint of accent green */
    border-bottom: 1px solid rgba(0, 0, 0, 0.08);
}
.lc-match-card-score {
    display: flex;
    align-items: center;
    gap: 0.6em;
    font-size: 1.05em;
    line-height: 1.3;
}
.lc-match-card-team {
    flex: 1 1 0;
    min-width: 0;
    font-weight: 500;
}
.lc-match-card-team-home { text-align: right; }
.lc-match-card-team-away { text-align: left; }
.lc-match-card-team.is-us { font-weight: 700; }
.lc-match-card-total {
    flex: 0 0 auto;
    padding: 0 0.7em;
    font-weight: 700;
    font-size: 1.1em;
    color: var(--ghost-accent-color, #2e7d32);
    white-space: nowrap;
}
.lc-match-card-meta {
    margin-top: 0.35em;
    display: flex;
    justify-content: space-between;
    gap: 0.8em;
    flex-wrap: wrap;
    font-size: 0.82em;
    color: #666;
}

/* Boards table. */
.lc-match-card-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.93em;
}
/* Source's .gh-content rule injects 48px above any <table>; override so
   the boards sit flush under the header bar. */
.gh-content .lc-match-card-table { margin-top: 0 !important; }
.lc-match-card-table th,
.lc-match-card-table td {
    padding: 0.45em 0.7em;
    border-bottom: 1px solid rgba(0, 0, 0, 0.06);
    vertical-align: middle;
}
.lc-match-card-table th {
    font-weight: 600;
    background: rgba(0, 0, 0, 0.02);
    text-align: left;
    font-size: 0.95em;
}
/* Lichfield's column header stays the default text colour (the bold
   weight from .is-us elsewhere is enough emphasis on its own). */
.lc-match-card-board-h,
.lc-match-card-board { text-align: center; width: 3em; font-variant-numeric: tabular-nums; }
.lc-match-card-rating-h,
.lc-match-card-rating { text-align: center; width: 4.5em; font-variant-numeric: tabular-nums; color: #555; }
.lc-match-card-result-h,
.lc-match-card-result { text-align: center; white-space: nowrap; font-weight: 600; }
.lc-match-card-player.is-us { font-weight: 600; }

/* Colour markers (white/black to move at start of game on that board). */
.lc-match-card-piece {
    display: inline-block;
    width: 0.85em;
    height: 0.85em;
    border-radius: 50%;
    vertical-align: -0.08em;
    margin-right: 0.15em;
    border: 1px solid rgba(0, 0, 0, 0.55);
}
.lc-piece-white { background: #fff; }
.lc-piece-black { background: #111; border-color: #111; }

/* Totals row sits on top of a tinted bar. */
.lc-match-card-totals td {
    background: rgba(0, 0, 0, 0.025);
    font-weight: 600;
    border-bottom: 0;
    /* "Total" must not wrap to a second line — the board# column is sized
       for a 1-digit number, but on the totals row this cell holds the
       word "Total" instead. */
    white-space: nowrap;
}
.lc-match-card-totals .lc-match-card-result {
    color: var(--ghost-accent-color, #2e7d32);
}

/* Sits BELOW the bordered card, not part of it — plain right-aligned link. */
.lc-match-card-source {
    margin-top: 0.4em;
    text-align: right;
    font-size: 0.82em;
}
.lc-match-card-source a { color: inherit; text-decoration: underline dotted; }
.lc-match-card-source a:hover { text-decoration-style: solid; }

@media (max-width: 600px) {
    .lc-match-card-table { font-size: 0.85em; }
    .lc-match-card-table th,
    .lc-match-card-table td { padding: 0.35em 0.45em; }
    /* Tighter: drop ratings on small screens. Player names get the room. */
    .lc-match-card-rating-h,
    .lc-match-card-rating { display: none; }
    .lc-match-card-score { font-size: 1em; }
    .lc-match-card-total { font-size: 1.05em; padding: 0 0.4em; }
}

/* ---------------------------------------------------------------- */
/* Tournament cross-tables                                            */
/* ---------------------------------------------------------------- */
/* Authors paste <div class="lc-tournament" data-slug="…"></div> into a
   Ghost post. chess.js fills it from /content/files/tournaments.json,
   which is rewritten by the scraper from chessdb.tournament_configs.   */
.lc-tournament {
    display: block;
    margin: 1.8em 0 0.6em;
}
.lc-tournament-loading,
.lc-tournament-placeholder { color: #888; font-style: italic; font-size: 0.9em; }
.lc-tournament-error {
    padding: 0.7em 0.9em;
    background: rgba(196, 68, 68, 0.07);
    border-left: 3px solid #c44;
    color: #933;
    font-size: 0.9em;
}

.lc-tournament-inner {
    border: 1px solid rgba(0, 0, 0, 0.1);
    border-radius: 6px;
    background: #fff;
    overflow: hidden;
}
.lc-tournament-header {
    padding: 0.8em 1em;
    background: rgba(46, 125, 50, 0.06);
    border-bottom: 1px solid rgba(0, 0, 0, 0.08);
}
.lc-tournament-title {
    margin: 0;
    font-size: 1.1em;
    font-weight: 600;
    line-height: 1.3;
    color: inherit;
}
.lc-tournament-meta { margin-top: 0.2em; font-size: 0.82em; color: #666; }

/* Allow horizontal scroll for the cross-table when 7+ rounds push the
   width past the column. The inner table is full-width; the wrap is
   what scrolls. */
.lc-tournament-table-wrap { overflow-x: auto; }
.lc-tournament-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.92em;
}
.gh-content .lc-tournament-table { margin-top: 0 !important; }
.lc-tournament-table th,
.lc-tournament-table td {
    padding: 0.4em 0.55em;
    border-bottom: 1px solid rgba(0, 0, 0, 0.06);
    vertical-align: middle;
    text-align: center;
    white-space: nowrap;
}
.lc-tournament-table th {
    font-weight: 600;
    background: rgba(0, 0, 0, 0.02);
    font-size: 0.95em;
}
.lc-tournament-table td.lc-t-name,
.lc-tournament-table th.lc-t-name {
    text-align: left;
    white-space: normal;
    min-width: 8em;
}
.lc-t-rank, .lc-t-rating, .lc-t-total { font-variant-numeric: tabular-nums; }
.lc-t-rank { color: #555; }
.lc-t-rating { color: #555; }
.lc-t-total { font-weight: 600; font-size: 1.05em; }

/* Per-round cells. */
.lc-t-round { font-variant-numeric: tabular-nums; }
.lc-t-round .lc-t-result { font-weight: 600; font-size: 0.92em; }
.lc-t-win  { background: rgba(46, 125, 50, 0.10); }    /* green tint */
.lc-t-draw { background: rgba(200, 170, 0, 0.10); }    /* amber tint */
.lc-t-loss { background: rgba(180, 60, 60, 0.10); }    /* red tint */
.lc-t-round-bye { color: #aaa; }
.lc-t-piece {
    display: inline-block;
    width: 0.65em; height: 0.65em;
    border-radius: 50%;
    vertical-align: 0.05em;
    margin-right: 0.25em;
    border: 1px solid rgba(0, 0, 0, 0.55);
}

.lc-tournament-source {
    margin-top: 0.4em;
    text-align: right;
    font-size: 0.82em;
}
.lc-tournament-source a { color: inherit; text-decoration: underline dotted; }
.lc-tournament-source a:hover { text-decoration-style: solid; }

/* Mobile: keep every column visible and let the user swipe horizontally
   to see the per-round details. .lc-tournament-table-wrap already has
   overflow-x: auto so the gesture works out of the box; we just tighten
   typography so the table fits more vertically. */
@media (max-width: 600px) {
    .lc-tournament-table { font-size: 0.88em; }
    .lc-tournament-table th,
    .lc-tournament-table td { padding: 0.35em 0.45em; }
    .lc-tournament-table th.lc-t-rating,
    .lc-tournament-table td.lc-t-rating { font-size: 0.85em; }
    /* Smoother gesture on iOS. */
    .lc-tournament-table-wrap { -webkit-overflow-scrolling: touch; }
}

/* ---------------------------------------------------------------- */
/* Homepage row: Daily Puzzle (left) + Latest Results (right)         */
/* ---------------------------------------------------------------- */
/* Two columns matching .lc-feeds-grid above (same max-width, gap and
   minmax breakpoint) so the homepage's stacked rows align in width.
   Zero top padding: .lc-feeds already has 3.5rem of bottom padding;
   that's the gap we want. */
.lc-puzzle-results { padding: 0 0 3.5rem; }
.lc-puzzle-results-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
    gap: 3rem;
    max-width: 920px;
    margin: 0 auto;
    /* 3.5rem of breathing room above the new row to match the feeds
       section's 3.5rem bottom padding, so the divider sits in the
       middle of a balanced 7rem gap. */
    padding: 3.5rem 2rem 0;
    align-items: start;
    /* Divider line — drawn via ::before so we can inset it from the
       grid's 2rem side padding, making it span just the column area
       (not the side padding) and so visually match the column widths. */
    position: relative;
}
.lc-puzzle-results-grid::before {
    content: '';
    position: absolute;
    top: 0;
    left: 2rem;
    right: 2rem;
    border-top: 1px solid var(--lc-border);
}

/* Daily puzzle column. Heading + .lc-daily-puzzle widget. */
.lc-daily-puzzle-loading,
.lc-daily-puzzle-placeholder {
    display: block;
    color: #888;
    font-style: italic;
    padding: 2em 0;
    text-align: center;
}
.lc-daily-puzzle-error {
    padding: 0.7em 0.9em;
    background: rgba(196, 68, 68, 0.07);
    border-left: 3px solid #c44;
    color: #933;
    font-size: 0.9em;
}
.lc-daily-puzzle-caption {
    text-align: center;
    font-size: 0.95em;
    color: #555;
    font-weight: 600;
    margin-bottom: 0.4em;
}
.lc-daily-puzzle .chess-puzzle-wrapper {
    margin: 0.8em auto;
    /* The default chess-puzzle widget caps at 480px. In the homepage
       column it's surrounded by results / news, so a smaller board
       reads better in the visual hierarchy. */
    max-width: 320px;
}
.lc-daily-puzzle-attrib {
    margin: 0.4em auto 0;
    font-size: 0.82em;
    color: #777;
    line-height: 1.45;
    text-align: center;
}
.lc-daily-puzzle-attrib a { color: inherit; text-decoration: underline dotted; }
.lc-daily-puzzle-attrib a:hover { text-decoration-style: solid; }

/* Latest Results column. */
.lc-lr-placeholder { color: #888; font-style: italic; padding: 0.6em 0; }
.lc-lr-error {
    padding: 0.7em 0.9em;
    background: rgba(196, 68, 68, 0.07);
    border-left: 3px solid #c44;
    color: #933;
    font-size: 0.9em;
}
.lc-lr-empty { color: #888; font-style: italic; padding: 0.6em 0; }
.lc-lr-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.95em;
}
/* Source's gh-content injects margin above any <table>; not in scope
   on the homepage but be defensive in case the widget ever lands in a
   post. */
.gh-content .lc-lr-table { margin-top: 0 !important; }
.lc-lr-table th,
.lc-lr-table td {
    padding: 0.4em 0.5em 0.4em 0;
    border-bottom: 1px solid rgba(0, 0, 0, 0.06);
    vertical-align: middle;
    white-space: nowrap;
}
.lc-lr-table th {
    font-weight: 600;
    text-align: left;
    font-size: 0.85em;
    color: #555;
    background: rgba(0, 0, 0, 0.025);
}
.lc-lr-table thead th.lc-lr-result { text-align: right; }
.lc-lr-date { color: #555; font-variant-numeric: tabular-nums; }
.lc-lr-league { color: #555; font-size: 0.9em; }
.lc-lr-opp { white-space: normal; }
.lc-lr-result { text-align: right; font-variant-numeric: tabular-nums; }
.lc-lr-code {
    display: inline-block;
    min-width: 1.4em;
    padding: 0.05em 0.4em;
    border-radius: 3px;
    font-weight: 700;
    font-size: 0.82em;
    text-align: center;
    color: #fff;
    background: #888;
    vertical-align: 1px;
}
.lc-lr-w .lc-lr-code { background: var(--lc-accent, #2e7d32); }
.lc-lr-l .lc-lr-code { background: #c14a4a; }
.lc-lr-d .lc-lr-code { background: #b08a00; }
.lc-lr-score { font-weight: 600; }
.lc-lr-link { color: inherit; text-decoration: none; }
/* Mirror the dotted-underline style used by score links in the main
   fixtures widget (.lc-fixtures-table td.lc-fixtures-score a) — dotted
   by default, solid on hover. Only the score text gets the underline;
   the W/L/D badge has its own background and would look ugly with one. */
.lc-lr-link .lc-lr-score {
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
}
.lc-lr-link:hover .lc-lr-score { text-decoration-style: solid; }
.lc-lr-updated {
    margin-top: 0.5em;
    font-size: 0.78em;
    color: #888;
    text-align: left;
}

@media (max-width: 480px) {
    .lc-lr-table { font-size: 0.88em; }
    /* On the narrowest screens drop the date column rather than the
       league — the league + opponent + result combo is more useful than
       the date alone, and recent results are recent by definition. */
    .lc-lr-table th.lc-lr-date,
    .lc-lr-table td.lc-lr-date { display: none; }
}

/* === home.css === */
/* Lichfield home page — hero, meeting cards, news/match-report feeds, welcome.
   Source theme uses html { font-size: 62.5% } so 1rem = 10px. All font sizes
   below are on that scale. Body text is 1.6rem (16px), prose 1.7rem (17px).
   Colours derive from --ghost-accent-color (Settings → Design → Brand). */

.lc-home {
    --lc-accent: var(--ghost-accent-color, #2e7d32);
    --lc-accent-dark: color-mix(in srgb, var(--lc-accent) 80%, #000);
    --lc-accent-soft: color-mix(in srgb, var(--lc-accent) 12%, #fff);
    --lc-text-muted: #5a5a5a;
    --lc-border: #dde1e3;
}

/* --- Hero --- */
.lc-hero {
    background: var(--lc-accent);
    color: #fff;
    padding: 6rem 0 5.5rem;
    text-align: center;
    position: relative;
}
/* When a banner image is set, layer it behind a darkening overlay so the
   title and tagline stay legible regardless of the photo. */
.lc-hero.has-bg-image {
    background-size: cover;
    background-position: center;
    background-repeat: no-repeat;
}
.lc-hero.has-bg-image::before {
    content: "";
    position: absolute;
    inset: 0;
    background: linear-gradient(180deg, rgba(0, 0, 0, 0.42), rgba(0, 0, 0, 0.62));
    pointer-events: none;
    z-index: 0;
}
.lc-hero-inner {
    max-width: 820px;
    margin: 0 auto;
    padding: 0 2rem;
    position: relative;
    z-index: 1;
}
.lc-hero-title {
    font-size: clamp(3.6rem, 6vw, 5.6rem);
    line-height: 1.1;
    margin: 0 0 0.4em;
    color: #fff;
    letter-spacing: -0.01em;
}
.lc-hero-tagline {
    font-size: clamp(1.8rem, 2.2vw, 2.2rem);
    line-height: 1.5;
    margin: 0 auto 2rem;
    max-width: 640px;
    opacity: 0.95;
}
.lc-hero-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 1rem;
    justify-content: center;
}

/* Buttons */
.lc-btn {
    display: inline-block;
    /* border-box so the 2px ghost-variant border doesn't add to the
       button's total height and shift its text down relative to the
       primary variant (which has no border). */
    box-sizing: border-box;
    padding: 1.1rem 2rem;
    font-weight: 600;
    text-decoration: none;
    border: 2px solid transparent;
    border-radius: 6px;
    font-size: 1.7rem;
    transition: opacity 0.15s, transform 0.15s, background 0.15s;
}
.lc-btn:hover { opacity: 0.92; transform: translateY(-1px); }
.lc-btn-primary {
    background: #fff;
    color: var(--lc-accent-dark);
}
.lc-btn-ghost {
    background: transparent;
    color: #fff;
    border: 2px solid rgba(255, 255, 255, 0.7);
}
.lc-welcome .lc-btn-primary {
    background: var(--lc-accent);
    color: #fff;
}
.lc-welcome .lc-btn-primary:hover { background: var(--lc-accent-dark); opacity: 1; }

/* --- Meeting times --- */
.lc-meet {
    padding: 4rem 0 3rem;
    background: var(--lc-accent-soft);
}
.lc-meet-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
    gap: 1.8rem;
    max-width: 920px;
    margin: 0 auto;
    padding: 0 2rem;
}
.lc-meet-card {
    background: #fff;
    border: 1px solid var(--lc-border);
    border-radius: 10px;
    padding: 2.4rem 2.4rem;
    line-height: 1.5;
    font-size: 1.7rem;
}
.lc-meet-day {
    font-size: 2.6rem;
    font-weight: 700;
    color: var(--lc-accent-dark);
    margin-bottom: 0.1em;
    line-height: 1.15;
}
.lc-meet-time {
    color: var(--lc-text-muted);
    font-size: 1.7rem;
    margin-bottom: 1rem;
}
.lc-meet-place {
    margin-bottom: 0.6em;
    font-size: 1.7rem;
}
.lc-meet-when {
    font-size: 1.5rem;
    color: var(--lc-text-muted);
    font-style: italic;
}

/* --- Latest news + match reports --- */
.lc-feeds {
    /* Bottom padding pairs with the matching top padding inside
       .lc-puzzle-results-grid to balance the divider line between the
       two sections. Reduced from 3.5rem so the gap above the line is
       slightly tighter than the gap below it. */
    padding: 4rem 0 2.5rem;
}
.lc-feeds-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(320px, 1fr));
    gap: 3rem;
    /* Match the meeting-times grid directly above so the homepage
       content blocks align in width. */
    max-width: 920px;
    margin: 0 auto;
    padding: 0 2rem;
}
.lc-feed-header {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    border-bottom: 3px solid var(--lc-accent);
    padding-bottom: 0.6rem;
    margin-bottom: 1.2rem;
}
.lc-feed-header h2 {
    margin: 0;
    font-size: 2.4rem;
    color: var(--lc-accent-dark);
}
.lc-feed-all {
    text-decoration: none;
    color: var(--lc-accent-dark);
    font-size: 1.5rem;
    font-weight: 600;
}
.lc-feed-all:hover { text-decoration: underline; }
.lc-feed-list {
    list-style: none;
    padding: 0;
    margin: 0;
}
.lc-feed-item {
    border-bottom: 1px solid var(--lc-border);
}
.lc-feed-item:last-child { border-bottom: none; }
.lc-feed-item a {
    display: block;
    padding: 1.4rem 0;
    text-decoration: none;
    color: inherit;
}
.lc-feed-item a:hover .lc-feed-title { color: var(--lc-accent-dark); }
.lc-feed-title {
    font-size: 1.9rem;
    font-weight: 600;
    margin: 0 0 0.3em;
    line-height: 1.3;
    transition: color 0.15s;
}
.lc-feed-excerpt {
    font-size: 1.6rem;
    color: var(--lc-text-muted);
    line-height: 1.5;
    margin: 0 0 0.4em;
}
/* "Read more →" cue at the end of each excerpt. Inline with the excerpt
   text so the ellipsis flows naturally into it. The whole feed item is
   already wrapped in <a> so this <span> is link-coloured for affordance
   and underlined on hover (alongside the title) to feel like a CTA. */
.lc-feed-readmore {
    color: var(--lc-accent-dark);
    font-weight: 600;
    white-space: nowrap;
    /* Dotted underline matching the site's body-link convention. */
    text-decoration: underline dotted;
    text-decoration-thickness: 1px;
    text-underline-offset: 0.18em;
    transition: text-decoration-style 0.15s, color 0.15s;
}
.lc-feed-item a:hover .lc-feed-readmore {
    text-decoration-style: solid;
}
.lc-feed-date {
    font-size: 1.3rem;
    color: var(--lc-text-muted);
    text-transform: uppercase;
    letter-spacing: 0.04em;
}

/* --- Welcome --- */
.lc-welcome {
    background: var(--lc-accent-soft);
    padding: 4rem 0;
    margin-bottom: 6rem;  /* gap before the footer panel so the two soft-tinted
                             bands don't blend into one */
}
.lc-welcome-inner {
    max-width: 760px;
    margin: 0 auto;
    padding: 0 2rem;
    text-align: center;
}
.lc-welcome h2 {
    color: var(--lc-accent-dark);
    margin-top: 0;
    font-size: 2.8rem;
}
.lc-welcome p {
    line-height: 1.6;
    color: #2a2a2a;
    font-size: 1.8rem;
    margin: 1rem 0;
}
.lc-welcome a:not(.lc-btn) {
    color: var(--lc-accent-dark);
}
.lc-welcome .lc-btn {
    margin-top: 1rem;
}

@media (max-width: 600px) {
    .lc-hero { padding: 4rem 0 3.5rem; }
    .lc-meet { padding: 3rem 0 2rem; }
    .lc-feeds { padding: 3rem 0 2.5rem; }
    .lc-welcome { padding: 3rem 0; }
}

