/* ==========================================================================
   Camp portal stylesheet.

   screen.css is loaded first and supplies the BRAND: the sky, the panel, the
   fonts, the tokens, links, buttons and inputs. This file supplies the
   portal's own layout on top of it, and the student pages deliberately do
   NOT mirror the quiz portal's — see base.html for why. The shared part is
   what a student recognises (the emblem, the starfield, the type); the
   layout is this product's, built for a school student on a phone choosing
   between eight Saturdays.

   Tokens are screen.css's, with ONE deliberate exception: the accent, three
   lines below. Do not add a second — beyond that one difference, a colour
   that is not already a token is how two portals stop looking like one body.
   ========================================================================== */

/* --------------------------------------------------------------------------
   The one colour that differs
   --------------------------------------------------------------------------
   Same sky, same emblem, same fonts — so the difference that says "this is
   the camp portal, not the quiz" has to be carried by ONE thing, and an
   accent is the thing a reader registers without being told. Gold is the
   quiz. Camp is lime.

   Three lines is the whole change: screen.css derives every gold — the named
   tokens and every rgba() tint of them — from these triples. Nothing below
   restates a colour, and nothing here may either.

   Lime was chosen with one cost accepted knowingly: GREEN ALREADY MEANS
   SOMETHING here. It is `--correct` on a quiz answer, and it was the
   "confirmed" allotment pill. The pill is what gave way: the statuses
   separate by FILL and BORDER STYLE, never by a second green.

   Contrast, which is why these exact values: the accent is mostly TEXT on
   dark panels, and it has to clear AA in the two worst places — 10.4:1 on
   --panel-solid and 7.2:1 on the --button-bg fill. Check both if this is
   ever re-tinted.

   THE TWO FILES SHIP TOGETHER. This override feeds tokens that only the
   current screen.css defines; a cache holding a pre-refactor screen.css
   alongside a fresh camp.css renders the camp portal in the quiz's GOLD and
   reports no error at all. Collect and hard-refresh both. */
:root {
  --accent-rgb: 190, 227, 106;        /* #BEE36A */
  --accent-soft-rgb: 214, 240, 160;   /* #D6F0A0 — hover text */
  --accent-deep-rgb: 150, 190, 60;    /* #96BE3C — the gradient's deep end */

  /* Surfaces of this portal's own. One card surface, one raised one; the
     quiz's translucent --panel stays the outer panel. */
  --camp-card: #15202e;
  --camp-card-raised: #1b2838;
  --camp-ink-soft: #c3d0de;   /* body copy inside cards — brighter than --ink-dim,
                                 which at 15px on the card surface was the
                                 "unreadable" the redesign was asked for */
}

/* --------------------------------------------------------------------------
   Corrections to quiz-portal rules
   -------------------------------------------------------------------------- */

/* screen.css paints EVERY <form> as a card — right for a registration page,
   absurd around the header's single sign-out button or a row of checkboxes
   inside a table. */
.plain-form,
td form {
  display: inline;
  background: none;
  border: none;
  border-radius: 0;
  box-shadow: none;
  margin: 0;
  padding: 0;
}

/* Headings are page labels in the UI font, left-aligned. screen.css sizes h1
   in the brand face at up to 2.9rem, which on a phone is a third of the
   screen before a word of content. */
h1 {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 1.55rem;
  letter-spacing: -0.015em;
  line-height: 1.2;
  color: var(--ink);
  text-align: left;
  margin: 4px 0 10px;
}
h2 {
  font-family: var(--font-display);
  font-size: 1.15rem;
  text-align: left;
  margin: 0 0 6px;
}

/* Body copy: a little larger and brighter than the quiz portal's, and never
   dimmed inside a card. The quiz page is read once at a desk; these are read
   on a phone in a corridor. */
.camp-main { font-size: 1.04rem; line-height: 1.6; }
.camp-main p { margin: 0 0 10px; text-align: left; hyphens: manual; -webkit-hyphens: manual; }
.camp-main p:last-child { margin-bottom: 0; }
.muted { color: var(--ink-dim); }
.lead { font-size: 1.12rem; color: var(--ink); }
.lead strong { color: var(--gold); }

