/* Qwahabedi - public stylesheet.
   Hand-written, no framework, mobile-first: this file is the whole
   design system for the public site. Tokens mirror docs/qwahabedi-brand-final.html. */

:root{
  --ink:#1F2933; --paper:#FCFBF6; --indigo:#26356B; --red:#C43A28;
  --gold:#E3A722; --dgold:#8A6414; --teal:#1F6E5F; --muted:#6B7280;
  --line:#E6E1D5; --pitch:#2E5D3E; --radius:14px;
  --display:'Bricolage Grotesque',Georgia,serif;
  --body:'Archivo',system-ui,-apple-system,'Segoe UI',sans-serif;
}
*{margin:0;padding:0;box-sizing:border-box}
@media (prefers-reduced-motion: reduce){*{animation:none!important;transition:none!important}}
body{font-family:var(--body);background:var(--paper);color:var(--ink);line-height:1.5;-webkit-font-smoothing:antialiased}
a{color:inherit}
button{font-family:var(--body)}
img{max-width:100%;height:auto}
:focus-visible{outline:3px solid var(--gold);outline-offset:2px;border-radius:4px}
.skip{position:absolute;left:-9999px}
.skip:focus{left:8px;top:8px;z-index:200;background:var(--gold);color:var(--ink);padding:8px 14px;border-radius:999px;font-weight:700}

.band{height:10px;background:linear-gradient(90deg,
  var(--indigo) 0 22%, var(--paper) 22% 25%, var(--gold) 25% 40%, var(--paper) 40% 43%,
  var(--red) 43% 58%, var(--paper) 58% 61%, var(--teal) 61% 78%, var(--paper) 78% 81%, var(--indigo) 81% 100%)}
.band.thin{height:6px}
/* 1100 to match the section bands. It was 840, which squeezed every card row
   inside a band that ran wider than it - visible as empty margins either side
   of the big places while the doors above them reached the edge. */
.wrap{max-width:1100px;margin:0 auto;padding:0 20px}

/* Running text does not want 1100px of line. .prose already caps itself
   further down; these are the two that did not. */
.sub,.lede{max-width:68ch}

