/* mapindex site styles. Colours come only from the --color-* roles of
   design/tokens.css; this file adds type, spacing and components on top. */

/* Figtree for text, Plus Jakarta Sans for headings; each in a Latin and a
   Latin Extended file, so most pages load only the first. */
@font-face {
  font-family: "Figtree";
  src: url("../vendor/figtree/figtree-latin-wght-normal.202cfb54d4e6.woff2") format("woff2");
  font-weight: 300 900;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC,
    U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215,
    U+FEFF, U+FFFD;
}

@font-face {
  font-family: "Figtree";
  src: url("../vendor/figtree/figtree-latin-ext-wght-normal.eca8d8b337ff.woff2") format("woff2");
  font-weight: 300 900;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304,
    U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB,
    U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}

@font-face {
  font-family: "Plus Jakarta Sans";
  src: url("../vendor/plus-jakarta-sans/plus-jakarta-sans-latin-wght-normal.7660bd9909fb.woff2")
    format("woff2");
  font-weight: 200 800;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC,
    U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215,
    U+FEFF, U+FFFD;
}

@font-face {
  font-family: "Plus Jakarta Sans";
  src: url("../vendor/plus-jakarta-sans/plus-jakarta-sans-latin-ext-wght-normal.341687eeeb6a.woff2")
    format("woff2");
  font-weight: 200 800;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304,
    U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB,
    U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}

@font-face {
  font-family: "Geist Mono";
  src: url("../vendor/geist/GeistMono-Variable.308360d8a547.woff2") format("woff2");
  font-weight: 100 900;
  font-style: normal;
  font-display: swap;
}

:root {
  --z-tooltip: 1000;
  --font-sans: "Figtree", ui-sans-serif, system-ui, sans-serif;
  --font-display: "Plus Jakarta Sans", "Figtree", ui-sans-serif, system-ui, sans-serif;
  /* Only for code and identifiers, never for labels, dates or counts. */
  --font-mono: "Geist Mono", ui-monospace, "SFMono-Regular", monospace;

  --space-1: 0.25rem;
  --space-2: 0.5rem;
  --space-3: 0.75rem;
  --space-4: 1rem;
  --space-5: 1.25rem;
  --space-6: 1.5rem;
  --space-8: 2rem;
  --space-10: 2.5rem;
  --space-12: 3rem;
  --space-16: 4rem;

  --radius-s: 8px;
  --radius-m: 12px;
  --radius-l: 18px;
  --radius-xl: 24px;
  --radius-pill: 999px;

  --gutter: clamp(1rem, 0.5rem + 2vw, 2rem);
  --masthead-height: 4rem;
  --heading-size: clamp(1.75rem, 1.35rem + 1.6vw, 2.5rem);
  --row-head-height: 1.5rem;
  --page-width: 105rem;
  --explorer-start: 9rem;
  --explorer-side: 19rem;
  --shadow-card:
    0 1px 2px color-mix(in srgb, var(--color-shadow) 10%, transparent),
    0 6px 18px -8px color-mix(in srgb, var(--color-shadow) 24%, transparent);
  --shadow-lift:
    0 2px 4px color-mix(in srgb, var(--color-shadow) 8%, transparent),
    0 14px 30px -12px color-mix(in srgb, var(--color-shadow) 26%, transparent);
  --shadow-float:
    0 16px 40px -14px color-mix(in srgb, var(--color-shadow) 35%, transparent),
    0 2px 6px color-mix(in srgb, var(--color-shadow) 14%, transparent);
  --ease: cubic-bezier(0.2, 0.7, 0.2, 1);
  /* Where the 2400 px contour landscape is centred; narrow screens move its summit
     into view. Opacities per layer, a little stronger at night where lines glow. */
  --terrain-shift: 0px;
  --terrain-x: calc(50% + var(--terrain-shift));
  --terrain-size: max(2400px, 100%);
  /* The landscape is square; tall enough for any viewport plus the whole drift. */
  --terrain-height: max(2400px, 100vw);
  --drift-range: 4000px;
  --drift-max: 600px;
  --card-mat: 5px;
  --chevron-down: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='2.75' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='m5 8.5 7 7 7-7'/%3E%3C/svg%3E");
  --color-surface-veil: color-mix(in srgb, var(--color-surface) 86%, transparent);
  /* Light keeps its line work quiet, so the page stays restful. */
  --contour-minor-hero: 0.18;
  --contour-index-hero: 0.3;
  --contour-minor-page: 0.1;
  --contour-index-page: 0.17;
  /* By day a white highlight below each index line crisps it like print. */
  --contour-filter: drop-shadow(0 1px 0 var(--color-contour-glow));
}

@media (max-width: 47.99rem) {
  :root {
    --terrain-shift: -300px;
  }
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --contour-minor-hero: 0.12;
    --contour-index-hero: 0.3;
    --contour-minor-page: 0.1;
    --contour-index-page: 0.26;
    --contour-filter: drop-shadow(0 0 4px var(--color-contour-glow));
  }
}

:root[data-theme="dark"] {
  --contour-minor-hero: 0.12;
  --contour-index-hero: 0.3;
  --contour-minor-page: 0.1;
  --contour-index-page: 0.26;
  --contour-filter: drop-shadow(0 0 4px var(--color-contour-glow));
}

/* --- Base ------------------------------------------------------------------ */

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  -webkit-text-size-adjust: 100%;
  text-size-adjust: 100%;
  scroll-padding-top: calc(var(--masthead-height) + var(--space-4));
}

body {
  margin: 0;
  min-height: 100vh;
  display: flex;
  flex-direction: column;
  background: var(--color-canvas);
  color: var(--color-text);
  font-family: var(--font-sans);
  font-size: 1rem;
  line-height: 1.55;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

img,
svg {
  display: block;
  max-width: 100%;
}

h1,
h2,
h3,
h4 {
  margin: 0;
  font-family: var(--font-display);
  line-height: 1.2;
  font-weight: 650;
  letter-spacing: -0.015em;
  text-wrap: balance;
}

h1 {
  font-size: var(--heading-size);
  font-weight: 700;
  letter-spacing: -0.025em;
}

h2 {
  font-size: 1.125rem;
}

h3 {
  font-size: 1rem;
}

p {
  margin: 0;
  text-wrap: pretty;
}

a {
  color: var(--color-accent);
  text-decoration-thickness: 1px;
  text-underline-offset: 0.2em;
}

a:hover {
  color: var(--color-accent-hover);
}

button,
input,
select,
textarea {
  font: inherit;
  color: inherit;
}

:focus-visible {
  outline: 2px solid var(--color-focus);
  outline-offset: 2px;
}

::selection {
  background: var(--color-accent-soft);
  color: var(--color-text);
}

[hidden] {
  display: none !important;
}

.visually-hidden {
  position: absolute !important;
  width: 1px;
  height: 1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  clip-path: inset(50%);
  white-space: nowrap;
}

.skip-link {
  position: absolute;
  top: var(--space-2);
  left: var(--space-2);
  z-index: 100;
  padding: var(--space-2) var(--space-4);
  border-radius: var(--radius-m);
  background: var(--color-accent);
  color: var(--color-on-accent);
  font-weight: 600;
  transform: translateY(-200%);
}

.skip-link:focus-visible {
  transform: none;
}

.icon {
  width: 1.125rem;
  height: 1.125rem;
  flex: none;
  fill: none;
  stroke: currentColor;
  stroke-width: 1.85;
  stroke-linecap: round;
  stroke-linejoin: round;
}

.mono {
  font-family: var(--font-mono);
}

/* Short labels and figures speak in the text face; tabular digits keep counts steady. */
.eyebrow {
  font-size: 0.75rem;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--color-earth);
}

.muted {
  color: var(--color-text-muted);
}

/* --- Masthead -------------------------------------------------------------- */

/* Nearly solid, like the footer: the page's landscape shows through only as a trace,
   so it always lines up without a copy of its own. */
.masthead {
  position: sticky;
  top: 0;
  z-index: 40;
  background: color-mix(in srgb, var(--color-surface) 96%, transparent);
  box-shadow: 0 1px 0 color-mix(in srgb, var(--color-shadow) 8%, transparent);
}

/* The contour landscape, the brand's signature: minor lines in blue-grey ink, every
   fifth an index line in the accent, six summits in pools of light; generated by
   design/export_contours.py in five elevation bands (components/terrain.html).
   One fixed layer behind every page (.terrain) shows it in the gaps between cards
   and columns and faintly through panels; a fixed element rather than
   background-attachment: fixed, which mobile Safari ignores. The nearly solid
   masthead and footer let it through only as a trace.
   - Drift: the land moves up gently as the page scrolls (0.15 times the scroll, at
     most --drift-max), through a scroll-driven animation. Browsers without one
     (Firefox) keep the land still: a script would follow the compositor's scroll a
     frame late, which reads as lag.
   - Rise: on every page load (.terrain-rise, set in base.html) the bands appear from
     the lowest to the highest, each lifting a little, and the summits light up last,
     like a range growing out of a flat sheet.
   Both stay still under reduced motion; without JavaScript the land is just there. */
.terrain {
  position: fixed;
  inset: 0;
  z-index: -1;
  overflow: hidden;
  pointer-events: none;
}

.terrain__land {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  height: var(--terrain-height);
}

.terrain__band,
.terrain__lines,
.terrain__glow,
.terrain__index,
.terrain__light {
  position: absolute;
  inset: 0;
}

.terrain__light {
  background:
    radial-gradient(28rem 14rem at calc(50% + 60px + var(--terrain-shift)) 80px, var(--color-summit), transparent),
    radial-gradient(20rem 12rem at calc(50% - 500px + var(--terrain-shift)) 700px, var(--color-summit), transparent),
    radial-gradient(20rem 12rem at calc(50% + 620px + var(--terrain-shift)) 1150px, var(--color-summit), transparent),
    radial-gradient(18rem 10rem at calc(50% - 150px + var(--terrain-shift)) 1600px, var(--color-summit), transparent),
    radial-gradient(20rem 12rem at calc(50% - 720px + var(--terrain-shift)) 2080px, var(--color-summit), transparent),
    radial-gradient(18rem 11rem at calc(50% + 400px + var(--terrain-shift)) 2240px, var(--color-summit), transparent),
    radial-gradient(64rem 30rem at calc(50% + 60px + var(--terrain-shift)) 80px, var(--color-summit-halo), transparent 75%),
    radial-gradient(44rem 26rem at calc(50% - 500px + var(--terrain-shift)) 700px, var(--color-summit-halo), transparent 75%),
    radial-gradient(44rem 26rem at calc(50% + 620px + var(--terrain-shift)) 1150px, var(--color-summit-halo), transparent 75%),
    radial-gradient(44rem 26rem at calc(50% - 720px + var(--terrain-shift)) 2080px, var(--color-summit-halo), transparent 75%);
}