/* Organiser pages are data: dashboards run to hundreds of rows. */
.admin-page h1 { font-size: 1.5rem; }
.admin-page td,
.admin-page th { padding: 6px 10px; line-height: 1.35; }

/* The organiser tables are genuinely wide (eleven columns on the dashboard).
   Rather than shrink the type until it is unreadable, let the table scroll
   inside its own box — the page itself must never scroll sideways. */
.table-scroll {
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
  margin: 1.2rem 0;
}
/* min-content, and overflow-wrap back to normal, or the table obeys
   screen.css's max-width:100% and squeezes to fit instead — which with
   `overflow-wrap: break-word` on td meant the eleven-column dashboard broke
   "Outstation" down the page one letter per line. */
.table-scroll table { margin: 0; min-width: max-content; }
.table-scroll td,
.table-scroll th {
  overflow-wrap: normal;
  hyphens: none;
  -webkit-hyphens: none;
}

/* --------------------------------------------------------------------------
   The shell: one header row, the panel, a footer
   -------------------------------------------------------------------------- */
.camp-wrap { max-width: 720px; }

.camp-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 18px 4px 14px;
}
.camp-brand {
  display: flex;
  align-items: center;
  gap: 12px;
  flex: 1 1 auto;
  min-width: 0;
  color: var(--ink);
}
.camp-brand:hover { color: var(--ink); }
/* The emblem, small, with design.md's white halo — the same art as the quiz
   portal's header so the organisation is recognised, at a size that leaves
   the page to the page. */
.camp-emblem {
  height: 46px;
  width: auto;
  flex: 0 0 auto;
  filter:
    drop-shadow(0 0 2px rgba(255, 255, 255, 0.9))
    drop-shadow(0 0 6px rgba(255, 255, 255, 0.2))
    drop-shadow(2px 3px 5px rgba(0, 0, 0, 0.5));
}
.camp-wordmark {
  display: flex;
  flex-direction: column;
  line-height: 1.1;
  min-width: 0;
}
.camp-org {
  font-family: var(--font-display);
  font-size: .78rem;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--ink-dim);
}
.camp-title {
  font-family: var(--font-brand);
  font-size: 1.45rem;
  color: var(--gold);
  white-space: nowrap;
  text-shadow: 0 2px 8px rgba(0, 0, 0, 0.5);
}
.camp-year { color: var(--ink); }

.camp-nav {
  display: flex;
  align-items: center;
  gap: 8px;
  flex: 0 0 auto;
}
/* The rules: a ghost button, accent on dark (design.md §2.2), present on
   every signed-in page. `is-current` on the rules page itself. */
.rules-link {
  display: inline-flex;
  align-items: center;
  font-family: var(--font-display);
  font-size: .9rem;
  font-weight: 600;
  min-height: 36px;
  padding: 6px 14px;
  border: 1px solid rgba(var(--accent-rgb), 0.5);
  border-radius: var(--button-radius);
  color: var(--gold);
  background: rgba(var(--accent-rgb), 0.06);
  transition: background .2s ease, border-color .2s ease;
}
.rules-link:hover { background: rgba(var(--accent-rgb), 0.14); border-color: var(--gold); color: var(--gold-soft); }
.rules-link.is-current { background: transparent; border-style: dashed; cursor: default; }
/* Sign out reads as a link, not as one of the call-to-action buttons
   screen.css makes every <button>. */
.camp-signout {
  font-family: var(--font-display);
  font-size: .9rem;
  font-weight: 500;
  min-height: 36px;
  padding: 6px 10px;
  background: transparent;
  border: 1px solid transparent;
  border-radius: var(--button-radius);
  color: var(--ink-dim);
  box-shadow: none;
}
.camp-signout:hover {
  background: rgba(255, 255, 255, 0.05);
  border-color: var(--border);
  color: var(--ink);
  box-shadow: none;
  transform: none;
}

.camp-main { padding: 20px 22px 22px; }

