/* ============================================================
   FESTIVAL PLANNER — Theme-Layer ueber Foundation 6
   ------------------------------------------------------------
   Hier stehen Struktur und Komponenten. Keine festen Farben,
   keine festen Schriften: alles kommt aus var(--fx-*).
   Die Werte liefert themes/<name>.css.
   Praefix aller Klassen: .fx-
   ============================================================ */

/* ---------- 1. Grundlagen ---------------------------------- */

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

html { scroll-behavior: smooth; }

body.fx-body {
  margin: 0;
  background: var(--fx-bg);
  color: var(--fx-ink);
  font-family: var(--fx-font-body);
  font-size: 1rem;
  line-height: 1.55;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}

/* Filmkorn. Ueber --fx-grain: 0 in jedem Theme abschaltbar. */
body.fx-body::after {
  content: "";
  position: fixed;
  inset: 0;
  z-index: 9000;
  pointer-events: none;
  opacity: var(--fx-grain, 0);
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='140' height='140'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='3'/%3E%3C/filter%3E%3Crect width='140' height='140' filter='url(%23n)'/%3E%3C/svg%3E");
}

a { color: var(--fx-accent); text-decoration: none; }
a:hover { color: var(--fx-accent-hover); }

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

/* ---------- 2. Typografie ---------------------------------- */

.fx-display,
h1, h2, h3, h4, h5, h6 {
  font-family: var(--fx-font-display);
  font-weight: var(--fx-display-weight);
  letter-spacing: var(--fx-display-tracking);
  text-transform: var(--fx-display-transform);
  color: var(--fx-ink);
  line-height: 1.05;
  margin: 0 0 0.5rem;
}

h1 { font-size: clamp(1.9rem, 4.4vw, 3.1rem); }
h2 { font-size: clamp(1.5rem, 3vw, 2.1rem); }
h3 { font-size: 1.25rem; }
h4 { font-size: 1.05rem; }

p { margin: 0 0 1rem; }
p:last-child { margin-bottom: 0; }

/* Eyebrow: kleines Label ueber einer Ueberschrift.
   Traegt die Einordnung, nicht die Deko. */
.fx-eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  font-family: var(--fx-font-data);
  font-size: 0.68rem;
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  margin-bottom: 0.6rem;
}
.fx-eyebrow::before {
  content: "";
  width: 1.6rem;
  height: 2px;
  background: var(--fx-accent);
}

.fx-data { font-family: var(--fx-font-data); }
.fx-dim  { color: var(--fx-ink-dim); }
.fx-faint{ color: var(--fx-ink-faint); }

/* Plakat-Satz: Namen durch Trenner getrennt wie auf einem
   Line-up-Poster. Nur dort einsetzen, wo es wirklich eine
   Aufzaehlung gleichrangiger Namen gibt (z. B. Crew). */
.fx-billing {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: 0.04em;
  line-height: 1.3;
  color: var(--fx-ink);
}
.fx-billing span:not(:last-child)::after {
  content: "✦";
  color: var(--fx-accent);
  margin: 0 0.5rem;
  font-size: 0.7em;
  vertical-align: 0.15em;
}

/* ---------- 3. Grundgeruest -------------------------------- */

.fx-shell {
  display: flex;
  min-height: 100vh;
}

.fx-main {
  flex: 1 1 auto;
  min-width: 0;
  display: flex;
  flex-direction: column;
}

.fx-content {
  flex: 1 1 auto;
  padding: 1.5rem 1rem 2.5rem;
}
@media screen and (min-width: 40em) {
  .fx-content { padding: 2rem 2rem 3rem; }
}
.fx-content-inner { max-width: 1200px; margin: 0 auto; }

/* ---------- 4. Sidebar ------------------------------------- */

.fx-sidebar {
  position: fixed;
  top: 0; bottom: 0; left: 0;
  z-index: 1000;
  width: 268px;
  background: var(--fx-sidebar-bg);
  border-right: var(--fx-border) solid var(--fx-line);
  transform: translateX(-100%);
  transition: transform 0.22s ease;
  display: flex;
  flex-direction: column;
  overflow-y: auto;
  overscroll-behavior: contain;
}
.fx-sidebar.is-open { transform: translateX(0); }

@media screen and (min-width: 64em) {
  .fx-sidebar {
    position: sticky;
    top: 0; bottom: auto;
    height: 100vh;
    transform: none;
    flex: 0 0 268px;
  }
  .fx-sidebar-backdrop { display: none !important; }
}

.fx-sidebar-backdrop {
  position: fixed;
  inset: 0;
  z-index: 999;
  background: rgba(0, 0, 0, 0.6);
  backdrop-filter: blur(2px);
  opacity: 0;
  visibility: hidden;
  transition: opacity 0.22s ease, visibility 0.22s;
}
.fx-sidebar-backdrop.is-open { opacity: 1; visibility: visible; }

