/* ===========================================================================
 * FLYER THEME — the look of the "KTB AED Nominate" flyer (Big AED Giveaway).
 *
 * Loaded AFTER styles.css on every public page, and only restyles: no layout
 * that game.js or the overlays measure is changed here, so it can be removed
 * by deleting one <link> per page. What it brings:
 *
 *   - the stepped pixel-art sky, pixel clouds and the grass strip
 *   - chunky 8-bit "block" buttons: dark notched outline, bevelled face and
 *     a hard lip underneath that the button sinks into when pressed
 *     (red + yellow rim = main action, green = join, blue = everything else)
 *   - flat flyer-blue panels with a navy outline instead of dark glass
 *   - the campaign type: Bungee for headings, buttons and the menu; Atma
 *     Bold for sub-headings and labels; Alegreya Sans Thin for body copy
 *     (its Bold is loaded too, for text styles.css already sets bold)
 *   - the Keep the Beat Going logo leading the nav bar (.site-brand)
 *   - the big campaign banner at the top of the home page (.flyer-hero)
 *
 * Fonts are self-hosted from public/fonts/ (SIL OFL, licences alongside) —
 * no third-party font request from a children's site.
 * ------------------------------------------------------------------------ */

@font-face {
  font-family: "Bungee";
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url("fonts/bungee-400.woff2") format("woff2");
}
@font-face {
  font-family: "Atma";
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url("fonts/atma-700.woff2") format("woff2");
}
@font-face {
  font-family: "Alegreya Sans";
  font-style: normal;
  font-weight: 100;
  font-display: swap;
  src: url("fonts/alegreya-sans-100.woff2") format("woff2");
}
@font-face {
  font-family: "Alegreya Sans";
  font-style: italic;
  font-weight: 100;
  font-display: swap;
  src: url("fonts/alegreya-sans-100-italic.woff2") format("woff2");
}
/* Only for text styles.css already sets bold (labels, <strong>, inputs):
   without it the browser fakes bold by smearing the Thin outlines. */
@font-face {
  font-family: "Alegreya Sans";
  font-style: normal;
  font-weight: 700;
  font-display: swap;
  src: url("fonts/alegreya-sans-700.woff2") format("woff2");
}

:root {
  /* Sampled from the flyer artwork. */
  --fl-sky: #439ed7;
  --fl-ink: #16192b;          /* the black outline round every sprite */
  --fl-navy: #10244a;
  --fl-blue: #2459a6;         /* panels */
  --fl-blue-2: #3a78c2;       /* ribbon / lighter panels */
  --fl-blue-hi: #7cb8ec;
  --fl-blue-lo: #173f7d;
  --fl-red: #e52629;
  --fl-red-hi: #ff6265;
  --fl-red-lo: #a8151a;
  --fl-yellow: #ffd200;
  --fl-yellow-hi: #fff07a;
  --fl-yellow-lo: #e09a00;
  --fl-green: #1fa64a;
  --fl-green-hi: #6ad98a;
  --fl-green-lo: #11702f;
  --fl-lip: rgba(16, 36, 74, 0.55);

  --fl-font-heading: "Bungee", "Arial Black", "Trebuchet MS", sans-serif;
  --fl-font-sub: "Atma", "Trebuchet MS", sans-serif;
  --fl-font-body: "Alegreya Sans", "Trebuchet MS", "Verdana", sans-serif;

  /* The legacy tokens the rest of styles.css reads. */
  --panel: var(--fl-blue);
  --panel-edge: var(--fl-navy);
  --shadow: rgba(16, 36, 74, 0.35);
}

/* ------------------------------ sky & ground ------------------------------ */

body {
  position: relative;
  font-family: var(--fl-font-body);
  font-weight: 100;
  font-size: 1.1rem; /* Alegreya runs small; Thin needs the extra size to read */
  background: var(--fl-sky);
}

/* Browsers don't pass the page font into form controls, so the mode and
   hero cards (they are <button>s) were still drawing in Arial. Classes that
   set their own face (the block buttons, the menu) still win. */
button,
input,
select,
textarea {
  font-family: inherit;
}

/* The stepped blocks of the flyer sky, pinned to the viewport. z-index -2/-1
   puts both layers under the page's in-flow content. */
body::before {
  z-index: -2;
  background: var(--fl-sky) url("Graphics/flyer/sky-blocks.png") center top / cover no-repeat;
  image-rendering: pixelated;
  -webkit-mask-image: none;
  mask-image: none;
}

body::after {
  z-index: -1;
  background:
    url("Graphics/flyer/cloud-large.png") no-repeat 1% 30% / 230px auto,
    url("Graphics/flyer/cloud-large.png") no-repeat 99% 64% / 280px auto,
    url("Graphics/flyer/cloud-large.png") no-repeat 6% 92% / 190px auto;
  image-rendering: pixelated;
  opacity: 0.85;
}

/* The grass-and-dirt strip along the bottom of every page, full bleed. The
   shell is at least a screen tall so on a short page the grass is still the
   floor, not a ledge halfway up. */
.page-shell {
  position: relative;
  min-height: 100vh;
  padding-bottom: 152px; /* 48px of the old gap + 40px air + the 64px strip */
}

.page-shell::after {
  content: "";
  position: absolute;
  left: 50%;
  bottom: 0;
  width: 100vw;
  height: 64px;
  transform: translateX(-50%);
  background: url("Graphics/flyer/grass-tile.png") repeat-x left bottom / auto 64px;
  image-rendering: pixelated;
  pointer-events: none;
}

body.immersive .page-shell::after {
  display: none;
}

/* --------------------------------- type ---------------------------------- */

.hero h1,
.page-header h1,
.overlay-card h2,
.highscore-card h2,
.leaderboard-panel h2,
.portal-panel h2,
.wizard-page h2 {
  font-family: var(--fl-font-heading);
  font-weight: 400;
  letter-spacing: 0.01em;
  text-transform: none;
  color: #fff;
  text-shadow: 3px 3px 0 var(--fl-navy);
}