/* Who is signed in: one small line at the top of the panel. */
.who {
  font-size: .9rem;
  color: var(--ink-dim);
  margin: 0 0 14px;
  padding-bottom: 10px;
  border-bottom: 1px solid var(--border);
}
.who b { color: var(--ink); font-weight: 600; }
.who-kind { margin-left: 6px; }

/* A saved/error message from the view, above the page's content. */
.flash {
  background: rgba(var(--accent-rgb), 0.10);
  border: 1px solid rgba(var(--accent-rgb), 0.35);
  border-radius: var(--border-radius-medium);
  padding: 10px 14px;
  margin: 0 0 14px;
  color: var(--ink);
}

#footer.camp-foot p {   /* the id beats screen.css's #footer p */
  text-align: center;
  color: var(--ink-dim);
  font-size: .8rem;
  letter-spacing: .04em;
  text-transform: none;
  margin: 18px 0 10px;
}
#footer.camp-foot a { color: var(--ink-dim); text-decoration: underline; text-underline-offset: 3px; }
#footer.camp-foot a:hover { color: var(--gold-soft); }

/* --------------------------------------------------------------------------
   Cards and sections
   -------------------------------------------------------------------------- */
.card {
  background: var(--camp-card);
  border: 1px solid var(--border);
  border-radius: var(--border-radius-large);
  padding: 16px 18px;
  margin: 0 0 14px;
  color: var(--camp-ink-soft);
  text-align: left;
}
.card strong, .card b { color: var(--ink); }
.card-title { color: var(--ink); font-weight: 700; margin-bottom: 8px; }
/* The card that asks for something: a rule down its left in the accent. */
.card-do { border-left: 4px solid var(--gold); }

/* The allotment: the one statement on the portal that matters, so it gets
   the most room. The status pill sits above the heading; the dates are the
   biggest thing on the page. */
.hero {
  background: linear-gradient(160deg, var(--camp-card-raised), var(--camp-card));
  border: 1px solid rgba(var(--accent-rgb), 0.45);
  border-radius: var(--border-radius-large);
  padding: 18px 20px 16px;
  margin: 0 0 14px;
  color: var(--camp-ink-soft);
  box-shadow: 0 0 28px rgba(var(--accent-rgb), 0.10);
}
.hero h1 { margin: 10px 0 6px; }
.hero-dates {
  font-family: var(--font-display);
  font-size: 1.35rem;
  font-weight: 700;
  color: var(--gold);
  line-height: 1.25;
  margin: 0 0 2px;
}
.hero-sub { color: var(--ink-dim); font-size: .95rem; margin: 0 0 12px; }
.hero a { color: var(--gold); text-decoration: underline; text-underline-offset: 3px; }
.hero-waitlisted { border-color: var(--border); box-shadow: none; }
.hero-declined { border-color: rgba(255, 123, 114, 0.4); box-shadow: none; }

/* "What a camp is" and "The season": plain sections under a small label. */
.about, .season { margin: 22px 0 0; color: var(--camp-ink-soft); }
.section-title {
  font-family: var(--font-display);
  font-size: .8rem;
  font-weight: 600;
  letter-spacing: .16em;
  text-transform: uppercase;
  color: var(--gold);
  margin: 0 0 8px;
}

/* Error box under a heading or a field. */
.error {
  background: var(--camp-card);
  border: 1px solid rgba(255, 123, 114, 0.45);
  border-left: 4px solid var(--text-error);
  border-radius: var(--border-radius-medium);
  padding: 10px 14px;
  margin: 0 0 12px;
  color: var(--ink);
  text-align: left;
}
/* Older organiser pages still use .note; keep it as a plain card. */
.note {
  background: var(--camp-card);
  border: 1px solid var(--border);
  border-radius: var(--border-radius-large);
  padding: 12px 16px;
  margin: 0 0 12px;
  text-align: left;
}

/* The one date that must not be missed. Its own line, accent-tinted. */
.deadline {
  display: inline-block;
  margin: 8px 0 0;
  padding: 7px 12px;
  border: 1px dashed rgba(var(--accent-rgb), 0.5);
  border-radius: var(--border-radius-medium);
  color: var(--ink);
  font-size: .95rem;
}
.deadline strong { color: var(--gold); white-space: nowrap; }