.fx-brand {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  padding: 1.25rem 1.25rem 1.1rem;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
.fx-brand__mark {
  flex: 0 0 auto;
  width: 38px; height: 38px;
  display: grid;
  place-items: center;
  background: var(--fx-accent);
  color: var(--fx-accent-ink);
  font-family: var(--fx-font-display);
  font-size: 1.15rem;
  font-weight: 700;
  border-radius: var(--fx-radius);
  clip-path: polygon(0 0, 100% 0, 100% 78%, 78% 100%, 0 100%);
}
.fx-brand__name {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 1.05rem;
  line-height: 1.1;
  color: var(--fx-ink);
}
.fx-brand__sub {
  font-family: var(--fx-font-data);
  font-size: 0.62rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}

.fx-nav { padding: 0.75rem 0 2rem; }
.fx-nav__group-label {
  font-family: var(--fx-font-data);
  font-size: 0.62rem;
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  padding: 1.15rem 1.25rem 0.4rem;
}
.fx-nav__list { list-style: none; margin: 0; padding: 0; }

.fx-nav__link {
  position: relative;
  display: flex;
  align-items: center;
  gap: 0.7rem;
  padding: 0.55rem 1.25rem;
  color: var(--fx-ink-dim);
  font-size: 0.95rem;
  line-height: 1.3;
  border-left: 3px solid transparent;
  transition: color 0.15s ease, background 0.15s ease, border-color 0.15s ease;
}
.fx-nav__link:hover {
  color: var(--fx-ink);
  background: var(--fx-accent-soft);
  border-left-color: var(--fx-line-strong);
}
.fx-nav__link.is-active {
  color: var(--fx-ink);
  background: var(--fx-accent-soft);
  border-left-color: var(--fx-accent);
  font-weight: 600;
}
.fx-nav__icon { flex: 0 0 auto; width: 18px; height: 18px; opacity: 0.85; }
.fx-nav__link.is-active .fx-nav__icon { color: var(--fx-accent); opacity: 1; }
.fx-nav__count {
  margin-left: auto;
  font-family: var(--fx-font-data);
  font-size: 0.7rem;
  padding: 0.05rem 0.4rem;
  border: 1px solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  color: var(--fx-ink-dim);
}
.fx-nav__link.is-active .fx-nav__count {
  border-color: var(--fx-accent);
  color: var(--fx-accent);
}

.fx-sidebar__foot {
  margin-top: auto;
  padding: 1rem 1.25rem;
  border-top: var(--fx-border) solid var(--fx-line);
  font-family: var(--fx-font-data);
  font-size: 0.68rem;
  color: var(--fx-ink-faint);
}

/* ---------- 5. Topbar -------------------------------------- */

.fx-topbar {
  position: sticky;
  top: 0;
  z-index: 900;
  display: flex;
  align-items: center;
  gap: 0.9rem;
  padding: 0.7rem 1rem;
  background: var(--fx-topbar-bg);
  backdrop-filter: blur(10px);
  border-bottom: var(--fx-border) solid var(--fx-line);
}
@media screen and (min-width: 40em) { .fx-topbar { padding: 0.7rem 2rem; } }

.fx-burger {
  display: inline-grid;
  place-items: center;
  width: 40px; height: 40px;
  background: transparent;
  border: var(--fx-border) solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  color: var(--fx-ink);
  cursor: pointer;
}
@media screen and (min-width: 64em) { .fx-burger { display: none; } }

.fx-topbar__title {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 1.05rem;
  line-height: 1.1;
  margin: 0;
}
.fx-topbar__crumb {
  font-family: var(--fx-font-data);
  font-size: 0.62rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}
.fx-topbar__actions {
  margin-left: auto;
  display: flex;
  align-items: center;
  gap: 0.5rem;
}

/* ---------- 6. Signature: der Crew-Pass -------------------- */
/* Akkreditierung am Bandl: das eine auffaellige Element der
   Seite. Alles andere bleibt bewusst ruhig.                   */

.fx-pass {
  position: relative;
  background: var(--fx-hero-bg);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  box-shadow: var(--fx-shadow);
  overflow: hidden;
}
.fx-pass__band {
  height: 6px;
  background: repeating-linear-gradient(
    135deg,
    var(--fx-accent) 0 14px,
    transparent 14px 28px
  );
  background-color: var(--fx-accent);
}
.fx-pass__body {
  display: grid;
  gap: 1.5rem;
  padding: 1.6rem 1.4rem;
}
@media screen and (min-width: 48em) {
  .fx-pass__body {
    grid-template-columns: 1fr auto;
    align-items: end;
    padding: 2.2rem 2rem;
  }
}
.fx-pass__title {
  font-size: clamp(2.1rem, 5.5vw, 3.6rem);
  margin: 0.2rem 0 0.35rem;
}
.fx-pass__meta {
  display: flex;
  flex-wrap: wrap;
  gap: 0.4rem 1.4rem;
  font-family: var(--fx-font-data);
  font-size: 0.82rem;
  color: var(--fx-ink-dim);
}
.fx-pass__meta b { color: var(--fx-ink); font-weight: 600; }

/* Abrissseite mit Perforation */
.fx-pass__stub {
  position: relative;
  min-width: 190px;
  padding: 1.1rem 1.2rem 1rem 1.6rem;
  background: rgba(0, 0, 0, 0.32);
  border: var(--fx-border) dashed var(--fx-line-strong);
  border-radius: var(--fx-radius);
  text-align: center;
}
.fx-pass__stub::before {
  content: "";
  position: absolute;
  left: -1px; top: 8px; bottom: 8px;
  width: 2px;
  background: repeating-linear-gradient(
    to bottom,
    var(--fx-line-strong) 0 5px,
    transparent 5px 11px
  );
}
.fx-pass__punch {
  width: 34px; height: 8px;
  margin: 0 auto 0.7rem;
  border-radius: 999px;
  background: var(--fx-bg);
  box-shadow: inset 0 1px 0 var(--fx-line-strong);
}
.fx-pass__count {
  font-family: var(--fx-font-display);
  font-size: 2.6rem;
  line-height: 1;
  color: var(--fx-accent);
}
.fx-pass__label {
  font-family: var(--fx-font-data);
  font-size: 0.62rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}
.fx-pass__barcode {
  height: 26px;
  margin-top: 0.9rem;
  background: repeating-linear-gradient(
    90deg,
    var(--fx-ink) 0 2px,
    transparent 2px 4px,
    var(--fx-ink) 4px 5px,
    transparent 5px 9px
  );
  opacity: 0.55;
}

/* ---------- 7. Karten -------------------------------------- */

.fx-card {
  background: var(--fx-surface);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  padding: 1.15rem 1.2rem;
  /* **Kein** `height: 100%`. Das stand hier, damit zwei Karten
     nebeneinander gleich hoch aussehen - streckte aber auch jede
     einzelne Karte in einer Spalte auf die volle Spaltenhoehe. Auf
     dem Handy, wo alles untereinander steht, wurden daraus
     meterlange leere Kaesten. Gleich hohe Nachbarn loest jetzt
     `.fx-cards-gleich` dort, wo es gewuenscht ist. */
}

/* Fuer nebeneinanderliegende Karten, die gleich hoch sein sollen:
   an die Zeile (`grid-x`) haengen, nicht an die Karte. */
.fx-cards-gleich > .cell { display: flex; }
.fx-cards-gleich > .cell > .fx-card { flex: 1; }
.fx-card--flush { padding: 0; overflow: hidden; }
.fx-card--quiet { background: var(--fx-bg-elev); }

.fx-card__head {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  padding-bottom: 0.85rem;
  margin-bottom: 0.95rem;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
.fx-card--flush .fx-card__head { padding: 1.05rem 1.2rem 0.85rem; margin-bottom: 0; }
.fx-card__title {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 1rem;
  margin: 0;
}
.fx-card__action { margin-left: auto; }

.fx-stat { display: flex; flex-direction: column; gap: 0.15rem; }
.fx-stat__value {
  font-family: var(--fx-font-display);
  font-size: 2.1rem;
  line-height: 1;
  color: var(--fx-ink);
}
.fx-stat__value--accent { color: var(--fx-accent); }
.fx-stat__label {
  font-family: var(--fx-font-data);
  font-size: 0.65rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}
.fx-stat__hint { font-size: 0.82rem; color: var(--fx-ink-dim); }

/* ---------- 8. Listen, Zeilen, Checklisten ----------------- */

.fx-list { list-style: none; margin: 0; padding: 0; }
.fx-list > li {
  display: flex;
  align-items: center;
  gap: 0.85rem;
  padding: 0.7rem 1.2rem;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
.fx-list > li:last-child { border-bottom: 0; }
.fx-list > li:hover { background: var(--fx-surface-2); }

.fx-list__main { min-width: 0; flex: 1 1 auto; }
.fx-list__title { display: block; color: var(--fx-ink); font-weight: 500; }
.fx-list__sub { display: block; font-size: 0.8rem; color: var(--fx-ink-dim); }
.fx-list__side {
  flex: 0 0 auto;
  font-family: var(--fx-font-data);
  font-size: 0.8rem;
  color: var(--fx-ink-dim);
  text-align: right;
}

/* Checkbox in Plakat-Optik */
.fx-check { position: relative; display: flex; align-items: center; gap: 0.75rem; cursor: pointer; }
.fx-list .fx-check { flex: 1 1 auto; }
.fx-check input { position: absolute; opacity: 0; width: 0; height: 0; }
.fx-check__box {
  flex: 0 0 auto;
  width: 20px; height: 20px;
  border: 2px solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  display: grid;
  place-items: center;
  transition: background 0.15s ease, border-color 0.15s ease;
}
.fx-check__box::after {
  content: "";
  width: 10px; height: 6px;
  border-left: 2px solid var(--fx-accent-ink);
  border-bottom: 2px solid var(--fx-accent-ink);
  transform: rotate(-45deg) scale(0.4);
  opacity: 0;
  transition: opacity 0.15s ease, transform 0.15s ease;
}
.fx-check input:checked + .fx-check__box {
  background: var(--fx-accent);
  border-color: var(--fx-accent);
}
.fx-check input:checked + .fx-check__box::after { opacity: 1; transform: rotate(-45deg) scale(1); }
.fx-check input:focus-visible + .fx-check__box { outline: 2px solid var(--fx-accent); outline-offset: 2px; }
/* Durchstreichen bedeutet "erledigt" und passt deshalb nur zu Listen
   mit Aufgaben - dort steht `.fx-check--liste` an der Beschriftung.
   Bei einer Einstellung wie "Vor dem Festival erinnern" hiesse ein
   Strich, die Erinnerung sei abgehakt; tatsaechlich ist sie gerade
   eingeschaltet. */
.fx-check--liste input:checked ~ .fx-check__text {
  color: var(--fx-ink-faint);
  text-decoration: line-through;
}
.fx-check__text { transition: color 0.15s ease; }

/* Erledigte Listenzeile leicht zuruecknehmen, ohne den Text zu verstecken.
   Die Pflicht-Marke bleibt sichtbar - erledigt heisst nicht unwichtig. */
[data-fx-liste] li.is-done .fx-list__side { opacity: 0.55; }
[data-fx-liste] li { transition: opacity 0.15s ease; }

/* ---------- 9. Tags, Badges, Avatare ----------------------- */

.fx-tag {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  padding: 0.18rem 0.5rem;
  border: 1px solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  color: var(--fx-ink-dim);
  white-space: nowrap;
}
.fx-tag--accent { border-color: var(--fx-accent); color: var(--fx-accent); }
.fx-tag--ok     { border-color: var(--fx-ok);     color: var(--fx-ok); }
.fx-tag--warn   { border-color: var(--fx-warn);   color: var(--fx-warn); }
.fx-tag--danger { border-color: var(--fx-danger); color: var(--fx-danger); }
.fx-tag--info   { border-color: var(--fx-info);   color: var(--fx-info); }
.fx-tag--solid  { background: var(--fx-accent); border-color: var(--fx-accent); color: var(--fx-accent-ink); }

.fx-avatar {
  width: 34px; height: 34px;
  flex: 0 0 auto;
  display: grid;
  place-items: center;
  border-radius: 999px;
  background: var(--fx-surface-2);
  border: 1px solid var(--fx-line-strong);
  font-family: var(--fx-font-data);
  font-size: 0.72rem;
  color: var(--fx-ink-dim);
}
.fx-avatar--accent { background: var(--fx-accent); color: var(--fx-accent-ink); border-color: var(--fx-accent); }
.fx-avatar-stack { display: flex; }
.fx-avatar-stack .fx-avatar:not(:first-child) { margin-left: -10px; }

/* ---------- 10. Fortschritt -------------------------------- */

.fx-bar {
  height: 8px;
  background: var(--fx-surface-2);
  border-radius: var(--fx-radius);
  overflow: hidden;
}
.fx-bar__fill {
  height: 100%;
  background: var(--fx-accent);
  border-radius: inherit;
  transition: width 0.4s ease;
}
.fx-bar__fill--ok   { background: var(--fx-ok); }
.fx-bar__fill--warn { background: var(--fx-warn); }
.fx-bar__fill--info { background: var(--fx-info); }

/* ---------- 11. Tabellen ----------------------------------- */

/* Foundation setzt `tbody { background-color: #fefefe }` - auf einer
   dunklen Oberflaeche waere das heller Text auf weissem Grund, also
   unlesbar. Die eigenen Regeln setzen kein Hintergrund auf tbody, also
   gewinnt Foundation dort kampflos. Deshalb hier ausdruecklich alle
   Ebenen der Tabelle zuruecksetzen. */
.fx-table,
.fx-table thead,
.fx-table tbody,
.fx-table tfoot,
.fx-table tr,
/* Auch die gestreiften Zeilen: `tbody tr:nth-child(even)` hat hoehere
   Spezifitaet als `.fx-table tr` und gewinnt sonst. */
.fx-table tbody tr:nth-child(even),
.fx-table tbody tr:nth-child(odd) { background-color: transparent; }
.fx-table { width: 100%; border-collapse: collapse; }

/* Kopfzeile abgesetzt und lesbar: vorher stand sie in ink-faint auf
   gleichem Grund wie der Inhalt und war kaum zu entziffern. */
.fx-table thead th {
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--fx-ink-dim);
  background: var(--fx-surface-2);
  text-align: left;
  font-weight: 500;
  padding: 0.7rem 1.2rem;
  border-bottom: 2px solid var(--fx-line-strong);
  white-space: nowrap;
}
.fx-table td {
  padding: 0.75rem 1.2rem;
  border-bottom: var(--fx-border) solid var(--fx-line);
  color: var(--fx-ink);
  font-size: 0.92rem;
  vertical-align: middle;
}

/* Zebrastreifen: sehr dezent, aber genug, um in einer breiten Zeile
   nicht zu verrutschen. Foundation bringt eigene Streifen mit, die auf
   dunklem Grund fast weiss sind - deshalb hier ueberschrieben. */
.fx-table tbody tr:nth-child(even) td { background: rgba(255, 255, 255, 0.022); }
.fx-table tbody tr:hover td { background: var(--fx-surface-2); }
.fx-table tbody tr:last-child td { border-bottom: 0; }
.fx-table tbody tr:focus-within td { background: var(--fx-surface-2); }
.fx-table .fx-num { font-family: var(--fx-font-data); text-align: right; white-space: nowrap; }
.fx-table-wrap { overflow-x: auto; }

/* ---------- 12. Messenger ---------------------------------- */

.fx-thread { display: flex; flex-direction: column; gap: 0.9rem; padding: 1.2rem; }
.fx-msg { display: flex; gap: 0.7rem; max-width: 86%; }
.fx-msg--own { margin-left: auto; flex-direction: row-reverse; }
.fx-msg__bubble {
  background: var(--fx-surface-2);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  padding: 0.6rem 0.85rem;
  font-size: 0.92rem;
}
.fx-msg--own .fx-msg__bubble {
  background: var(--fx-accent-soft);
  border-color: var(--fx-accent);
}
.fx-msg__who {
  display: block;
  font-family: var(--fx-font-data);
  font-size: 0.64rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  margin-bottom: 0.2rem;
}
.fx-composer {
  display: flex;
  gap: 0.6rem;
  padding: 0.9rem 1.2rem;
  border-top: var(--fx-border) solid var(--fx-line);
}

/* ---------- 13. Umfragen ----------------------------------- */

.fx-poll__option { margin-bottom: 0.9rem; }
.fx-poll__row {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: 1rem;
  margin-bottom: 0.3rem;
}
.fx-poll__label { font-weight: 500; }
.fx-poll__value { font-family: var(--fx-font-data); font-size: 0.8rem; color: var(--fx-ink-dim); }
.fx-poll__option.is-leading .fx-poll__value { color: var(--fx-accent); }

/* ---------- 14. Karte / Find Us ---------------------------- */

.fx-map {
  position: relative;
  min-height: 260px;
  border-radius: var(--fx-radius-lg);
  border: var(--fx-border) solid var(--fx-line);
  background:
    linear-gradient(var(--fx-line) 1px, transparent 1px) 0 0 / 44px 44px,
    linear-gradient(90deg, var(--fx-line) 1px, transparent 1px) 0 0 / 44px 44px,
    var(--fx-bg-elev);
  overflow: hidden;
}
.fx-map__pin {
  position: absolute;
  width: 14px; height: 14px;
  margin: -7px 0 0 -7px;
  border-radius: 999px;
  background: var(--fx-accent);
  box-shadow: var(--fx-glow);
}
.fx-map__pin::after {
  content: attr(data-label);
  position: absolute;
  left: 20px; top: -4px;
  font-family: var(--fx-font-data);
  font-size: 0.68rem;
  white-space: nowrap;
  color: var(--fx-ink);
}
.fx-map__pin--me { background: var(--fx-info); box-shadow: 0 0 0 6px var(--fx-accent-soft); }

/* ---------- 15. Leerzustaende ------------------------------ */

.fx-empty {
  text-align: center;
  padding: 2.5rem 1.5rem;
  border: 1px dashed var(--fx-line-strong);
  border-radius: var(--fx-radius-lg);
  color: var(--fx-ink-dim);
}
.fx-empty__title { font-family: var(--fx-font-display); text-transform: var(--fx-display-transform); color: var(--fx-ink); margin-bottom: 0.35rem; }

/* ---------- 16. Foundation-Overrides ----------------------- */
/* Foundation liefert Grid und Basiskomponenten. Hier bekommen
   sie die Theme-Optik. Keine !important-Kaskade noetig, solange
   die Reihenfolge stimmt: Foundation zuerst, dann diese Datei. */

.button {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: 0.06em;
  font-weight: var(--fx-display-weight);
  background: var(--fx-accent);
  color: var(--fx-accent-ink);
  border-radius: var(--fx-radius);
  padding: 0.6rem 1.1rem;
  margin-bottom: 0;
  transition: background 0.15s ease, transform 0.1s ease;
}
.button:hover, .button:focus { background: var(--fx-accent-hover); color: var(--fx-accent-ink); }
.button:active { transform: translateY(1px); }
.button.hollow {
  background: transparent;
  color: var(--fx-ink);
  border: 1px solid var(--fx-line-strong);
}
.button.hollow:hover, .button.hollow:focus {
  background: transparent;
  border-color: var(--fx-accent);
  color: var(--fx-accent);
}
.button.secondary { background: var(--fx-surface-2); color: var(--fx-ink); }
.button.secondary:hover { background: var(--fx-line); color: var(--fx-ink); }
.button.alert { background: var(--fx-danger); color: #fff; }
.button.success { background: var(--fx-ok); color: var(--fx-accent-ink); }
.button.tiny { padding: 0.35rem 0.6rem; font-size: 0.72rem; }
.button.small { padding: 0.45rem 0.8rem; font-size: 0.8rem; }

.callout {
  background: var(--fx-surface);
  border: var(--fx-border) solid var(--fx-line);
  border-left: 3px solid var(--fx-accent);
  border-radius: var(--fx-radius);
  color: var(--fx-ink);
}
.callout.success { border-left-color: var(--fx-ok); }
.callout.warning { border-left-color: var(--fx-warn); }
.callout.alert   { border-left-color: var(--fx-danger); }

label { color: var(--fx-ink-dim); font-size: 0.85rem; }

input[type="text"], input[type="email"], input[type="number"],
input[type="password"], input[type="search"], input[type="date"],
input[type="time"], input[type="url"], input[type="tel"],
input[type="datetime-local"], input[type="month"], input[type="week"],
textarea, select {
  background-color: var(--fx-field);
  border: var(--fx-border) solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  color: var(--fx-ink);
  box-shadow: none;
  margin-bottom: 0.85rem;
  height: auto;
  padding: 0.55rem 0.7rem;
  transition: background-color 0.15s ease, border-color 0.15s ease;
}

/* Wichtig: dieselben Attributselektoren wie oben, nicht nur `input:focus`.
   Foundation setzt `[type='text']:focus { background: #fefefe }` - das
   hat hoehere Spezifitaet als ein blosses `input:focus` und faerbt das
   Feld sonst beim Hineinklicken weiss, waehrend die Schrift hell
   bleibt. Ergebnis waere weiss auf weiss. */
input[type="text"]:focus, input[type="email"]:focus, input[type="number"]:focus,
input[type="password"]:focus, input[type="search"]:focus, input[type="date"]:focus,
input[type="time"]:focus, input[type="url"]:focus, input[type="tel"]:focus,
input[type="datetime-local"]:focus, input[type="month"]:focus, input[type="week"]:focus,
textarea:focus, select:focus {
  background-color: var(--fx-field-focus);
  border-color: var(--fx-accent);
  box-shadow: 0 0 0 3px var(--fx-accent-soft);
  color: var(--fx-ink);
  outline: none;
}

/* Auch der Autofill des Browsers faerbt sonst weiss. */
input:-webkit-autofill,
input:-webkit-autofill:focus {
  -webkit-text-fill-color: var(--fx-ink);
  -webkit-box-shadow: 0 0 0 1000px var(--fx-field) inset;
  caret-color: var(--fx-ink);
}

/* Deaktivierte Felder sollen erkennbar deaktiviert aussehen. */
input:disabled, textarea:disabled, select:disabled {
  background-color: var(--fx-surface);
  color: var(--fx-ink-faint);
  cursor: not-allowed;
}
::placeholder { color: var(--fx-ink-faint); }
select {
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16' fill='%239C949B'%3E%3Cpath d='M4 6l4 4 4-4z'/%3E%3C/svg%3E");
  background-size: 16px;
  background-position: right 0.6rem center;
  background-repeat: no-repeat;
}

.tabs { background: transparent; border: 0; border-bottom: var(--fx-border) solid var(--fx-line); }
.tabs-title > a {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: 0.06em;
  font-size: 0.9rem;
  color: var(--fx-ink-dim);
  padding: 0.7rem 1rem;
  border-bottom: 2px solid transparent;
}
.tabs-title > a:hover { background: transparent; color: var(--fx-ink); }
.tabs-title > a[aria-selected="true"] {
  background: transparent;
  color: var(--fx-ink);
  border-bottom-color: var(--fx-accent);
}
.tabs-content { background: transparent; border: 0; color: var(--fx-ink); }
.tabs-panel { padding: 1.2rem 0 0; }

.accordion { background: transparent; }
.accordion-item { border-bottom: var(--fx-border) solid var(--fx-line); }
.accordion-title {
  background: transparent;
  border: 0;
  color: var(--fx-ink);
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  font-size: 0.95rem;
  padding: 0.9rem 2rem 0.9rem 0;
}
.accordion-title:hover, .accordion-title:focus { background: transparent; color: var(--fx-accent); }
.accordion-title::before { color: var(--fx-accent); }
.accordion-content { background: transparent; border: 0; color: var(--fx-ink-dim); padding: 0 0 1rem; }

.switch-paddle { background: var(--fx-surface-2); border-radius: var(--fx-radius); }
input:checked ~ .switch-paddle { background: var(--fx-accent); }
.switch-paddle::after { border-radius: var(--fx-radius); }

.pagination a, .pagination button { color: var(--fx-ink-dim); border-radius: var(--fx-radius); }
.pagination .current { background: var(--fx-accent); color: var(--fx-accent-ink); }

/* ---------- 17. Hilfsklassen ------------------------------- */

.fx-stack > * + * { margin-top: 1rem; }
.fx-row { display: flex; align-items: center; gap: 0.6rem; }
.fx-row--wrap { flex-wrap: wrap; }
.fx-push { margin-left: auto; }
.fx-mt-0 { margin-top: 0; }
.fx-mb-0 { margin-bottom: 0; }
.fx-mb-1 { margin-bottom: 0.5rem; }
.fx-mb-2 { margin-bottom: 1rem; }
.fx-mb-3 { margin-bottom: 1.75rem; }
.fx-divider { height: 1px; background: var(--fx-line); margin: 1.25rem 0; border: 0; }
[hidden] { display: none !important; }
.fx-sr-only {
  position: absolute; width: 1px; height: 1px;
  padding: 0; margin: -1px; overflow: hidden;
  clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}

/* Sektionskopf einer Seite */
.fx-page-head {
  display: flex;
  align-items: flex-end;
  flex-wrap: wrap;
  gap: 1rem;
  margin-bottom: 1.5rem;
}
.fx-page-head__actions { margin-left: auto; display: flex; gap: 0.5rem; flex-wrap: wrap; }

/* ---------- 18. Bewegung ----------------------------------- */

.fx-rise { animation: fx-rise 0.5s cubic-bezier(0.2, 0.7, 0.3, 1) both; }
.fx-rise:nth-child(2) { animation-delay: 0.05s; }
.fx-rise:nth-child(3) { animation-delay: 0.1s; }
.fx-rise:nth-child(4) { animation-delay: 0.15s; }
@keyframes fx-rise {
  from { opacity: 0; transform: translateY(10px); }
  to   { opacity: 1; transform: none; }
}

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

/* ---------- 19. Druck -------------------------------------- */

@media print {
  .fx-sidebar, .fx-topbar, .fx-page-head__actions { display: none !important; }
  body.fx-body { background: #fff; color: #000; }
  .fx-card { border-color: #ccc; background: #fff; }
}

/* ============================================================
   20. Unterseiten
   Komponenten, die erst auf Detail-, Formular- und Auth-Seiten
   gebraucht werden. Gleiche Regel wie oben: nur var(--fx-*).
   ============================================================ */

/* ---------- 20.1 Zurueck-Link ------------------------------ */

.fx-back {
  display: inline-flex;
  align-items: center;
  gap: 0.45rem;
  font-family: var(--fx-font-data);
  font-size: 0.72rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  margin-bottom: 0.9rem;
}
.fx-back:hover { color: var(--fx-accent); }
.fx-back::before { content: "←"; font-size: 1rem; line-height: 1; }

/* ---------- 20.2 Datenliste (Detailseiten) ----------------- */

.fx-def { margin: 0; }
.fx-def > div {
  display: grid;
  grid-template-columns: 1fr;
  gap: 0.1rem;
  padding: 0.65rem 0;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
@media screen and (min-width: 30em) {
  .fx-def > div { grid-template-columns: 11rem 1fr; gap: 1rem; align-items: baseline; }
}
.fx-def > div:last-child { border-bottom: 0; }
.fx-def dt {
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  font-weight: 400;
}
.fx-def dd { margin: 0; color: var(--fx-ink); }

/* ---------- 20.3 Formulare --------------------------------- */

/* Der negative obere Abstand gleicht die margin-bottom eines
   Eingabefelds aus, damit der Hinweis direkt darunter klebt. Steht der
   Hinweis hinter etwas anderem - einem Knopf, einem Absatz -, zieht er
   sich sonst darueber. Deshalb die Ausnahmen darunter. */
.fx-field-hint {
  display: block;
  margin: -0.6rem 0 0.9rem;
  font-size: 0.78rem;
  color: var(--fx-ink-faint);
}
.button + .fx-field-hint,
p + .fx-field-hint,
form + .fx-field-hint,
hr + .fx-field-hint,
.fx-divider + .fx-field-hint { margin-top: 0.5rem; }
.fx-fieldset {
  border: 0;
  padding: 0;
  margin: 0 0 1.75rem;
}
.fx-fieldset__legend {
  display: block;
  width: 100%;
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  padding-bottom: 0.5rem;
  margin-bottom: 1.1rem;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
.fx-required { color: var(--fx-accent); }

/* Aktionsleiste unter Formularen. Bleibt beim Scrollen sichtbar. */
.fx-form-actions {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  flex-wrap: wrap;
  padding: 0.9rem 0 0.2rem;
  margin-top: 1.5rem;
}

/* Am Rechner klebt die Leiste unten, damit "Speichern" bei langen
   Formularen erreichbar bleibt. Auf dem Handy nicht: dort ist der
   Bildschirm ohnehin knapp, und die Leiste legte sich ueber die
   Karten darunter. Ein Verlauf als Hintergrund reicht dafuer nicht -
   der Inhalt scheint durch. */
@media screen and (min-width: 40em) {
  .fx-form-actions {
    position: sticky;
    bottom: 0;
    z-index: 5;
    background: linear-gradient(to top, var(--fx-bg) 65%, transparent);
  }
}
.fx-form-actions .fx-push + * { margin-left: 0; }

/* Upload-Feld */
.fx-drop {
  display: block;
  text-align: center;
  padding: 1.6rem 1rem;
  border: 1px dashed var(--fx-line-strong);
  border-radius: var(--fx-radius-lg);
  color: var(--fx-ink-dim);
  cursor: pointer;
  transition: border-color 0.15s ease, background 0.15s ease;
}
.fx-drop:hover { border-color: var(--fx-accent); background: var(--fx-accent-soft); }
.fx-drop strong { display: block; color: var(--fx-ink); font-family: var(--fx-font-display); text-transform: var(--fx-display-transform); }

/* ---------- 20.4 Segmentierte Umschalter ------------------- */

.fx-segment {
  display: inline-flex;
  border: var(--fx-border) solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  overflow: hidden;
}
.fx-segment > button,
.fx-segment > a {
  border: 0;
  background: transparent;
  color: var(--fx-ink-dim);
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: 0.06em;
  font-size: 0.78rem;
  padding: 0.4rem 0.85rem;
  cursor: pointer;
}
.fx-segment > * + * { border-left: var(--fx-border) solid var(--fx-line-strong); }
.fx-segment > .is-active {
  background: var(--fx-accent);
  color: var(--fx-accent-ink);
}

/* ---------- 20.5 Running Order ----------------------------- */
/* Raster: Spalten sind Buehnen, Zeilen sind halbe Stunden.
   Ein Slot bekommt grid-row: <start> / span <dauer>.           */

.fx-tt {
  display: grid;
  grid-template-columns: 4.5rem repeat(var(--fx-tt-stages, 3), minmax(9rem, 1fr));
  grid-auto-rows: 2.1rem;
  gap: 2px;
  background: var(--fx-bg-elev);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  overflow: hidden;
  min-width: 34rem;
}
.fx-tt__head {
  background: var(--fx-surface-2);
  padding: 0.6rem 0.7rem;
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 0.85rem;
  position: sticky;
  top: 0;
  z-index: 2;
}
.fx-tt__time {
  background: var(--fx-bg-elev);
  padding: 0.3rem 0.6rem;
  font-family: var(--fx-font-data);
  font-size: 0.7rem;
  color: var(--fx-ink-faint);
  text-align: right;
}
.fx-tt__cell { background: var(--fx-bg-elev); }
.fx-tt__slot {
  background: var(--fx-surface);
  border-left: 3px solid var(--fx-line-strong);
  padding: 0.45rem 0.6rem;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  gap: 0.1rem;
}
.fx-tt__slot:hover { background: var(--fx-surface-2); }
.fx-tt__slot.is-picked {
  border-left-color: var(--fx-accent);
  background: var(--fx-accent-soft);
}
.fx-tt__band {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  font-size: 0.86rem;
  line-height: 1.15;
  color: var(--fx-ink);
}
.fx-tt__when {
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  color: var(--fx-ink-faint);
}
.fx-tt__who { margin-top: auto; display: flex; }
.fx-tt__who .fx-avatar { width: 22px; height: 22px; font-size: 0.58rem; }
.fx-tt__who .fx-avatar:not(:first-child) { margin-left: -7px; }
.fx-tt-scroll { overflow-x: auto; padding-bottom: 0.5rem; }

/* ---------- 20.6 Verlauf / Aktivitaet ---------------------- */

.fx-timeline { list-style: none; margin: 0; padding: 0 0 0 1.1rem; border-left: 2px solid var(--fx-line); }
.fx-timeline > li { position: relative; padding: 0 0 1.1rem 1rem; }
.fx-timeline > li::before {
  content: "";
  position: absolute;
  left: -1.45rem; top: 0.45rem;
  width: 9px; height: 9px;
  border-radius: 999px;
  background: var(--fx-line-strong);
  border: 2px solid var(--fx-bg);
}
.fx-timeline > li.is-accent::before { background: var(--fx-accent); }
.fx-timeline__when {
  display: block;
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}

/* ---------- 20.7 Auth-Layout ------------------------------- */

.fx-auth {
  min-height: 100vh;
  display: grid;
  place-items: center;
  padding: 2rem 1rem;
  background: var(--fx-hero-bg);
}
.fx-auth__inner { max-width: 1000px; width: 100%; }
.fx-auth__brand {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  justify-content: center;
  margin-bottom: 1.5rem;
}
.fx-auth__card {
  background: var(--fx-surface);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  box-shadow: var(--fx-shadow);
  overflow: hidden;
}
.fx-auth__body { padding: 1.6rem 1.5rem; }
.fx-auth__foot {
  padding: 0.9rem 1.5rem;
  background: var(--fx-bg-elev);
  border-top: var(--fx-border) solid var(--fx-line);
  font-size: 0.88rem;
  color: var(--fx-ink-dim);
  text-align: center;
}
.fx-auth__note { text-align: center; margin-top: 1.2rem; font-size: 0.8rem; color: var(--fx-ink-faint); }

/* ---------- 20.8 Theme-Auswahl (Einstellungen) ------------- */

.fx-theme-grid { display: grid; gap: 0.85rem; grid-template-columns: repeat(auto-fit, minmax(11rem, 1fr)); }
.fx-theme-option {
  display: block;
  text-align: left;
  padding: 0.85rem;
  background: var(--fx-bg-elev);
  border: 2px solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  cursor: pointer;
  width: 100%;
}
.fx-theme-option.is-active { border-color: var(--fx-accent); }
.fx-theme-option__name {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  color: var(--fx-ink);
  font-size: 0.95rem;
}
.fx-theme-option__hint { font-size: 0.78rem; color: var(--fx-ink-faint); }
.fx-swatches { display: flex; gap: 4px; margin-top: 0.6rem; }
.fx-swatch { width: 22px; height: 22px; border-radius: var(--fx-radius); border: 1px solid rgba(255,255,255,0.12); }

/* ---------- 20.9 Grosse Kennzahl / Fehlerseite ------------- */

.fx-shout {
  font-family: var(--fx-font-display);
  font-size: clamp(4rem, 16vw, 9rem);
  line-height: 0.9;
  letter-spacing: var(--fx-display-tracking);
  color: var(--fx-accent);
}
.fx-avatar--lg { width: 64px; height: 64px; font-size: 1.1rem; }

/* ---------- 20.10 Styleguide ------------------------------- */

.fx-guide-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.6rem;
  padding: 0.9rem 0;
  border-bottom: var(--fx-border) solid var(--fx-line);
}
.fx-guide-row:last-child { border-bottom: 0; }
.fx-guide-label {
  flex: 0 0 100%;
  font-family: var(--fx-font-data);
  font-size: 0.64rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
}
@media screen and (min-width: 40em) { .fx-guide-label { flex: 0 0 9rem; } }
.fx-code {
  font-family: var(--fx-font-data);
  font-size: 0.78rem;
  color: var(--fx-ink-dim);
  background: var(--fx-bg-elev);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius);
  padding: 0.1rem 0.4rem;
}

/* ============================================================
   21. Galerie und Upload
   ============================================================ */

/* ---------- 21.1 Raster ------------------------------------ */

.fx-gallery {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(9.5rem, 1fr));
  gap: 0.5rem;
}
@media screen and (min-width: 40em) {
  .fx-gallery { grid-template-columns: repeat(auto-fill, minmax(12rem, 1fr)); gap: 0.75rem; }
}

.fx-shot {
  position: relative;
  display: block;
  aspect-ratio: 1 / 1;
  overflow: hidden;
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius-lg);
  background: var(--fx-surface);
  cursor: pointer;
  padding: 0;
}
/* Zwei Formate, damit die Wand nicht wie ein Kontaktbogen wirkt */
.fx-shot--wide { grid-column: span 2; aspect-ratio: 2 / 1; }
.fx-shot--tall { grid-row: span 2; aspect-ratio: 1 / 2; }
@media screen and (max-width: 39.9375em) {
  .fx-shot--tall { grid-row: span 1; aspect-ratio: 1 / 1; }
}

.fx-shot__img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
  transition: transform 0.4s cubic-bezier(0.2, 0.7, 0.3, 1);
}
.fx-shot:hover .fx-shot__img,
.fx-shot:focus-visible .fx-shot__img { transform: scale(1.04); }

.fx-shot__meta {
  position: absolute;
  inset: auto 0 0 0;
  padding: 1.6rem 0.6rem 0.5rem;
  background: linear-gradient(to top, rgba(0, 0, 0, 0.82), transparent);
  color: #fff;
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  letter-spacing: 0.06em;
  display: flex;
  align-items: center;
  gap: 0.4rem;
  opacity: 1;
  transition: opacity 0.2s ease;
}
/* Auf grossen Screens erst beim Ansteuern, sonst verdeckt es das Bild */
@media screen and (min-width: 64em) {
  .fx-shot__meta { opacity: 0; }
  .fx-shot:hover .fx-shot__meta,
  .fx-shot:focus-visible .fx-shot__meta { opacity: 1; }
}
.fx-shot__who { font-weight: 500; }
.fx-shot__when { margin-left: auto; opacity: 0.75; }

.fx-shot__badge {
  position: absolute;
  top: 0.45rem; left: 0.45rem;
  z-index: 2;
  background: rgba(0, 0, 0, 0.6);
  color: #fff;
  font-family: var(--fx-font-data);
  font-size: 0.6rem;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  padding: 0.12rem 0.4rem;
  border-radius: var(--fx-radius);
}
.fx-shot__badge--accent { background: var(--fx-accent); color: var(--fx-accent-ink); }

/* Auswahlmodus */
.fx-shot__pick {
  position: absolute;
  top: 0.45rem; right: 0.45rem;
  z-index: 3;
  width: 22px; height: 22px;
  border-radius: 999px;
  border: 2px solid rgba(255, 255, 255, 0.7);
  background: rgba(0, 0, 0, 0.4);
}
.fx-shot.is-picked { outline: 2px solid var(--fx-accent); outline-offset: -2px; }
.fx-shot.is-picked .fx-shot__pick { background: var(--fx-accent); border-color: var(--fx-accent); }

/* Platzhalter, solange kein echtes Bild da ist. Im Betrieb ersetzt
   das <img> in .fx-shot__img den Verlauf.                        */
.fx-shot__img--placeholder {
  background:
    radial-gradient(80% 60% at 50% 100%, rgba(255,255,255,0.12) 0%, transparent 60%),
    linear-gradient(200deg, var(--tone-a, #2A2630) 0%, var(--tone-b, #12111A) 100%);
}
.fx-shot__img--placeholder::after {
  content: "";
  position: absolute;
  inset: auto 0 0 0;
  height: 38%;
  background: var(--fx-bg);
  clip-path: polygon(0 100%, 0 62%, 8% 55%, 14% 66%, 22% 48%, 31% 60%, 39% 40%,
                     48% 58%, 56% 46%, 65% 63%, 74% 44%, 83% 58%, 92% 50%, 100% 64%, 100% 100%);
  opacity: 0.85;
}

/* ---------- 21.2 Tagesabschnitte --------------------------- */

.fx-day {
  display: flex;
  align-items: baseline;
  gap: 0.8rem;
  margin: 1.75rem 0 0.75rem;
}
.fx-day:first-child { margin-top: 0; }
.fx-day__label {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 1.05rem;
  color: var(--fx-ink);
}
.fx-day__count { font-family: var(--fx-font-data); font-size: 0.7rem; color: var(--fx-ink-faint); }
.fx-day__rule { flex: 1 1 auto; height: 1px; background: var(--fx-line); }

/* ---------- 21.3 Upload ------------------------------------ */

.fx-uploader {
  position: relative;
  border: 2px dashed var(--fx-line-strong);
  border-radius: var(--fx-radius-lg);
  background: var(--fx-bg-elev);
  padding: 1.4rem 1.2rem;
  text-align: center;
  transition: border-color 0.15s ease, background 0.15s ease;
}
.fx-uploader.is-dragover {
  border-color: var(--fx-accent);
  background: var(--fx-accent-soft);
}
.fx-uploader__title {
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: var(--fx-display-tracking);
  font-size: 1.05rem;
  color: var(--fx-ink);
  margin-bottom: 0.2rem;
}
.fx-uploader__hint { font-size: 0.85rem; color: var(--fx-ink-dim); margin-bottom: 1rem; }
.fx-uploader__actions {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  justify-content: center;
}
.fx-uploader__actions .button { margin: 0; }

/* Warteschlange */
.fx-queue { list-style: none; margin: 1.2rem 0 0; padding: 0; text-align: left; }
.fx-queue > li {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  padding: 0.55rem 0;
  border-top: var(--fx-border) solid var(--fx-line);
}
.fx-queue__thumb {
  flex: 0 0 auto;
  width: 42px; height: 42px;
  border-radius: var(--fx-radius);
  object-fit: cover;
  background: var(--fx-surface-2);
  border: var(--fx-border) solid var(--fx-line);
}
.fx-queue__main { flex: 1 1 auto; min-width: 0; }
.fx-queue__name {
  display: block;
  font-size: 0.85rem;
  color: var(--fx-ink);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.fx-queue__state {
  font-family: var(--fx-font-data);
  font-size: 0.66rem;
  color: var(--fx-ink-faint);
}
.fx-queue__state--done { color: var(--fx-ok); }
.fx-queue__state--error { color: var(--fx-danger); }
.fx-queue__bar { margin-top: 0.3rem; }

/* Schwebender Auslöser für unterwegs */
.fx-fab {
  position: fixed;
  right: 1rem;
  bottom: 1rem;
  z-index: 800;
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  padding: 0.85rem 1.1rem;
  border: 0;
  border-radius: 999px;
  background: var(--fx-accent);
  color: var(--fx-accent-ink);
  font-family: var(--fx-font-display);
  text-transform: var(--fx-display-transform);
  letter-spacing: 0.06em;
  box-shadow: 0 12px 30px -12px rgba(0, 0, 0, 0.9), var(--fx-glow);
  cursor: pointer;
}
@media screen and (min-width: 64em) { .fx-fab { display: none; } }

/* ---------- Festival-Banner -------------------------------- */

.fx-banner {
  position: relative;
  border-radius: var(--fx-radius-lg);
  overflow: hidden;
  border: var(--fx-border) solid var(--fx-line);
  line-height: 0;
}
.fx-banner img {
  width: 100%;
  height: auto;
  display: block;
  /* Auf schmalen Geraeten wuerde ein 3:1-Bild sonst zum Streifen. */
  max-height: 320px;
  object-fit: cover;
}
/* Verlauf nach unten, damit der Uebergang zum dunklen Hintergrund
   nicht wie eine harte Kante wirkt. */
.fx-banner::after {
  content: "";
  position: absolute;
  inset: auto 0 0 0;
  height: 40%;
  background: linear-gradient(to bottom, transparent, var(--fx-bg));
  pointer-events: none;
}
@media screen and (max-width: 39.9375em) {
  .fx-banner img { max-height: 180px; }
}

/* ---------- Standortkarte ---------------------------------- */

.fx-karte {
  height: 460px;
  border-radius: var(--fx-radius);
  border: var(--fx-border) solid var(--fx-line);
  /* Leaflet setzt eigene Farben; ohne das leuchtet die Karte weiss
     durch den Rahmen. */
  background: var(--fx-surface-2);
  z-index: 0;
}
@media screen and (max-width: 39.9375em) {
  .fx-karte { height: 340px; }
}

/* Marker im Stil der Avatare, damit die Karte zum Rest passt. */
.fx-karte__marker {
  display: grid;
  place-items: center;
  border-radius: 50%;
  background: var(--fx-surface-2);
  border: 2px solid var(--fx-line-strong);
  color: var(--fx-ink);
  font-family: var(--fx-font-data);
  font-size: 0.68rem;
  letter-spacing: 0.04em;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.45);
}
.fx-karte__marker.is-ich {
  border-color: var(--fx-accent);
  background: var(--fx-accent);
  color: #fff;
}
.fx-karte__marker.is-camp {
  border-color: var(--fx-ok);
  color: var(--fx-ok);
  font-size: 1rem;
}

/* Leaflets Bedienelemente auf dunklem Grund lesbar halten. */
.leaflet-control-attribution {
  background: rgba(20, 19, 23, 0.82) !important;
  color: var(--fx-ink-dim) !important;
  font-size: 0.66rem;
}
.leaflet-control-attribution a { color: var(--fx-ink-dim) !important; }
.leaflet-bar a {
  background: var(--fx-surface-2) !important;
  color: var(--fx-ink) !important;
  border-color: var(--fx-line) !important;
}
.leaflet-bar a:hover { background: var(--fx-surface) !important; }
.leaflet-popup-content-wrapper, .leaflet-popup-tip {
  background: var(--fx-surface-2);
  color: var(--fx-ink);
}

/* ---------- Galerie ----------------------------------------- */

.fx-galerie {
  display: grid;
  /* auto-fill statt fester Spaltenzahl: auf dem Handy zwei, am
     Rechner so viele, wie hineinpassen. */
  grid-template-columns: repeat(auto-fill, minmax(190px, 1fr));
  gap: 1rem;
}
.fx-galerie__kachel {
  margin: 0;
  background: var(--fx-surface);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius);
  overflow: hidden;
  position: relative;
}
.fx-galerie__kachel img {
  width: 100%;
  /* Feste Höhe, damit das Raster nicht ausfranst. */
  aspect-ratio: 4 / 3;
  object-fit: cover;
  display: block;
  background: var(--fx-surface-2);
}
.fx-galerie__kachel figcaption {
  padding: 0.6rem 0.7rem 0.7rem;
  font-size: 0.82rem;
}
.fx-galerie__titel {
  display: block;
  color: var(--fx-ink);
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.fx-galerie__wahl {
  position: absolute;
  top: 0.5rem;
  left: 0.5rem;
  z-index: 1;
  background: rgba(20, 19, 23, 0.75);
  border-radius: var(--fx-radius);
  padding: 0.2rem 0.35rem;
  margin: 0;
}
.fx-galerie__wahl input { margin: 0; }

/* Ablagefläche zum Hineinziehen */
.fx-ablage {
  border: 2px dashed var(--fx-line-strong);
  border-radius: var(--fx-radius);
  padding: 1.6rem 1rem;
  text-align: center;
  transition: border-color 0.15s ease, background 0.15s ease;
}
.fx-ablage.is-aktiv {
  border-color: var(--fx-accent);
  background: var(--fx-surface-2);
}
/* Der Hinweis steht hier hinter einer Knopfreihe, nicht hinter einem
   Eingabefeld - der uebliche negative Abstand zoege ihn darueber. */
.fx-ablage .fx-field-hint { margin-top: 0.9rem; }

/* Werkbank für Kameraaufnahmen */
.fx-leinwand {
  max-width: 100%;
  border-radius: var(--fx-radius);
  border: var(--fx-border) solid var(--fx-line);
  background: var(--fx-surface-2);
  /* Zuschnitt zieht man mit dem Finger - das Scrollen darf dabei
     nicht dazwischenfunken. */
  touch-action: none;
  cursor: crosshair;
}
.fx-fehler { color: var(--fx-accent); }

/* ---------- Lightbox ---------------------------------------- */

.fx-lightbox {
  position: fixed;
  inset: 0;
  /* Ueber allem: die Seitenleiste liegt bei 1000, Meldungen bei 9000.
     Eine Lightbox, die halb hinter dem Menue verschwindet, waere
     kaputt. */
  z-index: 9600;
  /* Das Bild mittig, alles andere darueber gelegt. Ein Raster mit
     Spalten fuer die Pfeile brach auf schmalen Geraeten auseinander -
     absolut positionierte Pfeile verhalten sich ueberall gleich. */
  display: grid;
  place-items: center;
  padding: 1rem;
  background: rgba(10, 9, 12, 0.94);
  /* Auf dem Handy nicht hinter der Systemleiste verschwinden. */
  padding-top: max(1rem, env(safe-area-inset-top));
  padding-bottom: max(1rem, env(safe-area-inset-bottom));
}
.fx-lightbox[hidden] { display: none; }

.fx-lightbox__buehne {
  margin: 0;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 0.8rem;
  min-width: 0;
  max-height: 100%;
}
.fx-lightbox__buehne img {
  max-width: 100%;
  /* Platz fuer die Fusszeile lassen, sonst schiebt ein hohes Bild
     die Angaben aus dem Bild. */
  max-height: calc(100vh - 9rem);
  object-fit: contain;
  border-radius: var(--fx-radius);
  /* Beim Wechsel kurz abblenden statt hart springen. */
  transition: opacity 0.12s ease;
}
.fx-lightbox__buehne img.is-laedt { opacity: 0.35; }

.fx-lightbox__fuss {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.4rem 0.8rem;
  justify-content: center;
  text-align: center;
  max-width: 46rem;
}
.fx-lightbox__titel {
  font-family: var(--fx-font-display);
  font-size: 1rem;
  letter-spacing: 0.04em;
  color: var(--fx-ink);
}
.fx-lightbox__meta { font-size: 0.82rem; color: var(--fx-ink-dim); }

.fx-lightbox__pfeil,
.fx-lightbox__schliessen {
  background: var(--fx-surface-2);
  border: var(--fx-border) solid var(--fx-line-strong);
  color: var(--fx-ink);
  border-radius: 50%;
  /* 44 px: darunter trifft man auf dem Handy zuverlaessig daneben. */
  width: 44px;
  height: 44px;
  font-size: 1.5rem;
  line-height: 1;
  cursor: pointer;
  display: grid;
  place-items: center;
  padding: 0;
}
.fx-lightbox__pfeil:hover,
.fx-lightbox__schliessen:hover { border-color: var(--fx-accent); }
.fx-lightbox__pfeil[disabled] { opacity: 0.2; cursor: default; }

.fx-lightbox__pfeil {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  z-index: 2;
}
.fx-lightbox__pfeil--links { left: max(0.8rem, env(safe-area-inset-left)); }
.fx-lightbox__pfeil--rechts { right: max(0.8rem, env(safe-area-inset-right)); }

.fx-lightbox__schliessen {
  position: absolute;
  top: max(1rem, env(safe-area-inset-top));
  right: 1rem;
  z-index: 2;
}
.fx-lightbox__zaehler {
  position: absolute;
  top: max(1.4rem, env(safe-area-inset-top));
  left: 1.2rem;
  font-family: var(--fx-font-data);
  font-size: 0.75rem;
  letter-spacing: 0.12em;
  color: var(--fx-ink-dim);
}

/* Auf schmalen Geraeten liegen die Pfeile ueber dem Bild und sind
   etwas durchscheinend - gewischt wird dort ohnehin meistens. */
@media screen and (max-width: 39.9375em) {
  .fx-lightbox { padding: 0.5rem; }
  .fx-lightbox__buehne img { max-height: calc(100vh - 8rem); }
  .fx-lightbox__pfeil {
    background: rgba(35, 32, 39, 0.8);
    width: 40px;
    height: 40px;
  }
  .fx-lightbox__fuss { font-size: 0.8rem; }
}

/* Solange die Lightbox offen ist, soll die Seite dahinter nicht
   mitscrollen. */
body.fx-lightbox-offen { overflow: hidden; }

/* ---------- Fussbereich ------------------------------------- */

.fx-fuss {
  display: flex;
  flex-wrap: wrap;
  gap: 0.4rem 1.2rem;
  padding: 2rem 0 1.2rem;
  /* `auto` schiebt den Fussbereich ans untere Ende, wenn der Inhalt
     kuerzer ist als das Fenster - vorher stand er direkt unter dem
     Inhalt und schwebte bei kurzen Seiten mitten im Bild. */
  margin-top: auto;
  border-top: var(--fx-border) solid var(--fx-line);
  font-size: 0.8rem;
}
/* Der Fussbereich spannt jetzt ueber die ganze Breite; die Links
   richten sich am selben Raster aus wie der Inhalt darueber. */
.fx-fuss { padding-left: 1rem; padding-right: 1rem; }
@media screen and (min-width: 40em) {
  .fx-fuss { padding-left: 2rem; padding-right: 2rem; }
}
.fx-fuss__inhalt {
  display: flex;
  flex-wrap: wrap;
  gap: 0.4rem 1.2rem;
  width: 100%;
}
.fx-fuss a { color: var(--fx-ink-faint); }
.fx-fuss a:hover { color: var(--fx-accent); }
/* Auf der Anmeldeseite mittig, dort gibt es keine Seitenleiste. */
.fx-auth .fx-fuss,
body > .fx-fuss { justify-content: center; padding: 1.5rem 1rem; }

/* Karte vor dem Laden */
.fx-karte--wartend {
  display: grid;
  place-items: center;
  text-align: center;
  padding: 1.5rem;
  background:
    repeating-linear-gradient(45deg, var(--fx-surface) 0 12px,
                              var(--fx-surface-2) 12px 24px);
}
.fx-karte__hinweis { max-width: 30rem; }

.fx-mt-3 { margin-top: 2rem; }

/* Filterleiste der Galerie */
.fx-filter {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  gap: 0.6rem 0.9rem;
}
.fx-filter label {
  margin: 0;
  font-size: 0.78rem;
  color: var(--fx-ink-dim);
}
.fx-filter select,
.fx-filter input {
  margin: 0.2rem 0 0;
  min-width: 8rem;
}
.fx-filter button { margin: 0; }
@media screen and (max-width: 39.9375em) {
  .fx-filter label { flex: 1 1 45%; }
  .fx-filter select, .fx-filter input { min-width: 0; width: 100%; }
  .fx-filter button { flex: 1 1 100%; }
}

/* Auswahl zwischen zwei Wegen (Registrierung) */
.fx-wahl { display: grid; gap: 0.5rem; }
.fx-wahl__feld {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  margin: 0;
  padding: 0.7rem 0.9rem;
  border: var(--fx-border) solid var(--fx-line-strong);
  border-radius: var(--fx-radius);
  background: var(--fx-field);
  cursor: pointer;
  font-size: 0.92rem;
}
.fx-wahl__feld input { margin: 0; }
.fx-wahl__feld:has(input:checked) {
  border-color: var(--fx-accent);
  background: var(--fx-field-focus);
}

/* ---------- Chat ---------------------------------------------- */

.fx-chat {
  display: flex;
  flex-direction: column;
  /* Feste Höhe statt mitwachsend: ein Chat, der die Seite immer
     länger macht, lässt sich nicht bedienen - man scrollt dann im
     Dokument statt im Verlauf. */
  height: calc(100vh - 15rem);
  min-height: 24rem;
  position: relative;
}

.fx-chat__verlauf {
  flex: 1;
  overflow-y: auto;
  padding: 1rem 0.8rem;
  background: var(--fx-surface);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: var(--fx-radius) var(--fx-radius) 0 0;
  display: flex;
  flex-direction: column;
  gap: 0.35rem;
  /* Sanft scrollen, wenn eine neue Nachricht kommt. */
  scroll-behavior: smooth;
}

.fx-chat__blase {
  position: relative;
  max-width: 78%;
  align-self: flex-start;
  background: var(--fx-surface-2);
  border: var(--fx-border) solid var(--fx-line);
  border-radius: 14px 14px 14px 4px;
  padding: 0.5rem 0.7rem 1.2rem;
  font-size: 0.92rem;
  line-height: 1.4;
}
.fx-chat__blase.is-ich {
  align-self: flex-end;
  background: #33301b;
  border-color: #4a4526;
  border-radius: 14px 14px 4px 14px;
}

.fx-chat__wer {
  display: block;
  font-size: 0.75rem;
  color: var(--fx-accent);
  margin-bottom: 0.15rem;
}
.fx-chat__inhalt {
  /* Umbrüche aus der Nachricht erhalten, lange Wörter trennen. */
  white-space: pre-wrap;
  overflow-wrap: anywhere;
  color: var(--fx-ink);
}
.fx-chat__inhalt.is-geloescht,
.fx-chat__inhalt.is-verschluesselt {
  color: var(--fx-ink-faint);
  font-style: italic;
  font-size: 0.86rem;
}
.fx-chat__bild {
  max-width: 100%;
  max-height: 320px;
  border-radius: 8px;
  display: block;
  cursor: zoom-in;
}
.fx-chat__zeit {
  position: absolute;
  right: 0.6rem;
  bottom: 0.35rem;
  font-size: 0.68rem;
  color: var(--fx-ink-faint);
  font-family: var(--fx-font-data);
}
.fx-chat__weg {
  position: absolute;
  top: 0.15rem;
  right: 0.2rem;
  background: none;
  border: 0;
  color: var(--fx-ink-faint);
  font-size: 1.05rem;
  line-height: 1;
  cursor: pointer;
  /* Trefferflaeche: darunter trifft man auf dem Handy daneben. */
  min-width: 30px;
  min-height: 30px;
  padding: 0;
  opacity: 0.45;
  transition: opacity 0.12s ease;
}
.fx-chat__blase:hover .fx-chat__weg { opacity: 1; }

/* Auf Geraeten ohne Mauszeiger gibt es kein :hover - dort war der
   Knopf vorher dauerhaft unsichtbar und damit nicht bedienbar. */
@media (hover: none) {
  .fx-chat__weg { opacity: 0.6; }
}

.fx-chat__tag {
  align-self: center;
  font-size: 0.7rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--fx-ink-faint);
  background: var(--fx-bg-elev);
  border-radius: 10px;
  padding: 0.2rem 0.7rem;
  margin: 0.6rem 0 0.2rem;
}
.fx-chat__leer {
  margin: auto;
  color: var(--fx-ink-faint);
  font-size: 0.9rem;
}

/* Hinweis auf neue Nachrichten, wenn man weiter oben liest */
.fx-chat__neu {
  position: absolute;
  bottom: 6.5rem;
  left: 50%;
  transform: translateX(-50%);
  background: var(--fx-accent);
  color: #fff;
  border: 0;
  border-radius: 20px;
  padding: 0.4rem 1rem;
  font-size: 0.8rem;
  cursor: pointer;
  box-shadow: 0 4px 14px rgba(0, 0, 0, 0.4);
  z-index: 2;
}

.fx-chat__eingabe {
  border: var(--fx-border) solid var(--fx-line);
  border-top: 0;
  border-radius: 0 0 var(--fx-radius) var(--fx-radius);
  background: var(--fx-surface-2);
  padding: 0.6rem 0.7rem;
}
.fx-chat__zeile {
  display: flex;
  align-items: flex-end;
  gap: 0.4rem;
}
.fx-chat__zeile textarea {
  flex: 1;
  margin: 0;
  resize: none;
  min-height: 2.5rem;
  max-height: 140px;
  border-radius: 18px;
  padding: 0.6rem 0.9rem;
}
.fx-chat__knopf,
.fx-chat__senden {
  flex: 0 0 auto;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  border: var(--fx-border) solid var(--fx-line-strong);
  background: var(--fx-field);
  color: var(--fx-ink);
  font-size: 1.1rem;
  cursor: pointer;
  display: grid;
  place-items: center;
  margin: 0;
  padding: 0;
}
.fx-chat__senden {
  background: var(--fx-accent);
  border-color: var(--fx-accent);
  color: #fff;
}
.fx-chat__knopf:hover { border-color: var(--fx-accent); }

.fx-emojis {
  display: flex;
  flex-wrap: wrap;
  gap: 0.2rem;
  padding: 0.5rem 0.2rem 0.7rem;
  max-height: 9rem;
  overflow-y: auto;
}
.fx-emoji {
  background: none;
  border: 0;
  font-size: 1.3rem;
  cursor: pointer;
  padding: 0.2rem 0.3rem;
  border-radius: 6px;
  line-height: 1;
}
.fx-emoji:hover { background: var(--fx-surface); }

@media screen and (max-width: 39.9375em) {
  .fx-chat { height: calc(100vh - 11rem); }
  .fx-chat__blase { max-width: 88%; }
}