/* Separate from the masked index lines: a filter applies before the mask would. */
.terrain__glow {
  filter: var(--contour-filter);
}

.terrain__lines,
.terrain__index {
  -webkit-mask-position: var(--terrain-x) 0;
  mask-position: var(--terrain-x) 0;
  -webkit-mask-size: var(--terrain-size) auto;
  mask-size: var(--terrain-size) auto;
  -webkit-mask-repeat: no-repeat;
  mask-repeat: no-repeat;
}

.terrain__lines {
  background: var(--color-contour);
  opacity: var(--contour-minor-page);
}

.terrain__index {
  background: var(--color-contour-index);
  opacity: var(--contour-index-page);
}

.terrain__band--0 {
  --band: 0;
}

.terrain__band--0 .terrain__lines {
  -webkit-mask-image: url("../patterns/contours-0.09fcd984ecde.svg");
  mask-image: url("../patterns/contours-0.09fcd984ecde.svg");
}

.terrain__band--1 {
  --band: 1;
}

.terrain__band--1 .terrain__lines {
  -webkit-mask-image: url("../patterns/contours-1.87b6dd865e28.svg");
  mask-image: url("../patterns/contours-1.87b6dd865e28.svg");
}

.terrain__band--1 .terrain__index {
  -webkit-mask-image: url("../patterns/contours-index-1.4f4a8ff8efa7.svg");
  mask-image: url("../patterns/contours-index-1.4f4a8ff8efa7.svg");
}

.terrain__band--2 {
  --band: 2;
}

.terrain__band--2 .terrain__lines {
  -webkit-mask-image: url("../patterns/contours-2.5c034495acb2.svg");
  mask-image: url("../patterns/contours-2.5c034495acb2.svg");
}

.terrain__band--2 .terrain__index {
  -webkit-mask-image: url("../patterns/contours-index-2.47dc7b0303fc.svg");
  mask-image: url("../patterns/contours-index-2.47dc7b0303fc.svg");
}

.terrain__band--3 {
  --band: 3;
}

.terrain__band--3 .terrain__lines {
  -webkit-mask-image: url("../patterns/contours-3.08dbc258176e.svg");
  mask-image: url("../patterns/contours-3.08dbc258176e.svg");
}

.terrain__band--3 .terrain__index {
  -webkit-mask-image: url("../patterns/contours-index-3.d1ba6b2d7feb.svg");
  mask-image: url("../patterns/contours-index-3.d1ba6b2d7feb.svg");
}

.terrain__band--4 {
  --band: 4;
}

.terrain__band--4 .terrain__lines {
  -webkit-mask-image: url("../patterns/contours-4.022db67d8e61.svg");
  mask-image: url("../patterns/contours-4.022db67d8e61.svg");
}

.terrain__band--4 .terrain__index {
  -webkit-mask-image: url("../patterns/contours-index-4.e55be2a8c905.svg");
  mask-image: url("../patterns/contours-index-4.e55be2a8c905.svg");
}

@media (prefers-reduced-motion: no-preference) {
  @supports (animation-timeline: scroll()) {
    .terrain__land {
      animation: terrain-drift linear both;
      animation-timeline: scroll(root);
      animation-range: 0 var(--drift-range);
    }
  }

  .terrain-rise .terrain__band {
    animation: terrain-rise 0.9s cubic-bezier(0.2, 0.7, 0.2, 1) both;
    animation-delay: calc(0.1s + var(--band) * 0.16s);
  }

  .terrain-rise .terrain__light {
    animation: terrain-light 1.1s 0.8s ease-out both;
  }
}

@keyframes terrain-drift {
  from {
    transform: translateY(0);
  }
  to {
    transform: translateY(calc(-1 * var(--drift-max)));
  }
}

@keyframes terrain-rise {
  from {
    opacity: 0;
    transform: translateY(12px);
  }
}

@keyframes terrain-light {
  from {
    opacity: 0;
  }
}

/* --- Masthead layout ------------------------------------------------------- */

/* The masthead shares the explorer's columns: the brand in the empty one at the
   start, the search above the maps, the theme switch above the noticeboard. Phones
   put the search in a row of its own. */
.masthead__inner {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: center;
  gap: var(--space-2) var(--space-3);
  max-width: var(--page-width);
  min-height: var(--masthead-height);
  margin: 0 auto;
  padding: var(--space-2) var(--gutter);
}

.brand {
  display: inline-flex;
  align-items: center;
  gap: var(--space-3);
  color: var(--color-text);
  text-decoration: none;
  font-family: var(--font-display);
  font-size: 1.25rem;
  font-weight: 700;
  letter-spacing: -0.015em;
  border-radius: var(--radius-m);
}

.brand:hover {
  color: var(--color-text);
}

.brand img,
.brand svg {
  width: 2rem;
  height: 2rem;
}

/* An animated brand logo is the loader at rest; site.js plays the wave while it is
   waving. It keeps the logo's own colour, never the theme's accent. */
.brand--animated .mapindex-loader path {
  fill: var(--color-logo);
  animation-name: none;
}

@media (prefers-reduced-motion: no-preference) {
  .brand--animated[data-waving] .mapindex-loader path {
    animation-name: mapindex-loader-wave;
  }
}

/* The filters' button right of the search box. */
.masthead__search {
  grid-column: 1 / -1;
  display: flex;
  align-items: center;
  gap: var(--space-2);
}

.masthead__search .search-box {
  flex: 1;
  min-width: 0;
}

.masthead__nav {
  grid-area: 1 / -2;
  justify-self: end;
  display: flex;
  align-items: center;
  gap: var(--space-1);
}

@media (min-width: 48rem) {
  .masthead__inner {
    grid-template-columns: auto minmax(0, 1fr) auto;
    column-gap: var(--space-6);
  }

  .masthead__search {
    grid-area: 1 / 2;
  }
}

@media (min-width: 64rem) {
  .masthead__inner {
    grid-template-columns: auto minmax(0, 1fr) var(--explorer-side);
  }
}

@media (min-width: 80rem) {
  .masthead__inner {
    grid-template-columns: var(--explorer-start) minmax(0, 1fr) var(--explorer-side);
  }
}

/* The theme switch offers the theme not in effect. */
.theme-switch .theme-switch__light {
  display: none;
}

:root[data-theme="dark"] .theme-switch .theme-switch__light {
  display: inline-flex;
}

:root[data-theme="dark"] .theme-switch .theme-switch__dark {
  display: none;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) .theme-switch .theme-switch__light {
    display: inline-flex;
  }

  :root:not([data-theme="light"]) .theme-switch .theme-switch__dark {
    display: none;
  }
}

@media (max-width: 47.99rem) {
  .masthead__search {
    margin-bottom: var(--space-1);
  }

  .masthead__nav .button {
    padding-inline: 0;
    width: 2.5rem;
  }

  /* Phones keep the search box wide: no keyboard hint, the filters' button shows its
     icon only, and the filters span the search row. */
  .masthead__search .search-box__shortcut {
    display: none;
  }

  .masthead__search .search-box .input {
    padding-left: var(--space-3);
  }

  .filters__toggle {
    width: 2.5rem;
    padding: 0;
  }

  .filters__toggle-label {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip-path: inset(50%);
    white-space: nowrap;
  }

  .filters__toggle .filters__dot {
    position: absolute;
    top: 0.5rem;
    right: 0.5rem;
  }
}

/* --- Page and explorer layout -------------------------------------------- */

.page {
  flex: 1;
  width: 100%;
  max-width: var(--page-width);
  margin: 0 auto;
  padding: var(--space-6) var(--gutter) var(--space-16);
}

.explorer {
  display: grid;
  gap: var(--space-6);
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas:
    "content"
    "noticeboard";
}

.explorer__content {
  grid-area: content;
  min-width: 0;
}

.explorer__noticeboard {
  position: relative;
  grid-area: noticeboard;
  display: grid;
  align-content: start;
  gap: var(--space-4);
}

/* The noticeboard's heading is for screen readers only. */
.explorer__noticeboard > .section-head {
  position: absolute;
  top: calc(-1 * var(--space-5));
  right: var(--space-2);
  min-height: 0;
}

@media (min-width: 64rem) {
  .explorer {
    grid-template-columns: minmax(0, 1fr) var(--explorer-side);
    grid-template-areas: "content noticeboard";
    align-items: start;
  }

  /* The noticeboard has no visible heading: its box starts level with the first map,
     below the results heading where there is one. */
  .explorer:has(.results__head) {
    --explorer-lead: calc(var(--heading-size) * 1.2 + var(--space-6));
  }

  .explorer:has(.active-filters) {
    --explorer-lead: calc(var(--heading-size) * 1.2 + 1.75rem + 2 * var(--space-6));
  }

  .explorer__noticeboard {
    margin-top: var(--explorer-lead, 0px);
  }
}

/* Wide screens leave the brand's column empty, so the search starts with the maps. */
@media (min-width: 80rem) {
  .explorer {
    grid-template-columns: var(--explorer-start) minmax(0, 1fr) var(--explorer-side);
    grid-template-areas: ". content noticeboard";
  }
}

/* --- Panels ---------------------------------------------------------------- */

/* Panels let the landscape show faintly through; cards stay opaque so maps lead. */
.panel {
  display: grid;
  gap: var(--space-5);
  padding: var(--space-5);
  border-radius: var(--radius-l);
  background: var(--color-surface-veil);
}

.panel__title {
  font-size: 0.9375rem;
  font-weight: 600;
}

/* --- Buttons --------------------------------------------------------------- */

.button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
  min-height: 2.5rem;
  padding: 0 var(--space-5);
  border: 0;
  border-radius: var(--radius-pill);
  background: var(--color-accent-soft);
  color: var(--color-accent-soft-ink);
  font-size: 0.9375rem;
  font-weight: 600;
  line-height: 1;
  text-decoration: none;
  white-space: nowrap;
  cursor: pointer;
  position: relative;
  transition:
    background-color 0.15s var(--ease),
    color 0.15s var(--ease);
}