/* The Rules and Regulations. A numbered list read once, end to end, so it
   wants reading measure and room between items. */
.rules {
  margin: 8px 0 0;
  padding-left: 1.5rem;
  max-width: 68ch;
}
.rules li { margin: 0 0 16px; padding-left: 4px; color: var(--ink); line-height: 1.65; }
.rules li::marker { color: var(--gold); font-weight: 600; }

/* --------------------------------------------------------------------------
   Buttons
   --------------------------------------------------------------------------
   screen.css gives .link and <button> the quiz's primary treatment. Two
   refinements here, both design.md §2.2: the primary gets its halo, and a
   ghost exists for the second action on a page. */
.actions {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  margin: 14px 0 0;
}
.button-primary {
  border-width: 1.5px;
  border-color: var(--gold);
  box-shadow: 0 0 22px rgba(var(--accent-rgb), 0.18), inset 0 1px 0 rgba(var(--accent-rgb), 0.12);
}
.button-primary:hover { box-shadow: 0 0 32px rgba(var(--accent-rgb), 0.26), inset 0 1px 0 rgba(var(--accent-rgb), 0.12); }
.button-ghost {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-family: var(--font-display);
  font-size: 1rem;
  font-weight: 600;
  min-height: 42px;
  padding: 10px 20px;
  border: 1px solid rgba(var(--accent-rgb), 0.5);
  border-radius: var(--button-radius);
  color: var(--gold);
  background: transparent;
  transition: background .2s ease, border-color .2s ease;
}
.button-ghost:hover { background: rgba(var(--accent-rgb), 0.08); border-color: var(--gold); color: var(--gold-soft); }

/* A secondary submit on the organiser pages: "Remove selected" must not read
   at the emphasis of "Allot selected". */
.btn-quiet {
  background: transparent;
  color: var(--ink-dim);
  border-color: var(--border);
  font-weight: 600;
}
.btn-quiet:hover {
  background: rgba(255, 123, 114, 0.10);
  border-color: rgba(255, 123, 114, 0.5);
  color: var(--text-error);
}

/* The row of secondary links at the foot of a page. */
.linkbar {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  align-items: center;
  margin: 22px 0 0;
  padding-top: 14px;
  border-top: 1px solid var(--border);
}
/* Navigation / action chips: compact, panel-coloured, accent only on hover. */
.chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-family: var(--font-display);
  font-size: .86rem;
  font-weight: 500;
  min-height: 0;
  padding: 7px 12px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--camp-card);
  color: var(--ink);
  box-shadow: none;
}
.chip:hover {
  background: rgba(var(--accent-rgb), 0.10);
  border-color: var(--button-border-hover);
  color: var(--gold-soft);
  transform: none;
  box-shadow: none;
}
.chip-quiet { background: transparent; color: var(--ink-dim); font-size: .84rem; padding: 6px 10px; }

/* --------------------------------------------------------------------------
   The ranking: weekend tiles
   --------------------------------------------------------------------------
   One tile per weekend. The day number is the biggest thing on it because
   it is the only thing that differs between the eight; the month and the
   small print are under it. A picked tile wears its rank in the corner —
   the whole form is about order, and the first version (five identical
   dropdowns) was filled in wrongly because nothing showed which outranked
   which. */