/* ---- header ---- */
.pub-top{background:var(--indigo);color:#FDFCF8;padding:12px 20px;display:flex;justify-content:space-between;align-items:center;gap:10px;flex-wrap:wrap}
.logo{display:flex;align-items:center;gap:9px;text-decoration:none}
.logo img{width:34px;height:21px}
.logo b{font-family:var(--display);font-weight:800;font-size:1.05rem}
.logo b span{color:var(--gold)}
.pub-top nav{display:flex;gap:13px;font-size:.8rem;font-weight:600;flex-wrap:wrap}
.pub-top nav a{text-decoration:none;opacity:.88;border-bottom:2px solid transparent;padding:2px 0}
.pub-top nav a.active,.pub-top nav a:hover{opacity:1;border-bottom-color:var(--gold)}

/* ---- headings ---- */
h1.pg{font-family:var(--display);font-weight:800;font-size:clamp(1.7rem,6vw,2.6rem);margin:24px 0 6px;line-height:1.07}
h1.pg em{font-style:normal;color:var(--teal)}
.sub{color:var(--muted);font-size:.89rem;margin-bottom:18px;max-width:58ch}
h2.sec{font-family:var(--display);font-weight:800;font-size:1.2rem;margin:24px 0 11px}
.sotho{display:block;font-weight:600;font-size:.71rem;color:var(--muted);letter-spacing:.1em;text-transform:uppercase;margin-top:2px}
.crumb{font-size:.72rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;color:var(--red);margin-top:22px}
.crumb a{color:var(--muted);text-decoration:none}
.crumb a:hover{text-decoration:underline}
.crumb + h1.pg{margin-top:6px}

/* ---- buttons ---- */
.btn{display:inline-flex;align-items:center;gap:7px;border:none;border-radius:999px;padding:10px 18px;font-size:.85rem;font-weight:700;cursor:pointer;text-decoration:none}
.btn.solid{background:var(--indigo);color:#fff}
.btn.solid:hover{background:#1C2A57}
.btn.gold{background:var(--gold);color:var(--ink)}
.btn.gold:hover{background:#F0B93B}
.btn.ghost{background:transparent;border:1.5px solid var(--line);color:var(--ink)}
.btn.ghost:hover{border-color:var(--indigo)}
.btn.wa{background:var(--teal);color:#fff}
.btn.sm{padding:7px 13px;font-size:.77rem}

/* ---- hubs (home) ---- */
.hubs{display:grid;grid-template-columns:1fr;gap:14px;margin-top:8px}
@media(min-width:640px){.hubs{grid-template-columns:repeat(3,1fr)}}
.hub{border-radius:var(--radius);padding:20px 19px;color:#FDFCF8;text-decoration:none;display:block;transition:transform .15s ease}
.hub:hover{transform:translateY(-3px)}
.hub.v{background:var(--teal)}
.hub.t{background:var(--indigo)}
.hub.e{background:var(--red)}
.hub .num{font-family:var(--display);font-weight:800;font-size:.7rem;letter-spacing:.2em;text-transform:uppercase;opacity:.75}
.hub h2{font-family:var(--display);font-weight:800;font-size:1.4rem;margin:2px 0 5px}
.hub p{font-size:.83rem;opacity:.88}
.hub .go{display:inline-block;margin-top:12px;font-size:.8rem;font-weight:700;border-bottom:2px solid var(--gold)}

/* ---- village cards ---- */
.vgrid{display:grid;grid-template-columns:repeat(2,1fr);gap:12px}
@media(min-width:640px){.vgrid{grid-template-columns:repeat(3,1fr)}}
.vcard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:15px;text-decoration:none;display:block}
.vcard:hover{border-color:var(--teal)}
.vcard h3{font-family:var(--display);font-weight:800;font-size:1.03rem}
.vcard p{font-size:.75rem;color:var(--muted);margin-top:2px}
.vcard .mini{height:5px;border-radius:99px;margin-bottom:10px;background:linear-gradient(90deg,var(--indigo) 0 30%,var(--gold) 30% 55%,var(--red) 55% 80%,var(--teal) 80% 100%)}
/* A village with places and events is not the same thing as a name on a list,
   and for seventy-one of seventy-six the honest card is the quiet one that
   asks for the first place rather than the loud one that has nothing behind
   it. */
.vcard.quiet{background:#FBFAF4}
.vcard.quiet .mini{height:3px;background:var(--line);width:34px}
.vcard.quiet h3{font-weight:700;color:#4A5560}
.vcard .vcount{color:var(--teal);font-weight:700}
/* Jump to the villages that have something, or to the ones waiting for a
   first place. Shown only once the script that works them has loaded. */
.vchips{display:flex;gap:7px;flex-wrap:wrap;margin-top:9px}
.vchip{border:1.5px solid rgba(255,255,255,.45);background:transparent;color:#fff;border-radius:999px;
    padding:6px 13px;font-size:.76rem;font-weight:700;cursor:pointer;font-family:var(--body)}
.vchip span{opacity:.72;margin-left:5px;font-weight:600}
.vchip.on{background:#fff;border-color:#fff;color:var(--teal)}
.vchip:hover{border-color:#fff}

/* The long piece about a place. Running text wants a measure: the hero was
   small white type on indigo at the full width of the page, which is the
   least readable thing a long paragraph can be. */
/* The story beside the facts, where the screen is wide enough for both. The
   column keeps the measure honest, so the cap comes off inside it. */
.placebody{display:grid;gap:18px;align-items:start}
@media(min-width:900px){
    .placebody{grid-template-columns:minmax(0,1fr) 340px}
    .placebody.nostory{grid-template-columns:1fr}
    .placebody .story{max-width:none}
}
.story{max-width:68ch;margin:4px 0 18px}
.story p{font-size:.95rem;line-height:1.72;color:var(--ink)}
.story p + p{margin-top:12px}

.vinvite{background:#FFFBEF;border:1.5px solid var(--gold);border-radius:var(--radius);
    padding:12px 16px;margin:16px 0 4px;font-size:.84rem;color:#5A5346}
.vinvite a{font-weight:700;color:var(--indigo)}
.vcard .vfirst{margin-top:6px;font-size:.7rem;font-weight:700;color:var(--muted);opacity:0}
.vcard.quiet:hover .vfirst,.vcard.quiet:focus-visible .vfirst{opacity:1;color:var(--teal)}
/* Deliberately not shown on a touch screen: the same sentence under
   seventy-one cards is the wallpaper this was meant to remove. The page
   carries one invitation instead, above the list. */

/* ---- directory cards ---- */
.cards{display:grid;grid-template-columns:1fr;gap:12px}
@media(min-width:600px){.cards{grid-template-columns:1fr 1fr}}
/* Three across on a wide screen, not two. The picture is held to 150px tall
   and shown whole, so a landscape photograph comes out about 267px wide
   whatever the card does - in a 530px card that leaves half the strip filled
   with the blurred copy of itself, and in a 350px one it leaves a sliver. */
@media(min-width:960px){.cards{grid-template-columns:repeat(3,1fr)}}
.dcard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:15px 17px;position:relative;text-decoration:none;display:block}
.dcard:hover{border-color:var(--indigo)}
.dcard::before{content:"";position:absolute;left:0;top:13px;bottom:13px;width:4px;border-radius:0 4px 4px 0;background:var(--teal)}
.dcard.gold::before{background:var(--gold)}
.dcard.red::before{background:var(--red)}
.dcard.indigo::before{background:var(--indigo)}
.dcard .kind{font-size:.67rem;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--muted)}
.dcard h3{font-size:.99rem;font-weight:700;margin-top:1px}
.dcard p{font-size:.82rem;color:var(--muted);margin-top:3px}
.dcard .open{color:var(--teal);font-weight:600}

/* ---- leaders ---- */
.leaders{display:grid;grid-template-columns:1fr;gap:14px}
@media(min-width:560px){.leaders{grid-template-columns:1fr 1fr}}
.leader{background:#fff;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden}
.leader .pad{padding:15px 17px}
.leader .role{font-size:.7rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase}
.leader.c .role{color:var(--teal)}
.leader.k .role{color:var(--red)}
.leader h3{font-family:var(--display);font-weight:800;font-size:1.18rem;margin:3px 0 2px}
.leader .meta{font-size:.82rem;color:var(--muted);margin-bottom:10px}

/* ---- events & notices ---- */
.event{display:flex;gap:14px;background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:13px 16px;margin-bottom:10px;align-items:center;
    text-decoration:none;color:inherit}
a.event:hover{border-color:var(--indigo)}
.event .who{min-width:0}
.event .date{display:block}
.event .date{flex:0 0 54px;text-align:center;background:var(--paper);border:1px solid var(--line);border-radius:10px;padding:7px 4px}
.event .date b{font-family:var(--display);font-size:1.2rem;font-weight:800;display:block;line-height:1}
.event .date span{font-size:.64rem;font-weight:700;letter-spacing:.1em;text-transform:uppercase;color:var(--red)}
.event h3{font-size:.94rem;font-weight:700;line-height:1.3}
.event p{font-size:.79rem;color:var(--muted)}
.notice{border-left:4px solid var(--gold);background:#FFF9EC;border-radius:0 var(--radius) var(--radius) 0;padding:12px 16px;margin-bottom:10px}
.notice.urgent{border-color:var(--red);background:#FBEFED}
.notice b{font-size:.88rem}
.notice p{font-size:.8rem;color:#5A5346;margin-top:2px}
.notice time{font-size:.7rem;font-weight:700;letter-spacing:.08em;text-transform:uppercase;color:var(--muted)}

/* ---- chips, rows, misc ---- */
.chips{display:flex;flex-wrap:wrap;gap:9px}
.chip{border:1.5px solid var(--line);background:#fff;border-radius:999px;padding:9px 16px;font-size:.83rem;font-weight:600;text-decoration:none;color:var(--ink);cursor:pointer}
.chip:hover{border-color:var(--indigo)}
.chip i{font-style:normal;color:var(--muted);font-weight:500;font-size:.75rem}
.chip.on{background:var(--ink);border-color:var(--ink);color:#fff}
.card{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:16px 18px;margin-bottom:12px}
.consent{font-size:.76rem;color:var(--muted);background:#fff;border:1px dashed var(--line);border-radius:10px;padding:10px 14px;margin-top:12px}
.empty{background:#fff;border:1px dashed var(--line);border-radius:var(--radius);padding:18px;color:var(--muted);font-size:.85rem}
.fbadge{font-size:.6rem;font-weight:800;letter-spacing:.12em;text-transform:uppercase;background:var(--gold);color:var(--ink);border-radius:999px;padding:2px 9px;margin-right:6px}
.status{font-size:.62rem;font-weight:800;letter-spacing:.1em;text-transform:uppercase;border-radius:999px;padding:4px 11px;white-space:nowrap}
.status.live{background:#EAF2EF;color:var(--teal)}
.status.pending{background:#F6ECD9;color:var(--dgold)}

/* ---- list rows (market, jobs, order lines) ---- */
.row{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:14px 17px;margin-bottom:10px;
     display:flex;justify-content:space-between;gap:14px;align-items:center;flex-wrap:wrap}
.row h3{font-size:.95rem;font-weight:700}
.row p{font-size:.8rem;color:var(--muted)}
.row .price{font-family:var(--display);font-weight:800;font-size:1.02rem;color:var(--teal);white-space:nowrap}
.row.featured{border-color:var(--gold);background:#FFFBEF}

/* ---- visit places ---- */
.visit-grid{display:grid;grid-template-columns:1fr;gap:12px}
@media(min-width:640px){.visit-grid{grid-template-columns:1fr 1fr}}
/* Three across on a wide screen, as on the directory cards. These carry a
   drawn sky rather than a photograph, so nothing here is being letterboxed -
   it is density, and matching the rest of the site. */
@media(min-width:960px){.visit-grid{grid-template-columns:repeat(3,1fr)}}
.place{border-radius:var(--radius);overflow:hidden;background:#fff;border:1px solid var(--line);text-decoration:none;display:block}
.place:hover{border-color:var(--red)}
/* One height for the picture area whether it is a photograph or a drawing,
   so a row does not go ragged where somebody has uploaded and somebody else
   has not. 76px was a strip; a photograph of a dam deserves more. */
.place .sky{height:150px}
.place .pic{display:block;height:150px;background:#F6F4EC;border-bottom:1px solid var(--line);
    position:relative;overflow:hidden;isolation:isolate}
/* As on the directory cards: whatever the photograph does not cover is a
   blurred, enlarged copy of itself rather than a grey margin. */
.place .pic::after{content:"";position:absolute;inset:-16px;z-index:-1;
    background-image:var(--shot);background-size:cover;background-position:center;
    filter:blur(13px) saturate(1.12)}
.place .pic img{display:block;width:100%;height:150px;object-fit:contain;position:relative}
.place .sky svg{width:100%;height:100%;display:block}
.place .pad{padding:12px 16px 14px}
.place .kind{font-size:.66rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;color:var(--red)}
.place h3{font-family:var(--display);font-weight:800;font-size:1rem;margin:2px 0 3px}
.place p{font-size:.8rem;color:var(--muted)}

/* ---- listing detail ---- */
.detail-head{background:var(--indigo);color:#FDFCF8;padding:26px 0 22px}
.detail-head h1{font-family:var(--display);font-weight:800;font-size:clamp(1.5rem,5vw,2.2rem);line-height:1.1}
.detail-head .kind{font-size:.68rem;font-weight:800;letter-spacing:.14em;text-transform:uppercase;color:var(--gold)}
.detail-head p{opacity:.86;font-size:.88rem;margin-top:6px;max-width:56ch}
.detail-actions{display:flex;gap:8px;flex-wrap:wrap;margin:16px 0}
.facts{list-style:none;margin:0;padding:0}
.facts li{display:flex;gap:12px;padding:10px 0;border-bottom:1px dashed var(--line);font-size:.87rem}
.facts li:last-child{border-bottom:none}
.facts .k{flex:0 0 110px;color:var(--muted);font-weight:700;font-size:.74rem;letter-spacing:.08em;text-transform:uppercase}

/* ---- the photograph on "My entry" ----
   Side by side so somebody can see what is on the site against what they
   have just sent and is still waiting. */
.portrait-row{display:flex;gap:16px;flex-wrap:wrap;margin-bottom:14px}
.portrait-now{width:150px;aspect-ratio:3/4;object-fit:cover;border-radius:12px;display:block;border:1px solid var(--line)}
.portrait-now.initials{background:#E9E4D6;display:flex;align-items:center;justify-content:center;
    font-family:var(--display);font-size:2.2rem;font-weight:800;color:#6B5A2A}

/* ---- Bana ba Motse on a village page ----
   These cards had no rules at all: .pros, .pro and .init never matched
   anything in this file, so the people a village is proudest of rendered as
   bare text with their initials loose on the page. Built to sit beside the
   front page's .person cards rather than to be a second design. */
.pros{display:grid;gap:16px;grid-template-columns:repeat(auto-fill,minmax(230px,1fr));margin-bottom:28px}
.pro{background:#fff;border:1px solid var(--line);border-radius:14px;overflow:hidden;display:flex;flex-direction:column}
.pro .face{width:100%;aspect-ratio:3/4;object-fit:cover;display:block}
/* Their initials on sand, never a stock photograph or a silhouette. */
.pro .init{aspect-ratio:3/4;background:#E9E4D6;display:flex;align-items:center;justify-content:center;
    font-family:var(--display);font-size:2.6rem;font-weight:800;color:#6B5A2A}
.pro>div:last-child{padding:14px 16px;display:flex;flex-direction:column;gap:5px}
.pro h3{font-family:var(--display);font-weight:800;font-size:1.02rem;line-height:1.2}
.pro .title{color:var(--teal);font-weight:700;font-size:.85rem}
.pro p{font-size:.84rem;color:var(--muted);line-height:1.5}

/* ---- policy pages ---- */
.prose{max-width:62ch;font-size:.92rem}
.prose h2{font-family:var(--display);font-weight:800;font-size:1.15rem;margin:22px 0 8px}
.prose p{margin-bottom:11px}
.prose ul{margin:0 0 12px 20px}
.prose li{margin-bottom:5px}

/* ---- footer ---- */
.mountains{display:block;width:100%;height:56px}
footer.pub{padding:24px 20px 40px;text-align:center;color:var(--muted);font-size:.79rem}
/* The footer is indigo since the redesign; ink here was all but invisible. */
footer.pub b{color:#FDFCF8}
footer.pub a{text-decoration:none;color:var(--teal);font-weight:600}
footer.pub .legal{margin-top:10px;font-size:.75rem}

/* ---- tournaments ---- */
.tcard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden;margin-bottom:12px}
.tcard .strip{height:6px}
.tcard .pad{padding:15px 18px;display:flex;justify-content:space-between;gap:12px;align-items:center;flex-wrap:wrap}
.tcard h3{font-family:var(--display);font-weight:800;font-size:1.06rem}
.tcard p{font-size:.8rem;color:var(--muted)}
.tcard .when{font-size:.71rem;font-weight:800;letter-spacing:.1em;text-transform:uppercase;color:var(--red)}
.tcard .acts{display:flex;gap:7px;flex-wrap:wrap;align-items:center}
.status.open,.status.approved{background:#EAF2EF;color:var(--teal)}
.status.soon{background:#F6ECD9;color:var(--dgold)}
.status.done{background:#EEE;color:var(--muted)}

/* Text left, action right - the same shape as the What's on bar. The
   paragraph was capped at 56ch, which looked squeezed once the container
   widened to 1100 and left the right half of the panel empty. */
.bignote{background:var(--pitch);color:#F3F7F1;border-radius:var(--radius);padding:24px 26px;margin:24px 0;
         display:flex;align-items:center;justify-content:space-between;gap:28px;flex-wrap:wrap}
.bignote .said{flex:1 1 32ch;min-width:0}
.bignote h2{font-family:var(--display);font-weight:800;font-size:1.3rem;margin-bottom:6px}
.bignote p{font-size:.87rem;opacity:.88;max-width:none}
.bignote .btn{margin-top:0;flex:0 0 auto}
@media (max-width:719px){
  .bignote{flex-direction:column;align-items:flex-start;gap:16px}
  .bignote .btn{width:100%;text-align:center}
}

.hero-pitch{background:var(--pitch);color:#F3F7F1;padding:32px 0 26px}
.hero-pitch h1{font-family:var(--display);font-weight:800;font-size:clamp(1.9rem,6.6vw,3rem);line-height:1.05;margin:6px 0 8px}
.hero-pitch .lede{opacity:.85;font-size:.93rem;max-width:52ch}
.hero-pitch .facts{display:flex;gap:20px;flex-wrap:wrap;margin-top:16px}
.hero-pitch .fact b{font-family:var(--display);font-weight:800;font-size:1.4rem;display:block;line-height:1}
.hero-pitch .fact span{font-size:.7rem;letter-spacing:.08em;text-transform:uppercase;opacity:.75;font-weight:600}
.hero-pitch .crumb{color:var(--gold);margin-top:0}
.hero-pitch .crumb a{color:#CFE0CC}
.credit{display:inline-flex;align-items:center;gap:8px;margin-top:16px;background:rgba(0,0,0,.25);
        border:1px solid rgba(255,255,255,.18);border-radius:999px;padding:6px 14px;font-size:.74rem;font-weight:600}
.credit i{width:8px;height:8px;border-radius:50%;background:var(--gold)}

.tablewrap{overflow-x:auto;border-radius:var(--radius);border:1px solid var(--line);margin-bottom:10px}
table{width:100%;border-collapse:collapse;background:#fff;font-size:.84rem;min-width:520px}
thead th{text-align:left;font-size:.65rem;letter-spacing:.11em;text-transform:uppercase;color:var(--muted);
         padding:10px 14px;border-bottom:1px solid var(--line);background:#FBFAF6}
tbody td{padding:11px 14px;border-bottom:1px solid #F0EDE4;vertical-align:middle}
tbody tr:last-child td{border-bottom:none}
tbody tr:hover{background:#FBFAF6}
td.year{font-family:var(--display);font-weight:800}
td .champ{font-weight:700}
td .star{color:var(--gold)}
td .meta{display:block;font-size:.73rem;color:var(--muted)}

.final{background:#fff;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden;margin-bottom:14px}
.final .head{background:var(--ink);color:#FDFCF8;padding:9px 16px;font-size:.68rem;font-weight:800;
             letter-spacing:.14em;text-transform:uppercase;display:flex;justify-content:space-between;gap:10px}
.final .head span:last-child{color:var(--gold)}
.final .score{display:grid;grid-template-columns:1fr auto 1fr;align-items:center;padding:18px 14px;gap:10px}
.final .team{text-align:center}
.final .team .tb{width:48px;height:48px;border-radius:50%;margin:0 auto 7px;display:grid;place-items:center;
                 font-family:var(--display);font-weight:800;color:#fff}
/* A club that has given us a badge shows it instead of initials. The circle
   keeps its size; only the coloured fill goes, so a logo is not tinted. */
.final .team .tb.hasbadge{background:#fff;border:1px solid var(--line);padding:4px}
.final .team .tb.hasbadge img{width:100%;height:100%;object-fit:contain}
.final .team:first-child .tb{background:var(--teal)}
.final .team:last-child .tb{background:var(--red)}
.final .team .tb.hasbadge{background:#fff}
/* Champions and runners-up, the two that decide the day, above the rest. */
.titles{display:grid;grid-template-columns:repeat(auto-fit,minmax(220px,1fr));gap:10px;margin-bottom:12px}
.titlecard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:14px 16px;text-align:center}
.titlecard.champion{border-color:var(--gold);background:#FFFDF6}
.titlecard .kind{display:block;font-size:.62rem;font-weight:800;letter-spacing:.14em;
                 text-transform:uppercase;color:var(--muted);margin-bottom:7px}
.titlecard.champion .kind{color:var(--dgold)}
.titlecard .who{display:flex;align-items:center;justify-content:center;gap:7px}
.titlecard .who b{font-family:var(--display);font-weight:800;font-size:1.05rem}
.titlecard .gave{display:block;font-size:.75rem;color:var(--muted);margin-top:4px}
.titlecard .handedby{display:block;font-size:.7rem;color:var(--muted);font-style:italic;margin-top:6px}
.rollbadge{width:18px;height:18px;object-fit:contain;vertical-align:-4px;margin-right:5px}
.final .team h3{font-size:.9rem;font-weight:700;line-height:1.25}
.final .team p{font-size:.71rem;color:var(--muted)}
.final .nums{font-family:var(--display);font-weight:800;font-size:2.1rem;white-space:nowrap;text-align:center}
.final .nums small{font-size:.8rem;color:var(--muted);display:block;text-align:center;font-family:var(--body);font-weight:600}

.awards{display:grid;grid-template-columns:1fr;gap:10px}
@media(min-width:600px){.awards{grid-template-columns:repeat(3,1fr)}}
.award{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:12px 14px;border-top:4px solid var(--gold)}
.award .kind{font-size:.62rem;font-weight:800;letter-spacing:.13em;text-transform:uppercase;color:var(--dgold)}
.award h3{font-size:.93rem;font-weight:700;margin-top:2px}
.award p{font-size:.76rem;color:var(--muted)}

.albums{display:grid;grid-template-columns:repeat(2,1fr);gap:12px}
@media(min-width:640px){.albums{grid-template-columns:repeat(3,1fr)}}
.album{border-radius:var(--radius);overflow:hidden;border:1px solid var(--line);background:#fff;display:block}
.album .thumb{height:96px;position:relative;background:#F6F4EC}
.album .thumb svg{width:100%;height:100%;display:block}
/* The cover had no rule of its own and leaned on the crop that used to be
   baked into the conversion. Contain, so a cover is a small whole photograph
   rather than somebody's middle. */
.album .thumb img{width:100%;height:100%;object-fit:contain;display:block}
.album .count{position:absolute;right:8px;bottom:8px;background:rgba(0,0,0,.55);color:#fff;
              font-size:.66rem;font-weight:700;border-radius:999px;padding:2px 9px}
.album .pad{padding:10px 13px 12px}
.album h3{font-size:.86rem;font-weight:700}
.album p{font-size:.71rem;color:var(--muted)}

.findme{border:1.5px solid var(--gold);background:#FFFBEF;border-radius:var(--radius);padding:17px 19px;margin-top:16px}
.findme h3{font-family:var(--display);font-weight:800;font-size:1.1rem}
.findme p{font-size:.84rem;color:#5A5346;margin:5px 0 12px;max-width:78ch}
/* One sentence of facts, not prose - it reads worse broken across lines than
   run wide, so this panel alone drops the measure cap. */
.findme.entries p{max-width:none}

.fixture{display:grid;grid-template-columns:64px 1fr auto;gap:12px;align-items:center;background:#fff;
         border:1px solid var(--line);border-radius:var(--radius);padding:12px 15px;margin-bottom:9px}
.fixture .kick{font-size:.72rem;font-weight:700;color:var(--muted);text-align:center;line-height:1.3}
.fixture .kick b{display:block;font-family:var(--display);font-size:.95rem;color:var(--ink)}
.fixture .teams{font-size:.9rem;font-weight:600}
.fixture .teams span{color:var(--muted);font-weight:500}
.fixture .result{font-family:var(--display);font-weight:800;font-size:1.1rem;white-space:nowrap}
.fixture .result small{display:block;font-family:var(--body);font-size:.65rem;font-weight:700;
                       letter-spacing:.1em;text-transform:uppercase;color:var(--muted);text-align:right}
.fixture.livegame{border-color:var(--red)}
/* A match that was stopped or called off. The reason spans the whole card -
   .fixture is a three-column grid, so these must not sit in a cell. */
.fixture.stopped{border-color:var(--gold);background:#FFFDF6}
.fixture .outcome{grid-column:1/-1;margin:8px 0 0;padding-top:8px;border-top:1px dashed var(--line);
                  font-size:.72rem;font-weight:700;color:var(--dgold)}
.fixture .officials,.final .officials{grid-column:1/-1;margin:6px 0 0;display:flex;flex-wrap:wrap;gap:4px 14px;
                  font-size:.68rem;color:var(--muted)}
.fixture .officials b,.final .officials b{font-weight:800;letter-spacing:.08em;text-transform:uppercase;
                  font-size:.6rem;margin-right:4px}
.final .outcome{margin:10px 0 0;padding-top:10px;border-top:1px dashed var(--line);
                font-size:.75rem;font-weight:700;text-align:center;color:var(--dgold)}
.final .officials{justify-content:center;padding-bottom:4px}
/* The half-time hand-over. */
.giving h3{margin:0 0 6px}
.award .handedby{font-size:.7rem;color:var(--muted);font-style:italic;margin-top:4px}
.roundhead{font-size:.7rem;font-weight:800;letter-spacing:.14em;text-transform:uppercase;color:var(--red);margin:18px 0 8px}

/* The pride of QwaQwa. Each card names where the thing actually is - a
   hospital on this page must still say Naledi. */
.bigplace{display:block;background:#fff;border:1px solid var(--line);border-radius:var(--radius);
          padding:12px 14px;text-decoration:none;color:inherit;border-left:3px solid var(--indigo)}
.bigplace:hover{border-left-color:var(--gold)}
.bigplace .cat{display:block;font-size:.6rem;font-weight:800;letter-spacing:.13em;
               text-transform:uppercase;color:var(--muted);margin-bottom:4px}
.bigplace b{display:block;font-family:var(--display);font-weight:800;font-size:.95rem;line-height:1.25}
.bigplace .where{display:block;font-size:.72rem;color:var(--teal);font-weight:600;margin-top:4px}
/* The areas inside a town. */
.areas{display:flex;flex-wrap:wrap;gap:7px;margin:0 0 18px}
.area{font-size:.78rem;font-weight:600;border:1px solid var(--line);border-radius:999px;
      padding:5px 13px;text-decoration:none;color:inherit;background:#fff}
.area:hover{border-color:var(--indigo)}
.area .n{color:var(--muted);font-weight:700;font-size:.68rem;margin-left:5px}
/* Where to find a place. The map slot is empty until somebody taps for it. */
.findit .addr{font-size:.95rem;font-weight:600;margin:0 0 6px}
.findit .coords{font-size:.8rem;color:var(--muted);margin:0 0 12px;display:flex;gap:8px;align-items:center}
.findit .coords .k{font-size:.6rem;font-weight:800;letter-spacing:.13em;text-transform:uppercase}
.findit .coords code{font-family:ui-monospace,Menlo,Consolas,monospace;font-size:.78rem;
                     background:var(--paper);border:1px solid var(--line);border-radius:6px;padding:2px 7px;
                     user-select:all}
.findit-actions{display:flex;flex-wrap:wrap;gap:8px;align-items:center}
.mapslot{margin-top:12px;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden;
         background:var(--paper)}
.mapslot iframe{display:block;width:100%;height:280px;border:0}
.maphint{margin-top:7px}
/* Pictures on a listing. The card keeps its shape when there is none, so a
   directory of mixed listings does not look half-finished. */
.dcard.haspic{padding:0;overflow:hidden;display:flex;flex-direction:column}
.dcard.haspic .pic{display:block;background:var(--paper);border-bottom:1px solid var(--line)}
/* The whole picture, never cropped: flyers carry their logo and number at
   the edges. What does not fill the strip sits on a soft ground. */
.dcard.haspic .pic{background:#F6F4EC;position:relative;overflow:hidden;isolation:isolate}
/* The same photograph, enlarged and blurred, filling whatever the picture
   itself does not. It is why a tall shopfront and a wide clinic can sit in one
   row without either being cut. --shot is set on the element in the card. */
.dcard.haspic .pic::after{content:"";position:absolute;inset:-16px;z-index:-1;
    background-image:var(--shot);background-size:cover;background-position:center;
    filter:blur(13px) saturate(1.12)}
.dcard.haspic .pic img{display:block;width:100%;height:150px;object-fit:contain;position:relative}
.dcard.haspic .body{display:block;padding:13px 16px 15px}
.dcard.haspic::before{top:0;bottom:auto;height:150px;width:4px;z-index:1}

/* The logo beside the name, contained so any shape survives. */
.detail-head .headline{display:flex;align-items:center;gap:14px}
.detail-head .headline .mark{width:64px;height:64px;object-fit:contain;background:#fff;
                             border-radius:12px;padding:6px;flex:0 0 auto}
.detail-head .headline h1{margin:0}

/* Photographs: the first one leads, the rest sit under it. */
.shots{display:grid;grid-template-columns:repeat(auto-fill,minmax(140px,1fr));gap:8px;margin:18px 0}
.shots .shot{display:block;border-radius:var(--radius);overflow:hidden;border:1px solid var(--line);background:var(--paper)}
.shots .shot img{display:block;width:100%;height:120px;object-fit:cover}
.shots .shot.lead{grid-column:1/-1}
/* The lead photograph is shown whole. Cropped to a fixed 230px it zoomed
   a wide flyer about twofold on a phone and cut the logo off one end and
   the phone number off the other. */
.shots .shot.lead img{height:auto;max-height:min(70vh,420px);object-fit:contain;background:#F6F4EC}
/* Finding one village among seventy-two. */
.vfilter{margin:14px 0 6px}
.vfilter input{width:100%;font:inherit;font-size:.95rem;padding:11px 14px;background:#fff;
               border:1px solid var(--line);border-radius:999px}
.vfilter input:focus{outline:3px solid var(--gold);outline-offset:2px;border-color:var(--indigo)}
.vfilter .hint{margin:7px 0 0}
.vgroup{margin-bottom:6px}
.vletter{font-family:var(--display);font-weight:800;font-size:.78rem;letter-spacing:.16em;
         color:var(--red);margin:16px 0 8px;text-transform:uppercase}
[hidden]{display:none !important}
/* ---- portal ---- */
/* What someone says they do in the community: held roles, and asks waiting
   for a phone call. The waiting one must not look like a granted one. */
.askrole{border-left:4px solid var(--gold)}
.askrole h3{font-family:var(--display);font-weight:800;font-size:1rem}
.askrole h3 small{display:block;font-family:var(--body);font-weight:600;font-size:.7rem;
                  letter-spacing:.14em;text-transform:uppercase;color:var(--gold)}
.askrole p{font-size:.85rem;color:var(--muted);margin:8px 0 12px}
.askrole .askrow{display:flex;gap:10px;align-items:center}
.askrole .askskip{margin-top:10px}
.linkbtn{background:none;border:0;padding:0;font:inherit;font-size:.78rem;color:var(--muted);
         text-decoration:underline;cursor:pointer}
.linkbtn:hover{color:var(--ink)}
.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;
         clip:rect(0,0,0,0);white-space:nowrap;border:0}
.rolechips{display:flex;flex-wrap:wrap;gap:6px;margin:0 0 12px}
.rolechip{font-size:.7rem;font-weight:700;border-radius:999px;padding:4px 11px;border:1px solid var(--line)}
.rolechip.on{background:var(--teal);border-color:var(--teal);color:#fff}
.rolechip.wait{background:#FFFBEF;border-color:var(--gold);color:var(--dgold);font-weight:600}

.app{display:flex;min-height:100vh}
.side{width:220px;background:var(--indigo);color:#FDFCF8;padding:18px 0;flex:0 0 auto;display:flex;flex-direction:column}
.side .logo{padding:0 18px 16px}
.side .logo small{display:block;font-size:.6rem;letter-spacing:.2em;text-transform:uppercase;color:var(--gold);font-weight:700}
.side nav{display:flex;flex-direction:column}
.side nav a{display:flex;justify-content:space-between;align-items:center;padding:10px 18px;font-size:.85rem;
            font-weight:600;text-decoration:none;opacity:.82;border-left:3px solid transparent}
.side nav a:hover{opacity:1;background:rgba(255,255,255,.06)}
.side nav a.active{opacity:1;border-left-color:var(--gold);background:rgba(255,255,255,.09)}
.side nav .count{font-size:.64rem;font-weight:800;background:var(--red);border-radius:999px;padding:1px 7px}
.side .grp{padding:14px 18px 5px;font-size:.6rem;font-weight:800;letter-spacing:.18em;text-transform:uppercase;opacity:.5}
.side .foot{margin-top:auto;padding:14px 18px;font-size:.7rem;opacity:.6;line-height:1.5}
.appmain{flex:1;min-width:0;display:flex;flex-direction:column}
.topline{background:#fff;border-bottom:1px solid var(--line);padding:12px 22px;display:flex;
         justify-content:space-between;align-items:center;gap:10px;flex-wrap:wrap}
.topline .hello{font-size:.88rem;font-weight:600}
.topline .hello span{color:var(--muted);font-weight:500}
.avatar{width:32px;height:32px;border-radius:50%;color:#fff;display:grid;place-items:center;
        font-family:var(--display);font-weight:800;font-size:.8rem;background:var(--teal)}
.content{padding:22px;max-width:920px}
@media(max-width:740px){
  .app{flex-direction:column}
  .side{width:100%;flex-direction:row;align-items:center;overflow-x:auto;padding:8px 4px;
        -webkit-overflow-scrolling:touch;scrollbar-width:none}
  .side::-webkit-scrollbar{display:none}
  /* Nothing in the strip may shrink - it scrolls sideways instead of
     collapsing the wordmark under the first nav item. */
  .side .logo,.side nav,.side nav a{flex:0 0 auto}
  .side .logo{padding:0 10px 0 12px}
  .side .logo small{display:none}
  .side nav{flex-direction:row}
  .side nav a{white-space:nowrap;border-left:none;border-bottom:3px solid transparent;padding:8px 11px}
  .side nav a.active{border-bottom-color:var(--gold);border-left-color:transparent}
  .side .grp,.side .foot{display:none}
  .content{padding:16px}
}
@media(max-width:460px){
  /* On a real phone the mark alone is enough - the room goes to the nav. */
  .side .logo b{display:none}
}
h1.app-h{font-family:var(--display);font-weight:800;font-size:1.55rem;margin-bottom:3px}

.tiles{display:grid;grid-template-columns:repeat(2,1fr);gap:11px}
@media(min-width:640px){.tiles{grid-template-columns:repeat(4,1fr)}}
.tile{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:13px 15px}
.tile b{font-family:var(--display);font-weight:800;font-size:1.45rem;display:block;line-height:1.1}
.tile span{font-size:.7rem;color:var(--muted);letter-spacing:.05em;text-transform:uppercase;font-weight:700}
.tile.alert{border-color:var(--red);background:#FBEFED}

.rowitem{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:13px 16px;margin-bottom:9px;
         display:flex;justify-content:space-between;gap:12px;align-items:center;flex-wrap:wrap}
.rowitem h3{font-size:.93rem;font-weight:700}
.rowitem p{font-size:.78rem;color:var(--muted)}
.rowitem .acts{display:flex;gap:7px;flex-wrap:wrap;align-items:center}
.status.action{background:#FBEFED;color:var(--red)}
.status.consent{background:#EDEFF7;color:var(--indigo)}
.status.sold{background:#EEE;color:var(--muted)}

.field{margin-bottom:12px}
.field label{display:block;font-size:.77rem;font-weight:700;margin-bottom:5px}
.field input,.field select,.field textarea{width:100%;border:1.5px solid var(--line);border-radius:10px;
    padding:10px 13px;font-family:var(--body);font-size:.88rem;background:#fff;color:var(--ink)}
.field input:focus,.field select:focus,.field textarea:focus{outline:none;border-color:var(--indigo)}
.field .err{color:var(--red);font-size:.76rem;font-weight:600;margin-top:4px}
.hint{font-size:.73rem;color:var(--muted);margin-top:4px}
.grid2{display:grid;grid-template-columns:1fr 1fr;gap:11px}
@media(max-width:520px){.grid2{grid-template-columns:1fr}}

.steps{counter-reset:s}
.step{display:flex;gap:12px;padding:9px 0;border-bottom:1px dashed var(--line);font-size:.84rem;align-items:flex-start}
.step:last-child{border-bottom:none}
.step::before{counter-increment:s;content:counter(s);flex:0 0 25px;height:25px;border-radius:50%;background:var(--teal);
              color:#fff;display:grid;place-items:center;font-family:var(--display);font-weight:800;font-size:.78rem}
.step b{display:block}
.step span{color:var(--muted);font-size:.78rem}
.upgrade{border:1.5px solid var(--gold);background:#FFFBEF;border-radius:var(--radius);padding:16px 18px;margin-top:12px}
.upgrade h3{font-family:var(--display);font-weight:800;font-size:1.02rem}
.upgrade p{font-size:.82rem;color:#5A5346;margin:4px 0 11px}
.team-c{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:15px 17px;margin-bottom:12px}
.team-c .head{display:flex;justify-content:space-between;align-items:center;gap:10px;flex-wrap:wrap;margin-bottom:7px}
.team-c h3{font-family:var(--display);font-weight:800;font-size:1.06rem}
.team-c .kit{display:inline-block;width:13px;height:13px;border-radius:3px;vertical-align:-1px;margin-right:5px;background:var(--gold)}
.team-c p{font-size:.79rem;color:var(--muted)}
.enterlist{margin-top:11px;border-top:1px dashed var(--line);padding-top:9px}
.enterlist .rowitem{border:none;padding:7px 0;margin-bottom:0;background:transparent}

.authwrap{max-width:400px;margin:0 auto;padding:48px 20px 60px}
.authwrap h1{font-family:var(--display);font-weight:800;font-size:1.7rem;margin-bottom:4px}
.authcard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:20px 22px;margin-top:16px}
.flash{background:#EAF2EF;border-left:4px solid var(--teal);border-radius:0 10px 10px 0;padding:10px 14px;
       font-size:.84rem;margin-bottom:12px}
.otpinput input{font-family:var(--display);font-size:1.5rem;letter-spacing:.4em;text-align:center}

/* ---- match day ---- */
.mtabs{display:flex;gap:8px;overflow-x:auto;padding:14px 0 4px}
.mtab{flex:0 0 auto;border:1.5px solid var(--line);background:#fff;border-radius:999px;padding:9px 18px;
      font-size:.86rem;font-weight:700;cursor:pointer;color:var(--muted);text-decoration:none}
.mtab.on{background:var(--ink);border-color:var(--ink);color:#fff}
/* The one tab that is happening right now. */
.mtab.live{border-color:var(--red);color:var(--red);font-weight:800}
.mtab.live::before{content:"";display:inline-block;width:8px;height:8px;border-radius:50%;
    background:var(--red);margin-right:7px;vertical-align:middle}
.menu{display:grid;grid-template-columns:1fr;gap:11px}
@media(min-width:560px){.menu{grid-template-columns:1fr 1fr}}
.dish{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:13px 15px;
      display:flex;justify-content:space-between;gap:10px}
/* ---- the ground itself, with the zones on it ----
   The drawn pitch is a picture of a football field; this is a picture of
   THIS one, so somebody standing on the slope can find where they are. */
.groundmap{position:relative;border-radius:var(--radius);overflow:hidden;line-height:0;margin-bottom:10px}
.groundmap img{width:100%;height:auto;display:block}
.zonepin{position:absolute;transform:translate(-50%,-50%);min-width:38px;min-height:38px;
    border-radius:50%;border:2px solid #fff;background:rgba(31,41,51,.72);color:var(--gold);
    font-family:var(--display);font-weight:800;font-size:1.05rem;line-height:1;cursor:pointer;
    display:grid;place-items:center;padding:0;box-shadow:0 2px 8px rgba(0,0,0,.35)}
.zonepin:hover{background:rgba(31,41,51,.9)}
/* The one they have chosen, readable at arm's length in sunlight. */
.zonepin.on{background:var(--gold);color:var(--ink);border-color:var(--ink)}
.groundcredit{margin:-4px 0 10px;font-size:.7rem}

/* A picture of the plate, beside it rather than above: the row has to stay
   thumbable on a phone with a whole menu under it. */
.dish .dishpic{flex:0 0 64px;align-self:flex-start;text-decoration:none;cursor:zoom-in;
    background:#EDEFF7;border-radius:10px;overflow:hidden;display:grid;place-items:center;height:64px}
.dish .dishpic img{max-width:100%;max-height:64px;object-fit:contain;display:block}
.dish h3{font-size:.93rem;font-weight:700}
.dish p{font-size:.76rem;color:var(--muted)}
.dish .price{font-family:var(--display);font-weight:800;color:var(--teal);white-space:nowrap}
.qty{display:flex;align-items:center;gap:8px;margin-top:8px}
.qty button{width:27px;height:27px;border-radius:50%;border:1.5px solid var(--line);background:#fff;
            font-weight:800;cursor:pointer;line-height:1;color:var(--ink)}
.qty output{font-family:var(--display);font-weight:800;min-width:18px;text-align:center}
.fieldmap{background:var(--pitch);border-radius:var(--radius);padding:13px;margin-top:4px}
.fieldmap svg{width:100%;height:auto;display:block}
/* Pins are placed against the picture, so whatever holds them must be the
   thing they are measured from - the drawing as much as the photograph. */
.fieldmap.pinned,.groundmap.pinned{position:relative}
.zones{display:grid;grid-template-columns:repeat(2,1fr);gap:9px;margin-top:11px}
@media(min-width:560px){.zones{grid-template-columns:repeat(4,1fr)}}
.zone{border:2px solid var(--line);background:#fff;border-radius:12px;padding:10px 12px;cursor:pointer;
      text-align:left;display:block}
.zone b{font-family:var(--display);font-weight:800;display:block;font-size:.98rem}
.zone span{font-size:.69rem;color:var(--muted)}
.zone input{position:absolute;opacity:0;pointer-events:none}
.zone:has(input:checked){border-color:var(--gold);background:#FFFBEF}
.zone:focus-within{outline:3px solid var(--gold);outline-offset:2px}
.fee{background:#FFFBEF;border:1.5px solid var(--gold);border-radius:var(--radius);padding:13px 16px;
     display:flex;justify-content:space-between;align-items:center;gap:10px;flex-wrap:wrap;margin:14px 0}
.fee b{font-family:var(--display);font-weight:800;font-size:1.2rem}
.fee p{font-size:.77rem;color:#5A5346}
.track{display:flex;margin:14px 0 6px}
.tstep{flex:1;text-align:center;position:relative;font-size:.68rem;font-weight:700;color:var(--muted)}
.tstep::before{content:"";display:block;width:24px;height:24px;border-radius:50%;background:#fff;
               border:2.5px solid var(--line);margin:0 auto 6px;position:relative;z-index:2}
.tstep::after{content:"";position:absolute;top:11px;left:-50%;width:100%;height:3px;background:var(--line);z-index:1}
.tstep:first-child::after{display:none}
.tstep.done::before{background:var(--teal);border-color:var(--teal)}
.tstep.done::after{background:var(--teal)}
.tstep.now::before{background:var(--gold);border-color:var(--gold);animation:pulse 1.4s infinite}
@keyframes pulse{0%,100%{box-shadow:0 0 0 0 rgba(227,167,34,.5)}50%{box-shadow:0 0 0 8px rgba(227,167,34,0)}}
.ordernum{font-family:var(--display);font-weight:800;font-size:1.9rem;letter-spacing:.04em}
.shopgrid{display:grid;grid-template-columns:repeat(2,1fr);gap:12px}
@media(min-width:620px){.shopgrid{grid-template-columns:repeat(3,1fr)}}
.prod{background:#fff;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden;
      display:flex;flex-direction:column}
.prod .img{height:96px;display:grid;place-items:center;background:#EDEFF7}
/* Contain, not cover: the whole item, the way the conversion keeps it. */
.prod .img img{max-width:100%;max-height:96px;object-fit:contain;display:block}
/* The photo is a link to itself, and must not read as one. */
.prod a.img{text-decoration:none;cursor:zoom-in}

/* ---- age-restricted goods ----
   Marked per bottle, not per shop: a tavern sells Savanna 0.0 beside the
   beer, and hiding a whole shelf would hide what nobody needs to be
   eighteen to buy. */
.age18{display:inline-block;margin-left:6px;background:var(--red);color:#fff;border-radius:999px;
    padding:1px 7px;font-size:.62rem;font-weight:800;letter-spacing:.04em;vertical-align:middle}
/* The risk notice on an entry form. Plain and readable rather than small
   print - a term like this has to be put in front of somebody, not hidden
   where it can be scrolled past. */
.indemnity[hidden]{display:none}
.risks li{display:list-item;list-style:disc;margin-left:18px;padding:6px 0;border-bottom:none;font-size:.86rem}

.agebox{display:flex;gap:10px;align-items:flex-start;border:1.5px solid var(--gold);background:#FFFBEF;
    border-radius:var(--radius);padding:12px 14px;margin:12px 0;cursor:pointer;font-size:.85rem;font-weight:700}
/* Sized explicitly: a checkbox that inherits width:100% from a form takes the
   whole box and leaves the sentence a column one word wide. */
.agebox input[type=checkbox]{width:18px;height:18px;min-width:18px;margin:2px 0 0;flex:0 0 18px}
.agebox>span{flex:1 1 auto;min-width:0}
.agebox small{display:block;color:var(--muted);font-size:.76rem;font-weight:400;margin-top:3px;line-height:1.45}

/* ---- the basket, written out before it is paid for ---- */
.basketlist{background:#fff;border:1px solid var(--line);border-radius:var(--radius);
    padding:13px 16px;margin-bottom:10px}
.basketlist>b{display:block;font-size:.78rem;letter-spacing:.06em;text-transform:uppercase;
    color:var(--muted);margin-bottom:8px}
.basketlist ul{list-style:none;margin:0;padding:0}
.basketlist li{display:flex;justify-content:space-between;gap:12px;align-items:baseline;
    padding:5px 0;border-bottom:1px dashed var(--line);font-size:.86rem}
.basketlist li:last-child{border-bottom:none}
.basketlist small{color:var(--muted)}
.prod .pad{padding:10px 13px 13px;flex:1;display:flex;flex-direction:column}
.prod h3{font-size:.86rem;font-weight:700;line-height:1.3}
.prod .price{font-family:var(--display);font-weight:800;color:var(--teal);margin:3px 0 7px}
.prod .tagline{font-size:.7rem;color:var(--muted)}
.prod .qty{margin-top:auto}
.soon18{font-size:.6rem;font-weight:800;letter-spacing:.12em;text-transform:uppercase;background:#F6ECD9;
        color:var(--dgold);border-radius:999px;padding:3px 9px;align-self:flex-start;margin-bottom:5px}
.pickup{background:#fff;border:1.5px dashed var(--line);border-radius:var(--radius);padding:13px 16px;
        font-size:.82rem;color:var(--muted);margin-top:14px}
.pickup b{color:var(--ink)}

/* ---- sponsor slots ---- */
.sponsor{border:1.5px solid var(--gold);background:#FFFBEF;border-radius:var(--radius);padding:14px 17px;
         display:flex;gap:13px;align-items:center;flex-wrap:wrap;margin-bottom:10px}
.sponsor .badge{font-size:.62rem;font-weight:800;letter-spacing:.14em;text-transform:uppercase;
                background:var(--gold);color:var(--ink);border-radius:999px;padding:3px 10px}
.sponsor h3{font-size:.95rem;font-weight:700}
.sponsor p{font-size:.8rem;color:var(--muted)}

/* ---- squad roster ---- */
table.roster{width:100%;border-collapse:collapse;font-size:.88rem;min-width:460px}
table.roster th{text-align:left;font-size:.65rem;letter-spacing:.11em;text-transform:uppercase;
                color:var(--muted);padding:8px 10px;border-bottom:1px solid var(--line)}
table.roster td{padding:5px 6px;border-bottom:1px solid #F3F0E7;vertical-align:middle}
table.roster tr:last-child td{border-bottom:none}
table.roster td.no{font-family:var(--display);font-weight:800;color:var(--muted);text-align:center;width:44px}
table.roster input{width:100%;border:1.5px solid var(--line);border-radius:8px;padding:8px 10px;
                   font-family:var(--body);font-size:.85rem;background:#fff;color:var(--ink)}
table.roster input:focus{outline:none;border-color:var(--indigo)}
table.roster tr.over{background:#FBEFED}
.rosterwrap{overflow-x:auto}
.rostercount{font-size:.78rem;font-weight:700;color:var(--muted);margin-top:9px}
.rostercount.ok{color:var(--teal)}
.rostercount.short{color:var(--red)}

/* ---- one card per stand on the ground ---- */
.standcard{padding:0;overflow:hidden}
.standhead{display:flex;justify-content:space-between;align-items:center;gap:12px;
           padding:14px 18px;border-bottom:1px solid var(--line);background:#FBFAF6}
.standhead h3{font-family:var(--display);font-weight:800;font-size:1.05rem}
.standhead p{font-size:.78rem;color:var(--muted);margin-top:2px}
.standbadge{font-family:var(--display);font-weight:800;font-size:1rem;background:var(--ink);color:#FDFCF8;
            width:34px;height:34px;border-radius:50%;display:grid;place-items:center;flex:0 0 auto}
.standcard .menu{padding:16px 18px}
.standcard .fee{margin:0 18px 18px}
.standcard[data-stand].active{border-color:var(--gold)}
.standtotal{display:flex;justify-content:space-between;align-items:center;gap:10px;
            padding:12px 18px;border-top:1px solid var(--line);background:#FBFAF6;font-size:.86rem}
.standtotal span{color:var(--muted);font-weight:600}
.standtotal b{font-family:var(--display);font-weight:800;font-size:1.02rem;color:var(--teal)}

/* ---- the stand owner's own screen: thumbs, sunlight, one hand free ---- */
.standorder{background:#fff;border:1px solid var(--line);border-left:4px solid var(--gold);border-radius:var(--radius);padding:14px 15px;margin-bottom:12px}
.standorder-head{display:flex;justify-content:space-between;align-items:flex-start;gap:10px}
.standorder-head .hint{display:block;margin-top:2px}
.standorder-where{margin:9px 0 0;font-size:.92rem}
.standorder-where b{font-family:var(--display);font-weight:800}
.standorder-items{list-style:none;margin:9px 0 0;padding:0;font-size:.92rem}
.standorder-items li{padding:3px 0;border-bottom:1px dashed var(--line)}
.standorder-items li:last-child{border-bottom:none}
.standorder-items b{font-family:var(--display);font-weight:800;margin-right:5px}
.standorder-money{margin:9px 0 0;font-size:.85rem;color:var(--muted);font-weight:600}
.standorder-money .owed{color:var(--red);font-weight:800}
.standactions{display:flex;flex-wrap:wrap;gap:8px;margin-top:12px}
.standactions .btn{padding:13px 20px;font-size:.95rem;min-height:48px}
.runnerform{display:flex;gap:8px;flex:1 1 100%}
.runnerform select{flex:1;min-height:48px;border:1.5px solid var(--line);border-radius:999px;padding:0 14px;font:inherit;background:#fff}
.btn.no{background:transparent;border:1.5px solid var(--line);color:var(--muted)}
.btn.no:hover{border-color:var(--red);color:var(--red)}
.standorder-who{font-family:var(--display);font-weight:800;font-size:1.15rem;margin:8px 0 0;color:var(--indigo)}

/* ---- the hand-off card: read at arm's length, through smoke ---- */
.slip{background:#fff;border:2px solid var(--ink);border-radius:var(--radius);overflow:hidden}
.slip-top{display:flex;justify-content:space-between;align-items:baseline;gap:10px;
          background:var(--ink);color:#fff;padding:12px 16px}
.slip-top b{font-family:var(--display);font-weight:800;font-size:1.9rem;line-height:1}
.slip-top span{font-weight:800;font-size:.9rem;letter-spacing:.04em;text-align:right}
.slip-who{font-family:var(--display);font-weight:800;font-size:2.4rem;line-height:1.05;
          margin:0;padding:16px 16px 4px;color:var(--indigo)}
.slip-where{margin:0;padding:0 16px 14px;font-size:1.25rem;font-weight:700}
.slip-where span{display:block;font-weight:500;font-size:1rem;color:var(--muted);margin-top:2px}
.slip-items{list-style:none;margin:0;padding:12px 16px;border-top:2px dashed var(--line);font-size:1.15rem}
.slip-items li{padding:4px 0}
.slip-items b{font-family:var(--display);font-weight:800;margin-right:6px}
.slipactions{display:flex;flex-wrap:wrap;gap:9px;margin-top:14px}
.slipactions .btn{padding:14px 20px;font-size:.95rem;min-height:50px}
.outwith{background:#EDEFF7;border-radius:var(--radius);padding:11px 14px;margin-bottom:9px}
.outwith-who{margin:0;font-family:var(--display);font-weight:800;font-size:1.05rem;
             display:flex;justify-content:space-between;gap:10px}
.outwith-who b{color:var(--red)}
.outwith-list{margin:4px 0 0;font-size:.85rem}
.outwith-list a{color:var(--indigo);font-weight:600}
.btn[disabled]{opacity:.5;cursor:not-allowed}

/* ---- her own menu: sold out, mid-service, one tap ---- */
.menucard{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:12px 14px;margin-bottom:11px}
.menucard-top{display:flex;justify-content:space-between;align-items:center;gap:10px;
              padding-bottom:9px;border-bottom:1px solid var(--line)}
.menucard-top b{font-family:var(--display);font-weight:800;font-size:1.05rem}
.menucard-shut{margin:9px 0 0;font-size:.8rem;color:var(--red);font-weight:600}
.dishrow{display:flex;justify-content:space-between;align-items:center;gap:10px;padding:9px 0;
         border-bottom:1px dashed var(--line)}
.dishrow:last-child{border-bottom:none}
.dishrow b{font-weight:700}
.dishrow b.gone{text-decoration:line-through;color:var(--muted)}
.dishrow span{color:var(--muted);font-size:.85rem;margin-left:7px}
.dishrow .btn{min-height:40px}

/* ---- entering an event as a person, or a household ---- */
.picks{display:grid;gap:9px}
@media(min-width:640px){.picks{grid-template-columns:repeat(2,1fr)}}
.pick{display:block;border:1.5px solid var(--line);border-radius:var(--radius);padding:11px 13px;cursor:pointer}
.pick:has(input:checked){border-color:var(--indigo);background:#EDEFF7}
.pick input{margin-right:7px}
.pick b{font-family:var(--display);font-weight:800}
.pick span{display:block;font-size:.78rem;color:var(--muted);margin-top:2px;padding-left:21px}
.entrant{display:grid;gap:9px;align-items:end;padding:11px 0;border-bottom:1px dashed var(--line)}
@media(min-width:640px){.entrant{grid-template-columns:2fr 1.2fr 1.2fr auto}}
.entrant .field{margin:0}
.entrant .opt{font-weight:500;color:var(--muted);font-size:.72rem}

/* ---- the squad list a coach can actually see ---- */
.err{color:var(--red);font-size:.76rem;font-weight:600;margin-top:3px}
.squadrow{display:flex;align-items:center;gap:10px;padding:7px 0;border-bottom:1px dashed var(--line)}
.squadrow:last-of-type{border-bottom:none}
.squadrow b{flex:1;font-weight:600}
.squadrow form{margin:0}
.shirt{display:grid;place-items:center;width:28px;height:28px;flex:0 0 auto;border-radius:50%;
       background:var(--indigo);color:#fff;font-family:var(--display);font-weight:800;font-size:.78rem}
.agebadge{font-size:.7rem;font-weight:800;background:#EAF2EF;color:var(--teal);border-radius:999px;padding:2px 9px}
.agebadge.over{background:#FBEFED;color:var(--red)}

/* ---- a public team sheet: names and numbers, nothing else ---- */
.sheet{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:6px 14px}
.sheetrow{display:flex;align-items:center;gap:11px;padding:9px 0;border-bottom:1px dashed var(--line)}
.sheetrow:last-child{border-bottom:none}
.sheetrow b{font-weight:600}
.teamchips{display:flex;flex-wrap:wrap;gap:7px;margin-bottom:12px}
.teamchip{display:inline-flex;align-items:center;gap:6px;border:1.5px solid var(--line);border-radius:999px;
          padding:6px 13px;font-size:.82rem;font-weight:600;text-decoration:none;color:var(--ink);background:#fff}
.teamchip:hover{border-color:var(--indigo);color:var(--indigo)}
.teamchip.plain{cursor:default;background:#F4F2EA}
.more{font-weight:700;color:var(--indigo)}

/* ---- albums: a few highlights here, the rest where they already live ---- */
.album .thumb{position:relative;overflow:hidden}
.album .thumb img{display:block;width:100%;height:112px;object-fit:cover}
.album .thumb .count{position:absolute;right:8px;bottom:8px;background:rgba(31,41,51,.82);color:#fff;
                     font-size:.68rem;font-weight:700;border-radius:999px;padding:3px 10px;letter-spacing:.02em}
.album .pad .btn{margin-top:9px}

/* ---- what an organiser runs, on their own portal ---- */
.runs{display:flex;flex-wrap:wrap;gap:12px;align-items:center;justify-content:space-between;
      background:#fff;border:1px solid var(--line);border-left:4px solid var(--indigo);
      border-radius:var(--radius);padding:14px 16px;margin-bottom:11px}
.runs h3{font-family:var(--display);font-weight:800;font-size:1.02rem;margin:0 0 3px}
.runs p{margin:0;font-size:.86rem;color:var(--muted)}
.runs-counts{margin-top:5px !important}
.runs-counts .waiting{color:var(--red);font-weight:800}
.hidden{display:none !important}
[data-home-town]{margin-top:7px}

/* ---- the one or two businesses who paid for the trophies ---- */
.sponsors{display:grid;gap:12px;grid-template-columns:1fr;margin-bottom:16px}
@media(min-width:560px){.sponsors{grid-template-columns:repeat(auto-fit,minmax(220px,1fr))}}
.sponsorcard{display:flex;flex-direction:column;align-items:center;gap:6px;text-align:center;
             background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:16px 14px}
.sponsorcard img{max-width:100%;height:auto;max-height:110px;object-fit:contain}
.sponsorcard b{font-family:var(--display);font-weight:800;font-size:1rem}
.sponsorcard .level{font-size:.62rem;font-weight:800;letter-spacing:.12em;text-transform:uppercase;color:var(--dgold)}
.sponsorcard .gave{font-size:.82rem;color:var(--muted)}
.sponsorcard a{font-size:.8rem;font-weight:700;color:var(--indigo);text-decoration:none}
.teamchip .badge{width:20px;height:20px;object-fit:contain;margin-right:2px}
.teamhead{display:flex;align-items:center;gap:12px;flex-wrap:wrap}
.teamhead img{object-fit:contain}

/* ---- an album page: a few photographs, then the way to the rest ---- */
a.album{display:block;text-decoration:none;color:inherit;transition:border-color .12s ease}
a.album:hover{border-color:var(--indigo)}
a.album .pad .btn{margin-top:9px;pointer-events:none}
.gallery{display:grid;gap:10px;grid-template-columns:repeat(auto-fill,minmax(150px,1fr));margin-bottom:12px}
.gallery a{display:block;border:1px solid var(--line);border-radius:var(--radius);overflow:hidden;background:#fff}
/* Contain, not cover: the conversion already keeps the whole photograph, and
   a second crop here would undo it. Square tiles still line up; a tall
   photograph simply sits on the sand rather than losing its top. */
.gallery img{display:block;width:100%;aspect-ratio:1;height:auto;object-fit:contain;background:#F6F4EC}
.gallery a:hover{border-color:var(--indigo)}
.albumlinks{display:flex;flex-wrap:wrap;gap:7px;margin-bottom:10px}

/* ---- lightbox ---- */
/* A photograph over the page rather than a new tab. The markup is still a plain
   link, so none of this is required for the picture to open. */
.lbox{border:0;padding:0;max-width:100vw;max-height:100vh;width:100vw;height:100vh;
      background:transparent;overflow:hidden;display:none}
/* The dark sits on the dialog itself, not only on ::backdrop - the dialog
   covers the whole viewport, so a transparent one let the page read through. */
.lbox[open]{display:grid;grid-template-columns:auto 1fr auto;grid-template-rows:1fr auto;
            align-items:center;justify-items:center;gap:4px;
            background:rgba(16,20,26,.95)}
.lbox::backdrop{background:rgba(16,20,26,.95)}
.lbox img{grid-column:2;grid-row:1;max-width:100%;max-height:calc(100vh - 76px);
          width:auto;height:auto;object-fit:contain;border-radius:8px}
.lbox .lbclose{position:fixed;top:10px;right:12px;z-index:2;width:44px;height:44px;
               border-radius:50%;border:0;cursor:pointer;font-size:1.6rem;line-height:1;
               background:rgba(0,0,0,.55);color:#fff}
.lbox .lbnav{width:44px;height:64px;border:0;border-radius:8px;cursor:pointer;
             font-size:2rem;line-height:1;background:rgba(0,0,0,.45);color:#fff}
.lbox .lbprev{grid-column:1;grid-row:1}
.lbox .lbnext{grid-column:3;grid-row:1}
.lbox .lbnav:hover,.lbox .lbclose:hover{background:rgba(0,0,0,.75)}
.lbox .lbcap{grid-column:1/-1;grid-row:2;margin:0;padding:10px 14px;color:#F3F1EA;
             font-size:.8rem;text-align:center;display:flex;gap:12px;justify-content:center;
             align-items:center;flex-wrap:wrap}
.lbox .lbcount{color:#B9BDC4;font-size:.72rem}
.lbox .lbfull{color:var(--gold);font-weight:700;text-decoration:none}
.lbox .lbfull:hover{text-decoration:underline}
@media (max-width:560px){
  /* On a phone the arrows sit under the picture, not over it - a 44px target
     on each edge of a small screen eats the photograph. */
  .lbox[open]{grid-template-columns:1fr;grid-template-rows:1fr auto auto}
  .lbox img{grid-column:1;max-height:calc(100vh - 140px)}
  /* Both sit in the same cell, one pushed left and one right, so they share a
     line without any nudging. */
  .lbox .lbprev,.lbox .lbnext{grid-column:1;grid-row:2;width:88px;height:44px}
  .lbox .lbprev{justify-self:start;margin-left:14px}
  .lbox .lbnext{justify-self:end;margin-right:14px}
  .lbox .lbcap{grid-row:3}
}

/* ---- home, option 1b: find your village first ---- */
/* Handoff palette mapped onto the locked tokens: its navy is our indigo, its
   green our teal, its yellow our gold. One palette, not two. */
.homehero{background:var(--teal);padding:52px 0 44px;color:#fff}
.homehero .kicker{font-size:.75rem;font-weight:700;letter-spacing:.18em;text-transform:uppercase;color:var(--gold)}
.homehero h1{font-family:var(--display);font-size:clamp(2.1rem,6vw,3.4rem);font-weight:800;
             letter-spacing:-.03em;line-height:1;margin:10px 0 0}
.homehero .lede{font-size:1.05rem;line-height:1.5;color:rgba(255,255,255,.85);max-width:52ch;margin-top:10px}

.herosearch{position:relative;display:flex;gap:10px;max-width:720px;margin-top:24px}
.herosearch input{flex:1 1 auto;min-width:0;background:#fff;border:0;border-radius:8px;
                  padding:17px 20px;font:inherit;font-size:1rem;color:var(--ink)}
.herosearch input::placeholder{color:#9A958A}
.herosearch .btn{padding:17px 26px;border-radius:8px;white-space:nowrap}

.suggest{position:absolute;top:calc(100% + 6px);left:0;right:0;z-index:30;background:#fff;
         border:1px solid var(--line);border-radius:10px;overflow:hidden;
         box-shadow:0 14px 30px rgba(31,41,51,.16);max-height:60vh;overflow-y:auto}
.suggest .sgroup{font-size:.62rem;font-weight:800;letter-spacing:.14em;text-transform:uppercase;
                 color:var(--muted);padding:10px 14px 4px}
.suggest .srow{display:block;padding:8px 14px;text-decoration:none;color:var(--ink)}
.suggest .srow b{display:block;font-size:.9rem}
.suggest .srow span{display:block;font-size:.72rem;color:var(--muted)}
.suggest .srow:hover,.suggest .srow:focus{background:#F3EFE4;outline:none}

.villagechips{display:flex;flex-wrap:wrap;gap:8px;align-items:center;margin-top:22px}
.villagechips .chiplabel{font-size:.72rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;
                         color:rgba(255,255,255,.6);margin-right:6px}
.vchip{font-size:.85rem;font-weight:600;color:#fff;text-decoration:none;
       border:1.5px solid rgba(255,255,255,.35);border-radius:999px;padding:7px 15px}
.vchip:hover{background:rgba(255,255,255,.12);border-color:rgba(255,255,255,.6)}

/* The three doors, demoted to a ruled band. */
/* Filled panels, as they were before - the ruled band read as sub-navigation
   next to the cards below it, and these are the three main ways in. */
.doors{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:14px;
       max-width:1100px;margin:22px auto 26px;padding:0 20px}
.door{padding:22px 22px 20px;display:flex;flex-direction:column;gap:7px;text-decoration:none;
      border-radius:var(--radius);color:#FDFCF8;transition:transform .15s ease}
.door:hover{transform:translateY(-3px)}
.door .num{font-family:var(--display);font-size:.68rem;font-weight:800;letter-spacing:.18em;
           text-transform:uppercase;opacity:.75}
.door h2{font-family:var(--display);font-size:1.4rem;font-weight:800;letter-spacing:-.02em;color:#fff}
.door p{font-size:.88rem;line-height:1.5;opacity:.9}
.door .go{align-self:flex-start;margin-top:5px;font-size:.83rem;font-weight:700;
          border-bottom:2px solid var(--gold);padding-bottom:2px}
.door.v{background:var(--teal)}
.door.t{background:var(--indigo)}
.door.e{background:var(--red)}
.door:focus-visible{outline:3px solid var(--gold);outline-offset:3px}

/* Big places as cards. Equal height, place line pinned to the bottom - names
   run from 13 to 43 characters and the row breaks without it. */
.bigplaces{display:grid;grid-template-columns:repeat(4,minmax(0,1fr));gap:18px;align-items:stretch;margin-bottom:20px}
.bigplace{display:flex;flex-direction:column;gap:10px;background:#fff;border:1px solid var(--line);
          border-radius:10px;padding:22px 20px;text-decoration:none;
          box-shadow:0 1px 0 rgba(31,41,51,.06),0 10px 24px rgba(31,41,51,.05)}
.bigplace:hover{box-shadow:0 14px 30px rgba(31,41,51,.1)}
.bigplace .bar{width:30px;height:4px;border-radius:999px;background:var(--muted)}
.bigplace .cat{font-size:.66rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;color:var(--muted)}
.bigplace b{font-size:1.02rem;font-weight:700;color:var(--ink);line-height:1.25}
.bigplace .where{font-size:.85rem;color:var(--teal);margin-top:auto;padding-top:6px}
.bigplace.a-teal .bar{background:var(--teal)}
.bigplace.a-red .bar{background:var(--red)}
.bigplace.a-gold .bar{background:var(--gold)}
.bigplace.a-indigo .bar{background:var(--indigo)}
.bigplace.a-teal:hover b{color:var(--teal)}
.bigplace.a-red:hover b{color:var(--red)}
.bigplace.a-gold:hover b{color:var(--dgold)}
.bigplace.a-indigo:hover b{color:var(--indigo)}

/* What's on: an invitation, not an empty box. */
.whatson{display:flex;align-items:center;justify-content:space-between;gap:30px;flex-wrap:wrap;
         background:var(--indigo);border-radius:10px;padding:24px 28px;margin:18px 0}
.whatson .said .h{display:flex;align-items:baseline;gap:12px;font-family:var(--display);
                  font-size:1.25rem;font-weight:800;color:#fff}
.whatson .said .h small{font-family:var(--body);font-size:.72rem;font-weight:600;letter-spacing:.16em;
                        text-transform:uppercase;color:rgba(255,255,255,.55)}
.whatson .said p{font-size:.93rem;color:rgba(255,255,255,.8);margin-top:4px}
.whatson .acts{display:flex;gap:10px;flex-wrap:wrap}
.btn.onnavy{background:transparent;color:#fff;border:1.5px solid rgba(255,255,255,.3)}
.btn.onnavy:hover{border-color:rgba(255,255,255,.6)}

/* Search results page. */
.bigsearch{display:flex;gap:10px;max-width:720px;margin:14px 0 18px}
.bigsearch input{flex:1 1 auto;min-width:0;background:#fff;border:1px solid var(--line);border-radius:8px;
                 padding:15px 18px;font:inherit;font-size:1rem;color:var(--ink)}
.bigsearch .btn{padding:15px 24px;border-radius:8px}
.reslist{display:flex;flex-direction:column;margin-bottom:6px}
.res{display:flex;flex-direction:column;gap:2px;padding:12px 2px;text-decoration:none;
     border-bottom:1px solid var(--line);color:var(--ink)}
.res:hover{background:rgba(38,53,107,.03)}
.res b{font-size:.95rem;font-weight:700}
.res span{font-size:.78rem;color:var(--muted)}
.field .opt{font-weight:400;color:var(--muted)}

/* Every interactive element gets a visible ring - the browser default is not
   enough on the coloured bands. */
.homehero a:focus-visible,.homehero input:focus-visible,.homehero button:focus-visible,
.whatson a:focus-visible{outline:3px solid #fff;outline-offset:2px}
.door:focus-visible,.bigplace:focus-visible,.res:focus-visible{outline:3px solid var(--gold);outline-offset:2px}

@media (max-width:1199px){
  .bigplaces{grid-template-columns:repeat(2,minmax(0,1fr))}
}
@media (max-width:899px){
  .homehero{padding:36px 0 32px}
  .bigplaces{grid-template-columns:1fr}
  /* The doors stack, so the dividers move from the side to the top. */
  .doors{grid-template-columns:1fr}
  .door{border-right:0;border-top:1px solid var(--line)}
  .door:first-child{border-top:0}
  .herosearch{flex-direction:column}
  .herosearch .btn{width:100%}
  .whatson{flex-direction:column;align-items:flex-start;gap:16px}
  .whatson .acts{width:100%}
  .whatson .acts .btn{flex:1 1 auto;text-align:center}
}

/* ---- section header bands ---- */
/* The home hero, generalised. A reader who followed the teal Villages door
   lands on a teal page; the colour is the section, not decoration. */
.pagehero{padding:34px 0 30px;margin-bottom:20px}
.pagehero .wrap{padding-top:0;padding-bottom:0}
.pagehero .crumb{color:rgba(255,255,255,.7)}
.pagehero .crumb a{color:rgba(255,255,255,.9)}
.pagehero .pg{color:#fff}
.pagehero .pg em{color:var(--gold);font-style:normal}
.pagehero .sub,.pagehero .lede{color:rgba(255,255,255,.85);max-width:60ch}
.pagehero .hint{color:rgba(255,255,255,.7)}

.pagehero.t-teal{background:var(--teal)}
.pagehero.t-indigo{background:var(--indigo)}
.pagehero.t-red{background:var(--red)}
.pagehero.t-pitch{background:var(--pitch)}

/* Gold is too light to carry white text, so this one flips to ink and the
   highlight becomes indigo rather than gold-on-gold. */
.pagehero.t-gold{background:var(--gold)}
.pagehero.t-gold .pg,.pagehero.t-gold .crumb a{color:var(--ink)}
.pagehero.t-gold .pg em{color:var(--indigo)}
.pagehero.t-gold .crumb,.pagehero.t-gold .sub,.pagehero.t-gold .hint{color:rgba(31,41,51,.75)}
.pagehero.t-gold .chip{color:var(--ink);border-color:rgba(31,41,51,.3)}
.pagehero.t-gold .chip.on{background:var(--ink);color:#fff;border-color:var(--ink)}

/* Filter chips sitting on a coloured band. */
.pagehero .chips{margin-top:16px}
.pagehero .chip{color:#fff;border-color:rgba(255,255,255,.35);background:transparent}
.pagehero .chip:hover{background:rgba(255,255,255,.12);border-color:rgba(255,255,255,.6)}
.pagehero .chip.on{background:#fff;color:var(--ink);border-color:#fff}
.pagehero .vfilter input{background:#fff;border:0}

.pagehero a:focus-visible,.pagehero input:focus-visible,.pagehero button:focus-visible{
  outline:3px solid #fff;outline-offset:2px}
.pagehero.t-gold a:focus-visible,.pagehero.t-gold input:focus-visible{outline-color:var(--ink)}

/* An empty section is an invitation, not a dead end - the same idea the
   What's on bar uses on the home page. */
.invite{display:flex;align-items:center;justify-content:space-between;gap:24px;flex-wrap:wrap;
        background:#fff;border:1px solid var(--line);border-left:4px solid var(--gold);
        border-radius:10px;padding:20px 22px;margin:14px 0}
.invite .said b{display:block;font-family:var(--display);font-size:1.05rem;font-weight:800;color:var(--ink)}
.invite .said p{font-size:.9rem;color:var(--muted);margin-top:4px;max-width:56ch}
.invite .acts{display:flex;gap:10px;flex-wrap:wrap}

@media (max-width:899px){
  .pagehero{padding:24px 0 22px}
  .invite{flex-direction:column;align-items:flex-start}
  .invite .acts{width:100%}
  .invite .acts .btn{flex:1 1 auto;text-align:center}
}

/* ---- tournament identity ---- */
.tlogo{width:28px;height:28px;object-fit:contain;vertical-align:-6px;margin-right:8px}
.tlogo.big{width:60px;height:60px;margin-right:12px;background:#fff;border-radius:10px;padding:5px}
h1.withlogo{display:flex;align-items:center;gap:0;flex-wrap:wrap}

/* A poster is portrait and text-heavy: never cropped, never stretched, and
   capped so it does not push the fixtures off the first screen. */
.poster{display:block;max-width:300px;margin:18px auto 22px}
.poster img{width:100%;height:auto;border-radius:var(--radius);border:1px solid var(--line);
            box-shadow:0 10px 24px rgba(31,41,51,.08)}
.poster:hover img{box-shadow:0 14px 30px rgba(31,41,51,.14)}
@media (max-width:560px){ .poster{max-width:100%} }

/* A drawn stand-in where a listing has no photograph. Same box as a real
   picture so a row of cards keeps its rhythm. */
.dcard .pic.drawn{display:block;overflow:hidden;height:150px}
.dcard .pic.drawn .sky,.dcard .pic.drawn svg{display:block;width:100%;height:150px}

/* ---- help ---- */
.helpsheet{max-width:none}
.helpsheet .whofor{font-size:.68rem;font-weight:700;letter-spacing:.16em;text-transform:uppercase;
                   color:var(--muted);margin-bottom:20px}
.hstep{display:grid;grid-template-columns:40px 1fr;gap:16px;align-items:start;margin-bottom:26px}
.hnum{width:36px;height:36px;border-radius:50%;background:var(--teal);color:#FCFBF6;
      font-family:var(--display);font-weight:800;display:grid;place-items:center}
.hstep:nth-of-type(even) .hnum{background:var(--indigo)}
.hbody h2{font-family:var(--display);font-weight:800;font-size:1.15rem;margin-bottom:7px}
.hbody p{font-size:.93rem;line-height:1.6;margin-bottom:10px}
.hbody p:last-child{margin-bottom:0}
.hbody ul,.hbody ol{margin:8px 0 12px;padding-left:20px;font-size:.93rem;line-height:1.6}
.hbody li{margin-bottom:6px}
.hbody .k{font-weight:700;color:var(--indigo)}

/* Anything the reader must not miss - what is private, what cannot be undone. */
.hnote{border:1px solid var(--line);border-left:4px solid var(--gold);background:#fff;
       border-radius:10px;padding:14px 16px;margin:12px 0;font-size:.9rem;line-height:1.55}
.hnote b{color:var(--dgold)}

.helpfoot{display:flex;gap:10px;flex-wrap:wrap;margin:26px 0 12px;
          padding-top:18px;border-top:1px solid var(--line)}

/* The guide index. */
.guidegrid{display:grid;grid-template-columns:repeat(auto-fill,minmax(260px,1fr));gap:14px;margin-bottom:18px}
.guide{display:flex;flex-direction:column;gap:6px;background:#fff;border:1px solid var(--line);
       border-radius:var(--radius);padding:18px 20px;text-decoration:none}
.guide:hover{box-shadow:0 10px 24px rgba(31,41,51,.07)}
.guide .who{font-size:.64rem;font-weight:700;letter-spacing:.14em;text-transform:uppercase;color:var(--muted)}
.guide b{font-family:var(--display);font-weight:800;font-size:1.05rem;color:var(--ink)}
.guide small{font-size:.68rem;font-weight:600;letter-spacing:.12em;text-transform:uppercase;color:var(--gold)}
.guide p{font-size:.87rem;color:var(--muted);line-height:1.5;margin-top:2px}

@media print{
  /* A guide saved to a phone for the ground, where the signal is poor. */
  .pub-top,.band,.helpfoot,.pub-foot,.mountains{display:none !important}
  .pagehero{background:none !important;padding:0 0 12px}
  .pagehero .pg,.pagehero .crumb,.pagehero .sub{color:#000 !important}
  .pagehero .pg em{color:#000 !important}
  .hnum{background:#000 !important;color:#fff !important}
  .hstep,.hnote{break-inside:avoid}
  body{background:#fff}
}

/* A year on the honour roll with nothing written up yet. */
.unrecorded td{color:var(--muted);font-style:italic;font-size:.88rem}


/* ==== Village storefronts ==== */
/* Customer shelf and owner screens, after the approved spaza prototype.
   Phone-first: the customer is in the street, the owner is behind a counter. */
.shopchips{display:flex;flex-wrap:wrap;gap:6px;margin-top:14px}
.shopchip{font-size:.72rem;font-weight:700;padding:5px 11px;border-radius:999px;
          background:rgba(255,255,255,.14);color:#fff}
.shopchip.open{background:#E4F0EA;color:var(--pitch)}
.shopchip.cash{background:#FDF3DC;color:var(--dgold)}
.shopchip.shut{background:#F7E0DB;color:var(--red)}

.shop{max-width:640px;padding-bottom:90px}
.shop .payline{font-size:.88rem;color:var(--muted);margin:0 0 6px}
/* Two to a row once there is room. A shisanyama with ten things on the shelf
   was ten full-width rows and a long scroll past food somebody had already
   decided against; side by side, a menu is read the way a menu is read. One
   column on a phone, where two would squeeze the name and the stepper into
   nothing. */
.shelf{display:grid;grid-template-columns:1fr;gap:8px;margin-bottom:6px}
/* 900px, the same width at which the order card moves beside the menu. Tried
   at 620 first and every second name wrapped: two cards in a 640px column are
   296px each, and "Beef Ribs, Chips or Pap" does not live in that. */
@media (min-width:900px){.shelf{grid-template-columns:1fr 1fr}}
.shelfitem{display:grid;grid-template-columns:52px 1fr auto;column-gap:10px;row-gap:1px;align-items:center;
           background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:10px 12px}
/* Big enough to see the food. 38px showed a thumbnail of a thumbnail, and
   what somebody is choosing between is the picture. */
.shelfitem .em,.shelfrow .em{font-size:1.3rem;width:52px;height:52px;display:grid;place-items:center;
           background:#F6F4EC;border-radius:10px;overflow:hidden}
.shelfitem .em img,.shelfrow .em img{width:100%;height:100%;object-fit:cover}
.shelfitem .nm,.shelfrow .nm{min-width:0}
.shelfitem .nm b{display:block;font-size:.9rem}
.shelfitem .em{grid-row:1/3}
.shelfitem .nm{grid-column:2;grid-row:1;align-self:end}
.shelfitem .pr{grid-column:2;grid-row:2;align-self:start;font-weight:700;font-size:.84rem;color:var(--muted);white-space:nowrap;font-variant-numeric:tabular-nums}
.shelfitem .stepper,.shelfitem input.qty{grid-column:3;grid-row:1/3}
.shelfitem.out{opacity:.55}
.oos{display:block;font-size:.64rem;font-weight:800;letter-spacing:.06em;text-transform:uppercase;color:var(--red)}
.shelfitem input.qty{width:58px;padding:7px;border:1.5px solid var(--line);border-radius:9px;
           font:inherit;text-align:center}

/* The script turns each number box into a stepper. */
.stepper{display:flex;align-items:center;gap:6px}
.stepper button{width:32px;height:32px;border-radius:9px;border:1.5px solid var(--indigo);background:#fff;
           color:var(--indigo);font-weight:800;font-size:1.05rem;line-height:1;cursor:pointer}
.stepper button.add{background:var(--indigo);color:#fff}
.shelfitem .stepper input.qty.stepped{width:30px;border:0;padding:0;font-weight:700;font-size:.95rem;
           background:transparent;-moz-appearance:textfield;appearance:textfield}
.stepper input.qty.stepped::-webkit-outer-spin-button,
.stepper input.qty.stepped::-webkit-inner-spin-button{-webkit-appearance:none;margin:0}

.checkout{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:4px 16px 18px;margin-top:18px}
.sum{background:#fff;border:1px solid var(--line);border-radius:12px;padding:10px 14px;margin:8px 0 12px}
.sum .sumrow{display:flex;justify-content:space-between;gap:12px;font-size:.88rem;padding:3px 0;font-variant-numeric:tabular-nums}
.sum .sumrow.total{border-top:1px dashed var(--line);margin-top:6px;padding-top:8px;font-weight:800}
fieldset.seg{border:0;padding:0;display:flex;gap:8px;flex-wrap:wrap}
fieldset.seg legend{font-size:.77rem;font-weight:700;margin-bottom:5px;padding:0}
.segopt{flex:1 1 120px;position:relative}
.segopt input{position:absolute;opacity:0;inset:0;margin:0}
.segopt span{display:block;text-align:center;font-weight:700;font-size:.85rem;padding:11px;border-radius:11px;
           border:1.5px solid var(--line);background:#fff;color:var(--muted);cursor:pointer}
.segopt input:checked + span{border-color:var(--indigo);background:#EEF1F8;color:var(--indigo)}
.segopt input:focus-visible + span{outline:3px solid var(--gold);outline-offset:2px}

.btn.red{background:var(--red);color:#fff}
.btn.red:hover{background:#A83020}
.btn.red:disabled{opacity:.7;cursor:wait}
.btn.big{display:flex;justify-content:center;width:100%;margin-top:14px;padding:14px;font-size:1rem;
         font-family:var(--display);font-weight:800}
.btn.wa-alt{display:flex;justify-content:center;margin:14px 0 4px;background:#fff;
            border:1.5px solid #25D366;color:#128C4B}
.err.big{background:#F7E0DB;border-radius:10px;padding:10px 14px;margin:12px 0;font-size:.86rem}
.centre{text-align:center}
.app-sub{font-family:var(--display);font-weight:800;font-size:1.05rem;margin:22px 0 10px}
.flash.warn{background:#FDF3DC;border-left-color:var(--gold)}

/* Sticky basket: appears once there is something in it. */
.basketbar{position:sticky;bottom:0;z-index:20;display:flex;align-items:center;justify-content:space-between;
           gap:12px;background:var(--pitch);color:#fff;padding:12px 18px;text-decoration:none;
           box-shadow:0 -6px 20px rgba(31,41,51,.15)}
.basketbar[hidden]{display:none}
.basketbar b{font-family:var(--display)}
.basketbar .go{background:var(--gold);color:var(--ink);font-weight:800;font-size:.82rem;border-radius:999px;padding:8px 16px}

/* Order code card and tracker. */
.shoptrack{padding-top:22px}
.codecard{background:var(--indigo);color:#fff;border-radius:var(--radius);padding:20px 16px;text-align:center;margin-bottom:16px}
.codecard .lbl{display:block;font-size:.64rem;font-weight:700;letter-spacing:.22em;text-transform:uppercase;opacity:.75}
.codecard .code{display:block;font-family:var(--display);font-weight:800;font-size:2.8rem;letter-spacing:.04em;
           color:var(--gold);line-height:1.15;font-variant-numeric:tabular-nums}
.codecard p{font-size:.82rem;opacity:.85}
ol.steps{list-style:none;margin:0 0 14px;padding:16px;background:#fff;border:1px solid var(--line);border-radius:var(--radius)}
ol.steps li{position:relative;padding:0 0 18px 36px}
ol.steps li:last-child{padding-bottom:0}
ol.steps li::before{content:"";position:absolute;left:0;top:0;width:24px;height:24px;border-radius:50%;
           background:#EDEAE0;border:2px solid var(--line);box-sizing:border-box}
ol.steps li::after{content:"";position:absolute;left:11px;top:26px;bottom:2px;width:2px;background:var(--line)}
ol.steps li:last-child::after{display:none}
ol.steps li.done::before{background:var(--teal);border-color:var(--teal)}
ol.steps li.done::after{background:var(--teal)}
ol.steps li.now::before{background:var(--gold);border-color:var(--gold)}
ol.steps b{display:block;font-size:.9rem}
ol.steps span{font-size:.76rem;color:var(--muted)}

/* Owner: orders. */
.shoptabs{display:flex;gap:8px;flex-wrap:wrap;margin:6px 0 16px}
.shoptabs a{flex:1 1 auto;text-align:center;padding:9px 12px;border-radius:10px;border:1.5px solid var(--line);
           background:#fff;font-weight:700;font-size:.82rem;text-decoration:none;color:var(--ink)}
.shoptabs a.on{border-color:var(--indigo);background:#EEF1F8;color:var(--indigo)}
.ocard{background:#fff;border:1px solid var(--line);border-left:4px solid var(--gold);border-radius:var(--radius);
       padding:12px 14px;margin-bottom:10px}
.ocard.ready{border-left-color:var(--teal)}
.ocard.done{border-left-color:#B9B3A5;opacity:.75}
.ohd{display:flex;justify-content:space-between;align-items:baseline;gap:10px}
.ohd b{font-family:var(--display);font-size:1.15rem;font-variant-numeric:tabular-nums}
.ost{font-size:.66rem;font-weight:800;letter-spacing:.08em;text-transform:uppercase;color:var(--muted)}
.ost.new{color:var(--red)}
.ost.rd{color:var(--teal)}
ul.olines{list-style:none;margin:8px 0;padding:0;font-size:.86rem}
ul.olines li{display:flex;justify-content:space-between;gap:10px;padding:2px 0;font-variant-numeric:tabular-nums}
ul.olines li.ototal{font-weight:800;border-top:1px dashed var(--line);padding-top:5px;margin-top:3px}
.owho{font-size:.76rem;color:var(--muted)}
.oacts{display:flex;flex-direction:column;gap:8px;margin-top:10px}
.oacts form{margin:0}
.obtn{width:100%;font:inherit;font-weight:800;font-size:.86rem;border:0;border-radius:10px;padding:12px;
      cursor:pointer;background:var(--teal);color:#fff}
.obtn.collect{background:var(--indigo)}
.obtn.ghost{background:#fff;color:var(--ink);border:1.5px solid var(--line)}
.obtn.danger{background:#fff;color:var(--red);border:1.5px solid var(--red);margin-top:6px}
.ocancel summary{font-size:.76rem;color:var(--muted);cursor:pointer;padding:4px 0}
.ocancel input{width:100%;margin-top:6px;border:1.5px solid var(--line);border-radius:10px;padding:9px 11px;font:inherit}

/* Owner: shelf. */
.addprod{border:1.5px solid var(--gold)}
.addprod h3{font-family:var(--display);font-weight:800;font-size:1rem;margin-bottom:10px}
.addrow{display:flex;gap:8px;align-items:flex-end;flex-wrap:wrap}
.addrow .field{margin-bottom:8px}
.addrow .field.grow{flex:1 1 180px}
.addrow .field.price{flex:0 0 96px}
.addrow .field.emoji{flex:0 0 72px}
.addrow .field.emoji input{text-align:center;font-size:1.2rem}
.addrow .btn{margin-bottom:8px}
.addprod #emojihint{margin:0 0 8px}
.emojipicks{display:grid;grid-template-columns:repeat(auto-fill,minmax(68px,1fr));gap:6px;margin:0 0 12px}
.emojipicks button{display:flex;flex-direction:column;align-items:center;gap:2px;padding:6px 2px;
      border-radius:10px;border:1.5px solid var(--line);background:#fff;cursor:pointer;
      font:inherit;font-size:.66rem;font-weight:600;color:var(--ink);line-height:1.15}
.emojipicks button span{font-size:1.25rem;line-height:1.2}
.emojipicks button:hover{border-color:var(--gold)}
.emojipicks button[aria-pressed="true"]{border-color:var(--indigo);background:#EEF1F8;color:var(--indigo)}
.emojipicks button:focus-visible{outline:3px solid var(--gold);outline-offset:1px}
.shelfrow{display:grid;grid-template-columns:38px 1fr auto;gap:10px;align-items:center;background:#fff;
      border:1px solid var(--line);border-radius:var(--radius);padding:10px 12px;margin-bottom:8px}
.shelfrow .nm b{display:block;font-size:.9rem}
.shelfrow .nm span{font-size:.74rem;color:var(--muted)}
.shelfrow.off .em,.shelfrow.off .nm{opacity:.5}
.shelfrow form{margin:0}
.shelfedit{grid-column:1/-1}
.shelfedit summary{font-size:.74rem;color:var(--muted);cursor:pointer}
.shelfedit form{display:flex;flex-wrap:wrap;gap:6px;margin-top:8px}
.shelfedit input,.shelfedit select{flex:1 1 90px;min-width:0;border:1.5px solid var(--line);border-radius:9px;
      padding:8px 10px;font:inherit;font-size:.85rem}
.toggle{width:46px;height:26px;border-radius:999px;background:#CBD5DE;position:relative;border:0;cursor:pointer}
.toggle::after{content:"";position:absolute;top:3px;left:3px;width:20px;height:20px;border-radius:50%;
      background:#fff;transition:left .15s}
.toggle.on{background:var(--teal)}
.toggle.on::after{left:23px}
.toggle:focus-visible{outline:3px solid var(--gold);outline-offset:2px}
.freeline{background:#FDF3DC;border:1px solid #EFD9A0;border-radius:12px;padding:12px 14px;font-size:.82rem;
      color:#6B4E0A;margin-top:16px}
@media (prefers-reduced-motion:reduce){ .toggle::after{transition:none} }

/* Product photos: approved ones stand where the emoji would. */
/* Whole product, never cropped: a tall bottle sits in the box with space
   either side. White, because most product photos are on white. */
img.em.ph{display:block;object-fit:contain;background:#fff;border:1px solid var(--line);border-radius:10px;padding:2px;box-sizing:border-box}
.shelfitem .phlink{grid-row:1/3;display:block;border-radius:10px;cursor:zoom-in}
.shelfitem .phlink:focus-visible{outline:3px solid var(--gold);outline-offset:2px}
.shelfitem img.em.ph{width:56px;height:56px}
.shelfitem:has(img.em.ph){grid-template-columns:56px 1fr auto}
.shelfrow img.em.ph{width:48px;height:48px}
.shelfrow:has(img.em.ph){grid-template-columns:48px 1fr auto}
.shelfrow .nm .photostate{display:flex;align-items:center;gap:6px;margin-top:3px;font-size:.72rem;font-weight:600}
.shelfrow .nm .photostate img{border-radius:4px;object-fit:contain;background:#fff;opacity:.85}
.shelfrow .nm .photostate.wait{color:var(--dgold)}
.shelfrow .nm .photostate.no{color:var(--red)}
.photofield input[type=file]{font:inherit;font-size:.8rem;max-width:100%}
.photofield input[type=file]::file-selector-button,
.editphoto input[type=file]::file-selector-button{font:inherit;font-weight:700;border:1.5px solid var(--line);
      background:#fff;border-radius:999px;padding:7px 14px;margin-right:8px;cursor:pointer}
img.photopreview{display:block;margin-top:6px;border-radius:9px;object-fit:contain;background:#fff;border:1px solid var(--line)}
.editphoto{flex:1 1 100%;display:flex;flex-direction:column;gap:4px;font-size:.74rem;font-weight:700}
.editphoto input{font-size:.78rem;max-width:100%}

/* Tap a product photo to see it bigger. */
dialog.phview{margin:auto;border:0;padding:0;border-radius:var(--radius);background:#fff;max-width:min(92vw,600px);
      box-shadow:0 20px 60px rgba(31,41,51,.35)}
dialog.phview::backdrop{background:rgba(31,41,51,.7)}
dialog.phview img{display:block;max-width:100%;max-height:70vh;margin:0 auto;object-fit:contain}
dialog.phview .phbar{display:flex;justify-content:space-between;align-items:center;gap:12px;padding:10px 14px;
      border-top:1px solid var(--line);font-weight:700;font-size:.9rem}
dialog.phview button{font:inherit;font-weight:700;border:1.5px solid var(--line);background:#fff;border-radius:999px;
      padding:7px 16px;cursor:pointer}

/* Shop page: the business's logo beside its name, as on the listing page. */
.shophead{display:flex;align-items:center;gap:14px;margin-top:6px}
.shophead .pg{margin:0}
.shophead .sub{margin-bottom:0}
.shoplogo{flex:0 0 auto;width:64px;height:64px;object-fit:contain;background:#fff;border-radius:12px;padding:4px;box-sizing:border-box}
@media (max-width:420px){ .shoplogo{width:52px;height:52px} }

/* Tracker: how to pay a bank order, repeated from the ready SMS. */
.payshap{background:#EEF1F8;border:1px solid #C9D2EA;border-left:4px solid var(--indigo);border-radius:12px;
         padding:12px 14px;margin:0 0 14px}
.payshap b{display:block;font-family:var(--display);font-size:.95rem;color:var(--indigo)}
.payshap p{font-size:.86rem;margin-top:4px}

/* A tournament edition called off - postponed or cancelled. */
.status.off{background:#F7E0DB;color:var(--red)}
.statusnote,.tcard .statusnote,.tcard .pad .statusnote{font-size:.82rem;color:var(--red);font-weight:600;margin-top:4px}
.calledoff{background:#F7E0DB;border:1px solid #E7BFB6;border-left:4px solid var(--red);border-radius:var(--radius);
           padding:12px 15px;margin:16px 0 4px}
.calledoff b{display:block;font-family:var(--display);font-size:1rem;color:var(--red)}
.calledoff p{font-size:.86rem;margin-top:3px}

/* ==== Mmaraka: classified adverts ==== */
/* On a market the picture is the advert, so cards rather than grey rows. */
.adverts{display:grid;grid-template-columns:repeat(auto-fill,minmax(240px,1fr));gap:12px;margin-bottom:16px}
.advertcard{display:flex;flex-direction:column;background:#fff;border:1px solid var(--line);
      border-radius:var(--radius);overflow:hidden;text-decoration:none;color:var(--ink)}
.advertcard:hover{border-color:var(--indigo)}
.advertcard.featured{border-color:var(--gold);background:#FFFBEF}
.advertcard .pic{display:block;height:150px;background:#F6F4EC;border-bottom:1px solid var(--line);
    position:relative;overflow:hidden;isolation:isolate}
/* As on the directory cards: what the photograph does not cover is a blurred
   copy of itself, so a tall picture of a couch and a wide one of a bakkie fill
   the same card without either being cut. */
.advertcard .pic::after{content:"";position:absolute;inset:-16px;z-index:-1;
    background-image:var(--shot);background-size:cover;background-position:center;
    filter:blur(13px) saturate(1.12)}
.advertcard .pic.nopic::after{display:none}
.advertcard .pic img{display:block;width:100%;height:150px;object-fit:contain;position:relative}
.advertcard .pic.nopic{display:grid;place-items:center;font-family:var(--display);font-weight:800;
      font-size:.95rem;color:var(--muted);background:#F1EEE4}
.advertcard .body{display:block;padding:12px 14px 14px}
.advertcard .kind{display:block;font-size:.67rem;font-weight:700;letter-spacing:.1em;text-transform:uppercase;color:var(--muted)}
.advertcard h3{font-size:.97rem;font-weight:700;margin-top:3px;line-height:1.25}
.advertcard .price{display:block;font-family:var(--display);font-weight:800;font-size:1.05rem;color:var(--teal);margin-top:5px}
.advertcard .when{display:block;font-size:.74rem;color:var(--muted);margin-top:2px}
.advertcard .fbadge{margin-right:5px}

/* One advert's own page. */
.advert{max-width:760px}
.advert .askprice{font-family:var(--display);font-weight:800;font-size:1.6rem;color:var(--teal);margin:4px 0 6px}
.advert .advertbody{font-size:.92rem;white-space:pre-line}
.advert .shots{margin-top:6px}

/* Advert page: who is selling, and reporting one. */
.seller h3{font-size:1rem;font-weight:700}
.seller p{font-size:.8rem;color:var(--muted);margin-top:2px}
.seller .verified{color:var(--teal);font-weight:700}
ul.otherads{list-style:none;margin:10px 0 0;padding:0;border-top:1px dashed var(--line)}
ul.otherads li{display:flex;justify-content:space-between;gap:12px;padding:7px 0;border-bottom:1px dashed var(--line);font-size:.86rem}
ul.otherads li:last-child{border-bottom:0}
ul.otherads span{color:var(--muted);white-space:nowrap}
.reportbox{margin:12px 0 4px}
.reportbox summary{font-size:.82rem;color:var(--muted);cursor:pointer}
.reportbox form{background:#fff;border:1px solid var(--line);border-radius:var(--radius);padding:12px 15px;margin-top:8px}
.reportbox fieldset{border:0;padding:0;margin:0 0 10px}
.reportbox legend{font-size:.8rem;font-weight:700;margin-bottom:6px;padding:0}
.radioline{display:flex;align-items:center;gap:8px;padding:4px 0;font-size:.86rem;cursor:pointer}
.radioline input{width:18px;height:18px}

/* Changing your own advert: the pictures already on it. */
.editphotos{display:flex;flex-wrap:wrap;gap:10px}
.editphoto-item{display:flex;flex-direction:column;gap:4px;align-items:center;font-size:.74rem;
      border:1px solid var(--line);border-radius:10px;padding:6px;background:#fff;cursor:pointer}
.editphoto-item img{display:block;width:80px;height:80px;object-fit:contain;background:#F6F4EC;border-radius:7px}
.editphoto-item span{display:flex;align-items:center;gap:4px}

/* ==== Public header and footer, 2026-10 design ==== */
/* The header gains a menu button on a phone; the footer gains the peaks band,
   the slogan and four columns. Both live here rather than in home.css because
   every public page uses them. */
.pub-top nav a.signin{background:var(--gold);color:var(--indigo);border-radius:999px;padding:9px 18px;
    font-weight:700;opacity:1;border-bottom:0;min-height:44px;display:inline-flex;align-items:center}
.pub-top nav a.signin:hover{background:#F0B935;border-bottom:0}
.navtoggle{display:none;font:inherit;font-weight:700;font-size:.82rem;color:#FDFCF8;background:transparent;
    border:1.5px solid rgba(255,255,255,.5);border-radius:999px;padding:9px 16px;cursor:pointer;min-height:44px}

@media (max-width:1000px){
    body.has-navtoggle .navtoggle{display:inline-flex;align-items:center;gap:7px}
    body.has-navtoggle .pub-top nav{display:none;width:100%}
    body.has-navtoggle .pub-top nav.open{display:flex;flex-direction:column;gap:2px;padding-top:8px}
    body.has-navtoggle .pub-top nav.open a{padding:11px 2px;font-size:.95rem;border-bottom:1px solid rgba(255,255,255,.12)}
    body.has-navtoggle .pub-top nav.open a.signin{align-self:start;margin-top:8px;border-bottom:0}
}

footer.pub{position:relative;background:var(--indigo);color:#fff;overflow:hidden;text-align:left;padding:0}
footer.pub .peaks{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;opacity:.18}
footer.pub .band{position:relative;margin:0}
footer.pub .wrap{position:relative}
.footgrid{display:grid;grid-template-columns:minmax(0,1.4fr) repeat(3,minmax(0,1fr));gap:40px;padding-block:64px 40px}
.footmark{display:flex;flex-direction:column;gap:16px;min-width:0}
.footmark .slogan{font-family:var(--display);font-size:1.75rem;font-weight:800;line-height:1.15;margin:0;color:#fff}
.footmark .slogan span{color:var(--gold)}
.footmark .partner{color:#C9D0E8;font-size:.88rem;margin:0}
.footcol{display:flex;flex-direction:column;gap:12px}
.footcol strong{font-size:.81rem;letter-spacing:.16em;color:var(--gold);text-transform:uppercase}
/* footer.pub a is teal site-wide; these columns are on indigo. */
footer.pub .footcol a{color:#C9D0E8;text-decoration:none;font-size:.94rem;font-weight:500}
footer.pub .footcol a:hover{color:var(--gold)}
footer.pub .legalline a{color:#C9D0E8}
.legalline{display:flex;justify-content:space-between;gap:12px;flex-wrap:wrap;color:#C9D0E8;font-size:.81rem;
    border-top:1px solid rgba(255,255,255,.2);padding-top:20px;padding-bottom:28px;margin-top:0}

@media (max-width:1000px){ .footgrid{grid-template-columns:repeat(2,minmax(0,1fr));gap:28px} }
@media (max-width:640px){ .footgrid{grid-template-columns:minmax(0,1fr)} }


/* ---- privacy notice ---- */
/* Sits at the bottom of the window rather than at the top of the page: the
   first thing a visitor sees should be QwaQwa, not a bar about cookies. */
.privnote{position:fixed;left:0;right:0;bottom:0;z-index:150;background:var(--indigo);color:#FDFCF8;
    box-shadow:0 -6px 24px rgba(31,41,51,.22)}
.privnote[hidden]{display:none}
.privnote-in{display:flex;align-items:center;justify-content:space-between;gap:18px;
    padding-top:14px;padding-bottom:16px;flex-wrap:wrap}
.privnote-words{min-width:0;flex:1 1 420px}
.privnote-words strong{font-family:var(--display);font-weight:700;font-size:1rem;display:block;margin-bottom:2px}
.privnote-words p{font-size:.86rem;line-height:1.45;color:#D8DEF2;max-width:72ch}
.privnote-words a{color:var(--gold);text-underline-offset:3px}
.privnote-ok{flex:0 0 auto;background:var(--gold);color:var(--ink);border:0;border-radius:999px;
    padding:10px 24px;font-weight:700;font-size:.9rem;cursor:pointer}
.privnote-ok:hover{background:#F0B62F}
.builtby{color:#AEB7D4}
.builtby b{color:#EDE3C8;font-weight:700}

/* On a phone the bar sits over the hero's own search button, so it has to be
   slim: smaller type, tighter padding, and the button beside the words rather
   than a full-width block under them. */
@media (max-width:560px){
  .privnote-in{gap:8px;padding-top:10px;padding-bottom:12px}
  .privnote-words{flex:1 1 100%}
  .privnote-words strong{font-size:.92rem}
  .privnote-words p{font-size:.78rem;line-height:1.4}
  .privnote-ok{margin-left:auto;padding:8px 22px;font-size:.85rem}
}


/* ---- jobs ---- */
/* The vacancy card is a link now; before this the page printed the title and
   left you with nowhere to read the rest of it. */
a.row.joblink{text-decoration:none;color:inherit;align-items:center}
a.row.joblink:hover{border-color:var(--pitch);box-shadow:0 2px 10px rgba(46,93,62,.12)}
a.row.joblink .seemore{color:var(--pitch);font-weight:700;font-size:.82rem;white-space:nowrap}
.closedjob{background:#FBEDEA;border:1px solid #EBC6BE;border-radius:10px;padding:11px 14px;
    font-size:.85rem;color:#7A2718;margin-bottom:14px}
.closedjob a{color:#7A2718}
.applyhead{font-size:1rem;font-weight:700;margin-bottom:6px}
.applyline{font-size:.95rem;white-space:pre-line;margin-bottom:10px}


/* ---- rich text from the panel ---- */
/* A vacancy written in the editor. Only the handful of tags SafeHtml allows
   can arrive here, so this is the whole of it. */
.richtext{font-size:.95rem;line-height:1.6}
.richtext p{margin-bottom:12px}
.richtext p:last-child{margin-bottom:0}
.richtext h3,.richtext h4{font-family:var(--display);font-weight:800;margin:18px 0 8px}
.richtext h3{font-size:1.15rem}
.richtext h4{font-size:1rem}
.richtext ul,.richtext ol{margin:0 0 12px 22px;display:flex;flex-direction:column;gap:6px}
.richtext li{line-height:1.5}
.richtext a{color:var(--indigo);text-underline-offset:3px}
.richtext blockquote{border-left:3px solid var(--line);padding-left:14px;color:var(--muted);margin:0 0 12px}
.richtext strong{font-weight:700}
.richtext hr{border:0;border-top:1px solid var(--line);margin:16px 0}


/* ---- the search box on a list page ---- */
.listsearch{display:flex;gap:8px;flex-wrap:wrap;align-items:center;margin:0 0 6px}
.listsearch input[type=search]{flex:1 1 260px;min-width:0;height:46px;border-radius:12px;
    border:1.5px solid var(--line);background:#fff;padding:0 16px;font:inherit;font-size:1rem;color:var(--ink)}
.listsearch input[type=search]:focus{border-color:var(--indigo);outline:none}
.listsearch button{height:46px;padding:0 20px;border:0;border-radius:12px;background:var(--indigo);
    color:#fff;font:inherit;font-weight:700;cursor:pointer}
.listsearch button:hover{background:#1C2850}
.listsearch .clearsearch{font-size:.86rem;color:var(--muted);text-underline-offset:3px}
.searchsaid{font-size:.86rem;color:var(--muted);margin:0 0 14px}

@media (max-width:560px){
  .listsearch input[type=search]{flex:1 1 100%}
  .listsearch button{flex:1 1 auto}
}


/* ---- choosing between your own shops ---- */
.shopswitch{display:flex;gap:8px;flex-wrap:wrap;margin:0 0 16px}
.shopswitch a{display:inline-flex;align-items:center;gap:6px;padding:8px 14px;border-radius:999px;
    border:1px solid var(--line);background:#fff;text-decoration:none;color:var(--ink);font-weight:600;font-size:.9rem}
.shopswitch a.on{background:var(--indigo);border-color:var(--indigo);color:#fff}
.shopswitch a small{font-weight:600;font-size:.72rem;opacity:.75}

/* The small writing box on a vacancy form. Hand-written: the portal runs on
   cheap phones over data people pay for, so no editor library is loaded. */
/* overflow:clip, not hidden: hidden would make this the scroll container for
   the sticky toolbar below and quietly stop it sticking. clip rounds the
   corners without doing that. */
.rtx{border:1.5px solid var(--line);border-radius:12px;background:#fff;overflow:clip}
/* Sticky, because the box grows as somebody types. Measured on a phone with
   the keyboard up: after fourteen lines the toolbar had scrolled 215px above
   the screen, so reaching for a bullet meant scrolling back and losing your
   place. */
.rtx-bar{position:sticky;top:0;z-index:2;display:flex;gap:2px;flex-wrap:wrap;padding:6px;
    border-bottom:1px solid var(--line);background:#FAF8F2;border-radius:11px 11px 0 0}
/* 44px: a thumb on a phone, not a mouse pointer on a laptop. Measured at
   360px wide - the toolbar stays on one row at that size. */
.rtx-b{min-width:44px;height:44px;padding:0 10px;border:1px solid transparent;border-radius:8px;
    background:transparent;color:var(--ink);font-size:.95rem;line-height:1;cursor:pointer}
.rtx-b:hover,.rtx-b:focus-visible{border-color:var(--line);background:#fff}
.rtx-area{min-height:190px;padding:12px 14px;font-size:.95rem;line-height:1.55;outline:0}
.rtx-area:focus{box-shadow:inset 0 0 0 2px rgba(38,53,107,.14)}
.rtx-area p{margin:0 0 .7em}
.rtx-area h3{font-family:'Bricolage Grotesque',system-ui,sans-serif;font-size:1rem;margin:.9em 0 .4em}
.rtx-area ul,.rtx-area ol{margin:0 0 .7em;padding-left:1.25em}
.rtx-area li{margin:0 0 .25em}
.rtx-area:empty::before{content:attr(data-placeholder);color:var(--muted)}
/* The real hiding is done inline by richtext.js, because ".field textarea"
   outranks a single class and left this full width - sixteen pixels past the
   edge of a 360px phone, which scrolled the whole page sideways. */
.rtx-hidden{position:absolute;left:-9999px;width:1px;height:1px;padding:0;border:0;opacity:0;pointer-events:none}

/* An event poster. Shown whole: a flyer carries its date down one edge and a
   phone number along the bottom, and a crop keeps neither. */
.poster{margin:0 0 16px;text-align:center}
.poster img{max-width:100%;max-height:70vh;width:auto;height:auto;border-radius:14px;
    border:1px solid var(--line);background:#fff}
.rtx-b svg{display:block;margin:0 auto}
/* Below 360px the six buttons wrapped, leaving the last one alone on a second
   row looking like a mistake. Narrower, not shorter: the height is what a
   thumb needs. Measured on a 320px screen. */
@media (max-width:359px){
    .rtx-b{min-width:40px;padding:0 5px}
    .rtx-bar{gap:0}
}

/* A shop on a wide screen. The page was a 640px column in the middle of a
   1100px page, and the order card sat below the whole menu - so on a desktop
   you chose eight things and then scrolled past them to find the form. Side by
   side, the order stays in sight while you pick, which is the point of the
   space rather than merely filling it. Below 900px nothing changes: the phone
   layout was never the problem. */
@media (min-width:900px){
    .shop{max-width:1100px;padding-bottom:40px}
    .shop #shopform{display:grid;grid-template-columns:minmax(0,1fr) 340px;
        gap:30px;align-items:start}
    .shop .checkout{position:sticky;top:18px;margin-top:0}
    /* The bar is for a thumb reaching the form far below; beside it, it is
       telling somebody to go where they are already looking. */
    .basketbar{display:none}
    /* The WhatsApp alternative is a sibling of the form, so it ran the full
       width of the page under both columns. It belongs under the order card:
       it is the other way to do that same thing. */
    .shop .wa-alt{width:340px;margin-left:auto;margin-right:0}
}

/* "How did you do that?" - the shop page is where somebody is asked, so the
   share sits above the menu rather than at the bottom of it. */
.shopshare{margin:0 0 14px}
@media (min-width:900px){.shopshare{display:flex;justify-content:flex-end}}