.button:hover {
  background: color-mix(in srgb, var(--color-accent-soft) 82%, var(--color-accent));
  color: var(--color-accent-soft-ink);
}

.button--primary {
  background: var(--color-accent);
  color: var(--color-on-accent);
}

.button--primary:hover {
  background: var(--color-accent-hover);
  color: var(--color-on-accent);
}

.button--quiet {
  background: transparent;
  color: var(--color-text-muted);
}

.button--quiet:hover {
  background: var(--color-raised);
  color: var(--color-text);
}

.button--icon {
  width: 2.5rem;
  padding: 0;
}

.button--small {
  min-height: 2rem;
  padding: 0 var(--space-4);
  font-size: 0.8125rem;
}

.button--block {
  width: 100%;
}

.button[aria-pressed="true"] {
  background: var(--color-accent);
  color: var(--color-on-accent);
}

.button:disabled {
  opacity: 0.55;
  cursor: not-allowed;
}

.button--small.button--icon {
  width: 2rem;
}

/* An icon button names its action, and a chip its figure, in a tooltip on hover
   and keyboard focus. The tooltip is also the accessible name, so it fades
   instead of hiding.
   It is fixed to the viewport so no scrolling or clipping container can hide
   it, and site.js places it beside its anchor, flipped and kept on screen. */
.tip {
  position: fixed;
  top: 0;
  left: 0;
  z-index: var(--z-tooltip);
  max-width: calc(100vw - 2 * var(--space-2));
  padding: var(--space-1) var(--space-2);
  border-radius: var(--radius-s);
  background: var(--color-text);
  color: var(--color-canvas);
  font-size: 0.75rem;
  white-space: nowrap;
  pointer-events: none;
  opacity: 0;
  transition: opacity 0.15s var(--ease);
}

@media (prefers-reduced-motion: reduce) {
  .tip {
    transition: none;
  }
}

.button:focus-visible .tip,
.button[data-tip-shown] .tip,
.tip[data-shown] {
  opacity: 1;
}

/* A card's own tips stay transparent, for screen readers only: site.js shows them
   outside the card, which would clip them. */
.map-card .tip,
.map-card .chip:hover .tip {
  opacity: 0;
}

/* A tooltip with whole sentences: a card's cut title and description. */
.tip--text {
  display: grid;
  gap: var(--space-1);
  max-width: min(22rem, calc(100vw - 2 * var(--space-2)));
  padding: var(--space-2) var(--space-3);
  font-size: 0.8125rem;
  line-height: 1.4;
  white-space: normal;
  overflow-wrap: anywhere;
}

@media (hover: hover) {
  .button:hover .tip,
  .chip:hover .tip,
  .fact:hover .tip {
    opacity: 1;
  }
}

/* --- Forms ----------------------------------------------------------------- */

.field {
  display: grid;
  gap: var(--space-2);
}

.field__label {
  font-size: 0.8125rem;
  font-weight: 600;
  color: var(--color-text-muted);
}

.input,
.select,
.textarea {
  width: 100%;
  min-height: 2.75rem;
  padding: 0.625rem var(--space-3);
  border: 0;
  border-radius: var(--radius-m);
  background: var(--color-field);
  color: var(--color-text);
  font-size: 0.9375rem;
}

.textarea {
  min-height: 6rem;
  resize: vertical;
  line-height: 1.5;
}

.select {
  appearance: none;
  padding-right: 2.25rem;
}

/* The chevron of a select or dropdown: one stroke with a round join, drawn in the
   text colour through a mask. A native select takes no pseudo-elements, so it sits
   in a `.select-box`. */
.select-box {
  position: relative;
  display: block;
}

.select-box::after,
.dropdown__summary::after {
  content: "";
  position: absolute;
  top: 50%;
  right: 0.85rem;
  width: 0.8rem;
  height: 0.8rem;
  translate: 0 -50%;
  background: currentColor;
  pointer-events: none;
  -webkit-mask: var(--chevron-down) center / contain no-repeat;
  mask: var(--chevron-down) center / contain no-repeat;
}

.input::placeholder,
.textarea::placeholder {
  color: var(--color-text-subtle);
}

.search-box {
  position: relative;
  display: flex;
  align-items: center;
}

.search-box .input {
  padding-left: 2.75rem;
  padding-right: 3rem;
  border-radius: var(--radius-pill);
}

.search-box__submit {
  position: absolute;
  right: var(--space-1);
  display: inline-grid;
  place-items: center;
  width: 2.25rem;
  height: 2.25rem;
  border: 0;
  border-radius: 50%;
  background: transparent;
  color: var(--color-text-muted);
  cursor: pointer;
}

.search-box__submit:hover,
.search-box__submit:focus-visible {
  background: var(--color-raised);
  color: var(--color-accent);
}

/* While a search loads (htmx marks the button), the loader takes the
   magnifier's place; a short delay keeps quick answers from flickering. */
.search-box__submit > * {
  grid-area: 1 / 1;
  transition: opacity 0.2s var(--ease);
}

.search-box__loader {
  display: inline-grid;
  opacity: 0;
}

.search-box__loader svg {
  width: 1.375rem;
  height: 1.375rem;
}

.search-box__submit.htmx-request > .icon {
  opacity: 0;
  transition-delay: 0.15s;
}

.search-box__submit.htmx-request > .search-box__loader {
  opacity: 1;
  transition-delay: 0.15s;
}

.search-box__shortcut {
  position: absolute;
  left: var(--space-2);
  display: inline-grid;
  place-items: center;
  min-width: 1.5rem;
  height: 1.5rem;
  padding: 0 0.3rem;
  border-radius: var(--radius-pill);
  background: var(--color-raised);
  color: var(--color-text-subtle);
  font-size: 0.75rem;
  font-weight: 600;
}

.search-box__shortcut {
  left: 0.6rem;
}

.search-box .input:focus + .search-box__shortcut {
  display: none;
}

@media (pointer: coarse) {
  .search-box__shortcut {
    display: none !important;
  }

  .search-box .input {
    padding-left: var(--space-3);
  }
}

.choice-list {
  display: grid;
  gap: var(--space-1);
  margin: 0;
  padding: 0;
  border: 0;
}

.choice {
  display: flex;
  align-items: center;
  gap: var(--space-3);
  min-height: 2.25rem;
  padding: 0 var(--space-3);
  border-radius: var(--radius-m);
  font-size: 0.9375rem;
  cursor: pointer;
}

.choice:hover {
  background: var(--color-raised);
}

.choice input {
  width: 1rem;
  height: 1rem;
  margin: 0;
  accent-color: var(--color-accent);
}

.choice__count {
  margin-left: auto;
  font-size: 0.8125rem;
  font-variant-numeric: tabular-nums;
  color: var(--color-text-subtle);
}

.choice:has(input:checked:not([value=""])) {
  background: var(--color-accent-soft);
  color: var(--color-accent-soft-ink);
}

/* A button sizes its icon against itself: without padding the icon's
   `max-width: 100%` would shrink it to nothing. */
.filters__toggle .icon {
  max-width: none;
}

.filters__toggle[aria-expanded="true"] {
  background: var(--color-raised);
  color: var(--color-text);
}

.filters__dot {
  width: 0.5rem;
  height: 0.5rem;
  border-radius: 50%;
  background: var(--color-accent);
}

/* The form leaves its parts to the masthead's grid, so the filters unfold as a row
   of their own below it: the masthead grows and pushes the page down (site.js
   animates it), the dropdowns side by side and their menus floating below them. */
.filters {
  display: contents;
}

.filters__body {
  grid-column: 1 / -1;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(10rem, 1fr));
  align-items: start;
  gap: var(--space-5);
  padding-block: var(--space-2);
}

/* The sort's label sits on its select like a dropdown's legend, which takes no gap. */
.filters__body .field {
  gap: 0;
}

.filters__body .dropdown__panel {
  position: absolute;
  top: 100%;
  right: 0;
  left: 0;
  z-index: 1;
  min-width: 12rem;
  box-shadow: var(--shadow-float);
}

.filters__actions {
  display: flex;
  flex-wrap: wrap;
  justify-content: end;
  gap: var(--space-2);
}

.dropdown {
  position: relative;
}

.dropdown__summary {
  position: relative;
  display: flex;
  align-items: center;
  gap: var(--space-2);
  cursor: pointer;
  list-style: none;
}

.dropdown__summary::-webkit-details-marker {
  display: none;
}

.dropdown__summary .icon,
.dropdown .choice .icon {
  flex: none;
  width: 1rem;
  height: 1rem;
}

.dropdown__label {
  overflow: hidden;
  white-space: nowrap;
  text-overflow: ellipsis;
}

.dropdown__panel {
  display: grid;
  gap: var(--space-1);
  margin-top: var(--space-1);
  padding: var(--space-1);
  border-radius: var(--radius-m);
  background: var(--color-field);
}

.dropdown__menu {
  display: grid;
  max-height: 18rem;
  overflow-y: auto;
  gap: var(--space-1);
}

.dropdown__search {
  min-height: 2.25rem;
  padding-block: var(--space-2);
  background: var(--color-surface);
}

.dropdown__empty {
  padding: var(--space-2) var(--space-3);
  font-size: 0.875rem;
}

.dropdown__loader {
  justify-content: center;
  padding: var(--space-1);
}

.honeypot {
  position: absolute;
  left: -100vw;
  width: 1px;
  height: 1px;
  overflow: hidden;
}

/* --- Chips ----------------------------------------------------------------- */

.chips {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2);
  margin: 0;
  padding: 0;
  list-style: none;
}

.chip {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  min-height: 1.75rem;
  padding: 0 0.65rem;
  border-radius: var(--radius-pill);
  background: var(--color-raised);
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  font-weight: 500;
  line-height: 1;
  text-decoration: none;
  white-space: nowrap;
}

a.chip:hover {
  background: var(--color-hover);
  color: var(--color-text);
}

.chip--tag {
  background: var(--color-accent-soft);
  color: var(--color-accent-soft-ink);
}

a.chip--tag:hover {
  background: color-mix(in srgb, var(--color-accent-soft) 80%, var(--color-accent));
  color: var(--color-accent-soft-ink);
}