.picker {
  background: none;
  border: none;
  border-radius: 0;
  margin: 16px 0 0;
  padding: 0;
}
.weekends {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(6.4rem, 1fr));
  gap: 10px;
  margin: 0 0 10px;
}
.wk {
  position: relative;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: flex-start;
  min-height: 0;
  padding: 14px 6px 12px;
  background: var(--camp-card);
  border: 1.5px solid var(--border);
  border-radius: var(--border-radius-medium);
  color: var(--ink);
  font-family: var(--font-display);
  line-height: 1.1;
  box-shadow: none;
  transition: border-color .15s ease, background .15s ease, opacity .15s ease, transform .1s ease;
  -webkit-tap-highlight-color: transparent;
}
.wk:hover { background: var(--camp-card-raised); border-color: rgba(var(--accent-rgb), 0.5); color: var(--ink); transform: none; box-shadow: none; }
.wk:active { transform: scale(.97); }
.wk:focus-visible { outline: 2px solid var(--gold); outline-offset: 2px; }
.wk-day { font-size: 2.1rem; font-weight: 700; letter-spacing: -0.02em; }
.wk-month { font-size: .82rem; font-weight: 600; letter-spacing: .12em; text-transform: uppercase; color: var(--ink-dim); margin-top: 2px; }
.wk-more { font-size: .74rem; color: var(--ink-dim); margin-top: 6px; font-family: var(--font-body); text-align: center; }
.wk-rank {
  position: absolute;
  top: -9px;
  right: -9px;
  width: 1.7rem;
  height: 1.7rem;
  border-radius: 50%;
  display: none;
  align-items: center;
  justify-content: center;
  background: var(--gold);
  color: #16202c;
  font-size: .95rem;
  font-weight: 700;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.45);
}
.wk.is-picked {
  border-color: var(--gold);
  background: rgba(var(--accent-rgb), 0.10);
}
.wk.is-picked .wk-rank { display: flex; }
.wk.is-picked .wk-month { color: var(--gold-soft); }
/* Every rank is taken: the unpicked tiles step back, so the eye goes to the
   picked ones a student would have to take out first. Still tappable — the
   tap explains itself in the status line. */
.wk.is-full { opacity: .45; }

.picker-status {
  min-height: 1.4em;
  color: var(--ink-dim);
  font-size: .95rem;
  margin: 0 0 12px;
}

/* The selects: the no-JavaScript form. Hidden by the script once the tiles
   are live (`hidden` attribute); this is only how they look when shown. */
.choice-fallback { margin: 0 0 16px; }
.choice-row {
  display: flex;
  align-items: flex-start;
  gap: 12px;
  padding: 10px 0;
  border-bottom: 1px solid var(--border);
}
.choice-row:last-of-type { border-bottom: none; }
.choice-rank {
  flex: 0 0 auto;
  width: 2rem;
  height: 2rem;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  border: 1px solid rgba(var(--accent-rgb), 0.45);
  color: var(--gold);
  font-family: var(--font-display);
  font-weight: 700;
  font-size: .95rem;
  margin-top: 4px;
}
.choice-field { flex: 1 1 auto; min-width: 0; }

/* The free-text field and the save button. */
.picker label,
.stack label,
.constraints label {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: .98rem;
  color: var(--ink);
  display: block;
  margin-bottom: 6px;
}
.field-help { color: var(--ink-dim); font-size: .88rem; margin-top: 6px; }
.constraints { margin: 6px 0 0; }
.picker select,
.picker textarea,
.stack input[type=text],
.stack textarea,
.stack select {
  box-sizing: border-box;
  width: 100%;
  max-width: 100%;
  font-size: 1rem;
}
.picker select,
.stack select {
  padding: 11px 12px;
  background: var(--input-focus-bg);
  color: var(--ink);
  border: 1px solid var(--border-color-input);
  border-radius: var(--border-radius-medium);
}
.picker select:focus,
.stack select:focus {
  border-color: var(--border-color-input-focus);
  box-shadow: 0 0 0 3px var(--border-color-input-focus-shadow);
  outline: none;
}
.actions-save { margin-top: 18px; }
.actions-save button { font-size: 1.15rem; padding: 14px 34px; }