/* Bungee is all capitals and wide, so headings step down from the Impact
   sizes they replace. */
.page-header h1 {
  font-size: clamp(1.6rem, 3.2vw, 2.4rem);
  line-height: 1.08;
}

.overlay-card h2 {
  font-size: clamp(1.5rem, 3vw, 2.2rem);
  line-height: 1.05;
}

.leaderboard-panel h2,
.portal-panel h2,
.wizard-page h2 {
  font-size: clamp(1.25rem, 2.2vw, 1.7rem);
  line-height: 1.1;
}

/* Card titles are sub-headings: Atma Bold. */
.level-preview h3,
.legend-card h3,
.process-strip h2 {
  font-family: var(--fl-font-sub);
  font-weight: 700;
  font-size: 1.3rem;
  line-height: 1.15;
  letter-spacing: 0;
  text-transform: none;
  color: #fff;
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.stat-label,
.eyebrow,
.legend-details summary,
.howitworks-strip h3,
.process-number,
.level-progress-chip {
  font-family: var(--fl-font-sub);
  font-weight: 700;
  line-height: 1.3;
}

.stat-label {
  color: #d9ecff;
  font-size: 0.8rem;
  letter-spacing: 0.04em;
}

.eyebrow {
  font-size: 1rem;
  letter-spacing: 0.06em;
}

.legend-details summary {
  font-size: 1.05rem;
}

.howitworks-strip h3 {
  font-size: 1.1rem;
}

.level-progress-chip {
  font-size: 0.8rem;
}

.stat-value {
  font-family: var(--fl-font-heading);
  font-weight: 400;
  font-size: 1.05rem;
  line-height: 1.35;
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.eyebrow {
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.hero-text,
.overlay-card p,
.howitworks-strip p {
  color: #f2f8ff;
}

/* ------------------------------ 8-bit buttons ----------------------------- *
 * The outline is four offset box-shadows rather than a border: they leave the
 * four corner pixels empty, which is what makes it read as a sprite and not a
 * rounded rectangle. The layers, top to bottom:
 *   1-4  the dark notched outline
 *   5    the coloured rim just inside it
 *   6    the light bevel (top + left)
 *   7    the dark bevel (bottom + right)
 *   8    the hard lip under the button (the "depth" styles.css reserves 16px
 *        of margin for)
 * ------------------------------------------------------------------------ */

.primary-button,
.secondary-button,
.danger-button {
  --btn-face: var(--fl-red);
  --btn-rim: var(--fl-yellow);
  --btn-hi: var(--fl-red-hi);
  --btn-lo: var(--fl-red-lo);
  --btn-text: #fff;
  border: 0;
  border-radius: 0;
  padding: 14px 26px;
  background: var(--btn-face);
  color: var(--btn-text);
  font-family: var(--fl-font-heading);
  font-size: 1rem;
  font-weight: 400;
  line-height: 1.3;
  letter-spacing: 0.02em;
  text-shadow: 2px 2px 0 rgba(22, 25, 43, 0.8);
  image-rendering: pixelated;
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    inset 0 0 0 4px var(--btn-rim),
    inset 8px 8px 0 0 var(--btn-hi),
    inset -8px -8px 0 0 var(--btn-lo),
    0 12px 0 0 var(--fl-lip);
  transition: transform 90ms steps(2), box-shadow 90ms steps(2), filter 90ms steps(2);
}

.secondary-button {
  --btn-face: #2f6fbe;
  --btn-rim: var(--fl-blue-hi);
  --btn-hi: #4f8fd8;
  --btn-lo: var(--fl-blue-lo);
}

/* "Join with a school code" — the green of GOING / SCAN TO on the flyer. The
   hue-rotate in styles.css was how the old orange became teal; drop it. */
.hero-cta-alt {
  --btn-face: var(--fl-green);
  --btn-rim: #b6f05a;
  --btn-hi: var(--fl-green-hi);
  --btn-lo: var(--fl-green-lo);
  filter: none;
}

.danger-button {
  --btn-rim: #ffb0a4;
  margin-bottom: 12px;
}

.primary-button:hover,
.secondary-button:hover,
.danger-button:hover {
  transform: translateY(2px);
  filter: brightness(1.08);
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    inset 0 0 0 4px var(--btn-rim),
    inset 8px 8px 0 0 var(--btn-hi),
    inset -8px -8px 0 0 var(--btn-lo),
    0 10px 0 0 var(--fl-lip);
}

.primary-button:active,
.secondary-button:active,
.danger-button:active {
  transform: translateY(8px);
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    inset 0 0 0 4px var(--btn-rim),
    inset -8px -8px 0 0 var(--btn-hi),
    inset 8px 8px 0 0 var(--btn-lo),
    0 4px 0 0 var(--fl-lip);
}

.primary-button:focus-visible,
.secondary-button:focus-visible,
.danger-button:focus-visible,
.site-nav-link:focus-visible,
.secondary-link:focus-visible {
  outline: 3px dashed #fff;
  outline-offset: 8px;
}

.primary-button:disabled,
.secondary-button:disabled {
  transform: none;
  filter: none;
}

.primary-button.is-loading {
  --btn-face: #9aa9bb;
  --btn-rim: #d4dde8;
  --btn-hi: #b9c6d4;
  --btn-lo: #6f7e90;
  background: var(--btn-face);
}

/* ------------------------ nav links / small blocks ------------------------ */

.site-nav {
  gap: 16px 18px;
  margin-bottom: 26px;
  padding: 4px;
}

.site-nav-link,
.secondary-link,
.nav-burger {
  border: 0;
  border-radius: 0;
  margin-bottom: 8px;
  background: #fff;
  color: var(--fl-navy);
  font-family: var(--fl-font-heading);
  font-size: 0.9rem;
  font-weight: 400;
  line-height: 1.3;
  letter-spacing: 0.01em;
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    inset -4px -4px 0 0 #c4d6ee,
    0 9px 0 0 var(--fl-lip);
  transition: transform 90ms steps(2), background 90ms steps(2);
}

.site-nav-link:hover,
.secondary-link:hover,
.nav-burger:hover {
  border-color: transparent;
  background: var(--fl-yellow-hi);
  color: var(--fl-navy);
  transform: translateY(2px);
}

/* The Keep the Beat Going logo, first in the nav bar on every page. `order`
   keeps it ahead of the phone "Menu" button, which api.js prepends. */
.site-nav {
  align-items: center;
}

.site-brand {
  order: -1;
  display: block;
  flex: 0 0 auto;
  margin: -6px 10px 0 -4px;
  line-height: 0;
  transition: transform 120ms ease-out;
}

.site-brand img {
  display: block;
  width: 190px;
  height: auto;
  filter: drop-shadow(3px 4px 0 rgba(16, 36, 74, 0.35));
}

.site-brand:hover {
  transform: translateY(-2px) rotate(-1deg);
}

.site-brand:focus-visible {
  outline: 3px dashed #fff;
  outline-offset: 6px;
}

/* "You are here" is the yellow ? block. */
.site-nav-link.active {
  background: var(--fl-yellow);
  color: var(--fl-navy);
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    inset 4px 4px 0 0 var(--fl-yellow-hi),
    inset -4px -4px 0 0 var(--fl-yellow-lo),
    0 9px 0 0 var(--fl-lip);
}

.identity-chip {
  border: 0;
  border-radius: 0;
  margin-bottom: 8px;
  background: var(--fl-navy);
  box-shadow:
    0 -4px 0 0 var(--fl-ink),
    0 4px 0 0 var(--fl-ink),
    -4px 0 0 0 var(--fl-ink),
    4px 0 0 0 var(--fl-ink),
    0 9px 0 0 var(--fl-lip);
}

.identity-chip .identity-name {
  color: #b9ffcb;
}

.identity-chip .identity-signout,
.identity-chip .identity-code,
.identity-chip .identity-join {
  border-radius: 0;
  background: var(--fl-blue-2);
  font-family: var(--fl-font-sub);
  font-size: 0.85rem;
  font-weight: 700;
}

/* --------------------------------- panels --------------------------------- *
 * Flat flyer blue, a navy outline, square corners and a hard offset shadow
 * — the "Who wins" box on the flyer, not frosted glass.
 * ------------------------------------------------------------------------ */

.hero-copy,
.page-header,
.process-strip article,
.hud-panel,
.legend-details,
.legend-card,
.leaderboard-panel,
.portal-panel,
.winner-panel,
.howitworks-strip,
.path-card,
.wizard-panel {
  border: 4px solid var(--fl-navy);
  border-radius: 0;
  background: var(--fl-blue);
  box-shadow:
    inset 0 4px 0 0 rgba(255, 255, 255, 0.14),
    8px 8px 0 0 var(--fl-lip);
  backdrop-filter: none;
}

.summary-card,
.record-card,
.wizard-step,
.connection-badge,
.level-progress-chip,
.level-preview,
.level-preview-list span,
.mode-card,
.character-card {
  border-radius: 0;
}

.summary-card .stat-label {
  font-size: 0.55rem;
  letter-spacing: 0;
}

.leaderboard-item {
  border-radius: 0;
  border: 2px solid rgba(16, 36, 74, 0.6);
}

.summary-card {
  border: 3px solid var(--fl-navy);
  background: var(--fl-blue-2);
  box-shadow: 4px 4px 0 0 var(--fl-lip);
}

/* The game's frame: a console bezel — navy, with the yellow rim of the
   buttons running round the screen. */
.canvas-wrap {
  border: 4px solid var(--fl-ink);
  border-radius: 0;
  background: var(--fl-navy);
  box-shadow:
    inset 0 0 0 4px var(--fl-yellow),
    inset 0 0 0 8px var(--fl-navy),
    10px 10px 0 0 var(--fl-lip);
}

#game-canvas {
  border-radius: 0;
  outline: 4px solid var(--fl-ink);
}

.overlay {
  border-radius: 0;
  background: rgba(16, 36, 74, 0.45);
}

.overlay-card {
  border: 4px solid var(--fl-ink);
  border-radius: 0;
  background: var(--fl-blue);
  box-shadow:
    inset 0 0 0 4px var(--fl-blue-2),
    inset 0 8px 0 4px rgba(255, 255, 255, 0.08),
    10px 10px 0 0 rgba(16, 36, 74, 0.6);
}

.mode-card,
.character-card {
  border: 3px solid var(--fl-navy);
  background: var(--fl-blue-2);
  box-shadow: 4px 4px 0 0 var(--fl-lip);
}

.mode-card:hover,
.character-card:hover {
  border-color: var(--fl-navy);
  background: #4c89d2;
}

.mode-card.active,
.character-card.active {
  border-color: var(--fl-ink);
  background: var(--fl-green);
  box-shadow:
    inset 0 0 0 3px #b6f05a,
    4px 4px 0 0 var(--fl-lip);
}

.mode-card strong {
  font-family: var(--fl-font-sub);
  font-weight: 700;
  font-size: 1.25rem;
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.mode-card span {
  color: #eef6ff;
}

.mode-card.active strong,
.character-card.active strong {
  color: #fff;
}

.character-current {
  font-family: var(--fl-font-sub);
  font-weight: 700;
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.level-preview {
  border: 3px solid var(--fl-navy);
  background: var(--fl-blue-2);
}

.level-preview-list span {
  background: var(--fl-blue);
}

.highscore-card {
  border: 4px solid var(--fl-ink);
  border-radius: 0;
  background: var(--fl-blue);
  box-shadow:
    inset 0 0 0 4px var(--fl-yellow),
    10px 10px 0 0 rgba(16, 36, 74, 0.6);
}

.game-toast {
  border: 3px solid var(--fl-ink);
  border-radius: 0;
  background: var(--fl-navy);
  box-shadow: 4px 4px 0 0 var(--fl-lip);
}

.save-status:not(:empty),
.leaderboard-status:not(:empty) {
  border-radius: 0;
  background: var(--fl-navy);
}

/* Beat meter: a pixel bar, not a pill. */
.beat-bar {
  height: 22px;
  border: 3px solid var(--fl-ink);
  border-radius: 0;
  background: var(--fl-navy);
}

.beat-fill {
  background: repeating-linear-gradient(90deg, var(--fl-red) 0 12px, #ff7b2e 12px 24px, var(--fl-yellow) 24px 36px);
  box-shadow: none;
}

.process-number {
  border-radius: 0;
  border: 3px solid var(--fl-ink);
  background: var(--fl-yellow);
  color: var(--fl-navy);
  box-shadow: 3px 3px 0 0 var(--fl-lip);
}

.howitworks-strip h3 {
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-navy);
}

.legend-details summary {
  color: #fff;
}

.legend-details summary::before {
  color: var(--fl-yellow);
}

.legend-details summary:hover {
  background: var(--fl-blue-2);
}

/* Form fields: the white box of the flyer's "How it works" panel, so typed
   text and placeholders stay readable on the blue. background-color only —
   select.name-input keeps any arrow image styles.css gives it. */
.name-input {
  border: 3px solid var(--fl-navy);
  border-radius: 0;
  background-color: #fff;
  color: var(--fl-navy);
  box-shadow: inset 3px 3px 0 0 #d5e3f5;
}

.name-input::placeholder {
  color: #6b7fa3;
  opacity: 1;
}

.name-input:focus {
  border-color: var(--fl-ink);
  outline: 3px solid var(--fl-yellow);
  outline-offset: 0;
}

.name-input[readonly] {
  background-color: #e6eef9;
}

select.name-input option {
  background: #fff;
  color: var(--fl-navy);
}

.combo-results {
  border: 3px solid var(--fl-navy);
  border-radius: 0;
  background: var(--fl-navy);
}

.touch-button {
  border-radius: 0;
  border: 3px solid var(--fl-ink);
  background: var(--fl-blue);
  font-family: var(--fl-font-heading);
  font-weight: 400;
  font-size: 0.9rem;
  box-shadow: 0 6px 0 0 var(--fl-lip);
}

.touch-button.accent {
  background: var(--fl-red);
  border-color: var(--fl-ink);
  box-shadow: inset 0 0 0 3px var(--fl-yellow), 0 6px 0 0 var(--fl-lip);
}

/* Inner pages: their logo is the full campaign lockup, on the flyer sky. */
.page-logo {
  max-width: 190px;
  filter: drop-shadow(4px 4px 0 rgba(16, 36, 74, 0.35));
  image-rendering: auto;
}

/* ===========================================================================
 * THE HOME PAGE BANNER
 *
 * Desktop: the lockup (left), the pitch + buttons (middle), Greg standing on
 * the grass (right) — the flyer's composition turned landscape. Tablets drop
 * Greg beside the pitch; phones stack everything and keep Greg beside the
 * buttons at half height so the game is still close to the fold.
 * ------------------------------------------------------------------------ */

.flyer-hero {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  display: grid;
  /* The heart gets the widest column — it is the banner's headline now that
     the Keep the Beat Going logo has moved up to the nav bar. */
  grid-template-columns: minmax(0, 1.7fr) minmax(300px, 1fr) minmax(150px, 200px);
  grid-template-areas: "brand copy greg";
  align-items: center;
  gap: 8px 20px;
  min-height: 560px;
  margin-bottom: 28px;
  padding: 26px 22px 64px;
  border: 4px solid var(--fl-ink);
  background: #439ed7 url("Graphics/flyer/sky-blocks.png") center / cover no-repeat;
  image-rendering: pixelated;
  box-shadow: 10px 10px 0 0 var(--fl-lip);
  text-align: left;
}

/* The grass the banner stands on. */
.flyer-hero::after {
  content: "";
  position: absolute;
  z-index: 1;
  left: 0;
  right: 0;
  bottom: 0;
  height: 66px;
  background: url("Graphics/flyer/grass-tile.png") repeat-x left bottom / auto 66px;
  image-rendering: pixelated;
  pointer-events: none;
}

.flyer-hero-art {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
}

.flyer-hero-art img {
  position: absolute;
  height: auto;
  image-rendering: pixelated;
}

.flyer-cloud-a {
  width: 300px;
  top: 30px;
  right: 18%;
  opacity: 0.95;
}

.flyer-cloud-b {
  width: 240px;
  top: 58%;
  right: -40px;
}

.flyer-boy-cloud {
  width: 250px;
  top: 16px;
  right: 190px;
  animation: flyer-float 6s ease-in-out infinite;
}

.flyer-kid {
  bottom: 46px;
  z-index: 2;
}

.flyer-kid-girl {
  width: 58px;
  left: 3%;
}

.flyer-hero-brand {
  grid-area: brand;
  position: relative;
  z-index: 2;
  display: flex;
  justify-content: center;
}

.flyer-lockup {
  display: block;
  width: 100%;
  max-width: 660px;
  height: auto;
  animation: flyer-bob 4.8s ease-in-out infinite;
}

.flyer-hero-copy {
  grid-area: copy;
  position: relative;
  z-index: 3;
  display: grid;
  gap: 16px;
  align-content: center;
  justify-items: start;
  padding-top: 90px; /* the boy-on-a-cloud floats above the pitch */
}

/* The yellow sign from the flyer ("Nominate Your School ..."). */
.flyer-hero .flyer-plaque {
  margin: 0;
  padding: 12px 20px 10px;
  background: var(--fl-yellow);
  color: var(--fl-navy);
  font-family: var(--fl-font-heading);
  font-size: clamp(1.2rem, 1.85vw, 1.6rem); /* "PLAY. LEARN CPR." on one line */
  font-weight: 400;
  line-height: 1.08;
  letter-spacing: 0.01em;
  text-transform: none;
  text-shadow: none;
  box-shadow:
    0 -5px 0 0 var(--fl-navy),
    0 5px 0 0 var(--fl-navy),
    -5px 0 0 0 var(--fl-navy),
    5px 0 0 0 var(--fl-navy),
    inset 0 0 0 4px var(--fl-yellow-hi),
    inset -8px -8px 0 0 var(--fl-yellow-lo),
    10px 12px 0 0 var(--fl-lip);
}

/* The second line is a sub-heading: Atma Bold. */
.flyer-plaque span {
  display: block;
  margin-top: 6px;
  color: var(--fl-red);
  font-family: var(--fl-font-sub);
  font-weight: 700;
  font-size: 0.82em;
  line-height: 1.1;
}

/* The blue sub-banner with the heart-and-bolt icon. */
.flyer-ribbon {
  display: flex;
  align-items: center;
  gap: 12px;
  max-width: 460px;
  margin: 4px 0 0;
  padding: 10px 16px 10px 12px;
  background: var(--fl-blue-2);
  color: #fff;
  font-size: 1.12rem;
  font-weight: 100;
  line-height: 1.35;
  box-shadow:
    0 -4px 0 0 var(--fl-navy),
    0 4px 0 0 var(--fl-navy),
    -4px 0 0 0 var(--fl-navy),
    4px 0 0 0 var(--fl-navy),
    inset 0 0 0 3px var(--fl-blue-hi),
    8px 9px 0 0 var(--fl-lip);
}

/* A pixel heart with the AED bolt through it, drawn as a data-URI sprite. */
.flyer-ribbon-heart {
  flex: 0 0 auto;
  width: 39px;
  height: 36px;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 13 12' shape-rendering='crispEdges'%3E%3Cpath fill='%2316192b' d='M2 0h1v1h-1zM3 0h1v1h-1zM4 0h1v1h-1zM8 0h1v1h-1zM9 0h1v1h-1zM10 0h1v1h-1zM1 1h1v1h-1zM5 1h1v1h-1zM7 1h1v1h-1zM11 1h1v1h-1zM0 2h1v1h-1zM6 2h1v1h-1zM12 2h1v1h-1zM0 3h1v1h-1zM12 3h1v1h-1zM0 4h1v1h-1zM12 4h1v1h-1zM0 5h1v1h-1zM12 5h1v1h-1zM1 6h1v1h-1zM11 6h1v1h-1zM2 7h1v1h-1zM10 7h1v1h-1zM3 8h1v1h-1zM9 8h1v1h-1zM4 9h1v1h-1zM8 9h1v1h-1zM5 10h1v1h-1zM7 10h1v1h-1zM6 11h1v1h-1z'/%3E%3Cpath fill='%23fff' d='M2 1h1v1h-1zM3 1h1v1h-1zM4 1h1v1h-1zM8 1h1v1h-1zM9 1h1v1h-1zM10 1h1v1h-1zM1 2h1v1h-1zM2 2h1v1h-1zM3 2h1v1h-1zM4 2h1v1h-1zM5 2h1v1h-1zM7 2h1v1h-1zM8 2h1v1h-1zM9 2h1v1h-1zM10 2h1v1h-1zM11 2h1v1h-1zM1 3h1v1h-1zM2 3h1v1h-1zM3 3h1v1h-1zM4 3h1v1h-1zM5 3h1v1h-1zM6 3h1v1h-1zM7 3h1v1h-1zM9 3h1v1h-1zM10 3h1v1h-1zM11 3h1v1h-1zM1 4h1v1h-1zM2 4h1v1h-1zM3 4h1v1h-1zM4 4h1v1h-1zM5 4h1v1h-1zM6 4h1v1h-1zM9 4h1v1h-1zM10 4h1v1h-1zM11 4h1v1h-1zM1 5h1v1h-1zM2 5h1v1h-1zM3 5h1v1h-1zM4 5h1v1h-1zM5 5h1v1h-1zM8 5h1v1h-1zM9 5h1v1h-1zM10 5h1v1h-1zM11 5h1v1h-1zM2 6h1v1h-1zM3 6h1v1h-1zM4 6h1v1h-1zM10 6h1v1h-1zM3 7h1v1h-1zM4 7h1v1h-1zM5 7h1v1h-1zM6 7h1v1h-1zM9 7h1v1h-1zM4 8h1v1h-1zM5 8h1v1h-1zM6 8h1v1h-1zM8 8h1v1h-1zM5 9h1v1h-1zM6 9h1v1h-1zM7 9h1v1h-1zM6 10h1v1h-1z'/%3E%3Cpath fill='%23e52629' d='M8 3h1v1h-1zM7 4h1v1h-1zM8 4h1v1h-1zM6 5h1v1h-1zM7 5h1v1h-1zM5 6h1v1h-1zM6 6h1v1h-1zM7 6h1v1h-1zM8 6h1v1h-1zM9 6h1v1h-1zM7 7h1v1h-1zM8 7h1v1h-1zM7 8h1v1h-1z'/%3E%3C/svg%3E") center / contain no-repeat;
  image-rendering: pixelated;
}

.flyer-hero .hero-actions {
  margin-top: 10px;
  gap: 18px 20px;
}

.flyer-hero .hero-actions .compact-button {
  min-width: 0;
}

.flyer-hero .secondary-link {
  font-size: 0.7rem;
}

.flyer-greg {
  grid-area: greg;
  position: relative;
  z-index: 2;
  align-self: end;
  justify-self: center;
  width: auto;
  height: 520px;
  max-width: 100%;
  object-fit: contain;
  object-position: bottom;
  margin-bottom: -58px; /* feet on the grass */
  filter: drop-shadow(6px 4px 0 rgba(16, 36, 74, 0.3));
}

@keyframes flyer-bob {
  0%, 100% { transform: translateY(0); }
  50% { transform: translateY(-8px); }
}

@keyframes flyer-float {
  0%, 100% { transform: translate(0, 0); }
  50% { transform: translate(-10px, 6px); }
}

@media (prefers-reduced-motion: reduce) {
  .flyer-lockup,
  .flyer-boy-cloud {
    animation: none;
  }
}

/* Tablet: Greg shrinks and the boy on the cloud moves out of the way. */
@media (max-width: 1080px) {
  .flyer-hero {
    grid-template-columns: minmax(0, 1.4fr) minmax(260px, 1fr) 150px;
    min-height: 500px;
  }

  .flyer-greg {
    height: 440px;
  }

  .flyer-boy-cloud {
    width: 200px;
    right: 130px;
  }
}

/* Narrow: lockup on top, then the pitch with Greg beside it. */
@media (max-width: 860px) {
  .flyer-hero {
    grid-template-columns: minmax(0, 1fr) minmax(110px, 34%);
    grid-template-areas:
      "brand brand"
      "copy greg";
    justify-items: stretch;
    text-align: left;
    min-height: 0;
    padding: 18px 16px 60px;
    gap: 6px 10px;
  }

  .flyer-lockup {
    max-width: 560px;
  }

  .flyer-hero-copy {
    padding-top: 0;
    gap: 14px;
  }

  .flyer-greg {
    height: 380px;
    margin-bottom: -54px;
  }

  .flyer-boy-cloud {
    width: 150px;
    top: 10px;
    right: 8px;
  }

  .flyer-cloud-a {
    width: 200px;
    top: 34%;
    right: -30px;
  }

  .flyer-cloud-b,
  .flyer-kid {
    display: none;
  }
}

@media (max-width: 900px) {
  .site-brand img {
    width: 150px;
  }
}

@media (max-width: 640px) {
  /* Logo, Menu and the "who is playing" chip share one row. */
  .site-nav {
    gap: 12px 14px;
  }

  .site-brand {
    margin: -4px 2px 0 -2px;
  }

  .site-brand img {
    width: 104px;
  }

  .identity-chip {
    padding: 4px 8px;
  }

  .identity-chip .identity-signout,
  .identity-chip .identity-code,
  .identity-chip .identity-join {
    font-size: 0.55rem;
    padding: 4px 6px;
  }

  .nav-burger {
    font-size: 0.7rem;
  }

  .page-shell {
    padding-bottom: 110px;
  }

  .page-shell::after {
    height: 48px;
    background-size: auto 48px;
  }

  /* styles.css centres the hero column here; the banner keeps its own grid. */
  .flyer-hero {
    justify-items: stretch;
    text-align: left;
  }

  .flyer-lockup {
    max-width: 420px;
  }

  /* The heart spans the banner here: the cloud boy would hide behind it. */
  .flyer-boy-cloud {
    display: none;
  }

  .flyer-hero .flyer-plaque {
    font-size: 1.15rem;
    padding: 10px 14px 8px;
  }

  .flyer-ribbon {
    font-size: 0.86rem;
    padding: 8px 10px;
  }

  .flyer-ribbon-heart {
    width: 28px;
    height: 25px;
  }

  .flyer-hero .hero-actions {
    display: grid;
    justify-items: stretch;
    gap: 14px;
  }

  .flyer-hero .hero-actions .compact-button {
    width: 100%;
    padding: 12px 14px;
    font-size: 0.82rem;
  }

  .flyer-hero .secondary-link {
    font-size: 0.62rem;
    text-align: center;
  }

  .flyer-greg {
    height: 330px;
  }

  .primary-button,
  .secondary-button {
    font-size: 0.82rem;
  }

  .overlay-card {
    background: var(--fl-blue);
  }
}

@media (max-width: 400px) {
  .flyer-hero {
    grid-template-columns: minmax(0, 1fr) 96px;
    padding: 14px 12px 56px;
  }

  .flyer-greg {
    height: 290px;
  }

  .flyer-hero .flyer-plaque {
    font-size: 1.05rem;
  }
}

/* ------------------------------ CPR check quiz ---------------------------- *
 * A picked answer is the yellow "?" block — chosen, not judged. Green and red
 * appear ONLY after "Check Answers" (and only on a card whose answer is still
 * the one that was checked; see isChallengeAnswerMarked in game.src.js), so a
 * picked answer can never be mistaken for a right one.
 * ------------------------------------------------------------------------ */

.challenge-question {
  border: 4px solid var(--fl-navy);
  border-radius: 0;
  background: rgba(16, 36, 74, 0.32);
  box-shadow: 4px 4px 0 0 var(--fl-lip);
}

.challenge-question.correct {
  border-color: var(--fl-green-lo);
  background: rgba(31, 166, 74, 0.28);
  box-shadow: inset 0 0 0 3px var(--fl-green-hi), 4px 4px 0 0 var(--fl-lip);
}

.challenge-question.wrong {
  border-color: var(--fl-red-lo);
  background: rgba(229, 38, 41, 0.22);
  box-shadow: inset 0 0 0 3px var(--fl-red-hi), 4px 4px 0 0 var(--fl-lip);
}

.challenge-question-head {
  grid-template-columns: auto minmax(0, 1fr) auto;
}

.challenge-number {
  border-radius: 0;
  background: var(--fl-yellow);
  color: var(--fl-navy);
  font-family: var(--fl-font-heading);
  font-weight: 400;
  box-shadow:
    0 -3px 0 0 var(--fl-ink),
    0 3px 0 0 var(--fl-ink),
    -3px 0 0 0 var(--fl-ink),
    3px 0 0 0 var(--fl-ink),
    inset -3px -3px 0 0 var(--fl-yellow-lo);
}

.challenge-prompt {
  font-family: var(--fl-font-sub);
  font-weight: 700;
}

.challenge-mark {
  align-self: start;
  padding: 4px 10px;
  color: #fff;
  font-family: var(--fl-font-heading);
  font-size: 0.78rem;
  font-weight: 400;
  line-height: 1.3;
  white-space: nowrap;
  text-shadow: 1px 1px 0 rgba(22, 25, 43, 0.7);
  box-shadow:
    0 -3px 0 0 var(--fl-ink),
    0 3px 0 0 var(--fl-ink),
    -3px 0 0 0 var(--fl-ink),
    3px 0 0 0 var(--fl-ink);
}

.challenge-mark.is-correct {
  background: var(--fl-green);
}

.challenge-mark.is-wrong {
  background: var(--fl-red);
}

.challenge-choice,
.challenge-inline-button {
  border: 0;
  border-radius: 0;
  margin: 4px;
  background: #fff;
  color: var(--fl-navy);
  font-family: var(--fl-font-sub);
  font-weight: 700;
  box-shadow:
    0 -3px 0 0 var(--fl-ink),
    0 3px 0 0 var(--fl-ink),
    -3px 0 0 0 var(--fl-ink),
    3px 0 0 0 var(--fl-ink),
    inset -3px -3px 0 0 #c4d6ee,
    0 7px 0 0 var(--fl-lip);
  transition: transform 90ms steps(2), background 90ms steps(2);
}

.challenge-choice:hover,
.challenge-inline-button:hover {
  border-color: transparent;
  background: #e4f1ff;
  transform: translateY(2px);
}

.challenge-choice.active {
  border-color: transparent;
  background: var(--fl-yellow);
  color: var(--fl-navy);
  box-shadow:
    0 -3px 0 0 var(--fl-ink),
    0 3px 0 0 var(--fl-ink),
    -3px 0 0 0 var(--fl-ink),
    3px 0 0 0 var(--fl-ink),
    inset 3px 3px 0 0 var(--fl-yellow-hi),
    inset -3px -3px 0 0 var(--fl-yellow-lo),
    0 3px 0 0 var(--fl-lip);
  transform: translateY(4px);
}

/* A marker that says "picked", in shape as well as colour. */
.challenge-choice.active::before {
  content: "\25B6\00a0";
  font-size: 0.8em;
}

.challenge-choice:disabled {
  background: #d7e2ef;
}

.challenge-inline-button {
  background: var(--fl-blue-2);
  color: #fff;
  box-shadow:
    0 -3px 0 0 var(--fl-ink),
    0 3px 0 0 var(--fl-ink),
    -3px 0 0 0 var(--fl-ink),
    3px 0 0 0 var(--fl-ink),
    inset -3px -3px 0 0 var(--fl-blue-lo),
    0 7px 0 0 var(--fl-lip);
}

.challenge-inline-button:hover {
  background: #4c89d2;
}

.challenge-feedback.error {
  color: #ffd6d1;
}

/* ---------------------------------------------------------------------------
 * Heroes on the ladder (hero-kit.js): the hero beside each ranked run on
 * leaderboard.html, the end screen's "<hero> is on the ladder!" card and the
 * hero in the high-score popup. A player's own hero is drawn from its look
 * code; any other run shows the built-in hero's sprite.
 * ------------------------------------------------------------------------ */
.hero-portrait {
  display: block;
  max-width: 100%;
  max-height: 100%;
  object-fit: contain;
  image-rendering: pixelated;
}

/* Inside a frame the portrait fills it, standing on the frame's floor. */
.leaderboard-hero-art .hero-portrait,
.ladder-hero-art .hero-portrait {
  width: 100%;
  height: 100%;
  object-position: 50% 100%;
}

/* A little framed patch of flyer sky for a hero to stand in. */
.leaderboard-hero-art,
.ladder-hero-art {
  display: grid;
  place-items: end center;
  box-sizing: border-box;
  overflow: hidden;
  border: 3px solid var(--fl-ink);
  background: var(--fl-sky) url("Graphics/flyer/sky-blocks.png") 30% 40% / 320% auto no-repeat;
  box-shadow: inset 0 -6px 0 0 rgba(16, 36, 74, 0.25), 3px 3px 0 0 var(--fl-lip);
}

.leaderboard-item.has-hero {
  grid-template-columns: 38px 64px minmax(0, 1fr) auto;
}

.leaderboard-item.has-hero.expandable {
  grid-template-columns: 38px 64px minmax(0, 1fr) auto 16px;
}

/* Full figure, big enough to recognise a player's own hero at a glance.
   Flex (not the shared grid) so the portrait's max-height resolves against
   the frame and the whole hero fits, feet on the floor. */
.leaderboard-hero-art {
  display: flex;
  align-items: flex-end;
  justify-content: center;
  width: 64px;
  height: 74px;
  padding: 4px 4px 3px;
}

.leaderboard-hero-art .hero-portrait {
  width: auto;
  height: auto;
  max-width: 100%;
  max-height: 100%;
}

/* A player-made hero gets the yellow rim of the flyer's buttons. */
.leaderboard-hero-art.own {
  border-color: var(--fl-ink);
  box-shadow:
    inset 0 0 0 2px var(--fl-yellow),
    inset 0 -6px 0 0 rgba(16, 36, 74, 0.25),
    3px 3px 0 0 var(--fl-lip);
}

.leaderboard-hero {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  min-width: 0;
  max-width: 100%;
  margin: 3px 0 1px;
  font-family: var(--fl-font-body);
  font-size: 0.9rem;
  line-height: 1.2;
  white-space: nowrap;
}

/* The hero's unique reel name: a yellow name badge, no outline tricks, so it
   reads cleanly at every size. */
.leaderboard-hero .leaderboard-hero-name {
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  padding: 2px 8px 1px;
  border: 2px solid var(--fl-ink);
  background: var(--fl-yellow);
  color: var(--fl-ink);
  font-family: var(--fl-font-sub);
  font-weight: 700;
  font-size: 0.98rem;
  letter-spacing: 0.01em;
  text-shadow: none;
}

/* A built-in hero ("as Amal") stays quiet: plain text, no badge. */
.leaderboard-hero.built-in .leaderboard-hero-name {
  padding: 0;
  border: 0;
  background: none;
  color: #d6e6fa;
  font-family: var(--fl-font-body);
  font-weight: 700;
  font-size: 0.9rem;
}

.leaderboard-hero-power {
  flex: 0 0 auto;
  width: 16px;
  height: 16px;
  image-rendering: pixelated;
}

.leaderboard-hero-power-name {
  color: #d6e6fa;
  font-family: var(--fl-font-body);
  font-size: 0.8rem;
  overflow: hidden;
  text-overflow: ellipsis;
}

@media (min-width: 900px) {
  .leaderboard-detail .leaderboard-hero {
    flex: 0 1 auto;
  }
}

@media (max-width: 480px) {
  .leaderboard-item.has-hero {
    grid-template-columns: 28px 50px minmax(0, 1fr) auto;
    gap: 9px;
    padding: 10px 10px;
  }

  .leaderboard-item.has-hero.expandable {
    grid-template-columns: 28px 50px minmax(0, 1fr) auto 12px;
  }

  .leaderboard-item.has-hero .leaderboard-rank {
    width: 28px;
    height: 28px;
  }

  .leaderboard-hero-art {
    width: 50px;
    height: 60px;
    padding: 3px 3px 2px;
  }

  /* The name comes first: the power icon drops under it rather than
     squeezing the name into an ellipsis. */
  .leaderboard-hero {
    flex-wrap: wrap;
    row-gap: 3px;
  }

  .leaderboard-hero .leaderboard-hero-name {
    font-size: 0.88rem;
    padding: 1px 6px 0;
  }

  .leaderboard-hero-power-name {
    display: none;
  }
}

/* The winner panel names the hero behind the leading run. */
.winner-hero {
  display: flex;
  align-items: center;
  gap: 12px;
  margin: 12px 0 0;
}

.winner-hero .leaderboard-hero-art {
  width: 76px;
  height: 88px;
  flex: 0 0 auto;
}

.winner-hero .leaderboard-hero {
  font-size: 1rem;
  white-space: normal;
}

.winner-hero .leaderboard-hero .leaderboard-hero-name {
  font-size: 1.1rem;
}

/* End screen: "<hero> is on the ladder!" */
.ladder-hero {
  display: flex;
  align-items: center;
  gap: 12px;
  box-sizing: border-box;
  width: min(100%, 560px);
  margin: 12px auto 6px;
  padding: 9px 14px 9px 9px;
  border: 3px solid var(--fl-ink);
  background: var(--fl-navy);
  box-shadow: inset 0 0 0 3px var(--fl-blue-lo), 5px 5px 0 0 var(--fl-lip);
  text-align: left;
}

.ladder-hero-art {
  flex: 0 0 auto;
  width: 58px;
  height: 64px;
  padding: 4px 3px 3px;
}

.ladder-hero-text {
  flex: 1 1 auto;
  display: grid;
  gap: 4px;
  min-width: 0;
}

.ladder-hero-name {
  font-family: var(--fl-font-heading);
  font-weight: 400;
  font-size: 0.95rem;
  line-height: 1.2;
  color: var(--fl-yellow);
  text-shadow: 2px 2px 0 var(--fl-ink);
  overflow-wrap: anywhere;
}

.ladder-hero-line {
  font-size: 0.9rem;
  line-height: 1.3;
  color: #d6e6fa;
}

.ladder-hero-power {
  width: 16px;
  height: 16px;
  vertical-align: -3px;
  image-rendering: pixelated;
}

.ladder-hero .ladder-hero-link {
  flex: 0 0 auto;
  margin: 0 4px 6px 0;
  padding: 7px 10px;
  font-size: 0.72rem;
  white-space: nowrap;
}

@media (max-width: 540px) {
  .ladder-hero {
    flex-wrap: wrap;
  }

  .ladder-hero-text {
    flex-basis: calc(100% - 80px);
  }

  .ladder-hero .ladder-hero-link {
    margin-left: 70px;
  }
}

/* High-score popup: the hero who set it, mid-leap, above the score. */
.highscore-hero {
  display: grid;
  justify-items: center;
  gap: 6px;
  margin: -6px auto 10px;
}

.highscore-hero-portrait {
  width: auto;
  height: clamp(78px, 14vh, 120px);
  filter: drop-shadow(4px 4px 0 rgba(16, 36, 74, 0.55));
  animation: highscore-hero-hop 900ms steps(6) infinite;
}

.highscore-hero-name {
  font-family: var(--fl-font-heading);
  font-size: 1rem;
  letter-spacing: 0.02em;
  color: #fff;
  text-shadow: 2px 2px 0 var(--fl-navy);
}

@keyframes highscore-hero-hop {
  0%, 100% { transform: translateY(0); }
  50% { transform: translateY(-10px); }
}

@media (prefers-reduced-motion: reduce) {
  .highscore-hero-portrait {
    animation: none;
  }
}

.winner-hero-text {
  display: inline-flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 4px 8px;
  min-width: 0;
  color: #d6e6fa;
  font-size: 0.95rem;
}

/* ------------------------- continue from your stage ------------------------ *
 * The overlay's secondary choice, set by game.js (showOverlay's altAction):
 * "Continue from Stage N" on the setup screen — green, the flyer's GOING
 * colour, because it is a way FORWARD — and "Start again from Stage 1" on the
 * out-of-retries screen, where the main button already carries on and this is
 * the quieter blue. It sits beside the main button when the card is wide
 * enough and drops underneath it on a phone (both reserve their 16px lip).
 * ------------------------------------------------------------------------- */
.continue-run-button {
  margin-left: 10px;
  margin-right: 10px;
}

.continue-run-button.is-go {
  --btn-face: var(--fl-green);
  --btn-rim: #b6f05a;
  --btn-hi: var(--fl-green-hi);
  --btn-lo: var(--fl-green-lo);
}

.overlay-card.compact .continue-run-button {
  margin-top: 8px;
}

#action-button:not(.hidden) + .continue-run-button:not(.hidden) {
  /* Nudge the pair apart so two block buttons never read as one wide one. */
  margin-left: 18px;
}

@media (max-width: 560px) {
  .continue-run-button,
  #action-button:not(.hidden) + .continue-run-button:not(.hidden) {
    margin-left: 0;
    margin-right: 0;
  }
}