/* A folding list keeps to one row; its last chip counts the rest and unfolds them.
   Until the script has folded it, the list is cut to one row, so it never jumps. */
.js .chips[data-fold]:not([data-fold-ready]) {
  max-height: 1.75rem;
  overflow: hidden;
}

.chip--more {
  border: 0;
  font: inherit;
  font-size: 0.8125rem;
  cursor: pointer;
}

.chip--more:hover {
  background: var(--color-hover);
  color: var(--color-text);
}

.chip__flag {
  width: 1.125rem;
  height: auto;
  aspect-ratio: 4 / 3;
  border-radius: 2px;
}

.chip__code {
  font-size: 0.75rem;
  font-weight: 600;
  letter-spacing: 0.03em;
}

.chip .icon {
  width: 0.875rem;
  height: 0.875rem;
}

/* --- Map cards ------------------------------------------------------------- */

.map-card {
  position: relative;
  container-type: inline-size;
  display: flex;
  flex-direction: column;
  height: 100%;
  overflow: hidden;
  border-radius: var(--radius-l);
  background: var(--color-card);
  box-shadow: var(--shadow-card);
  transition:
    background-color 0.18s var(--ease),
    box-shadow 0.18s var(--ease),
    transform 0.18s var(--ease);
}

.map-card:hover {
  background: var(--color-raised);
  box-shadow: var(--shadow-lift);
  transform: translateY(-2px);
}

@media (prefers-reduced-motion: reduce) {
  .map-card,
  .map-card:hover {
    transition: none;
    transform: none;
  }
}

.map-card:has(.map-card__link:focus-visible) {
  outline: 2px solid var(--color-focus);
  outline-offset: 2px;
}

/* The thumbnail sits in the card like a print in its mat: a narrow frame of card
   colour, its own rounded corners and a hairline that keeps a pale map off pale paper. */
.map-card__preview {
  position: relative;
  aspect-ratio: 4 / 3;
  margin: var(--card-mat) var(--card-mat) 0;
  overflow: hidden;
  border-radius: calc(var(--radius-l) - var(--card-mat));
  background: var(--color-raised);
}

.map-card__preview::after {
  content: "";
  position: absolute;
  inset: 0;
  border-radius: inherit;
  box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--color-shadow) 12%, transparent);
  pointer-events: none;
}

/* Clicks pass through the picture to the card's stretched link. */
.map-card__preview > * {
  pointer-events: none;
}

.map-card__preview img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* With JavaScript a thumbnail fades in once it has loaded (site.js marks it), so
   the grid fills softly instead of in hard jumps; without it, images just appear. */
.js .map-card__preview img {
  opacity: 0;
  transition: opacity 0.45s ease-out;
}

.js .map-card__preview img.is-loaded {
  opacity: 1;
}

@media (prefers-reduced-motion: reduce) {
  .js .map-card__preview img {
    transition: none;
  }
}

.preview-placeholder {
  position: relative;
  display: grid;
  place-items: center;
  align-content: center;
  gap: var(--space-2);
  width: 100%;
  height: 100%;
  overflow: hidden;
  background:
    radial-gradient(circle at 50% 45%, var(--color-summit), transparent 55%),
    var(--color-raised);
  color: var(--color-text-subtle);
  font-size: 0.8125rem;
  font-weight: 600;
}

/* A lone hill behind the icon: its minor lines in the ink, its index lines in the accent. */
.preview-placeholder::before,
.preview-placeholder::after {
  content: "";
  position: absolute;
  inset: -20%;
  pointer-events: none;
}

.preview-placeholder::before {
  background: var(--color-contour);
  opacity: calc(var(--contour-minor-hero) * 0.8);
  -webkit-mask: url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat;
  mask: url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat;
}

.preview-placeholder::after {
  background: var(--color-contour-index);
  opacity: calc(var(--contour-index-hero) * 0.75);
  -webkit-mask: url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat;
  mask: url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat;
}

.preview-placeholder > * {
  position: relative;
  z-index: 1;
}

.preview-placeholder .icon {
  width: 1.75rem;
  height: 1.75rem;
  color: var(--color-accent);
  stroke-width: 1.5;
}

/* Hovering a card reveals a soft hill of contour lines in its corner. */
.map-card__body {
  position: relative;
  isolation: isolate;
  display: flex;
  flex: 1;
  flex-direction: column;
  gap: var(--space-2);
  padding: var(--space-2) var(--space-3) var(--space-3);
}

/* The hill fills only the text area below the thumbnail: the layer covers the body
   exactly and the hill is placed inside it by its mask, so it never reaches the map. */
.map-card__body::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  background: var(--color-contour-index);
  opacity: 0;
  -webkit-mask: url("../patterns/summit.7d622108d3fb.svg") right -3.5rem bottom -5.5rem / 13rem no-repeat;
  mask: url("../patterns/summit.7d622108d3fb.svg") right -3.5rem bottom -5.5rem / 13rem no-repeat;
  transition: opacity 0.35s var(--ease);
  pointer-events: none;
}

.map-card:hover .map-card__body::before {
  opacity: 0.28;
}

/* Clamped text wraps plainly: Firefox balances or prettifies over every line, the
   hidden ones too, and then shows only a word or two per visible line. */
.map-card__title {
  display: -webkit-box;
  overflow: hidden;
  overflow-wrap: anywhere;
  font-size: 0.9rem;
  font-weight: 600;
  line-height: 1.3;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  line-clamp: 2;
  text-wrap: wrap;
}

.map-card__link {
  color: var(--color-text);
  text-decoration: none;
}

/* The whole card opens the map. The link sits in the body, which is positioned for
   its hill, so its hit area reaches up over the mat and the thumbnail from there:
   the preview is (card width - 2 mats) * 3/4 high, plus the mat above it. */
.map-card__link::after {
  content: "";
  position: absolute;
  inset: 0;
  top: calc(-1 * ((100cqw - 2 * var(--card-mat)) * 3 / 4 + var(--card-mat)));
}

.map-card__link:focus-visible {
  outline: none;
}

.map-card:hover .map-card__link {
  color: var(--color-text);
}

.map-card__description {
  display: -webkit-box;
  overflow: hidden;
  overflow-wrap: anywhere;
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  line-height: 1.45;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  line-clamp: 2;
  text-wrap: wrap;
}

/* Above the card's stretched link, so each chip can show its tooltip. */
.map-card__chips {
  position: relative;
  z-index: 1;
  flex-wrap: nowrap;
  gap: var(--space-1);
  margin-top: auto;
}

.map-card__chips .chip {
  min-height: 1.375rem;
  padding: 0 0.45rem;
  gap: 0.3rem;
  background: var(--color-canvas);
  font-size: 0.75rem;
}

.map-card__chips .chip .icon {
  width: 0.8125rem;
  height: 0.8125rem;
}

/* Centre digits on their cap height rather than the font's line box. */
.map-card__chips .chip > span:not(.tip) {
  line-height: 1;
  font-variant-numeric: lining-nums tabular-nums;
}

@supports (text-box: trim-both cap alphabetic) {
  .map-card__chips .chip > span:not(.tip) {
    text-box: trim-both cap alphabetic;
  }
}

/* --- Explore rows ---------------------------------------------------------- */

.row {
  container-type: inline-size;
  display: grid;
  gap: var(--space-4);
}

.row__head,
.section-head {
  display: flex;
  align-items: center;
  min-height: var(--row-head-height);
  gap: var(--space-3);
}

.row__head h2,
.section-head h2 {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0 var(--space-3);
  margin-right: auto;
}

.row__more {
  display: inline-flex;
  align-items: center;
  gap: var(--space-1);
  font-size: 0.875rem;
  font-weight: 550;
  text-decoration: none;
  white-space: nowrap;
}

.row__viewport {
  position: relative;
  min-width: 0;
}

.row__arrow {
  position: absolute;
  top: calc(50% - var(--space-3) / 2);
  display: grid;
  place-items: center;
  width: 2.75rem;
  height: 2.75rem;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: var(--color-raised);
  color: var(--color-text);
  box-shadow: var(--shadow-float);
  cursor: pointer;
  opacity: 0;
  transform: translateY(-50%);
  transition:
    opacity 0.15s var(--ease),
    background-color 0.15s var(--ease),
    transform 0.15s var(--ease);
}

.row__arrow[hidden] {
  display: none;
}

.row__arrow--previous {
  left: var(--space-2);
}

.row__arrow--next {
  right: var(--space-2);
}

.row__arrow .icon {
  width: 1.5rem;
  height: 1.5rem;
}

.row__arrow:hover {
  background: var(--color-hover);
}

.row__arrow--next {
  background: var(--color-accent);
  color: var(--color-on-accent);
}

.row__arrow--next:hover {
  background: var(--color-accent-hover);
}

.row__arrow:focus-visible,
.row__viewport:hover .row__arrow,
.row__viewport:focus-within .row__arrow {
  opacity: 1;
}

.row__arrow:active {
  transform: translateY(-50%) scale(0.94);
}

@media (hover: none), (pointer: coarse) {
  .row__arrow {
    display: none;
  }
}

@media (prefers-reduced-motion: reduce) {
  .row__arrow {
    transition: none;
  }
}

.row__track {
  --row-gap: var(--space-3);
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 62%;
  gap: var(--row-gap);
  margin: 0;
  padding: 0 0 var(--space-2);
  overflow-x: auto;
  overscroll-behavior-x: contain;
  scroll-snap-type: x mandatory;
  scrollbar-width: none;
  list-style: none;
}

.row__track::-webkit-scrollbar {
  display: none;
}

.row__track:focus {
  outline: none;
}

.row__track > li {
  scroll-snap-align: start;
}

/* Dense rows: two cards on phones' larger sizes, four from a typical laptop's
   content column, five and six on wide screens. */
@container (min-width: 30rem) {
  .row__track {
    grid-auto-columns: calc((100% - var(--row-gap)) / 2);
  }
}

@container (min-width: 38rem) {
  .row__track {
    grid-auto-columns: calc((100% - 2 * var(--row-gap)) / 3);
  }
}

@container (min-width: 46rem) {
  .row__track {
    grid-auto-columns: calc((100% - 3 * var(--row-gap)) / 4);
  }
}

@container (min-width: 58rem) {
  .row__track {
    grid-auto-columns: calc((100% - 4 * var(--row-gap)) / 5);
  }
}