/* A saved ranking, read back: number, then the weekend. */
.rank-list {
  list-style: none;
  margin: 4px 0 12px;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.rank-list li { display: flex; align-items: center; gap: 10px; }
.rank-n {
  flex: 0 0 auto;
  width: 1.7rem;
  height: 1.7rem;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  background: var(--gold);
  color: #16202c;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: .9rem;
}
.rank-what { font-family: var(--font-display); font-weight: 600; font-size: 1.05rem; color: var(--ink); }
.rank-what .muted { font-family: var(--font-body); font-weight: 400; font-size: .9rem; }

/* --------------------------------------------------------------------------
   The season (home page)
   -------------------------------------------------------------------------- */
/* The dates as chips, each led by its day number. */
.date-chips {
  list-style: none;
  margin: 10px 0 14px;
  padding: 0;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}
.date-chip {
  display: flex;
  align-items: center;
  gap: 7px;
  padding: 6px 12px 6px 8px;
  background: var(--camp-card);
  border: 1px solid var(--border);
  border-radius: 999px;
  font-family: var(--font-display);
  line-height: 1.05;
}
.date-chip-day { font-size: 1.3rem; font-weight: 700; color: var(--gold); }
.date-chip-rest { display: flex; flex-direction: column; }
.date-chip-month { font-size: .78rem; font-weight: 600; letter-spacing: .1em; text-transform: uppercase; color: var(--ink); }
.date-chip-more { font-size: .72rem; color: var(--ink-dim); font-family: var(--font-body); margin-top: 2px; }

/* Month grids: half of what a student needs to see is which weekends are
   NOT there — the season skips 17 Oct, the Diwali weekend and 21 Nov. */
.calendars {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(13rem, 1fr));
  gap: 12px;
  margin: 4px 0 4px;
}
.cal {
  background: var(--camp-card);
  border: 1px solid var(--border);
  border-radius: var(--border-radius-medium);
  padding: 12px 12px 14px;
}
.cal-title {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: .98rem;
  color: var(--ink);
  text-align: center;
  margin-bottom: 8px;
}
.cal-grid { display: grid; grid-template-columns: repeat(7, 1fr); gap: 2px; }
.cal-wd {
  text-align: center;
  font-size: .68rem;
  letter-spacing: .04em;
  text-transform: uppercase;
  color: var(--ink-dim);
  padding-bottom: 4px;
}
.cal-wd abbr { text-decoration: none; border: none; }
.cal-day {
  aspect-ratio: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 7px;
  font-size: .86rem;
  font-variant-numeric: tabular-nums;
  color: var(--camp-ink-soft);
}
.cal-day.is-out { color: transparent; }
/* A day a camp RUNS on — the outstation weekend is Saturday to Tuesday. */
.cal-day.is-span { background: rgba(var(--accent-rgb), 0.14); color: var(--gold-soft); }
/* The day it starts: a filled disc, so the difference is a SHAPE and not
   only a colour. */
.cal-day.is-start { background: var(--gold); color: #1a2636; font-weight: 700; }
.cal-legend {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 7px 10px;
  margin: 8px 0 0;
  font-size: .84rem;
  color: var(--ink-dim);
}
.cal-key { display: inline-block; width: 1.1rem; height: 1.1rem; border-radius: 5px; vertical-align: -0.2em; }
.cal-key.is-start { background: var(--gold); }
.cal-key.is-span { background: rgba(var(--accent-rgb), 0.14); }

/* --------------------------------------------------------------------------
   Status pills
   --------------------------------------------------------------------------
   Colour carries the difference, but never alone: the word is always there
   too, which is what makes this readable to a colour-blind student and in a
   printed list. */
.pill {
  display: inline-block;
  padding: 3px 11px;
  border-radius: 999px;
  font-family: var(--font-display);
  font-size: .76rem;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  border: 1px solid var(--border);
  color: var(--ink-dim);
  white-space: nowrap;
}
/* FILLED: a published allotment is final the moment it is made. Fill versus
   outline is a difference nobody has to learn and it survives being printed;
   a second green beside a lime accent is not. */
.pill-allotted { background: var(--gold); border-color: var(--gold); color: #16202c; }
/* "Dropped out", recorded by an organiser. */
.pill-declined { border-color: rgba(255, 123, 114, 0.5); color: var(--text-error); }
/* Dashed, not another colour: provisional is a shape here. */
.pill-waitlisted { border-style: dashed; border-color: var(--ink-dim); color: var(--ink-dim); }
.pill-unpublished { border-color: var(--border); color: var(--ink-dim); }

/* --------------------------------------------------------------------------
   The login page
   -------------------------------------------------------------------------- */
.stack {
  display: flex;
  flex-direction: column;
  gap: 14px;
  max-width: 22rem;
}
.page-centred h1,
.page-centred .sub { text-align: center; }
.page-centred .stack { margin-left: auto; margin-right: auto; }
.page-centred .linkbar { justify-content: center; text-align: center; }
.page-centred .actions { justify-content: center; }
.sub { color: var(--ink-dim); margin: 0 0 18px; font-size: .98rem; }
/* A mobile number and a six-digit code are read off a handset and thumbed
   in, so they get the biggest comfortable type — the width comes from the
   .stack rule, never from the `size` attribute. */
.big-input {
  font-size: 1.45rem !important;
  letter-spacing: .18em;
  text-align: center;
  padding: 14px 12px !important;
}

/* --------------------------------------------------------------------------
   Organiser dashboard
   -------------------------------------------------------------------------- */
.tiles {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(12rem, 1fr));
  gap: 10px;
  margin: 6px 0 18px;
}
.tile {
  background: var(--camp-card);
  border: 1px solid var(--border);
  border-radius: var(--border-radius-medium);
  padding: 12px 14px;
  color: var(--ink);
  display: block;
}
a.tile:hover { border-color: rgba(var(--accent-rgb), 0.4); }
.tile .n {
  display: block;
  font-family: var(--font-display);
  font-size: 1.75rem;
  font-weight: 700;
  line-height: 1.1;
  color: var(--ink);
}
.tile .k {
  display: block;
  margin-top: 2px;
  font-size: .78rem;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--ink-dim);
}
/* "Nobody is watching this" — the two numbers the dashboard exists for.
   Accent, not red: they are work outstanding, not a fault. */