@container (min-width: 70rem) {
  .row__track {
    grid-auto-columns: calc((100% - 5 * var(--row-gap)) / 6);
  }
}

.row__placeholder {
  display: grid;
  place-items: center;
  min-height: 14rem;
  border-radius: var(--radius-l);
  background: var(--color-surface);
}

/* --- Search results ------------------------------------------------------- */

.results {
  container-type: inline-size;
  display: grid;
  gap: var(--space-6);
}

.results__head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: var(--space-2) var(--space-4);
}

.results__count {
  color: var(--color-text-subtle);
  font-size: 0.875rem;
  font-variant-numeric: tabular-nums;
}

.results__grid {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-3);
  margin: 0;
  padding: 0;
  list-style: none;
}

@container (min-width: 30rem) {
  .results__grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

/* No four columns: a page of 30 cards fills its last row only with 2, 3 or 5. */
@container (min-width: 38rem) {
  .results__grid {
    grid-template-columns: repeat(3, minmax(0, 1fr));
  }
}

/* Five columns at most: wider screens get larger cards, not more of them. */
@container (min-width: 52rem) {
  .results__grid {
    grid-template-columns: repeat(5, minmax(0, 1fr));
  }
}

.active-filters {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-2);
}

.empty-state {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  display: grid;
  justify-items: start;
  gap: var(--space-3);
  padding: var(--space-8);
  padding-right: max(var(--space-8), 30%);
  border-radius: var(--radius-l);
  background: var(--color-surface);
}

/* Uncharted ground: a lone hill on the empty state's right. */
.empty-state::before,
.empty-state::after {
  content: "";
  position: absolute;
  top: 50%;
  right: -4rem;
  z-index: -1;
  width: 20rem;
  aspect-ratio: 1;
  translate: 0 -50%;
  pointer-events: none;
}

.empty-state::before {
  background: var(--color-contour);
  opacity: var(--contour-minor-hero);
  -webkit-mask: url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat;
  mask: url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat;
}

.empty-state::after {
  background: var(--color-contour-index);
  opacity: var(--contour-index-hero);
  -webkit-mask: url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat;
  mask: url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat;
}

/* Three fixed columns: the label keeps its place on the first and last page, where
   one arrow is missing and its column stays empty. */
.pagination {
  display: grid;
  grid-template-columns: 2.5rem auto 2.5rem;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
}

.pagination__previous {
  grid-column: 1;
}

.pagination__label {
  grid-column: 2;
}

.pagination__next {
  grid-column: 3;
}

/* --- Noticeboard ----------------------------------------------------------- */

.noticeboard {
  display: grid;
  gap: var(--space-4);
}

.reading-list {
  display: grid;
  gap: var(--space-1);
  margin: 0;
  padding: 0;
  list-style: none;
}

.reading-list a {
  display: block;
  padding: var(--space-1) 0;
  font-weight: 500;
}

.noticeboard-post {
  display: grid;
  gap: var(--space-3);
  padding: var(--space-4) var(--space-5) var(--space-5);
  border-radius: var(--radius-l);
  background: var(--color-surface-veil);
  font-size: 0.9rem;
}

.noticeboard-post--highlight {
  background: color-mix(in srgb, var(--color-surface) 55%, var(--color-earth-soft));
}

.noticeboard-post__head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-3);
}

.noticeboard-post__date {
  color: var(--color-text-subtle);
  font-size: 0.75rem;
}

.noticeboard-post h3 {
  font-size: 0.975rem;
}

.noticeboard-post p {
  color: var(--color-text-muted);
}

/* A line under the heading that belongs to it, closer than the post's gap. */
.noticeboard-post__subline {
  margin-top: calc(-1 * var(--space-2));
  font-size: 0.8125rem;
}

.noticeboard-post .noticeboard-post__subline {
  color: var(--color-text-subtle);
}

.roadmap {
  display: grid;
  gap: var(--space-2);
  margin: 0;
  padding: 0;
  list-style: none;
}

.roadmap li {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: var(--space-3);
  padding: var(--space-2) var(--space-3);
  border-radius: var(--radius-m);
  background: var(--color-card);
}

.status {
  display: inline-flex;
  align-items: center;
  min-height: 1.375rem;
  padding: 0 0.55rem;
  border-radius: var(--radius-pill);
  font-size: 0.75rem;
  font-weight: 600;
  white-space: nowrap;
}

.status--done {
  background: var(--color-success-bg);
  color: var(--color-success-ink);
}

.status--now {
  background: var(--color-accent-soft);
  color: var(--color-accent-soft-ink);
}

.status--next,
.status--later {
  background: var(--color-raised);
  color: var(--color-text-muted);
}

.survey-results {
  display: grid;
  gap: var(--space-3);
  margin: 0;
  padding: 0;
  list-style: none;
}

.survey-results li {
  display: grid;
  gap: var(--space-1);
}

.survey-results__label {
  display: flex;
  justify-content: space-between;
  gap: var(--space-2);
  font-size: 0.875rem;
}

.survey-results__label > span:first-child {
  display: inline-flex;
  align-items: center;
  gap: var(--space-1);
}

.survey-results__label .icon {
  width: 0.875rem;
  height: 0.875rem;
  color: var(--color-accent);
}

.survey-results__label .mono {
  color: var(--color-text-subtle);
  font-family: inherit;
  font-size: 0.8125rem;
  font-variant-numeric: tabular-nums;
}

/* The track carries the background, so the meter's fill can grow from zero by
   revealing it; a meter's own fill cannot be animated across browsers. */
.bar-track {
  display: block;
  height: 0.5rem;
  border-radius: 999px;
  background: var(--color-raised);
}

.bar {
  display: block;
  width: 100%;
  height: 100%;
  border: 0;
  border-radius: 999px;
  background: transparent;
  appearance: none;
  overflow: hidden;
  animation: bar-grow 0.9s var(--ease) both;
}

@keyframes bar-grow {
  from {
    clip-path: inset(0 100% 0 0);
  }

  to {
    clip-path: inset(0 0 0 0);
  }
}

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

.bar::-webkit-meter-bar {
  border: 0;
  border-radius: 999px;
  background: transparent;
}

.bar::-webkit-meter-optimum-value {
  border-radius: 999px;
  background: var(--color-accent);
}

.bar::-moz-meter-bar {
  border-radius: 999px;
  background: var(--color-accent);
}

/* --- Map details ----------------------------------------------------------- */

.map-page {
  display: grid;
  gap: var(--space-6);
}

.map-page__layout {
  display: grid;
  gap: var(--space-6);
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas:
    "map"
    "panel"
    "comments"
    "similar";
}

.map-frame {
  grid-area: map;
}

.map-page__panel {
  grid-area: panel;
}

.map-page__comments {
  grid-area: comments;
  min-width: 0;
}

.map-page__similar {
  grid-area: similar;
  min-width: 0;
}

.map-page__similar:empty {
  display: none;
}

@media (min-width: 64rem) {
  .map-page__layout {
    grid-template-columns: minmax(0, 1fr) 24rem;
    grid-template-rows: auto 1fr auto;
    grid-template-areas:
      "map panel"
      "comments panel"
      "similar similar";
    align-items: start;
  }
}

/* Wide screens list the similar maps in the brand's column beside the map, so the
   map starts with the masthead's search, as the explorer's maps do. */
@media (min-width: 80rem) {
  .map-page__layout {
    grid-template-columns: var(--explorer-start) minmax(0, 1fr) 24rem;
    grid-template-rows: auto 1fr;
    grid-template-areas:
      "similar map panel"
      "similar comments panel";
  }

  /* Beside the map the list speaks for itself: its heading is for screen readers
     only, and the first map starts level with the big one. */
  .map-page__similar .row {
    gap: 0;
  }

  .map-page__similar .row__head {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip-path: inset(50%);
    white-space: nowrap;
  }

  .map-page__similar .row__track {
    grid-auto-flow: row;
    grid-auto-columns: auto;
    overflow: visible;
    padding: 0;
  }

  .map-page__similar .row__arrow {
    display: none;
  }

  .map-page__similar .map-card__chips {
    display: none;
  }
}

@media (min-width: 90rem) {
  .map-page__layout {
    grid-template-columns: var(--explorer-start) minmax(0, 1fr) 27rem;
  }
}

/* Rounded by clip-path, not overflow: Chrome clips an overflowing embed layer by
   layer, so at the corners Google's map seams through its dark header. */
.map-frame {
  position: relative;
  clip-path: inset(0 round var(--radius-xl));
  border-radius: var(--radius-xl);
  background: var(--color-surface);
  aspect-ratio: 4 / 3;
}

@media (min-width: 64rem) {
  .map-frame {
    aspect-ratio: auto;
    height: calc(100vh - var(--masthead-height) - var(--space-12));
    min-height: 32rem;
    max-height: 56rem;
  }
}

.map-frame iframe {
  position: relative;
  display: block;
  width: 100%;
  height: 100%;
  border: 0;
  background: var(--color-raised);
}

/* While the provider's embed loads, the map's thumbnail stands in for it, heavily
   blurred (scaled up so the blur keeps clean edges), or the lone hill without one.
   The embed then fades in over it; without JavaScript it simply shows. */
.map-frame__preview {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
}

img.map-frame__preview {
  object-fit: cover;
  filter: blur(28px) saturate(1.15);
  transform: scale(1.15);
}

/* The logo's loader waits in the middle of the preview, only with JavaScript, which
   is what can tell when the embed has loaded. */
.map-frame__loader {
  display: none;
}

.js .map-frame__loader {
  position: absolute;
  top: 50%;
  left: 50%;
  display: grid;
  place-items: center;
  width: 4.5rem;
  height: 4.5rem;
  translate: -50% -50%;
  border-radius: 50%;
  background: var(--color-surface-veil);
  box-shadow: var(--shadow-card);
}

.map-frame__loader svg {
  width: 2.5rem;
  height: 2.5rem;
}

.js .map-frame iframe,
.js .map-frame__preview,
.js .map-frame__loader {
  transition: opacity 0.6s var(--ease);
}

.js .map-frame iframe {
  opacity: 0;
}

/* Loaded: the embed fades in as preview and loader fade out. */
.js .map-frame[data-embed-loaded] iframe {
  opacity: 1;
}

.js .map-frame[data-embed-loaded] .map-frame__preview,
.js .map-frame[data-embed-loaded] .map-frame__loader {
  visibility: hidden;
  opacity: 0;
  transition:
    opacity 0.6s var(--ease),
    visibility 0s 0.6s;
}

/* Arriving on a map, its frame, details and comments rise into place one after
   another, and the blurred preview settles. */
@media (prefers-reduced-motion: no-preference) {
  .map-frame,
  .map-page__panel,
  .map-page__comments {
    animation: map-page-enter 0.5s var(--ease) both;
  }

  .map-page__panel {
    animation-delay: 0.08s;
  }

  .map-page__comments {
    animation-delay: 0.16s;
  }

  img.map-frame__preview {
    animation: map-preview-settle 1.2s var(--ease) backwards;
  }
}

@keyframes map-page-enter {
  from {
    opacity: 0;
    transform: translateY(0.75rem);
  }
}

@keyframes map-preview-settle {
  from {
    opacity: 0;
    transform: scale(1.3);
  }
}

.detail-panel {
  display: grid;
  gap: var(--space-5);
  padding: var(--space-6);
  border-radius: var(--radius-xl);
  background: var(--color-surface);
}

.detail-panel__title {
  display: grid;
  gap: var(--space-2);
}

.detail-panel__title h1 {
  overflow-wrap: anywhere;
  font-size: clamp(1.5rem, 1.25rem + 1vw, 1.875rem);
}

/* Views and votes under the title: icon and number, the name is the tooltip. */
.stats,
.stats__group {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--space-4);
  margin: 0;
}

.stats {
  color: var(--color-text-subtle);
  font-size: 0.875rem;
  font-variant-numeric: tabular-nums;
}

.stats__link {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  color: inherit;
  text-decoration: none;
}

.stats__link:hover {
  color: var(--color-text);
}

.fact dd {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  margin: 0;
}

.fact .icon {
  flex: none;
  width: 0.875rem;
  height: 0.875rem;
}

/* The map's facts: one labelled line each. */
.facts {
  display: grid;
  margin: 0;
  padding: var(--space-1) var(--space-4);
  border-radius: var(--radius-l);
  background: var(--color-card);
}

.facts > div {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-4);
  padding: var(--space-3) 0;
}

.facts > div + div {
  border-top: 2px solid var(--color-surface);
}

.facts dt {
  flex: none;
  color: var(--color-text-subtle);
  font-size: 0.8125rem;
  font-weight: 600;
}

.facts dd {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  min-width: 0;
  margin: 0;
  overflow-wrap: anywhere;
  font-size: 0.875rem;
  text-align: right;
}

.facts dd .icon {
  flex: none;
  width: 1rem;
  height: 1rem;
}

.tabs {
  display: grid;
  gap: var(--space-4);
}

.tabs__list {
  display: inline-flex;
  gap: var(--space-1);
  width: fit-content;
  padding: var(--space-1);
  border-radius: var(--radius-pill);
  background: var(--color-card);
}

.tabs__tab {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  min-height: 2rem;
  padding: 0 var(--space-4);
  border: 0;
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--color-text-muted);
  font-size: 0.875rem;
  font-weight: 600;
  cursor: pointer;
}

.tabs__tab[aria-selected="true"] {
  background: var(--color-accent-soft);
  color: var(--color-accent-soft-ink);
}

.tabs__panel {
  display: grid;
  gap: var(--space-3);
}

.tabs__panel h2 {
  font-size: 0.875rem;
}

.tabs__tab .icon,
.tabs__panel h2 .icon {
  width: 0.875rem;
  height: 0.875rem;
}

.tabs__panel h2:has(.icon) {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
}

.author-links {
  display: grid;
  gap: var(--space-2);
}

.author-links h2 {
  font-size: 0.875rem;
}

.author-links ul {
  display: grid;
  gap: var(--space-1);
  margin: 0;
  padding: 0;
  list-style: none;
}

.author-links a {
  display: flex;
  align-items: baseline;
  gap: var(--space-2);
  min-width: 0;
  color: var(--color-text);
  font-size: 0.875rem;
  text-decoration: none;
}

.author-links a:hover span:first-of-type {
  text-decoration: underline;
}

.author-links .icon {
  flex: none;
  align-self: center;
  width: 0.875rem;
  height: 0.875rem;
  color: var(--color-text-subtle);
}

.author-links__target {
  overflow: hidden;
  color: var(--color-text-subtle);
  font-size: 0.8125rem;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.description {
  color: var(--color-text-muted);
  font-size: 0.9375rem;
  white-space: pre-line;
  overflow-wrap: anywhere;
}

.original-title {
  font-weight: 600;
}

.actions {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2);
}

.vote-group {
  display: inline-flex;
  gap: var(--space-2);
}

.section {
  display: grid;
  gap: var(--space-5);
}

.section__head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--space-4);
}

/* --- Comments -------------------------------------------------------------- */

.comments {
  display: grid;
  gap: var(--space-5);
  max-width: 52rem;
  margin-top: var(--space-4);
}

.comment-list {
  display: grid;
  gap: var(--space-3);
  margin: 0;
  padding: 0;
  list-style: none;
}

.comment {
  display: grid;
  gap: var(--space-2);
  padding: var(--space-4) var(--space-5);
  border-radius: var(--radius-l);
  background: var(--color-surface);
}

.comment__head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--space-1) var(--space-3);
}

.comment__author {
  font-weight: 600;
  font-size: 0.9375rem;
}

.comment__date {
  color: var(--color-text-subtle);
  font-size: 0.8125rem;
}

/* A comment's Markdown subset: paragraphs, lists, quotes, code and links. */
.comment__body {
  color: var(--color-text-muted);
  overflow-wrap: anywhere;
}

.comment__body > * + * {
  margin-top: 0.6em;
}

.comment__body ul,
.comment__body ol {
  padding-left: 1.4em;
}

.comment__body blockquote {
  margin-inline: 0;
  padding-left: var(--space-3);
  border-left: 3px solid var(--color-raised);
}

.comment__body code {
  padding: 0.1em 0.35em;
  border-radius: var(--radius-s);
  background: var(--color-raised);
  font-family: var(--font-mono);
  font-size: 0.875em;
}

.comment__body pre {
  overflow-x: auto;
  padding: var(--space-3);
  border-radius: var(--radius-m);
  background: var(--color-raised);
}

.comment__body pre code {
  padding: 0;
  background: none;
}

/* The "i" beside the heading opens how commenting works, over the comments. */
.comment-help {
  position: relative;
  align-self: center;
}

.comment-help > summary {
  list-style: none;
  color: var(--color-text-subtle);
}

.comment-help > summary::-webkit-details-marker {
  display: none;
}

.comment-help__panel {
  position: absolute;
  top: calc(100% + var(--space-1));
  right: 0;
  z-index: var(--z-tooltip);
  display: grid;
  gap: var(--space-2);
  width: min(22rem, calc(100vw - 2 * var(--space-4)));
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-m);
  background: var(--color-surface);
  box-shadow: var(--shadow-float);
  color: var(--color-text-muted);
  font-size: 0.875rem;
}

.comment-help__panel p {
  margin: 0;
}

.comment-help__panel ul {
  display: grid;
  gap: var(--space-1);
  margin: 0;
  padding-left: 1.2em;
}

.comment-help__panel code {
  padding: 0.1em 0.35em;
  border-radius: var(--radius-s);
  background: var(--color-raised);
  font-family: var(--font-mono);
  font-size: 0.875em;
}

/* Replies sit under the comment they answer, one level deep. */
.comment-thread {
  display: grid;
  gap: var(--space-2);
}

.comment-replies {
  display: grid;
  gap: var(--space-2);
  margin: 0 0 0 var(--space-4);
  padding: 0 0 0 var(--space-3);
  border-left: 2px solid var(--color-raised);
  list-style: none;
}

.comment-replies .comment {
  padding: var(--space-3) var(--space-4);
}

.comment--removed {
  margin: 0;
  color: var(--color-text-subtle);
  font-style: italic;
}

.comment__reply > summary {
  width: fit-content;
  color: var(--color-text-subtle);
  font-size: 0.8125rem;
  font-weight: 600;
  list-style: none;
  cursor: pointer;
}

.comment__reply > summary::-webkit-details-marker {
  display: none;
}

.comment__reply > summary:hover,
.comment__reply[open] > summary {
  color: var(--color-accent);
}

.comment-form {
  display: grid;
  gap: var(--space-3);
  padding: var(--space-4);
  border-radius: var(--radius-l);
  background: var(--color-surface);
}

.comment-form__name {
  max-width: 16rem;
}

.comment-form--reply {
  margin-top: var(--space-2);
  padding: 0;
}

/* A textarea with a round send button in its corner (comments, feedback). */

.compose {
  position: relative;
}

.compose .textarea {
  display: block;
  min-height: 5rem;
  padding-right: 3.75rem;
  resize: vertical;
}

.compose__send {
  position: absolute;
  right: var(--space-2);
  bottom: var(--space-2);
  border-radius: 50%;
}

.compose .loader {
  position: absolute;
  right: 3.5rem;
  bottom: 0.75rem;
}

/* --- Notices --------------------------------------------------------------- */

.notice {
  display: flex;
  align-items: flex-start;
  gap: var(--space-3);
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-m);
  background: var(--color-info-bg);
  color: var(--color-info-ink);
  font-size: 0.9rem;
}

.notice--success {
  background: var(--color-success-bg);
  color: var(--color-success-ink);
}

.notice--warning {
  background: var(--color-warning-bg);
  color: var(--color-warning-ink);
}

.notice--danger {
  background: var(--color-danger-bg);
  color: var(--color-danger-ink);
}

.notice .icon {
  margin-top: 0.15rem;
}

.messages {
  display: grid;
  gap: var(--space-2);
  margin-bottom: var(--space-6);
}

/* --- Popovers -------------------------------------------------------------- */

.popover {
  width: min(32rem, calc(100vw - 2rem));
  max-height: calc(100vh - 2rem);
  margin: auto;
  padding: 0;
  overflow: auto;
  border: 0;
  border-radius: var(--radius-xl);
  background: var(--color-surface);
  color: var(--color-text);
  box-shadow: var(--shadow-float);
}

.popover::backdrop {
  background: color-mix(in srgb, var(--color-shadow) 60%, transparent);
}