.tile.warn { border-color: rgba(var(--accent-rgb), 0.45); }
.tile.warn .n { color: var(--gold); }

.num { text-align: right; font-variant-numeric: tabular-nums; }
.over { color: var(--text-error); font-weight: 600; }
.full td { opacity: .55; }
.small { font-size: .84rem; color: var(--ink-dim); }
.none { color: var(--text-error); }
.rank {
  display: inline-block;
  min-width: 1.5rem;
  text-align: center;
  border: 1px solid rgba(var(--accent-rgb), 0.4);
  border-radius: 6px;
  color: var(--gold);
  font-size: .8rem;
}
.seated td { opacity: .7; }

/* --------------------------------------------------------------------------
   Responsive
   -------------------------------------------------------------------------- */
@media screen and (max-width: 600px) {
  .camp-head { padding: 12px 2px 10px; gap: 8px; }
  .camp-brand { gap: 8px; }
  .camp-emblem { height: 38px; }
  /* The emblem's own art says ARYABHAT; the small line above the title
     said it again, and at this width there is no room to say anything
     twice. The title may wrap to two short lines beside the emblem. */
  .camp-org { display: none; }
  .camp-title { font-size: 1.1rem; white-space: normal; line-height: 1.05; }
  .camp-nav { gap: 4px; }
  .rules-link, .camp-signout { font-size: .82rem; min-height: 34px; padding: 5px 9px; }
  .camp-main { padding: 16px 14px 18px; font-size: 1.02rem; }
  .hero { padding: 16px 16px 14px; }
  .hero-dates { font-size: 1.25rem; }
  .card { padding: 14px 14px; }
  .weekends { grid-template-columns: repeat(3, 1fr); gap: 9px; }
  .wk { padding: 12px 4px 10px; }
  .wk-day { font-size: 1.9rem; }
  .calendars { grid-template-columns: 1fr; }
  .tiles { grid-template-columns: repeat(2, 1fr); }
  .tile { padding: 10px 12px; }
  .tile .n { font-size: 1.5rem; }
  .stack { max-width: 100%; }
  .actions .link, .actions .button-ghost, .actions button { flex: 1 1 auto; }
}
@media screen and (max-width: 360px) {
  .camp-title { font-size: 1.15rem; }
  .weekends { grid-template-columns: repeat(2, 1fr); }
}

/* Organiser pages stack several labelled blocks; give each room above. */
.admin-page .section-title { margin-top: 24px; }
/* Organiser pages are tables eleven columns wide; give them the room the
   student pages deliberately do not take. */
.admin-page .camp-wrap { max-width: 980px; }