.popover__body {
  display: grid;
  gap: var(--space-5);
  padding: var(--space-6);
}

.popover__head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: var(--space-4);
}

.popover__head h2 {
  font-size: 1.25rem;
}

.popover__actions {
  display: flex;
  flex-wrap: wrap;
  justify-content: flex-end;
  gap: var(--space-2);
}

/* --- Loader ---------------------------------------------------------------- */

.loader {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  color: var(--color-text-muted);
  font-size: 0.8125rem;
}

.loader svg {
  width: 1.5rem;
  height: 1.5rem;
}

.htmx-indicator {
  opacity: 0;
  transition: opacity 0.2s var(--ease) 0.15s;
}

.htmx-request .htmx-indicator,
.htmx-request.htmx-indicator {
  opacity: 1;
}

/* --- Articles -------------------------------------------------------------- */

/* Long text reads on a sheet of paper laid over the landscape. */
/* One column as wide as the card: a wide table must not widen the text around it. */
.article {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--space-8);
  max-width: 50rem;
  margin: 0 auto;
  padding: clamp(var(--space-5), 4vw, var(--space-12));
  border-radius: var(--radius-xl);
  background: color-mix(in srgb, var(--color-card) 94%, transparent);
  box-shadow: var(--shadow-card);
}

.article__head {
  display: grid;
  gap: var(--space-3);
}

.article__head .lead {
  color: var(--color-text-muted);
  font-size: 1.125rem;
}

.prose {
  font-size: 1.0625rem;
  line-height: 1.7;
}

.prose > * + * {
  margin-top: 1.1em;
}

.prose h2 {
  margin-top: 2em;
  font-size: 1.375rem;
}

.prose h3 {
  margin-top: 1.6em;
  font-size: 1.125rem;
}

.prose ul,
.prose ol {
  padding-left: 1.4em;
}

.prose li + li {
  margin-top: 0.35em;
}

.prose code {
  padding: 0.1em 0.35em;
  border-radius: var(--radius-s);
  background: var(--color-raised);
  font-family: var(--font-mono);
  font-size: 0.875em;
}

.prose pre {
  overflow-x: auto;
  padding: var(--space-4);
  border-radius: var(--radius-m);
  background: var(--color-surface);
}

.prose pre code {
  padding: 0;
  background: none;
}

.prose blockquote {
  margin-inline: 0;
  padding: var(--space-3) var(--space-5);
  border-radius: var(--radius-m);
  background: var(--color-surface);
  color: var(--color-text-muted);
}

/* Tables keep to the text's width: columns share it, and long words wrap. */
.prose table {
  width: 100%;
  table-layout: fixed;
  border-collapse: collapse;
  font-size: 0.9375rem;
  overflow-wrap: break-word;
}

.prose th,
.prose td {
  padding: var(--space-2) var(--space-3);
  text-align: left;
}

.prose tr:nth-child(even) td {
  background: var(--color-surface);
}

/* On a phone, columns would split words: each row becomes a block instead, its
   first cell as the title over the others. */
@media (max-width: 40rem) {
  .prose table,
  .prose tbody,
  .prose tr,
  .prose td {
    display: block;
  }

  .prose thead {
    display: none;
  }

  .prose tr {
    padding: var(--space-3);
    border-radius: var(--radius-m);
  }

  .prose tr:nth-child(even),
  .prose tr:nth-child(even) td {
    background: var(--color-surface);
  }

  .prose td {
    padding: 0;
  }

  .prose td:first-child {
    font-weight: 600;
  }
}

/* Credit tables share their column widths, so the sections line up. */
.credits th:first-child {
  width: 42%;
}

.credits th:nth-child(2) {
  width: 30%;
}

/* Without a detail column the licence stays where the other tables have it. */
.credits--short th:first-child {
  width: 72%;
}

.credits--short th:nth-child(2) {
  width: auto;
}

.credits__author {
  display: block;
  color: var(--color-text-muted);
  font-size: 0.875rem;
}

.prose hr {
  height: 2px;
  border: 0;
  background: var(--color-raised);
}

/* --- Article contents ------------------------------------------------------- */

/* A long article lists its sections: beside the text where the page is wide enough,
   as a row of pills under the masthead where it is not. With JavaScript it shows
   once the title has scrolled away and marks the section in view (site.js). */
.contents__list {
  margin: 0;
  padding: 0;
  list-style: none;
}

.contents__link {
  display: block;
  color: var(--color-text-muted);
  text-decoration: none;
  transition: color 0.15s var(--ease), background-color 0.15s var(--ease);
}

.contents__link:hover {
  color: var(--color-text);
}

.contents__link[aria-current="true"] {
  color: var(--color-accent-soft-ink);
  background: var(--color-accent-soft);
}

.js .contents {
  transition: opacity 0.25s var(--ease), transform 0.25s var(--ease);
}

.js .contents:not(.is-shown) {
  opacity: 0;
  pointer-events: none;
}

@media (min-width: 84rem) {
  .article-layout--contents {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 50rem) minmax(0, 1fr);
    gap: var(--space-8);
    align-items: start;
  }

  .article-layout--contents .article {
    grid-column: 2;
    width: 100%;
  }

  .contents {
    grid-column: 1;
    grid-row: 1;
    justify-self: end;
    position: sticky;
    top: calc(var(--masthead-height) + var(--space-8));
    width: min(15rem, 100%);
    max-height: calc(100vh - var(--masthead-height) - var(--space-16));
    overflow-y: auto;
    padding: var(--space-4);
    border-radius: var(--radius-l);
    background: color-mix(in srgb, var(--color-card) 88%, transparent);
    box-shadow: var(--shadow-card);
  }

  .js .contents:not(.is-shown) {
    transform: translateX(calc(-1 * var(--space-3)));
  }

  .contents__title {
    margin: 0 0 var(--space-3) var(--space-3);
  }

  .contents__list {
    display: grid;
    gap: 2px;
  }

  .contents__link {
    padding: var(--space-2) var(--space-3);
    border-radius: var(--radius-m);
    font-size: 0.9rem;
    line-height: 1.35;
  }
}

@media (max-width: 83.99rem) {
  .contents {
    position: sticky;
    top: var(--masthead-height);
    z-index: 30;
    margin: calc(-1 * var(--space-6)) calc(-1 * var(--gutter)) var(--space-4);
    background: color-mix(in srgb, var(--color-surface) 96%, transparent);
    box-shadow: 0 6px 12px -10px color-mix(in srgb, var(--color-shadow) 40%, transparent);
  }

  .js .contents:not(.is-shown) {
    transform: translateY(calc(-1 * var(--space-2)));
  }

  .contents__title {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip-path: inset(50%);
  }

  .contents__list {
    display: flex;
    gap: var(--space-2);
    overflow-x: auto;
    padding: var(--space-2) var(--gutter);
    scrollbar-width: none;
  }

  .contents__link {
    padding: var(--space-1) var(--space-3);
    border-radius: var(--radius-pill);
    background: var(--color-raised);
    font-size: 0.8125rem;
    white-space: nowrap;
  }

  /* Headings land below the row of pills as well as the masthead. */
  html:has(.article-layout--contents) {
    scroll-padding-top: calc(var(--masthead-height) + 3.5rem);
  }
}

@media (prefers-reduced-motion: reduce) {
  .js .contents,
  .contents__link {
    transition: none;
  }

  .js .contents:not(.is-shown) {
    transform: none;
  }
}

/* --- Figures ---------------------------------------------------------------- */

/* A figure of the statistics article (curation/statistics.py): a panel of its own
   in the text, a title and note over the chart, its numbers folded away below.
   Charts are inline SVG coloured here from the chart tokens; site.js shows the
   `data-tip` of the mark under the pointer. */
.figure {
  display: grid;
  gap: var(--space-4);
  margin: 2em 0 0;
  padding: clamp(var(--space-4), 3vw, var(--space-6));
  border-radius: var(--radius-l);
  background: var(--color-raised);
  line-height: 1.5;
}

/* Lists in a figure are charts, not prose: no indent, no gaps of their own. */
.prose .figure :is(ul, ol) {
  padding-left: 0;
}

.prose .figure li + li {
  margin-top: 0;
}

.prose .figure .ranking {
  padding-left: 1.6em;
}

.figure__head {
  display: grid;
  gap: var(--space-1);
}

.figure__title {
  font-family: var(--font-display);
  font-size: 1.0625rem;
  font-weight: 700;
  letter-spacing: -0.01em;
}

.figure__note {
  color: var(--color-text-muted);
  font-size: 0.9rem;
}

.figure__legend {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-4);
  margin: 0;
  padding: 0;
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  list-style: none;
}

.figure__legend li,
.split__values > span {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
}

.figure__key {
  width: 0.75rem;
  height: 0.75rem;
  border-radius: 3px;
  flex: none;
}

.figure__key--1,
.chart-mark--1,
.bars__bar--1 {
  background: var(--color-series-1);
  fill: var(--color-series-1);
}

.figure__key--2,
.chart-mark--2,
.bars__bar--2 {
  background: var(--color-series-2);
  fill: var(--color-series-2);
}

.figure__key--3,
.chart-mark--3 {
  background: var(--color-series-3);
  fill: var(--color-series-3);
}

.figure__table summary {
  width: fit-content;
  color: var(--color-accent);
  font-size: 0.875rem;
  font-weight: 600;
  cursor: pointer;
}

.figure__table table {
  margin-top: var(--space-3);
  font-size: 0.875rem;
  font-variant-numeric: tabular-nums;
}

.figure__table tr:nth-child(even) td {
  background: var(--color-card);
}

.chart-grid,
.chart-baseline {
  stroke: var(--color-chart-grid);
  stroke-width: 1px;
  vector-effect: non-scaling-stroke;
}

.chart-baseline {
  stroke: var(--color-text-subtle);
  stroke-opacity: 0.5;
}

.chart-hit {
  fill: transparent;
}

.chart-hit:hover {
  fill: color-mix(in srgb, var(--color-text) 6%, transparent);
}

/* The tooltip of the mark under the pointer: one for the page, placed by site.js. */
.chart-tip {
  white-space: normal;
  max-width: min(22rem, calc(100vw - 2 * var(--space-2)));
  font-size: 0.8125rem;
}

.chart-tip.is-shown {
  opacity: 1;
}

/* Tiles: the numbers that open the article, large and proportional. */
.tiles {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--space-3);
  margin: 0;
  padding: 0;
  list-style: none;
}

.tile {
  display: grid;
  align-content: start;
  gap: var(--space-1);
  padding: clamp(var(--space-3), 2vw, var(--space-4));
  border-radius: var(--radius-m);
  background: var(--color-card);
}

@media (max-width: 40rem) {
  .tiles {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

.tile__value {
  font-family: var(--font-display);
  font-size: clamp(1.25rem, 1rem + 1vw, 2rem);
  font-weight: 700;
  letter-spacing: -0.02em;
  line-height: 1.15;
}

.tile__label {
  font-weight: 600;
}

.tile__note {
  color: var(--color-text-muted);
  font-size: 0.8125rem;
}

/* Bars: one ranked row each, its label, its bar and its value. */
.bars {
  display: grid;
  gap: var(--space-2);
  margin: 0;
  padding: 0;
  list-style: none;
}

.bars__row {
  display: grid;
  grid-template-columns: minmax(0, 15rem) minmax(4rem, 1fr) minmax(3.5rem, auto);
  align-items: center;
  gap: var(--space-3);
  font-size: 0.9375rem;
}

.bars__label {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.bars__label a {
  overflow: hidden;
  text-overflow: ellipsis;
}

.bars__label:has(.bars__note) {
  flex-wrap: wrap;
  row-gap: 0;
}

.bars__note {
  flex-basis: 100%;
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  line-height: 1.35;
  white-space: normal;
}

.bars__label:has(.chip__flag) .bars__note {
  padding-left: calc(18px + var(--space-2));
}

.bars__track {
  display: block;
  width: 100%;
  height: 12px;
}

.bars__value {
  font-variant-numeric: tabular-nums;
  text-align: right;
  font-weight: 600;
}

@media (max-width: 40rem) {
  .bars__row {
    grid-template-columns: minmax(0, 1fr) auto;
    gap: var(--space-1) var(--space-3);
  }

  .bars__track {
    grid-column: 1 / -1;
    grid-row: 2;
  }
}

/* Columns: equal bands, their labels underneath as text that stays legible. */
.columns__plot {
  position: relative;
  padding-top: var(--space-5);
}

.columns__top {
  position: absolute;
  top: 0;
  left: 0;
  color: var(--color-text-subtle);
  font-size: 0.75rem;
  font-variant-numeric: tabular-nums;
}

.columns__svg {
  display: block;
  width: 100%;
  height: auto;
  overflow: visible;
}

.columns__labels {
  display: grid;
  grid-auto-columns: minmax(0, 1fr);
  grid-auto-flow: column;
  margin: var(--space-2) 0 0;
  padding: 0;
  color: var(--color-text-subtle);
  font-size: 0.75rem;
  font-variant-numeric: tabular-nums;
  list-style: none;
  text-align: center;
}

@media (max-width: 40rem) {
  .columns__labels {
    font-size: 0.625rem;
  }
}

/* A split: one bar divided between the series, the shares written beside it. */
.split {
  display: grid;
  gap: var(--space-4);
}

.split__row {
  display: grid;
  grid-template-columns: minmax(0, 9rem) minmax(0, 1fr);
  align-items: center;
  gap: var(--space-1) var(--space-4);
  font-size: 0.9375rem;
}

.split__bar {
  display: block;
  width: 100%;
  height: 16px;
  border-radius: 4px;
}

.split__segment {
  stroke: var(--color-raised);
  stroke-width: 2px;
}

.split__values {
  grid-column: 2;
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-1) var(--space-4);
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  font-variant-numeric: tabular-nums;
}

@media (max-width: 40rem) {
  .split__row {
    grid-template-columns: minmax(0, 1fr);
  }

  .split__values {
    grid-column: 1;
  }
}

/* The world: countries on the magnitude scale, borders as gaps of the panel. */
.world {
  display: grid;
  gap: var(--space-3);
}

.world__svg {
  display: block;
  width: 100%;
  height: auto;
}

.world__land {
  fill: var(--color-chart-empty);
  fill-rule: evenodd;
  stroke: var(--color-raised);
  stroke-width: 0.6px;
  stroke-linejoin: round;
}

.world__land:hover {
  stroke: var(--color-text);
  stroke-width: 1.2px;
}

.world__land--1,
.world__key--1 {
  fill: var(--color-scale-1);
  background: var(--color-scale-1);
}

.world__land--2,
.world__key--2 {
  fill: var(--color-scale-2);
  background: var(--color-scale-2);
}

.world__land--3,
.world__key--3 {
  fill: var(--color-scale-3);
  background: var(--color-scale-3);
}

.world__land--4,
.world__key--4 {
  fill: var(--color-scale-4);
  background: var(--color-scale-4);
}

.world__land--5,
.world__key--5 {
  fill: var(--color-scale-5);
  background: var(--color-scale-5);
}

.world__key--0 {
  background: var(--color-chart-empty);
}

.world__legend {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-1) var(--space-4);
  margin: 0;
  padding: 0;
  color: var(--color-text-muted);
  font-size: 0.8125rem;
  list-style: none;
}

.world__legend li {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
}

.world__key {
  width: 0.75rem;
  height: 0.75rem;
  border-radius: 3px;
}

/* The landscape of topics, drawn like the brand's: minor lines in blue-grey ink,
   every fifth an index line in the accent; each topic a summit with its name. */
.landscape {
  display: block;
  width: 100%;
  height: auto;
  border-radius: var(--radius-m);
  background: var(--color-card);
}

.landscape__minor,
.landscape__index {
  fill: none;
  stroke-linecap: round;
  stroke-linejoin: round;
  vector-effect: non-scaling-stroke;
}

.landscape__minor {
  stroke: var(--color-contour);
  stroke-width: 1px;
  stroke-opacity: 0.35;
}

.landscape__index {
  stroke: var(--color-contour-index);
  stroke-width: 1.6px;
  stroke-opacity: 0.6;
}

.landscape__hit {
  fill: transparent;
}

.landscape__dot {
  fill: var(--color-earth);
  stroke: var(--color-card);
  stroke-width: 2px;
  vector-effect: non-scaling-stroke;
}

.landscape__summit text {
  display: none;
  fill: var(--color-text);
  font-family: var(--font-sans);
  font-size: 17px;
  font-weight: 600;
  paint-order: stroke;
  stroke: var(--color-card);
  stroke-width: 5px;
  stroke-linejoin: round;
}

.landscape__summit--labelled text,
.landscape__summit:hover text,
.landscape__summit:focus-visible text {
  display: inline;
}

.landscape__summit:hover .landscape__dot {
  fill: var(--color-accent);
}

@media (max-width: 40rem) {
  .landscape__summit text {
    font-size: 34px;
    stroke-width: 9px;
  }

  .landscape__summit--labelled:not(.landscape__summit--major) text {
    display: none;
  }
}

/* A ranking of maps, each linked to its page. */
.ranking {
  display: grid;
  gap: var(--space-2);
  margin: 0;
  padding-left: 1.6em;
  font-size: 0.9375rem;
}

.ranking__item::marker {
  color: var(--color-text-subtle);
  font-variant-numeric: tabular-nums;
}

.ranking__title {
  font-weight: 600;
}

.ranking__meta {
  display: block;
  color: var(--color-text-muted);
  font-size: 0.8125rem;
}

/* --- Footer ---------------------------------------------------------------- */

/* The footer is nearly solid: the landscape shows through only as a trace. */
.site-footer {
  background: color-mix(in srgb, var(--color-surface) 96%, transparent);
}

.site-footer__inner {
  display: grid;
  justify-items: center;
  gap: var(--space-8);
  max-width: var(--page-width);
  margin: 0 auto;
  padding: var(--space-10) var(--gutter) var(--space-8);
  text-align: center;
}

.site-footer__about {
  display: grid;
  justify-items: center;
  align-content: start;
  gap: var(--space-3);
  max-width: 26rem;
  color: var(--color-text-muted);
  font-size: 0.9rem;
}

.site-footer ul {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: var(--space-2) var(--space-5);
  margin: 0;
  padding: 0;
  list-style: none;
  font-size: 0.9rem;
}

.site-footer a {
  color: var(--color-text-muted);
  text-decoration: none;
}

.site-footer a:hover {
  color: var(--color-text);
  text-decoration: underline;
}

.site-footer .brand:hover {
  text-decoration: none;
}

/* --- Error pages ----------------------------------------------------------- */

/* Lost, but on the map: the logo stands on a summit, rings of contour lines around it. */
.error-page {
  position: relative;
  isolation: isolate;
  display: grid;
  justify-items: center;
  gap: var(--space-4);
  max-width: 34rem;
  margin: var(--space-12) auto;
  padding: var(--space-12) var(--gutter) 0;
  text-align: center;
}

.error-page::before,
.error-page::after {
  content: "";
  position: absolute;
  top: calc(var(--space-12) + 2rem);
  left: 50%;
  z-index: -1;
  width: min(32rem, 115vw);
  aspect-ratio: 1;
  translate: -50% -50%;
  pointer-events: none;
}

.error-page::before {
  background: var(--color-contour);
  opacity: var(--contour-minor-hero);
  -webkit-mask:
    url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat,
    radial-gradient(closest-side, #000 55%, transparent);
  -webkit-mask-composite: source-in;
  mask:
    url("../patterns/summit.7d622108d3fb.svg") center / contain no-repeat,
    radial-gradient(closest-side, #000 55%, transparent);
  mask-composite: intersect;
}

.error-page::after {
  background: var(--color-contour-index);
  opacity: var(--contour-index-hero);
  -webkit-mask:
    url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat,
    radial-gradient(closest-side, #000 55%, transparent);
  -webkit-mask-composite: source-in;
  mask:
    url("../patterns/summit-index.3a1460aa3eb5.svg") center / contain no-repeat,
    radial-gradient(closest-side, #000 55%, transparent);
  mask-composite: intersect;
}

.error-page img {
  width: 4rem;
  height: 4rem;
  margin-bottom: var(--space-8);
}

.error-page h1 {
  margin-top: var(--space-4);
}

.error-page p {
  color: var(--color-text-muted);
}

/* --- Motion ---------------------------------------------------------------- */

@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    scroll-behavior: auto !important;
    transition-duration: 0.01ms !important;
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
  }
}
