/* ════════════════════════════════════════════════════════════════
   DJDigital.de – Corporate Design
   Farben:  #454543 (Primär) · #c2ad9a (Sekundär)
            #f2efeb (Background) · #635a50 (Text)
   Fonts:   Playfair Display (Überschriften) · Noto Sans Display (Text)
   ════════════════════════════════════════════════════════════════ */

/* ── Fonts (self-hosted, DSGVO-konform) ─────────────────────────
   WOFF2-Dateien nach public/assets/fonts/ legen – siehe fonts/README.txt.
   Fehlen die Dateien, greifen elegante System-Fallbacks. */
@font-face {
    font-family: 'Playfair Display';
    src: url('../fonts/playfair-display-latin-400-normal.woff2') format('woff2');
    font-weight: 400; font-style: normal; font-display: swap;
}
@font-face {
    font-family: 'Playfair Display';
    src: url('../fonts/playfair-display-latin-600-normal.woff2') format('woff2');
    font-weight: 600; font-style: normal; font-display: swap;
}
@font-face {
    font-family: 'Playfair Display';
    src: url('../fonts/playfair-display-latin-700-normal.woff2') format('woff2');
    font-weight: 700; font-style: normal; font-display: swap;
}
@font-face {
    font-family: 'Noto Sans Display';
    src: url('../fonts/noto-sans-display-latin-400-normal.woff2') format('woff2');
    font-weight: 400; font-style: normal; font-display: swap;
}
@font-face {
    font-family: 'Noto Sans Display';
    src: url('../fonts/noto-sans-display-latin-500-normal.woff2') format('woff2');
    font-weight: 500; font-style: normal; font-display: swap;
}
@font-face {
    font-family: 'Noto Sans Display';
    src: url('../fonts/noto-sans-display-latin-700-normal.woff2') format('woff2');
    font-weight: 700; font-style: normal; font-display: swap;
}

/* ════════════════════════════════════════════════════════════════
   Design-Tokens – drei Erscheinungsbilder, je hell und dunkel
   ════════════════════════════════════════════════════════════════
   Gesteuert über zwei Attribute auf <html>:
     data-brand  = salon | nachtclub | studio | djdirk  (Systemeinstellung)
     data-theme  = light | dark                 (Schalter des Besuchers)

   Jeder der sechs Blöcke setzt den KOMPLETTEN Satz, auch wenn ein
   Wert dem der Vorgabe entspricht. Das ist bewusst redundant: So
   gibt es keine Reihenfolge, in der eine Welt Werte einer anderen
   erbt – der häufigste Grund für Darstellungsfehler, die sich nur
   in einer Kombination zeigen und schwer zu finden sind.

   Nachtclub und DJ Dirk sind in beiden Zuständen dunkel; der
   Schalter regelt dort die Tiefe (gedämpft ↔ volle Nacht), nicht
   hell gegen dunkel. Eine helle Clubnacht wäre ein Widerspruch in
   sich, und eine helle Hochzeitsnacht auch.
   ════════════════════════════════════════════════════════════════ */

/* ── 01 Salon · hell (Vorgabe) ──────────────────────────────────── */
:root,
[data-brand="salon"] {
    --primary: #454543;
    --secondary: #b08d6a;
    --accent2: #c2ad9a;
    --bg: #f2efeb;
    --text: #635a50;

    --surface: #ffffff;
    --surface-alt: #e9e3da;
    --border: #e0d8cc;
    --heading: #454543;
    --muted: #8a8073;
    --on-primary: #f2efeb;
    --sidebar-bg: #454543;

    --success: #5f7a5a;
    --success-bg: #e5ecdf;
    --warning: #9a7b3f;
    --warning-bg: #f3e8d3;
    --danger: #9a4f44;
    --danger-bg: #f3ded9;
    --info: #56656f;
    --info-bg: #e1e7ea;

    --font-heading: 'Playfair Display', Georgia, 'Times New Roman', serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 600;
    --heading-tracking: 0;

    --radius: 14px;
    --radius-sm: 9px;
    --btn-radius: 9px;
    --btn-primary-bg: #454543;
    --shadow: 0 10px 30px rgba(69, 69, 67, 0.08);
    --shadow-lg: 0 18px 50px rgba(69, 69, 67, 0.14);
    --page-glow: none;
    --container: 1120px;
}

/* ── 01 Salon · dunkel ──────────────────────────────────────────── */
[data-theme="dark"],
[data-brand="salon"][data-theme="dark"] {
    --primary: #c2ad9a;
    --secondary: #c9a87f;
    --accent2: #c2ad9a;
    --bg: #232322;
    --text: #cfc6ba;

    --surface: #2c2c2a;
    --surface-alt: #343432;
    --border: #3e3d3a;
    --heading: #f2efeb;
    --muted: #9a9186;
    --on-primary: #232322;
    --sidebar-bg: #1c1c1b;

    --success: #9dbb95;
    --success-bg: #2c352a;
    --warning: #d8b779;
    --warning-bg: #38301f;
    --danger: #d99a8e;
    --danger-bg: #3a2723;
    --info: #a9bcc7;
    --info-bg: #262f34;

    --font-heading: 'Playfair Display', Georgia, 'Times New Roman', serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 600;
    --heading-tracking: 0;

    --radius: 14px;
    --radius-sm: 9px;
    --btn-radius: 9px;
    --btn-primary-bg: #c2ad9a;
    --shadow: 0 10px 30px rgba(0, 0, 0, 0.35);
    --shadow-lg: 0 18px 50px rgba(0, 0, 0, 0.5);
    --page-glow: none;
    --container: 1120px;
}

/* ── 02 Nachtclub · gedämpft ────────────────────────────────────── */
[data-brand="nachtclub"] {
    --primary: #c04dff;
    --secondary: #35e0d8;
    --accent2: #35e0d8;
    --bg: #16151b;
    --text: #b9b4c6;

    --surface: #1e1d25;
    --surface-alt: #26242f;
    --border: #322f3d;
    --heading: #f4f2ff;
    --muted: #837e93;
    --on-primary: #0b0b0f;
    --sidebar-bg: #121118;

    --success: #4fd9a4;
    --success-bg: #142b24;
    --warning: #f5c451;
    --warning-bg: #2e2617;
    --danger: #ff6b8a;
    --danger-bg: #2f1720;
    --info: #6fa8ff;
    --info-bg: #16202f;

    --font-heading: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 700;
    --heading-tracking: -0.02em;

    --radius: 18px;
    --radius-sm: 12px;
    --btn-radius: 999px;
    --btn-primary-bg: linear-gradient(100deg, #c04dff 0%, #35e0d8 100%);
    --shadow: 0 10px 30px rgba(0, 0, 0, 0.45);
    --shadow-lg: 0 18px 50px rgba(0, 0, 0, 0.6);
    --page-glow:
        radial-gradient(52rem 34rem at 12% -8%, rgba(192, 77, 255, 0.20), transparent 60%),
        radial-gradient(46rem 30rem at 92% 4%, rgba(53, 224, 216, 0.16), transparent 62%);
    --container: 1120px;
}

/* ── 02 Nachtclub · volle Nacht ─────────────────────────────────── */
[data-brand="nachtclub"][data-theme="dark"] {
    --primary: #c04dff;
    --secondary: #35e0d8;
    --accent2: #35e0d8;
    --bg: #0b0b0f;
    --text: #b3aec2;

    --surface: #131218;
    --surface-alt: #1b1a22;
    --border: #272531;
    --heading: #ffffff;
    --muted: #7b7689;
    --on-primary: #0b0b0f;
    --sidebar-bg: #08080b;

    --success: #4fd9a4;
    --success-bg: #0f241e;
    --warning: #f5c451;
    --warning-bg: #272013;
    --danger: #ff6b8a;
    --danger-bg: #28131b;
    --info: #6fa8ff;
    --info-bg: #111a28;

    --font-heading: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 700;
    --heading-tracking: -0.02em;

    --radius: 18px;
    --radius-sm: 12px;
    --btn-radius: 999px;
    --btn-primary-bg: linear-gradient(100deg, #c04dff 0%, #35e0d8 100%);
    --shadow: 0 10px 30px rgba(0, 0, 0, 0.55);
    --shadow-lg: 0 18px 50px rgba(0, 0, 0, 0.7);
    --page-glow:
        radial-gradient(52rem 34rem at 12% -8%, rgba(192, 77, 255, 0.26), transparent 60%),
        radial-gradient(46rem 30rem at 92% 4%, rgba(53, 224, 216, 0.20), transparent 62%);
    --container: 1120px;
}

/* ── 04 DJ Dirk · gedämpft ──────────────────────────────────────
 *
 * Abgeleitet vom Moodboard auf djdirk.de: dunkle Räume, Magenta aus
 * der Lichtshow, warmes Gold vom Hochzeitslicht. Serifen in den
 * Überschriften wie im Salon – es geht meistens um Hochzeiten, und
 * eine Groteske wirkt dort nüchterner, als der Abend ist.
 *
 * Zwei Akzente statt einem: Magenta zieht den Blick (Knöpfe, „live"),
 * Gold trägt das Ruhige (Rahmen, Kennzeichen). Nur Magenta wäre auf
 * einer ganzen Seite laut; nur Gold wäre brav.
 *
 * Die Farbwerte sind aus den Fotos der Seite abgenommen, nicht aus
 * ihrem Stylesheet: Der Server gibt die CSS-Datei nicht heraus. Wer
 * die Originalwerte hat, ersetzt sie hier – an einer Stelle, und
 * beide Zustände unten mit.
 */
[data-brand="djdirk"] {
    --primary: #ff2e88;
    --secondary: #d8b26a;
    --accent2: #ff2e88;
    --bg: #17131b;
    --text: #c2b8c4;

    --surface: #201a25;
    --surface-alt: #2a222f;
    --border: #382e3e;
    --heading: #fbf6f2;
    --muted: #8d8292;
    --on-primary: #ffffff;
    --sidebar-bg: #130f16;

    --success: #4fd9a4;
    --success-bg: #142b24;
    --warning: #f5c451;
    --warning-bg: #2e2617;
    --danger: #ff6b8a;
    --danger-bg: #2f1720;
    --info: #6fa8ff;
    --info-bg: #16202f;

    --font-heading: 'Playfair Display', Georgia, 'Times New Roman', serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 600;
    --heading-tracking: 0;

    --radius: 16px;
    --radius-sm: 10px;
    --btn-radius: 999px;
    --btn-primary-bg: linear-gradient(100deg, #ff2e88 0%, #b4308f 100%);
    --shadow: 0 10px 30px rgba(0, 0, 0, 0.45);
    --shadow-lg: 0 18px 50px rgba(0, 0, 0, 0.6);
    --page-glow:
        radial-gradient(52rem 34rem at 10% -8%, rgba(255, 46, 136, 0.20), transparent 60%),
        radial-gradient(44rem 30rem at 90% 2%, rgba(216, 178, 106, 0.14), transparent 62%);
    --container: 1120px;
}

/* ── 04 DJ Dirk · volle Nacht ───────────────────────────────────── */
[data-brand="djdirk"][data-theme="dark"] {
    --primary: #ff2e88;
    --secondary: #d8b26a;
    --accent2: #ff2e88;
    --bg: #0e0b11;
    --text: #bdb2c0;

    --surface: #16121a;
    --surface-alt: #1f1923;
    --border: #2c2431;
    --heading: #ffffff;
    --muted: #857a8a;
    --on-primary: #ffffff;
    --sidebar-bg: #0a080c;

    --success: #4fd9a4;
    --success-bg: #0f241e;
    --warning: #f5c451;
    --warning-bg: #272013;
    --danger: #ff6b8a;
    --danger-bg: #28131b;
    --info: #6fa8ff;
    --info-bg: #111a28;

    --font-heading: 'Playfair Display', Georgia, 'Times New Roman', serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --heading-weight: 600;
    --heading-tracking: 0;

    --radius: 16px;
    --radius-sm: 10px;
    --btn-radius: 999px;
    --btn-primary-bg: linear-gradient(100deg, #ff2e88 0%, #b4308f 100%);
    --shadow: 0 10px 30px rgba(0, 0, 0, 0.55);
    --shadow-lg: 0 18px 50px rgba(0, 0, 0, 0.72);
    --page-glow:
        radial-gradient(52rem 34rem at 10% -8%, rgba(255, 46, 136, 0.26), transparent 60%),
        radial-gradient(44rem 30rem at 90% 2%, rgba(216, 178, 106, 0.18), transparent 62%);
    --container: 1120px;
}

/* ── 03 Studio · hell ───────────────────────────────────────────── */
[data-brand="studio"] {
    --primary: #17181a;
    --secondary: #ff5b1f;
    --accent2: #ff5b1f;
    --bg: #fbfbfa;
    --text: #4a4d52;

    --surface: #ffffff;
    --surface-alt: #f1f1ef;
    --border: #e2e2df;
    --heading: #17181a;
    --muted: #83868c;
    --on-primary: #ffffff;
    --sidebar-bg: #17181a;

    --success: #2f7d5c;
    --success-bg: #e3f1ea;
    --warning: #a8710f;
    --warning-bg: #f8eddb;
    --danger: #c0392b;
    --danger-bg: #fae5e2;
    --info: #2f6390;
    --info-bg: #e4eef6;

    --font-heading: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: ui-monospace, 'SFMono-Regular', 'Cascadia Mono', Menlo, Consolas, monospace;
    --heading-weight: 700;
    --heading-tracking: -0.03em;

    --radius: 10px;
    --radius-sm: 7px;
    --btn-radius: 7px;
    --btn-primary-bg: #17181a;
    --shadow: none;
    --shadow-lg: none;
    --page-glow: none;
    --container: 1120px;
}

/* ── 03 Studio · dunkel ─────────────────────────────────────────── */
[data-brand="studio"][data-theme="dark"] {
    --primary: #f4f4f2;
    --secondary: #ff6b33;
    --accent2: #ff6b33;
    --bg: #121314;
    --text: #b4b7bb;

    --surface: #1a1b1d;
    --surface-alt: #232426;
    --border: #2d2e31;
    --heading: #f7f7f5;
    --muted: #7f8288;
    --on-primary: #121314;
    --sidebar-bg: #0e0f10;

    --success: #63c79b;
    --success-bg: #16291f;
    --warning: #e0aa4e;
    --warning-bg: #2a2214;
    --danger: #ef7d6c;
    --danger-bg: #2c1a17;
    --info: #6aa7d8;
    --info-bg: #16222c;

    --font-heading: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-body: 'Noto Sans Display', 'Segoe UI', system-ui, sans-serif;
    --font-meta: ui-monospace, 'SFMono-Regular', 'Cascadia Mono', Menlo, Consolas, monospace;
    --heading-weight: 700;
    --heading-tracking: -0.03em;

    --radius: 10px;
    --radius-sm: 7px;
    --btn-radius: 7px;
    --btn-primary-bg: #f4f4f2;
    --shadow: none;
    --shadow-lg: none;
    --page-glow: none;
    --container: 1120px;
}

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

html { scroll-behavior: smooth; }

body {
    margin: 0;
    font-family: var(--font-body);
    font-size: 16.5px;
    line-height: 1.65;
    color: var(--text);
    background: var(--bg);
    background-image: var(--page-glow);
    background-repeat: no-repeat;
    background-attachment: fixed;
    -webkit-font-smoothing: antialiased;
    transition: background 0.25s ease, color 0.25s ease;
}

h1, h2, h3, h4 {
    font-family: var(--font-heading);
    color: var(--heading);
    line-height: 1.2;
    margin: 0 0 0.6em;
    font-weight: var(--heading-weight);
    letter-spacing: var(--heading-tracking);
}

p { margin: 0 0 1em; }

a { color: var(--primary); text-decoration-color: var(--secondary); text-underline-offset: 3px; }
a:hover { color: var(--secondary); }

img, svg { vertical-align: middle; }

code {
    font-family: ui-monospace, 'Cascadia Code', Menlo, monospace;
    background: var(--surface-alt);
    padding: 0.15em 0.45em;
    border-radius: 6px;
    font-size: 0.92em;
}

.container { max-width: var(--container); margin: 0 auto; padding: 0 22px; }
.container.narrow { max-width: 760px; }
.center { text-align: center; }

/* ── Header ─────────────────────────────────────────────────────── */
.site-header {
    position: sticky;
    top: 0;
    z-index: 50;
    background: color-mix(in srgb, var(--bg) 88%, transparent);
    backdrop-filter: blur(10px);
    border-bottom: 1px solid var(--border);
}

.header-inner {
    display: flex;
    align-items: center;
    gap: 26px;
    min-height: 68px;
}

.brand {
    display: flex;
    align-items: center;
    gap: 10px;
    text-decoration: none;
    color: var(--heading);
}

.brand-mark { color: var(--secondary); display: inline-flex; }

/* Das Signet ist eine Schallplatte – also dreht es sich, dauerhaft und so
   langsam, dass es beim Lesen nicht stört. Wer Bewegung abgestellt hat,
   sieht es still (Regel weiter unten bei prefers-reduced-motion). */
.brand-mark svg {
    animation: djd-spin 18s linear infinite;
    transform-origin: 50% 50%;
}

.brand-name {
    font-family: var(--font-heading);
    font-weight: 700;
    font-size: 1.35rem;
    letter-spacing: 0.4px;
    color: var(--heading);
}
.brand-name span { color: var(--secondary); }

.main-nav { display: flex; gap: 22px; margin-left: 8px; }
.main-nav a {
    text-decoration: none;
    color: var(--text);
    font-weight: 500;
    font-size: 0.98rem;
}
.main-nav a:hover { color: var(--heading); }

.header-actions { margin-left: auto; display: flex; align-items: center; gap: 10px; }
.inline-form { display: inline; }

.icon-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 38px; height: 38px;
    border-radius: 50%;
    border: 1px solid var(--border);
    background: var(--surface);
    color: var(--text);
    cursor: pointer;
    transition: border-color 0.2s ease, color 0.2s ease;
}
.icon-btn:hover { border-color: var(--secondary); color: var(--heading); }

[data-theme="dark"] .icon-sun { display: block; }
[data-theme="dark"] .icon-moon { display: none; }
[data-theme="light"] .icon-sun, html:not([data-theme="dark"]) .icon-sun { display: none; }
[data-theme="light"] .icon-moon, html:not([data-theme="dark"]) .icon-moon { display: block; }
[data-theme="dark"] .icon-moon { display: none; }
[data-theme="dark"] .icon-sun { display: block; }

.nav-toggle { display: none; }

/* ── Buttons ────────────────────────────────────────────────────── */
.btn {
    display: inline-block;
    padding: 11px 22px;
    border-radius: var(--btn-radius);
    border: 1.5px solid transparent;
    font-family: var(--font-body);
    font-size: 0.98rem;
    font-weight: 600;
    text-decoration: none;
    cursor: pointer;
    transition: transform 0.15s ease, box-shadow 0.2s ease, background 0.2s ease, color 0.2s ease, border-color 0.2s ease;
}
.btn:hover { transform: translateY(-1px); }

.btn-primary { background: var(--btn-primary-bg); color: var(--on-primary); box-shadow: var(--shadow); }
/* filter statt color-mix: --btn-primary-bg ist im Nachtclub ein Verlauf,
   den color-mix nicht verarbeiten kann. */
.btn-primary:hover { filter: brightness(1.08) saturate(1.05); color: var(--on-primary); }

.btn-outline { background: transparent; color: var(--heading); border-color: var(--secondary); }
.btn-outline:hover { background: var(--secondary); color: var(--on-primary); }

.btn-ghost { background: transparent; color: var(--text); }
.btn-ghost:hover { color: var(--heading); }

.btn-lg { padding: 14px 30px; font-size: 1.05rem; }
.btn-sm { padding: 8px 16px; font-size: 0.9rem; }
.btn-block { display: block; width: 100%; text-align: center; }

/* ── Flash-Meldungen ────────────────────────────────────────────── */
/* Hinweiskästen innerhalb einer Karte – gleiche Farbsprache wie die
   Flash-Meldungen, aber ortsgebunden: sie gehören zum Inhalt, nicht zur
   letzten Aktion. */
.msg {
    padding: 13px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid transparent;
    margin: 0 0 16px;
    line-height: 1.55;
}
.msg:last-child { margin-bottom: 0; }
.msg-ok { background: var(--success-bg); color: var(--success); border-color: color-mix(in srgb, var(--success) 30%, transparent); }
.msg-err { background: var(--danger-bg); color: var(--danger); border-color: color-mix(in srgb, var(--danger) 30%, transparent); }
.msg-warn { background: var(--warning-bg); color: var(--warning); border-color: color-mix(in srgb, var(--warning) 30%, transparent); }
.msg-info { background: var(--info-bg); color: var(--info); border-color: color-mix(in srgb, var(--info) 30%, transparent); }

.flash-stack { margin-top: 18px; display: grid; gap: 10px; }

.flash {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 14px;
    padding: 13px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid transparent;
    font-weight: 500;
    animation: flash-in 0.3s ease;
}
@keyframes flash-in { from { opacity: 0; transform: translateY(-6px); } }

.flash-success { background: var(--success-bg); color: var(--success); border-color: color-mix(in srgb, var(--success) 30%, transparent); }
.flash-danger { background: var(--danger-bg); color: var(--danger); border-color: color-mix(in srgb, var(--danger) 30%, transparent); }
.flash-warning { background: var(--warning-bg); color: var(--warning); border-color: color-mix(in srgb, var(--warning) 30%, transparent); }
.flash-info { background: var(--info-bg); color: var(--info); border-color: color-mix(in srgb, var(--info) 30%, transparent); }

.flash-close {
    background: none; border: none; cursor: pointer;
    font-size: 1.3rem; line-height: 1; color: inherit; opacity: 0.6;
}
.flash-close:hover { opacity: 1; }

/* ── Hero ───────────────────────────────────────────────────────── */
.hero {
    position: relative;
    padding: 110px 0 120px;
    overflow: hidden;
    background:
        radial-gradient(ellipse 900px 480px at 82% -10%, color-mix(in srgb, var(--secondary) 30%, transparent), transparent 65%),
        radial-gradient(ellipse 700px 420px at 8% 110%, color-mix(in srgb, var(--secondary) 18%, transparent), transparent 60%);
}

.hero-inner { max-width: 780px; }

.hero h1 {
    font-size: clamp(2.4rem, 5.4vw, 4rem);
    font-weight: 700;
    margin-bottom: 0.4em;
}

.eyebrow {
    text-transform: uppercase;
    letter-spacing: 3px;
    font-size: 0.8rem;
    font-weight: 700;
    color: var(--secondary);
    margin-bottom: 12px;
}
.eyebrow.center { text-align: center; }

.lead { font-size: 1.14rem; max-width: 620px; }
.lead-sm { font-size: 1.02rem; color: var(--muted); }
.center .lead, .center.lead { margin-left: auto; margin-right: auto; }

.hero-actions { display: flex; gap: 14px; flex-wrap: wrap; margin-top: 30px; }

/* ── Sektionen ──────────────────────────────────────────────────── */
.section { padding: 84px 0; }
.section-alt { background: color-mix(in srgb, var(--surface-alt) 55%, var(--bg)); }
.section-title { font-size: clamp(1.7rem, 3.4vw, 2.4rem); margin-bottom: 40px; }
.page-title { font-size: clamp(1.9rem, 4vw, 2.7rem); }

.cta-section {
    background:
        radial-gradient(ellipse 700px 340px at 50% 120%, color-mix(in srgb, var(--secondary) 26%, transparent), transparent 65%);
}

/* ── Cards ──────────────────────────────────────────────────────── */
.card-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(250px, 100%), 1fr));
    gap: 22px;
    margin-top: 30px;
}
.card-grid.three { grid-template-columns: repeat(auto-fit, minmax(min(270px, 100%), 1fr)); }

.card {
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    padding: 30px 28px;
    box-shadow: var(--shadow);
    transition: transform 0.2s ease, box-shadow 0.2s ease;
}
.card:hover { transform: translateY(-3px); box-shadow: var(--shadow-lg); }

.card h3 { font-size: 1.25rem; margin-bottom: 10px; }

.card-icon {
    width: 52px; height: 52px;
    display: flex; align-items: center; justify-content: center;
    border-radius: 14px;
    background: color-mix(in srgb, var(--secondary) 18%, transparent);
    color: var(--secondary);
    margin-bottom: 18px;
}

.card-highlight { border-color: var(--secondary); box-shadow: var(--shadow-lg); margin-bottom: 22px; }

/* Preis-Karten */
.price-card { position: relative; text-align: center; }
.price-featured { border-color: var(--secondary); }

.ribbon {
    position: absolute;
    top: -13px; left: 50%;
    transform: translateX(-50%);
    background: var(--secondary);
    color: var(--on-primary);
    font-size: 0.78rem;
    font-weight: 700;
    letter-spacing: 1.5px;
    text-transform: uppercase;
    padding: 4px 16px;
    border-radius: 999px;
}

.price-tag {
    font-family: var(--font-heading);
    font-size: 2rem;
    color: var(--heading);
    margin: 6px 0 18px;
}

.feature-list { list-style: none; padding: 0; margin: 0 0 20px; }
.feature-list li { padding: 7px 0; border-bottom: 1px dashed var(--border); }
.feature-list li:last-child { border-bottom: none; }

/* ── Ablauf-Schritte ────────────────────────────────────────────── */
.steps {
    list-style: none;
    counter-reset: step;
    padding: 0;
    margin: 34px 0 0;
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(220px, 100%), 1fr));
    gap: 26px;
}

.steps li { position: relative; padding-top: 8px; }

.step-num {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 46px; height: 46px;
    border-radius: 50%;
    background: var(--primary);
    color: var(--on-primary);
    font-family: var(--font-heading);
    font-size: 1.25rem;
    font-weight: 700;
    margin-bottom: 14px;
}

.steps h3 { font-size: 1.12rem; margin-bottom: 6px; }
.steps p { font-size: 0.97rem; color: var(--muted); }

/* ── FAQ ────────────────────────────────────────────────────────── */
.faq-item {
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    padding: 4px 22px;
    margin-bottom: 12px;
}

.faq-item summary {
    cursor: pointer;
    font-weight: 600;
    color: var(--heading);
    padding: 14px 0;
    list-style: none;
    position: relative;
    padding-right: 30px;
}
.faq-item summary::-webkit-details-marker { display: none; }
.faq-item summary::after {
    content: '+';
    position: absolute;
    right: 2px; top: 50%;
    transform: translateY(-50%);
    font-size: 1.4rem;
    color: var(--secondary);
    transition: transform 0.2s ease;
}
.faq-item[open] summary::after { content: '–'; }
.faq-item p { padding-bottom: 16px; }

/* ── Formulare ──────────────────────────────────────────────────── */
.form-group { margin-bottom: 18px; }
.form-row.two { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; }

label { display: block; font-weight: 600; font-size: 0.94rem; margin-bottom: 7px; color: var(--heading); }
label small { font-weight: 400; color: var(--muted); }

input[type="text"], input[type="email"], input[type="password"], input[type="tel"], select, textarea {
    width: 100%;
    padding: 12px 15px;
    font-family: var(--font-body);
    font-size: 1rem;
    color: var(--heading);
    background: var(--surface);
    border: 1.5px solid var(--border);
    border-radius: var(--radius-sm);
    transition: border-color 0.2s ease, box-shadow 0.2s ease;
}

input:focus, select:focus, textarea:focus {
    outline: none;
    border-color: var(--secondary);
    box-shadow: 0 0 0 3px color-mix(in srgb, var(--secondary) 25%, transparent);
}

.form-error { color: var(--danger); font-size: 0.88rem; margin: 6px 0 0; font-weight: 500; }

.form-check label { display: flex; gap: 10px; align-items: flex-start; font-weight: 400; color: var(--text); }
.form-check input { margin-top: 4px; accent-color: var(--secondary); }

.password-wrap { position: relative; }
.password-wrap input { padding-right: 46px; }
.password-toggle {
    position: absolute;
    right: 6px; top: 50%;
    transform: translateY(-50%);
    background: none; border: none;
    cursor: pointer;
    font-size: 1rem;
    opacity: 0.55;
    padding: 6px;
}
.password-toggle:hover { opacity: 1; }

.code-input { letter-spacing: 3px; font-size: 1.15rem; text-align: center; }

.inline-confirm { display: flex; gap: 10px; margin-top: 10px; }
.inline-confirm input { max-width: 220px; }

/* ── Auth-Karten ────────────────────────────────────────────────── */
.auth-section { display: flex; justify-content: center; padding: 70px 22px; }

.auth-card {
    width: 100%;
    max-width: 480px;
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    box-shadow: var(--shadow-lg);
    padding: 42px 38px;
}

.auth-title { font-size: 1.75rem; margin-bottom: 6px; }
.auth-sub { color: var(--muted); margin-bottom: 26px; font-size: 0.98rem; }
.auth-alt { text-align: center; margin-top: 22px; font-size: 0.95rem; color: var(--muted); }

/* ── Dashboard / Konto ──────────────────────────────────────────── */
.status-list { list-style: none; padding: 0; margin: 0 0 18px; }
.status-list li {
    display: flex;
    justify-content: space-between;
    align-items: center;
    gap: 12px;
    padding: 10px 0;
    border-bottom: 1px dashed var(--border);
}
.status-list li:last-child { border-bottom: none; }

.badge {
    display: inline-block;
    padding: 4px 12px;
    border-radius: 999px;
    font-size: 0.82rem;
    font-weight: 600;
    background: var(--surface-alt);
    color: var(--text);
    text-decoration: none;
}
.badge-success { background: var(--success-bg); color: var(--success); }
.badge-warning { background: var(--warning-bg); color: var(--warning); }
.badge-muted { background: var(--surface-alt); color: var(--muted); }
a.badge:hover { filter: brightness(0.96); }

.recovery-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(130px, 100%), 1fr));
    gap: 10px;
    margin: 16px 0;
}
.recovery-grid code { padding: 9px 12px; text-align: center; font-size: 1rem; letter-spacing: 1px; }

.secret-box { margin: 10px 0; }
.secret-box code { display: inline-block; padding: 10px 14px; font-size: 1.02rem; letter-spacing: 1px; }

.setup-steps { padding-left: 22px; }
.setup-steps li { margin-bottom: 22px; }

/*
 * Der QR-Code braucht seinen hellen Grund. Im Nachtmodus ist die Karte
 * dunkel – ein Code ohne weiße Fläche drumherum wäre dort für jede
 * Kamera unlesbar, weil sie die Ecken nicht findet. Deshalb steht das
 * Weiß hier fest und folgt NICHT den Farbtokens.
 */
.qr-box {
    display: inline-block;
    margin: 14px 0 4px;
    padding: 10px;
    background: #ffffff;
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    line-height: 0;
    max-width: 100%;
}
.qr-box svg {
    display: block;
    width: 260px;
    max-width: 100%;
    height: auto;
}
.hint { font-size: 0.88rem; color: var(--muted); margin-top: 6px; }
.stack-sm > * + * { margin-top: 10px; }

/* ── Rechtstexte ────────────────────────────────────────────────── */
.legal h2 { font-size: 1.25rem; margin-top: 1.8em; }
.todo-note {
    background: var(--warning-bg);
    color: var(--warning);
    border-radius: var(--radius-sm);
    padding: 12px 16px;
    font-weight: 600;
}

/* ── Footer ─────────────────────────────────────────────────────── */
.site-footer {
    border-top: 1px solid var(--border);
    padding: 46px 0 38px;
    margin-top: 40px;
    background: color-mix(in srgb, var(--surface-alt) 40%, var(--bg));
}

.footer-inner {
    display: grid;
    grid-template-columns: 1.4fr 1fr auto;
    gap: 30px;
    align-items: start;
}

.footer-brand p { color: var(--muted); font-size: 0.95rem; max-width: 340px; margin-top: 8px; }
.footer-nav { display: flex; flex-direction: column; gap: 8px; }
.footer-nav a { text-decoration: none; color: var(--text); font-size: 0.95rem; }
.footer-nav a:hover { color: var(--heading); }
.footer-copy { color: var(--muted); font-size: 0.9rem; margin: 0; }
.footer-version {
    display: inline-block;
    margin-left: 8px;
    padding: 1px 8px;
    border-radius: 999px;
    background: var(--surface-alt);
    font-size: 0.78rem;
    letter-spacing: 0.5px;
    cursor: help;
}

/* ── Responsive ─────────────────────────────────────────────────── */
@media (max-width: 860px) {
    .main-nav {
        display: none;
        position: absolute;
        top: 68px; left: 0; right: 0;
        flex-direction: column;
        gap: 0;
        background: var(--bg);
        border-bottom: 1px solid var(--border);
        padding: 8px 22px 16px;
    }
    .main-nav.open { display: flex; }
    .main-nav a { padding: 12px 0; border-bottom: 1px dashed var(--border); }
    .main-nav a:last-child { border-bottom: none; }

    .nav-toggle { display: inline-flex; }
    .btn-ghost { display: none; }

    .hero { padding: 70px 0 80px; }
    .section { padding: 60px 0; }

    .form-row.two { grid-template-columns: 1fr; }
    .footer-inner { grid-template-columns: 1fr; gap: 20px; }
    .auth-card { padding: 32px 24px; }
}

/* ════════════════════════════════════════════════════════════════
   Eventmanager (ab v0.2.0)
   ════════════════════════════════════════════════════════════════ */

.page-head {
    display: flex;
    align-items: flex-end;
    justify-content: space-between;
    gap: 20px;
    flex-wrap: wrap;
    margin-bottom: 26px;
}
.page-head .page-title { margin-bottom: 4px; }
.head-actions { display: flex; align-items: center; gap: 10px; }

.breadcrumb { font-size: 0.9rem; color: var(--muted); margin-bottom: 10px; }
.breadcrumb a { color: var(--muted); text-decoration: none; }
.breadcrumb a:hover { color: var(--heading); }
.breadcrumb span { margin: 0 6px; opacity: 0.5; }

.list-heading {
    font-size: 1.15rem;
    margin: 34px 0 14px;
    padding-bottom: 8px;
    border-bottom: 1px solid var(--border);
}

.back-link { margin-top: 34px; font-size: 0.95rem; }

/* ── Kennzahlen ── */
.stat-row {
    display: flex;
    gap: 14px;
    flex-wrap: wrap;
    margin-bottom: 8px;
}
.stat {
    flex: 1;
    min-width: 130px;
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    padding: 16px 18px;
}
.stat-value {
    display: block;
    font-family: var(--font-heading);
    font-size: 1.9rem;
    color: var(--heading);
    line-height: 1.1;
}
.stat-label { font-size: 0.88rem; color: var(--muted); }

/* ── Eventliste ── */
.event-list { display: grid; gap: 12px; }
.event-list.is-past { opacity: 0.72; }
.event-list.is-compact { margin-top: 14px; }

.event-card {
    display: flex;
    align-items: center;
    gap: 18px;
    padding: 16px 20px;
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    text-decoration: none;
    color: inherit;
    transition: transform 0.15s ease, box-shadow 0.2s ease, border-color 0.2s ease;
}
.event-card:hover {
    transform: translateY(-2px);
    box-shadow: var(--shadow);
    border-color: var(--secondary);
    color: inherit;
}

.event-date {
    flex: none;
    width: 62px;
    text-align: center;
    padding: 8px 0;
    background: color-mix(in srgb, var(--secondary) 16%, transparent);
    border-radius: var(--radius-sm);
    line-height: 1.15;
}
.event-day { display: block; font-family: var(--font-heading); font-size: 1.5rem; color: var(--heading); }
.event-month { display: block; font-size: 0.75rem; font-weight: 700; letter-spacing: 1px; color: var(--secondary); }
.event-year { display: block; font-size: 0.7rem; color: var(--muted); }

.event-body { flex: 1; min-width: 0; }
.event-body h3 { font-size: 1.1rem; margin: 0 0 3px; }
.event-meta { font-size: 0.9rem; color: var(--muted); margin: 0; }
.event-location { font-size: 0.86rem; color: var(--muted); margin: 3px 0 0; opacity: 0.85; }

.event-side { flex: none; text-align: right; display: grid; gap: 6px; justify-items: end; }
.event-countdown { font-size: 0.82rem; color: var(--muted); }

/* ── Leerzustand ── */
.empty-state {
    text-align: center;
    padding: 60px 24px;
    background: var(--surface);
    border: 1px dashed var(--border);
    border-radius: var(--radius);
}
.empty-icon {
    width: 72px; height: 72px;
    margin: 0 auto 20px;
    display: flex; align-items: center; justify-content: center;
    border-radius: 50%;
    background: color-mix(in srgb, var(--secondary) 18%, transparent);
    color: var(--secondary);
}
.empty-state h2 { font-size: 1.35rem; margin-bottom: 8px; }
.empty-state p { max-width: 430px; margin: 0 auto 22px; color: var(--muted); }

/* ── Detailansicht ── */
.detail-grid {
    display: grid;
    grid-template-columns: minmax(0, 1.7fr) minmax(min(260px, 100%), 1fr);
    gap: 20px;
    align-items: start;
}
.detail-main, .detail-side { display: grid; gap: 18px; }

.card-title { font-size: 1.15rem; margin-bottom: 14px; }
.card-title-row { display: flex; align-items: center; justify-content: space-between; gap: 12px; flex-wrap: wrap; }
.card-danger { border-color: color-mix(in srgb, var(--danger) 35%, var(--border)); }

.countdown-banner {
    background: color-mix(in srgb, var(--secondary) 18%, transparent);
    border-radius: var(--radius-sm);
    padding: 13px 18px;
    margin-bottom: 22px;
    font-size: 0.98rem;
}

.fact-list { display: grid; grid-template-columns: auto 1fr; gap: 8px 16px; margin: 0; font-size: 0.94rem; }
.fact-list dt { color: var(--muted); }
.fact-list dd { margin: 0; color: var(--heading); font-weight: 500; }

.muted-text { color: var(--muted); font-size: 0.92rem; }
.preserve-lines { white-space: pre-line; }

/* ── Phasen ── */
.phase-list { list-style: none; counter-reset: phase; padding: 0; margin: 0 0 18px; }
.phase-item {
    position: relative;
    padding: 14px 0 14px 34px;
    border-bottom: 1px dashed var(--border);
}
.phase-item:last-child { border-bottom: none; }
.phase-item::before {
    counter-increment: phase;
    content: counter(phase);
    position: absolute;
    left: 0; top: 16px;
    width: 24px; height: 24px;
    display: flex; align-items: center; justify-content: center;
    border-radius: 50%;
    background: var(--primary);
    color: var(--on-primary);
    font-size: 0.78rem;
    font-weight: 700;
}

.phase-head { display: flex; align-items: flex-start; justify-content: space-between; gap: 14px; flex-wrap: wrap; }
.phase-head h3 { font-size: 1.05rem; margin: 0 0 2px; }
.phase-time { font-size: 0.88rem; color: var(--muted); margin: 0; }

.phase-controls { display: flex; align-items: center; gap: 8px; }
.energy-meter {
    width: 78px; height: 7px;
    background: var(--surface-alt);
    border-radius: 999px;
    overflow: hidden;
}
.energy-fill { display: block; height: 100%; background: var(--secondary); border-radius: 999px; }
.energy-value { font-size: 0.8rem; color: var(--muted); min-width: 34px; }

.phase-notes { font-size: 0.9rem; margin: 8px 0 0; color: var(--text); }
.phase-actions { display: flex; gap: 12px; align-items: center; margin-top: 8px; flex-wrap: wrap; }

.link-btn {
    background: none; border: none; padding: 0;
    font: inherit; font-size: 0.86rem; font-weight: 600;
    color: var(--muted); cursor: pointer; text-decoration: underline;
    text-underline-offset: 3px; text-decoration-color: var(--border);
}
.link-btn:hover { color: var(--heading); }
.link-danger { color: var(--danger); }
.link-danger:hover { color: var(--danger); opacity: 0.8; }

.phase-form {
    margin-top: 14px;
    padding: 16px;
    background: color-mix(in srgb, var(--surface-alt) 45%, transparent);
    border-radius: var(--radius-sm);
}
.phase-form.is-hidden { display: none; }

.add-phase { border-top: 1px solid var(--border); padding-top: 14px; }
.add-phase summary {
    cursor: pointer; font-weight: 600; color: var(--heading);
    list-style: none; padding: 4px 0;
}
.add-phase summary::-webkit-details-marker { display: none; }
.add-phase form { margin-top: 14px; }

.range-input { width: 100%; accent-color: var(--secondary); }
.range-out { font-weight: 400; color: var(--muted); }

/* ── Formularerweiterungen ── */
.form-row.three { display: grid; grid-template-columns: repeat(3, 1fr); gap: 16px; }
.form-row.four { display: grid; grid-template-columns: repeat(4, 1fr); gap: 14px; }
.form-row.zip-city { display: grid; grid-template-columns: 130px 1fr; gap: 16px; }

textarea {
    resize: vertical;
    min-height: 84px;
    font-family: var(--font-body);
}
input[type="date"], input[type="time"], input[type="number"] {
    width: 100%;
    padding: 12px 15px;
    font-family: var(--font-body);
    font-size: 1rem;
    color: var(--heading);
    background: var(--surface);
    border: 1.5px solid var(--border);
    border-radius: var(--radius-sm);
}
input[type="date"]:focus, input[type="time"]:focus, input[type="number"]:focus {
    outline: none;
    border-color: var(--secondary);
    box-shadow: 0 0 0 3px color-mix(in srgb, var(--secondary) 25%, transparent);
}

.form-actions { display: flex; gap: 12px; align-items: center; flex-wrap: wrap; margin-top: 6px; }

/* ── Chips (Musikrichtungen) ── */
.chip-group { display: flex; flex-wrap: wrap; gap: 8px; }
.chip { cursor: pointer; }
.chip input { position: absolute; opacity: 0; width: 0; height: 0; }
.chip span {
    display: inline-block;
    padding: 7px 15px;
    border-radius: 999px;
    border: 1.5px solid var(--border);
    background: var(--surface);
    font-size: 0.9rem;
    transition: all 0.15s ease;
}
.chip input:checked + span {
    background: var(--primary);
    border-color: var(--primary);
    color: var(--on-primary);
}
.chip input:focus-visible + span { box-shadow: 0 0 0 3px color-mix(in srgb, var(--secondary) 35%, transparent); }
.chip:hover span { border-color: var(--secondary); }

.chip-static {
    display: inline-block;
    padding: 6px 14px;
    border-radius: 999px;
    background: color-mix(in srgb, var(--secondary) 18%, transparent);
    font-size: 0.88rem;
    color: var(--heading);
}

.badge-info { background: var(--info-bg); color: var(--info); }
.badge-danger { background: var(--danger-bg); color: var(--danger); }
.btn-danger { border-color: color-mix(in srgb, var(--danger) 45%, transparent); color: var(--danger); }
.btn-danger:hover { background: var(--danger); color: #fff; }

@media (max-width: 860px) {
    .detail-grid { grid-template-columns: 1fr; }
    .form-row.three, .form-row.four { grid-template-columns: 1fr 1fr; }
    .event-card { flex-wrap: wrap; }
    .event-side { text-align: left; justify-items: start; }
}
@media (max-width: 520px) {
    .form-row.three, .form-row.four, .form-row.zip-city { grid-template-columns: 1fr; }
}

/* ════════════════════════════════════════════════════════════════
   Verwaltungsbereich (ab v0.3.0)
   ════════════════════════════════════════════════════════════════ */

.admin-body { background: color-mix(in srgb, var(--surface-alt) 40%, var(--bg)); }

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

/* ── Seitenleiste ── */
.admin-sidebar {
    flex: none;
    width: 246px;
    background: var(--sidebar-bg);
    color: color-mix(in srgb, #ffffff 78%, transparent);
    display: flex;
    flex-direction: column;
    padding: 22px 16px;
    position: sticky;
    top: 0;
    height: 100vh;
}

.admin-brand {
    display: flex;
    align-items: center;
    gap: 11px;
    text-decoration: none;
    color: var(--on-primary);
    padding: 4px 8px 20px;
    border-bottom: 1px solid rgba(255, 255, 255, 0.12);
    margin-bottom: 16px;
}
.admin-brand .brand-name { color: #ffffff; font-size: 1.15rem; display: block; }
.admin-brand .brand-name span { color: var(--secondary); }
.admin-brand small { font-size: 0.74rem; letter-spacing: 2px; text-transform: uppercase; opacity: 0.65; }
.admin-brand .brand-mark { color: var(--secondary); }

.admin-nav { display: grid; gap: 3px; }
.admin-nav a {
    display: flex;
    align-items: center;
    gap: 11px;
    padding: 10px 12px;
    border-radius: var(--radius-sm);
    text-decoration: none;
    color: inherit;
    font-size: 0.95rem;
    font-weight: 500;
    transition: background 0.15s ease, color 0.15s ease;
}
.admin-nav a:hover { background: rgba(255, 255, 255, 0.09); color: #ffffff; }
.admin-nav a.is-active { background: var(--secondary); color: var(--on-primary); font-weight: 600; }
.admin-nav svg { flex: none; opacity: 0.85; }

.admin-sidebar-foot { margin-top: auto; padding-top: 18px; border-top: 1px solid rgba(255, 255, 255, 0.12); }
.admin-side-link {
    display: block;
    padding: 6px 12px;
    font-size: 0.88rem;
    text-decoration: none;
    color: inherit;
    opacity: 0.8;
}
.admin-side-link:hover { opacity: 1; color: #ffffff; }
.admin-version { padding: 10px 12px 0; font-size: 0.76rem; opacity: 0.55; margin: 0; }

/* ── Hauptbereich ── */
.admin-main { flex: 1; min-width: 0; display: flex; flex-direction: column; }

.admin-topbar {
    display: flex;
    align-items: center;
    gap: 14px;
    padding: 14px 26px;
    background: var(--surface);
    border-bottom: 1px solid var(--border);
    position: sticky;
    top: 0;
    z-index: 20;
}
.admin-topbar-title { font-size: 1.2rem; margin: 0; }
.admin-topbar-actions { margin-left: auto; display: flex; align-items: center; gap: 10px; }
.admin-user { font-size: 0.9rem; color: var(--muted); }
.admin-menu-toggle { display: none; }

.admin-flash { padding: 16px 26px 0; margin: 0; }
.admin-content { padding: 24px 26px 60px; }

.admin-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(340px, 100%), 1fr));
    gap: 18px;
    align-items: start;
}
.admin-wide { grid-column: 1 / -1; }

/* ── Kennzahlen ── */
.metric-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(190px, 100%), 1fr));
    gap: 14px;
    margin-bottom: 20px;
}
.metric {
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    padding: 18px 20px;
}
.metric-label { display: block; font-size: 0.8rem; text-transform: uppercase; letter-spacing: 1.5px; color: var(--secondary); font-weight: 700; }
.metric-value { display: block; font-family: var(--font-heading); font-size: 2.1rem; color: var(--heading); line-height: 1.2; margin: 4px 0 2px; }
.metric-sub { font-size: 0.85rem; color: var(--muted); }

/* ── Hinweise ── */
.notice {
    padding: 13px 18px;
    border-radius: var(--radius-sm);
    margin-bottom: 16px;
    font-size: 0.95rem;
    border: 1px solid transparent;
}
.notice-warning { background: var(--warning-bg); color: var(--warning); border-color: color-mix(in srgb, var(--warning) 30%, transparent); }
.notice-danger { background: var(--danger-bg); color: var(--danger); border-color: color-mix(in srgb, var(--danger) 30%, transparent); }
.notice-info { background: var(--info-bg); color: var(--info); border-color: color-mix(in srgb, var(--info) 30%, transparent); }
.notice a { color: inherit; font-weight: 600; }

/* ── Tabellen ── */
.table-scroll { overflow-x: auto; margin: 0 -4px; }
.data-table { width: 100%; border-collapse: collapse; font-size: 0.92rem; }
.data-table th {
    text-align: left;
    font-size: 0.78rem;
    text-transform: uppercase;
    letter-spacing: 1px;
    color: var(--muted);
    font-weight: 700;
    padding: 8px 10px;
    border-bottom: 1.5px solid var(--border);
    white-space: nowrap;
}
.data-table td { padding: 10px; border-bottom: 1px solid var(--border); vertical-align: top; }
.data-table tr:last-child td { border-bottom: none; }
.data-table.striped tbody tr:nth-child(odd) { background: color-mix(in srgb, var(--surface-alt) 30%, transparent); }
.data-table a { font-weight: 500; }
.data-table .num { text-align: right; }
.data-table .nowrap { white-space: nowrap; }
.cell-sub { display: block; font-size: 0.82rem; color: var(--muted); }
.meta-cell { max-width: 300px; overflow-wrap: anywhere; font-size: 0.84rem; }
.action-code { font-size: 0.82rem; background: var(--surface-alt); }

/* ── Filter und Blättern ── */
.filter-bar {
    display: flex;
    gap: 10px;
    flex-wrap: wrap;
    align-items: center;
    margin-bottom: 16px;
    padding-bottom: 16px;
    border-bottom: 1px solid var(--border);
}
.filter-bar input[type="search"] {
    flex: 1;
    min-width: 200px;
    padding: 9px 14px;
    font-family: var(--font-body);
    font-size: 0.95rem;
    color: var(--heading);
    background: var(--surface);
    border: 1.5px solid var(--border);
    border-radius: var(--radius-sm);
}
.filter-bar select { width: auto; padding: 9px 12px; font-size: 0.95rem; }
.filter-bar input:focus, .filter-bar select:focus {
    outline: none;
    border-color: var(--secondary);
    box-shadow: 0 0 0 3px color-mix(in srgb, var(--secondary) 25%, transparent);
}

.result-count { font-size: 0.88rem; color: var(--muted); margin-bottom: 10px; }

.pagination { display: flex; align-items: center; gap: 14px; justify-content: center; margin-top: 18px; }
.page-info { font-size: 0.88rem; color: var(--muted); }

.mini-title { font-size: 0.82rem; text-transform: uppercase; letter-spacing: 1.2px; color: var(--muted); margin: 18px 0 8px; }
.admin-actions { display: grid; gap: 18px; }
.admin-actions button[disabled] { opacity: 0.45; cursor: not-allowed; }
.admin-link { color: var(--secondary) !important; font-weight: 600; }

@media (max-width: 900px) {
    .admin-sidebar {
        position: fixed;
        left: 0; top: 0; bottom: 0;
        z-index: 60;
        transform: translateX(-100%);
        transition: transform 0.22s ease;
        box-shadow: var(--shadow-lg);
    }
    .admin-sidebar.is-open { transform: translateX(0); }
    .admin-menu-toggle { display: inline-flex; }
    .admin-content { padding: 18px 16px 50px; }
    .admin-topbar { padding: 12px 16px; }
    .admin-user { display: none; }
}

/* ── Auswahl des Erscheinungsbilds (Verwaltung → Einstellungen) ──── */
.form-label {
    display: block;
    font-weight: 600;
    font-size: 0.94rem;
    margin: 0 0 6px;
    color: var(--heading);
}

.brand-choice {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(200px, 100%), 1fr));
    gap: 12px;
    margin-top: 12px;
}

.brand-option { cursor: pointer; margin: 0; }
.brand-option input { position: absolute; opacity: 0; width: 0; height: 0; }

.brand-option-body {
    display: block;
    height: 100%;
    padding: 14px 16px 16px;
    border: 1.5px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--surface);
    transition: border-color 0.18s ease, box-shadow 0.18s ease;
}

.brand-option-body strong { display: block; font-size: 1.02rem; color: var(--heading); }
.brand-option-body small { display: block; margin-top: 4px; font-size: 0.85rem; color: var(--muted); line-height: 1.45; }

.brand-swatches { display: flex; gap: 5px; margin-bottom: 10px; }
.brand-swatches span {
    width: 22px;
    height: 22px;
    border-radius: 50%;
    border: 1px solid rgba(0, 0, 0, 0.12);
}

.brand-option:hover .brand-option-body { border-color: var(--secondary); }

/* Auswahl schon vor dem Speichern sichtbar – ohne eine Zeile JavaScript */
.brand-option:has(input:checked) .brand-option-body {
    border-color: var(--secondary);
    box-shadow: 0 0 0 2px color-mix(in srgb, var(--secondary) 35%, transparent);
}

.brand-option input:focus-visible + .brand-option-body { outline: 2px solid var(--secondary); outline-offset: 2px; }

/* Im Nachtclub und bei DJ Dirk läuft der zweite Wortteil farbig aus –
   die Wortmarke selbst bleibt unverändert, nur ihre Farbe folgt der
   Welt. */
[data-brand="nachtclub"] .brand-name span {
    background: linear-gradient(100deg, #c04dff 0%, #35e0d8 100%);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

[data-brand="djdirk"] .brand-name span {
    background: linear-gradient(100deg, #ff2e88 0%, #d8b26a 100%);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

/* ── Wartungsseite ──────────────────────────────────────────────── */
.maintenance {
    min-height: 100vh;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 8vh 20px;
    text-align: center;
}

.maintenance-inner { max-width: 540px; }

.maintenance-mark {
    color: var(--secondary);
    display: block;
    margin: 0 auto 26px;
    animation: djd-spin 14s linear infinite;
}

@keyframes djd-spin { to { transform: rotate(360deg); } }

.maintenance-title {
    font-family: var(--font-heading);
    font-weight: var(--heading-weight);
    letter-spacing: var(--heading-tracking);
    color: var(--heading);
    font-size: clamp(1.9rem, 5vw, 2.9rem);
    margin: 0 0 14px;
}

.maintenance-text { font-size: 1.06rem; margin: 0 0 30px; }

.maintenance-meter {
    display: flex;
    align-items: flex-end;
    justify-content: center;
    gap: 5px;
    height: 34px;
    margin: 0 0 30px;
}

.maintenance-meter span {
    width: 5px;
    border-radius: 3px;
    background: var(--secondary);
    opacity: 0.75;
    animation: djd-level 1.5s ease-in-out infinite;
}

.maintenance-meter span:nth-child(1) { height: 40%; animation-delay: 0s; }
.maintenance-meter span:nth-child(2) { height: 70%; animation-delay: 0.15s; }
.maintenance-meter span:nth-child(3) { height: 100%; animation-delay: 0.3s; }
.maintenance-meter span:nth-child(4) { height: 55%; animation-delay: 0.45s; }
.maintenance-meter span:nth-child(5) { height: 85%; animation-delay: 0.6s; }
.maintenance-meter span:nth-child(6) { height: 35%; animation-delay: 0.75s; }
.maintenance-meter span:nth-child(7) { height: 65%; animation-delay: 0.9s; }

@keyframes djd-level {
    0%, 100% { transform: scaleY(0.45); }
    50% { transform: scaleY(1); }
}

.maintenance-foot {
    font-family: var(--font-meta);
    font-size: 0.86rem;
    letter-spacing: 1px;
    text-transform: uppercase;
    color: var(--muted);
    margin-top: 34px;
}

/* Wer Bewegung abbestellt hat, bekommt eine ruhige Seite. */
@media (prefers-reduced-motion: reduce) {
    .maintenance-mark { animation: none; }
    .maintenance-meter span { animation: none; }
    .brand-mark svg { animation: none; }
}

/* Überfällige Rechnung: nur die Fälligkeit wird rot, nicht die ganze Zeile. */
.overdue { color: var(--danger); font-weight: 600; }

/* ── Statusleiste in der Kopfzeile der Verwaltung ───────────────── */
.admin-status {
    display: flex;
    align-items: center;
    gap: 8px;
    margin-left: auto;
    margin-right: 4px;
    flex-wrap: wrap;
}

.status-chip {
    display: inline-flex;
    align-items: center;
    gap: 7px;
    padding: 5px 12px;
    border-radius: 999px;
    border: 1px solid var(--border);
    background: var(--surface-alt);
    color: var(--text);
    font-family: var(--font-meta);
    font-size: 0.8rem;
    font-weight: 500;
    line-height: 1.4;
    letter-spacing: 0.2px;
    text-decoration: none;
    white-space: nowrap;
    transition: border-color 0.18s ease, color 0.18s ease, background 0.18s ease;
}

a.status-chip:hover,
.status-chip-btn:hover { border-color: var(--secondary); color: var(--heading); }

.status-chip-btn { cursor: pointer; font-family: var(--font-meta); }

.status-dot {
    width: 8px;
    height: 8px;
    border-radius: 50%;
    background: var(--muted);
    flex: none;
}

.status-chip.is-ok .status-dot { background: var(--success); }

.status-chip.is-warn {
    border-color: var(--warning);
    background: var(--warning-bg);
    color: var(--warning);
}

.status-chip.is-warn .status-dot { background: var(--warning); }

/* Bei aktiver Wartung soll der Schalter auffallen, nicht sich einfügen. */
.status-chip-btn.is-warn { font-weight: 700; }

@media (max-width: 900px) {
    /* Auf schmalen Geräten bleibt nur der Wartungsschalter – er ist der
       einzige Punkt, an dem man wirklich sofort handeln will. */
    .admin-status .status-chip:not(.status-chip-btn) { display: none; }
}

/* ── Registerkarten ─────────────────────────────────────────────── */
.tabs {
    display: flex;
    gap: 4px;
    flex-wrap: wrap;
    margin: 0 0 18px;
    border-bottom: 1px solid var(--border);
    padding-bottom: 0;
}

.tab {
    appearance: none;
    background: transparent;
    border: 1px solid transparent;
    border-bottom: none;
    border-radius: var(--radius-sm) var(--radius-sm) 0 0;
    padding: 10px 18px;
    margin-bottom: -1px;
    font-family: var(--font-body);
    font-size: 0.94rem;
    font-weight: 600;
    color: var(--muted);
    cursor: pointer;
    transition: color 0.16s ease, background 0.16s ease, border-color 0.16s ease;
}

.tab:hover { color: var(--heading); }

.tab.is-active {
    color: var(--heading);
    background: var(--surface);
    border-color: var(--border);
    border-bottom: 1px solid var(--surface);
}

.tab:focus-visible { outline: 2px solid var(--secondary); outline-offset: -2px; }

/* Ohne JavaScript trägt der Body die Klasse nicht – dann bleiben alle
   Gruppen sichtbar und die Leiste ist nur Zierde. */
body.has-tabs .tab-panel { display: none; }
body.has-tabs .tab-panel.is-active { display: block; }
body:not(.has-tabs) .tabs { display: none; }

.form-actions .hint { margin: 8px 0 0; }

/* ── Versionsgeschichte ─────────────────────────────────────────── */
.release-list { display: flex; flex-direction: column; gap: 14px; }

.release-head { display: flex; align-items: flex-start; gap: 14px; margin-bottom: 10px; }
.release-head .card-title { margin: 0; }

.release-version {
    flex: none;
    font-family: var(--font-meta);
    font-size: 0.82rem;
    font-weight: 700;
    letter-spacing: 0.5px;
    padding: 5px 11px;
    border-radius: 999px;
    background: var(--surface-alt);
    border: 1px solid var(--border);
    color: var(--muted);
    margin-top: 2px;
}

.release.is-current { border-color: var(--secondary); }
.release.is-current .release-version {
    background: var(--secondary);
    border-color: var(--secondary);
    color: var(--on-primary);
}

.release-date {
    margin: 2px 0 0;
    font-size: 0.86rem;
    color: var(--muted);
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
}

.release-notes { margin: 0; padding-left: 20px; }
.release-notes li { margin-bottom: 7px; line-height: 1.55; }
.release-notes li:last-child { margin-bottom: 0; }

/* ── Hinweisfenster ─────────────────────────────────────────────── */
.modal-backdrop {
    position: fixed;
    inset: 0;
    z-index: 60;
    background: rgba(12, 11, 10, 0.55);
    backdrop-filter: blur(2px);
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 24px;
    animation: djd-fade 0.2s ease;
}

@keyframes djd-fade { from { opacity: 0; } to { opacity: 1; } }

.modal {
    background: var(--surface);
    border: 1px solid var(--border);
    border-radius: var(--radius);
    box-shadow: var(--shadow-lg);
    padding: 28px 30px 26px;
    max-width: 560px;
    width: 100%;
    max-height: 82vh;
    overflow-y: auto;
}

.modal h2 {
    margin: 0 0 6px;
    font-family: var(--font-heading);
    font-weight: var(--heading-weight);
    letter-spacing: var(--heading-tracking);
    color: var(--heading);
}

.modal-lead { color: var(--muted); margin: 0 0 16px; }
.modal-section { font-weight: 600; color: var(--heading); margin: 18px 0 8px; }
.modal-actions { display: flex; gap: 10px; align-items: center; margin-top: 24px; flex-wrap: wrap; }

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

.modal { position: relative; }

.modal-close-form { position: absolute; top: 12px; right: 14px; margin: 0; }

.modal-close {
    appearance: none;
    background: transparent;
    border: none;
    font-size: 1.6rem;
    line-height: 1;
    padding: 4px 8px;
    border-radius: var(--radius-sm);
    color: var(--muted);
    cursor: pointer;
}

.modal-close:hover { color: var(--heading); background: var(--surface-alt); }
.modal-close:focus-visible { outline: 2px solid var(--secondary); outline-offset: 2px; }

/* Ein eigenes display: flex schlägt das [hidden] des Browsers – deshalb
   hier ausdrücklich. Ohne diese Zeile blieb der Speichern-Knopf auf den
   Karten „Neuerungen" und „Protokoll" sichtbar, obwohl er dort nichts
   zu tun hat. */
[hidden] { display: none !important; }

/* ── Löschbereich ───────────────────────────────────────────────── */
.danger-zone { border-color: color-mix(in srgb, var(--danger) 40%, var(--border)); }
.danger-zone .card-title { color: var(--danger); }
.danger-zone .form-group { max-width: 420px; }

.brand-swatches .swatch-inherit {
    width: auto;
    min-width: 22px;
    height: 22px;
    border: 1px dashed var(--border);
    border-radius: 999px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    font-size: 0.8rem;
    color: var(--muted);
    padding: 0 7px;
}

/* ── Buchungsstrecke ────────────────────────────────────────────── */
.package-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(240px, 100%), 1fr)); gap: 14px; }

.package-option { cursor: pointer; margin: 0; }
.package-option input { position: absolute; opacity: 0; width: 0; height: 0; }

.package-body {
    display: flex;
    flex-direction: column;
    gap: 8px;
    height: 100%;
    padding: 18px 20px 20px;
    border: 1.5px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--surface);
    transition: border-color 0.18s ease, box-shadow 0.18s ease;
}

.package-option:hover .package-body { border-color: var(--secondary); }
.package-option:has(input:checked) .package-body {
    border-color: var(--secondary);
    box-shadow: 0 0 0 2px color-mix(in srgb, var(--secondary) 35%, transparent);
}
.package-option input:focus-visible + .package-body { outline: 2px solid var(--secondary); outline-offset: 2px; }

.package-head { display: flex; align-items: baseline; justify-content: space-between; gap: 10px; }
.package-head strong { font-size: 1.15rem; color: var(--heading); }
.package-price { font-family: var(--font-meta); font-weight: 700; color: var(--secondary); white-space: nowrap; }
.package-desc { font-size: 0.92rem; color: var(--muted); line-height: 1.5; }
.package-features { margin: 4px 0 0; padding-left: 18px; font-size: 0.9rem; }
.package-features li { margin-bottom: 4px; }
.package-hours { margin-top: auto; padding-top: 8px; font-family: var(--font-meta); font-size: 0.82rem; color: var(--muted); }

.option-list { display: flex; flex-direction: column; gap: 2px; }

.option-row {
    display: flex;
    align-items: flex-start;
    gap: 12px;
    padding: 12px 4px;
    border-bottom: 1px solid var(--border);
    cursor: pointer;
    margin: 0;
}
.option-row:last-child { border-bottom: none; }
.option-row input { margin-top: 3px; flex: none; }
.option-text { flex: 1; }
.option-text strong { display: block; color: var(--heading); font-size: 0.98rem; }
.option-text small { color: var(--muted); }
.option-price { font-family: var(--font-meta); font-weight: 600; white-space: nowrap; color: var(--text); }

.booking-total {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 12px;
    margin-top: 20px;
    padding-top: 16px;
    border-top: 2px solid var(--border);
    font-size: 1.05rem;
}
.booking-total strong { font-family: var(--font-meta); font-size: 1.45rem; color: var(--heading); }

.total-row td { border-top: 2px solid var(--border); font-size: 1.05rem; }

.stat-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(180px, 100%), 1fr)); gap: 14px; margin-bottom: 18px; }
.stat { display: flex; flex-direction: column; gap: 4px; }
.stat-label { font-size: 0.85rem; color: var(--muted); }
.stat-value { font-family: var(--font-meta); font-size: 1.8rem; font-weight: 700; color: var(--heading); line-height: 1.1; }
.stat.is-warn { border-color: var(--warning); }
.stat.is-warn .stat-value { color: var(--warning); }
.stat .btn { align-self: flex-start; margin-top: 6px; }

/* Hinweis auf eine fehlende Pflichtangabe – nur Administratoren sehen ihn. */
.todo-inline {
    display: inline-block;
    padding: 1px 8px;
    border-radius: 999px;
    background: var(--warning-bg);
    color: var(--warning);
    font-size: 0.86rem;
    font-weight: 600;
}

/* ── Avatar-Creator (ab v0.6.0) ─────────────────────────────────── */
.avatar-layout {
    display: grid;
    grid-template-columns: minmax(min(280px, 100%), 400px) 1fr;
    gap: 26px;
    align-items: start;
}

.avatar-preview { position: sticky; top: 92px; }

.avatar-stage {
    border-radius: var(--radius);
    overflow: hidden;
    box-shadow: 0 12px 34px rgba(0, 0, 0, 0.18);
    background: #1d1d1c;
}

.avatar-stage svg { display: block; width: 100%; height: auto; }

.avatar-controls { display: grid; gap: 18px; }
.avatar-controls .card { margin: 0; }

.pick-heading {
    font-family: var(--font-meta);
    font-size: 0.78rem;
    letter-spacing: 1.4px;
    text-transform: uppercase;
    color: var(--muted);
    margin: 20px 0 10px;
}

.pick-row { display: flex; flex-wrap: wrap; gap: 8px; }

.pick { position: relative; cursor: pointer; }

/* Das Eingabefeld selbst bleibt bedienbar (Tastatur, Screenreader),
   sichtbar ist die Kachel daneben. */
.pick input {
    position: absolute;
    opacity: 0;
    width: 1px;
    height: 1px;
    margin: 0;
}

.pick-body {
    display: inline-flex;
    align-items: center;
    gap: 8px;
    padding: 9px 14px;
    border: 1px solid var(--border);
    border-radius: 999px;
    background: var(--surface);
    color: var(--text);
    font-size: 0.92rem;
    transition: border-color 0.15s ease, background 0.15s ease;
}

.pick:hover .pick-body { border-color: var(--secondary); }

.pick input:focus-visible + .pick-body { outline: 2px solid var(--secondary); outline-offset: 2px; }

.pick input:checked + .pick-body {
    border-color: var(--heading);
    background: var(--surface-alt);
    font-weight: 600;
}

.pick-dot {
    width: 16px;
    height: 16px;
    border-radius: 50%;
    border: 1px solid rgba(0, 0, 0, 0.18);
    flex: none;
}

.pick-swatch .pick-body { padding: 7px 13px 7px 9px; }

.stage-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; }

.pick-wide .pick-body {
    border-radius: var(--radius-sm);
    align-items: flex-start;
    flex-direction: column;
    gap: 4px;
    width: 100%;
    padding: 13px 16px;
}

.pick-wide small { color: var(--muted); font-weight: 400; line-height: 1.45; }

.color-input {
    width: 76px;
    height: 42px;
    padding: 4px;
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--surface);
    cursor: pointer;
}

.logo-preview {
    background: var(--surface-alt);
    border-radius: var(--radius-sm);
    padding: 14px;
    margin-bottom: 14px;
    text-align: center;
}

.logo-preview img { max-width: 200px; max-height: 90px; height: auto; }

.avatar-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(min(260px, 100%), 1fr));
    gap: 20px;
}

.avatar-card .avatar-stage { margin-bottom: 16px; }
.avatar-meta { display: flex; gap: 8px; flex-wrap: wrap; margin: 12px 0; }

.avatar-inline {
    display: flex;
    align-items: center;
    gap: 16px;
}

.avatar-inline .avatar-stage { width: 130px; flex: none; }
.avatar-inline .stack-form { flex: 1 1 220px; }
.avatar-inline .form-group { margin-bottom: 12px; }

@media (max-width: 520px) {
    .avatar-inline { flex-direction: column; align-items: stretch; }
    .avatar-inline .avatar-stage { width: 100%; max-width: 220px; }
}

@media (max-width: 900px) {
    .avatar-layout { grid-template-columns: 1fr; }
    .avatar-preview { position: static; }
    .avatar-stage { max-width: 420px; margin-inline: auto; }
}

@media (max-width: 560px) {
    .stage-grid { grid-template-columns: 1fr; }
}

/* Kleines Avatarbild auf dem Kundendashboard */
.dashboard-avatar { max-width: 190px; margin: 4px 0 14px; }

/* Vorstellung des Avatars auf der Startseite */
.showcase {
    display: grid;
    grid-template-columns: minmax(min(240px, 100%), 380px) 1fr;
    gap: 40px;
    align-items: center;
}

.showcase-text .section-title { text-align: left; margin-top: 6px; }
.showcase-text p { max-width: 52ch; }

@media (max-width: 820px) {
    .showcase { grid-template-columns: 1fr; gap: 26px; }
    .showcase-visual { max-width: 340px; margin-inline: auto; }
}

/* ── Musikverwaltung (ab v0.7.0) ────────────────────────────────── */
.track-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 2px; }

.track {
    display: flex;
    align-items: center;
    gap: 14px;
    padding: 11px 0;
    border-bottom: 1px dashed var(--border);
}

.track:last-child { border-bottom: none; }

.track-cover { width: 44px; height: 44px; border-radius: 6px; object-fit: cover; flex: none; }

.track-text { display: flex; flex-direction: column; gap: 2px; flex: 1 1 auto; min-width: 0; }
.track-text small { color: var(--muted); font-size: 0.85rem; }
.track-from { font-style: italic; }
.track-note { color: var(--secondary); }

.track-actions { display: flex; gap: 8px; flex: none; }
.track-actions select { padding: 6px 10px; font-size: 0.85rem; }

.card-title .count {
    display: inline-block;
    margin-left: 8px;
    padding: 1px 9px;
    border-radius: 999px;
    background: var(--surface-alt);
    color: var(--muted);
    font-size: 0.78rem;
    font-family: var(--font-meta);
    vertical-align: middle;
}

.track-form { position: relative; }

.search-hits {
    list-style: none;
    margin: 6px 0 0;
    padding: 6px;
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    background: var(--surface);
    box-shadow: 0 10px 26px rgba(0, 0, 0, 0.12);
    position: absolute;
    z-index: 5;
    width: 100%;
    max-width: 460px;
}

.search-hit {
    display: block;
    width: 100%;
    text-align: left;
    padding: 9px 12px;
    border: none;
    border-radius: 6px;
    background: none;
    color: var(--text);
    font: inherit;
    cursor: pointer;
}

.search-hit:hover, .search-hit:focus-visible { background: var(--surface-alt); }

.guest-link { display: inline-block; padding: 10px 14px; word-break: break-all; }

@media (max-width: 700px) {
    .track { flex-wrap: wrap; }
    .track-actions { width: 100%; }
    .track-actions .inline-form { flex-wrap: wrap; }
}

/* Musikübersicht in der Verwaltung */
.music-columns {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(180px, 100%), 1fr));
    gap: 20px;
}

.music-column .plain-list { margin: 0; padding-left: 18px; display: grid; gap: 8px; }
.music-column .plain-list small { color: var(--muted); }
.music-column.is-nogo .mini-title { color: var(--danger); }

/* ── Redaktion (ab v0.8.0) ──────────────────────────────────────── */
.slug-row { display: flex; align-items: center; gap: 6px; }
.slug-prefix { color: var(--muted); font-family: var(--font-meta); }
.slug-row input { flex: 1 1 auto; }

textarea.mono {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 0.92rem;
    line-height: 1.6;
}

.faq-row {
    padding: 16px 0;
    border-bottom: 1px dashed var(--border);
}
.faq-row:last-child { border-bottom: none; }

/* Redaktionell gepflegter Text – überall gleich gesetzt. */
.prose { max-width: 68ch; }
.prose h2 { font-family: var(--font-heading); font-size: 1.5rem; margin: 32px 0 12px; color: var(--heading); }
.prose h3 { font-family: var(--font-heading); font-size: 1.2rem; margin: 26px 0 10px; color: var(--heading); }
.prose h4 { font-size: 1.02rem; margin: 22px 0 8px; color: var(--heading); }
.prose p { margin: 0 0 14px; line-height: 1.7; }
.prose ul, .prose ol { margin: 0 0 16px; padding-left: 22px; display: grid; gap: 6px; }
.prose li { line-height: 1.65; }
.prose blockquote {
    margin: 0 0 16px;
    padding: 12px 18px;
    border-left: 3px solid var(--secondary);
    background: var(--surface-alt);
    border-radius: 0 var(--radius-sm) var(--radius-sm) 0;
}
.prose a { color: var(--secondary); }
.prose > :first-child { margin-top: 0; }

/* ── Systemprüfung in den Einstellungen (ab v0.8.1) ─────────────── */
.tab-dot {
    display: inline-block;
    width: 7px;
    height: 7px;
    border-radius: 50%;
    margin-left: 6px;
    vertical-align: middle;
}
.tab-dot.is-warn { background: var(--warning); }
.tab-dot.is-fail { background: var(--danger); }

.check-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 4px; }

.check {
    display: flex;
    gap: 14px;
    padding: 15px 0;
    border-bottom: 1px dashed var(--border);
}
.check:last-child { border-bottom: none; }

.check-state {
    width: 11px;
    height: 11px;
    border-radius: 50%;
    margin-top: 6px;
    flex: none;
    background: var(--muted);
}
.check.is-ok .check-state { background: var(--success); }
.check.is-warn .check-state { background: var(--warning); }
.check.is-fail .check-state { background: var(--danger); }

.check-body { flex: 1 1 auto; min-width: 0; }
.check-body h3 { font-size: 1rem; margin: 0 0 3px; display: flex; gap: 10px; align-items: baseline; }
.check-body h3 small { font-family: var(--font-meta); font-size: 0.76rem; text-transform: uppercase; letter-spacing: 1px; }
.check-body p { margin: 0 0 4px; line-height: 1.55; }
.check-details { display: flex; flex-wrap: wrap; gap: 6px; margin: 6px 0; }

/* ── Bewegung des Avatars (v0.8.3) ──────────────────────────────────────
 *
 * Alles hängt an zwei Werten, die auf dem <svg> stehen:
 *
 *   --av-beat     Dauer eines Taktschlags in Sekunden (aus dem Tempo)
 *   --av-energy   Ausschlag von 0 bis 1 (aus dem Energielevel der Phase)
 *
 * Damit gibt es EINEN Satz Keyframes statt drei Stufen zum Pflegen: Das
 * Tempo steuert die Dauer, die Energie den Ausschlag. Beide lassen sich
 * zur Laufzeit ändern, ohne die Animation neu zu starten – wer den
 * Regler schiebt, sieht die Wirkung sofort.
 *
 * Ohne data-dancing bewegt sich nichts. Ein stehendes Bild bleibt also
 * genau das Bild, das es vorher war. */

.avatar-svg { --av-beat: 0.5s; --av-energy: 0.7; }

.avatar-svg .av-sway,
.avatar-svg .av-nod,
.avatar-svg .av-arm-layer,
.avatar-svg .av-platter,
.avatar-svg .av-light {
    transform-box: view-box;
    transform-origin: 200px 300px;
}

.avatar-svg .av-nod { transform-origin: 200px 176px; }
.avatar-svg .av-platter-l { transform-origin: 132px 295px; }
.avatar-svg .av-platter-r { transform-origin: 268px 295px; }
.avatar-svg .av-light-l { transform-origin: 64px 24px; }
.avatar-svg .av-light-r { transform-origin: 336px 24px; }

.avatar-svg .av-light { opacity: 0; mix-blend-mode: screen; }

.avatar-svg[data-dancing] .av-sway {
    animation: av-sway calc(var(--av-beat) * 2) ease-in-out infinite;
}
.avatar-svg[data-dancing] .av-nod {
    animation: av-nod var(--av-beat) ease-in-out infinite;
}
.avatar-svg[data-dancing] .av-arm-layer {
    animation: av-arms calc(var(--av-beat) * 2) ease-in-out infinite;
}
.avatar-svg[data-dancing] .av-platter {
    /* Ein Teller dreht sich gleichmäßig weiter, nicht im Takt hin und
     * her – deshalb linear und eine eigene, vom Takt unabhängige Dauer. */
    animation: av-spin 1.8s linear infinite;
}
.avatar-svg[data-dancing] .av-light {
    animation: av-lights calc(var(--av-beat) * 2) ease-in-out infinite;
}
.avatar-svg[data-dancing] .av-light-r { animation-delay: var(--av-beat); }

@keyframes av-sway {
    0%, 100% { transform: translateY(0) rotate(calc(var(--av-energy) * -1.1deg)); }
    50%      { transform: translateY(calc(var(--av-energy) * -5px)) rotate(calc(var(--av-energy) * 1.1deg)); }
}

@keyframes av-nod {
    0%, 100% { transform: translateY(0) rotate(calc(var(--av-energy) * -2.4deg)); }
    50%      { transform: translateY(calc(var(--av-energy) * 3px)) rotate(calc(var(--av-energy) * 2.4deg)); }
}

@keyframes av-arms {
    0%, 100% { transform: translateY(0) rotate(calc(var(--av-energy) * 1.6deg)); }
    50%      { transform: translateY(calc(var(--av-energy) * -4px)) rotate(calc(var(--av-energy) * -1.6deg)); }
}

@keyframes av-spin {
    from { transform: rotate(0deg); }
    to   { transform: rotate(360deg); }
}

@keyframes av-lights {
    0%, 100% { opacity: calc(var(--av-energy) * 0.16); transform: rotate(-8deg); }
    50%      { opacity: calc(var(--av-energy) * 0.62); transform: rotate(8deg); }
}

/* Wer im Betriebssystem weniger Bewegung eingestellt hat, bekommt keine.
 * Das ist keine Vorliebe, sondern für manche Menschen der Unterschied
 * zwischen benutzbar und übel – deshalb ohne Ausnahme und ohne Schalter,
 * der es überstimmt. Die Bedienung sagt es auch dazu. */
@media (prefers-reduced-motion: reduce) {
    .avatar-svg[data-dancing] .av-sway,
    .avatar-svg[data-dancing] .av-nod,
    .avatar-svg[data-dancing] .av-arm-layer,
    .avatar-svg[data-dancing] .av-platter,
    .avatar-svg[data-dancing] .av-light {
        animation: none;
    }
}

/* ── Bedienung ─────────────────────────────────────────────────────── */

.motion-bar {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 12px 16px;
    margin-top: 14px;
}

.motion-bar .btn { flex: none; }

.motion-field {
    display: flex;
    align-items: center;
    gap: 9px;
    flex: 1 1 190px;
    min-width: 165px;
}

.motion-field label {
    font-family: var(--font-meta);
    font-size: 0.74rem;
    letter-spacing: 1.1px;
    text-transform: uppercase;
    color: var(--muted);
    margin: 0;
    white-space: nowrap;
}

.motion-field input[type="range"] { flex: 1 1 auto; min-width: 70px; }

.motion-value {
    font-variant-numeric: tabular-nums;
    font-family: var(--font-meta);
    font-size: 0.82rem;
    min-width: 58px;
    text-align: right;
}

.motion-phases { display: flex; flex-wrap: wrap; gap: 8px; margin-top: 12px; }

.motion-phase {
    font-family: var(--font-meta);
    font-size: 0.76rem;
    letter-spacing: 0.6px;
    padding: 5px 12px;
    border-radius: 999px;
    border: 1px solid var(--border);
    background: transparent;
    color: inherit;
    cursor: pointer;
}
.motion-phase:hover { border-color: var(--secondary); }
.motion-phase.is-active {
    background: var(--primary);
    border-color: var(--primary);
    color: var(--on-primary);
    font-weight: 600;
}

.motion-note { margin-top: 10px; }

/* ── Anfragen und Sicherungen (v0.9.0) ─────────────────────────────── */

/* Die Filterleiste im Posteingang benutzt die vorhandenen Pillen als
 * Links. Fehlte die aktive Kennzeichnung, waere nicht zu sehen, welcher
 * Filter gerade greift – und eine leere Liste sieht dann aus wie „keine
 * Anfragen" statt wie „keine mit diesem Zustand". */
a.chip-static { text-decoration: none; transition: background 0.15s ease; }
a.chip-static:hover { background: color-mix(in srgb, var(--secondary) 32%, transparent); }

.chip-static.is-active {
    background: var(--primary);
    color: var(--on-primary);
    font-weight: 600;
}

.nav-count {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 20px;
    height: 20px;
    padding: 0 6px;
    margin-left: auto;
    border-radius: 999px;
    background: var(--warning);
    color: #fff;
    font-family: var(--font-meta);
    font-size: 0.72rem;
    font-weight: 700;
    line-height: 1;
}

.nav-dot {
    display: inline-block;
    width: 8px;
    height: 8px;
    margin-left: 6px;
    border-radius: 50%;
    background: var(--warning);
    vertical-align: 2px;
}

.ticket-list { list-style: none; margin: 0; padding: 0; }

.ticket-row { border-bottom: 1px solid var(--border); }
.ticket-row:last-child { border-bottom: none; }

.ticket-link {
    display: flex;
    flex-wrap: wrap;
    gap: 10px 16px;
    align-items: center;
    justify-content: space-between;
    padding: 14px 4px;
    color: inherit;
    text-decoration: none;
}
.ticket-link:hover { color: var(--secondary); }

.ticket-main { display: flex; flex-direction: column; gap: 3px; min-width: 0; }
.ticket-main small { color: var(--muted); font-size: 0.83rem; }
.ticket-side { display: flex; gap: 8px; flex-wrap: wrap; flex: none; }

.ticket-row.is-unread .ticket-main strong::before {
    content: '';
    display: inline-block;
    width: 8px;
    height: 8px;
    margin-right: 8px;
    border-radius: 50%;
    background: var(--warning);
}

tr.is-unread td { background: var(--warning-bg); }

/* Der Verlauf. Bewusst kein Chat-Fenster mit Blasen links und rechts in
 * Messenger-Optik: Es sind meist wenige, längere Nachrichten, und die
 * sollen lesbar sein. Die eigene Seite hebt sich nur ab, damit man auf
 * einen Blick sieht, wer zuletzt geschrieben hat. */
.chat { list-style: none; margin: 0; padding: 0; display: grid; gap: 14px; }

.chat-bubble {
    border: 1px solid var(--border);
    border-radius: var(--radius);
    padding: 14px 16px;
    background: var(--surface);
}

.chat-mine .chat-bubble {
    background: var(--surface-alt);
    border-color: transparent;
}

.chat-meta {
    display: flex;
    gap: 10px;
    align-items: baseline;
    margin: 0 0 8px;
    font-family: var(--font-meta);
    font-size: 0.8rem;
}
.chat-meta span { color: var(--muted); }

.chat-body { line-height: 1.65; }
.chat-body p { margin: 0 0 10px; }
.chat-body p:last-child { margin-bottom: 0; }
.chat-body ul, .chat-body ol { margin: 0 0 10px 20px; }

/* ── Locationvorschläge (v0.9.1) ───────────────────────────────────── */

/* Die Trefferliste liegt absolut – ohne Bezugspunkt am Elternelement
 * würde sie am Kartenrand kleben statt unter dem Feld. Eine eigene
 * Klasse statt :has(), damit es genauso funktioniert wie bei der
 * Titelsuche und an keiner Browserfassung hängt. */
.venue-field { position: relative; }

.search-hit .hit-mark {
    display: block;
    margin-top: 2px;
    font-family: var(--font-meta);
    font-size: 0.74rem;
    letter-spacing: 0.4px;
    color: var(--secondary);
}

.attribution { margin-top: 14px; }
.attribution a { color: inherit; }

/* ── Anfragen im Dashboard (v0.9.2) ────────────────────────────────── */

/* Ein anklickbarer Hinweiskasten. Der ganze Kasten ist der Link, nicht
 * nur ein Wort darin – wer ihn sieht, will hin. */
.notice-link {
    display: flex;
    align-items: center;
    gap: 14px;
    text-decoration: none;
    transition: transform 0.12s ease, box-shadow 0.12s ease;
}
.notice-link:hover { transform: translateY(-1px); box-shadow: var(--shadow); }
.notice-link strong { display: block; }

.notice-badge {
    flex: none;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 34px;
    height: 34px;
    padding: 0 9px;
    border-radius: 999px;
    background: var(--danger);
    color: #fff;
    font-family: var(--font-meta);
    font-size: 1rem;
    font-weight: 700;
    line-height: 1;
}

/* Zweimal langsam pulsieren, dann Ruhe. Ein dauerhaft blinkender Kasten
 * wird nach zwei Tagen übersehen – und ist für manche Menschen schlicht
 * unerträglich. Deshalb endlich, und bei „weniger Bewegung" gar nicht. */
.notice-pulse { animation: notice-pulse 1.6s ease-in-out 2; }

@keyframes notice-pulse {
    0%, 100% { box-shadow: 0 0 0 0 color-mix(in srgb, var(--danger) 0%, transparent); }
    50%      { box-shadow: 0 0 0 6px color-mix(in srgb, var(--danger) 22%, transparent); }
}

@media (prefers-reduced-motion: reduce) {
    .notice-pulse { animation: none; }
    .notice-link:hover { transform: none; }
}

a.metric { text-decoration: none; color: inherit; }
a.metric:hover { border-color: var(--secondary); }

.metric-alert {
    border-color: color-mix(in srgb, var(--danger) 45%, transparent);
    background: var(--danger-bg);
}
.metric-alert .metric-value, .metric-alert .metric-label { color: var(--danger); }

/* ── Gerenderte DJ-Figuren (v0.10.0) ───────────────────────────────── */

.dj-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(min(230px, 100%), 1fr));
    gap: 20px;
}

.dj-card { margin: 0; }
.dj-card .card-title { margin-top: 12px; }
.dj-card .card-title a { color: inherit; text-decoration: none; }
.dj-card .card-title a:hover { color: var(--secondary); }

/* Fester Rahmen mit gleichem Seitenverhältnis: Ohne ihn springt die
 * Kachelhöhe, sobald eine Figur ein anderes Bildformat hat. */
.dj-cover {
    aspect-ratio: 1 / 1;
    border-radius: var(--radius-sm);
    background: #1d1d1c;
    overflow: hidden;
    display: flex;
    align-items: center;
    justify-content: center;
}

.dj-cover img, .dj-cover video {
    width: 100%;
    height: 100%;
    object-fit: contain;
    display: block;
}

.dj-cover-empty {
    font-family: var(--font-meta);
    font-size: 0.8rem;
    letter-spacing: 1px;
    text-transform: uppercase;
    color: var(--muted);
}

.dj-badges { display: flex; flex-wrap: wrap; gap: 6px; margin: 10px 0 0; }

.dj-slots {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(min(200px, 100%), 1fr));
    gap: 18px;
    margin-top: 16px;
}

.dj-slot { border: 1px solid var(--border); border-radius: var(--radius-sm); padding: 14px; }
.dj-slot h3 { margin: 0 0 10px; font-size: 1rem; }
.dj-slot input[type="file"] { width: 100%; font-size: 0.85rem; }

.dj-slot-preview {
    aspect-ratio: 1 / 1;
    border-radius: var(--radius-sm);
    background: #1d1d1c;
    overflow: hidden;
    display: flex;
    align-items: center;
    justify-content: center;
    margin-bottom: 10px;
}
.dj-slot-preview img { width: 100%; height: 100%; object-fit: contain; }

.dj-loop { width: 100%; max-width: 360px; border-radius: var(--radius-sm); background: #1d1d1c; display: block; }

.avatar-stage video { display: block; width: 100%; height: auto; }

/* ── Klappmenü in der Kopfzeile (v0.10.1) ──────────────────────────── */

.chip-menu { position: relative; }
.chip-menu > summary { list-style: none; cursor: pointer; user-select: none; }
.chip-menu > summary::-webkit-details-marker { display: none; }
.chip-menu > summary::marker { content: ''; }
.chip-menu[open] > summary { border-color: var(--secondary); }

.chip-caret { opacity: 0.55; transition: transform 0.15s ease; flex: none; }
.chip-menu[open] .chip-caret { transform: rotate(180deg); }

.chip-panel {
    position: absolute;
    top: calc(100% + 8px);
    right: 0;
    z-index: 40;
    min-width: 252px;
    padding: 8px;
    border: 1px solid var(--border);
    border-radius: var(--radius);
    background: var(--surface);
    box-shadow: var(--shadow-lg);
}

.chip-panel-head {
    margin: 6px 8px 4px;
    font-family: var(--font-meta);
    font-size: 0.7rem;
    letter-spacing: 1.2px;
    text-transform: uppercase;
    color: var(--muted);
}
.chip-panel-head:first-child { margin-top: 2px; }

.chip-panel form { margin: 0; }

.chip-option {
    display: flex;
    align-items: center;
    gap: 10px;
    width: 100%;
    padding: 8px 10px;
    border: none;
    border-radius: var(--radius-sm);
    background: none;
    color: var(--text);
    font: inherit;
    font-size: 0.9rem;
    text-align: left;
    cursor: pointer;
}
.chip-option:hover, .chip-option:focus-visible { background: var(--surface-alt); }
.chip-option.is-active { font-weight: 600; color: var(--heading); }

.chip-swatches { display: inline-flex; gap: 2px; flex: none; }
.chip-swatches span {
    width: 10px;
    height: 16px;
    border-radius: 3px;
    border: 1px solid color-mix(in srgb, var(--border) 70%, transparent);
}

.chip-inherit {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 22px;
    height: 16px;
    border-radius: 3px;
    border: 1px dashed var(--border);
    font-size: 0.7rem;
    color: var(--muted);
}

.chip-check { margin-left: auto; color: var(--success); }

.chip-more {
    display: block;
    margin-top: 6px;
    padding: 8px 10px;
    border-top: 1px solid var(--border);
    font-size: 0.82rem;
    color: var(--muted);
    text-decoration: none;
}
.chip-more:hover { color: var(--secondary); }

@media (max-width: 760px) {
    .chip-panel { right: auto; left: 0; }
}

/* ── Mail-Logo (v0.10.2) ───────────────────────────────────────────── */

/* Heller Grund, weil E-Mails hell sind: Ein Logo, das nur auf dunklem
 * Grund funktioniert, fiele hier auf – und genau das soll es. */
.mail-logo-preview {
    display: flex;
    align-items: center;
    padding: 20px;
    margin: 12px 0;
    border: 1px solid var(--border);
    border-radius: var(--radius-sm);
    background: #f2efeb;
}
.mail-logo-preview img { max-width: 100%; height: auto; display: block; }

/* ── Kontaktformular (v0.12.0) ─────────────────────────────────────── */

/* Der Honigtopf.
 *
 * NICHT display:none und nicht hidden – manche Bots überspringen genau
 * das, weil sie diese Falle kennen. Stattdessen aus dem Sichtfeld
 * geschoben: für das Auge weg, im Quelltext ein ganz normales Feld.
 *
 * Beim Drucken ebenfalls weg, sonst steht auf dem Ausdruck ein leeres
 * Kästchen ohne erkennbaren Zweck. */
.honeypot {
    position: absolute;
    left: -9999px;
    width: 1px;
    height: 1px;
    overflow: hidden;
}

/* Eckdaten einer Anfrage im Posteingang: Beschriftung links, Wert
 * rechts, und der Terminhinweis darf ausbrechen. */
.enquiry-facts { display: grid; grid-template-columns: auto 1fr; gap: 8px 16px; margin: 0 0 4px; font-size: 0.94rem; }
.enquiry-facts dt { color: var(--muted); }
.enquiry-facts dd { margin: 0; color: var(--heading); font-weight: 500; }

/* Frei oder vergeben – die Farbe muss man auf zwei Meter Abstand
 * unterscheiden können, ohne den Text zu lesen. */
.slot-free { color: var(--success); font-weight: 600; }
.slot-taken { color: var(--danger); font-weight: 600; }

/* Der Abschnitt unten auf der Startseite. */
.contact-teaser { display: grid; gap: 18px; align-items: start; }

@media (min-width: 860px) {
    .contact-teaser { grid-template-columns: 1fr 1fr; gap: 40px; }
}

/* ── Kopfzeile auf schmalen Geräten (Korrektur in v0.12.0) ─────────
 *
 * Gefunden beim Nachmessen der neuen Kontaktseite auf 390 Pixel – der
 * Breite eines iPhone 14. Die Kopfzeile war dort 444 Pixel breit, und
 * damit ließ sich JEDE Seite der Website seitlich verschieben. Das war
 * kein Fehler der Kontaktseite: Es galt seit jeher und auf allen
 * Seiten, nur hat es niemand gemessen.
 *
 * Warum das mehr ist als Kosmetik: Wer auf einem Handy versehentlich
 * zur Seite wischt, rutscht beim Tippen aus dem Formularfeld. Und
 * genau auf dem Handy wird eine Anfrage geschrieben.
 *
 * Behoben wird die Ursache – engere Abstände und ein kleinerer Knopf –
 * und nicht das Symptom. Ein `overflow-x: hidden` am Body würde das
 * Verschieben unterbinden und den zu breiten Kopf trotzdem behalten;
 * beim nächsten Knopf wäre alles wieder da, nur unsichtbar. */
@media (max-width: 560px) {
    .header-inner { gap: 12px; }
    .header-actions { gap: 6px; }
    .brand-name { font-size: 1.05rem; }
    .header-actions .btn { padding: 9px 14px; font-size: 0.85rem; }
}

/* Unter 380 Pixel (iPhone SE) muss der Schriftzug weichen. Das Signet
 * bleibt und führt weiterhin zur Startseite – ein Logo ohne Wort ist
 * besser als ein Wort, das den Anmeldeknopf hinausschiebt. */
@media (max-width: 380px) {
    .brand-name { display: none; }
}

/* Lange deutsche Wörter.
 *
 * „Allgemeine Geschäftsbedingungen" und „Datenschutzerklärung" passen
 * auf 390 Pixel nicht in eine Zeile und schoben die Seite um 15 Pixel
 * auf. Aufgefallen ist das erst beim Nachmessen von scrollWidth – im
 * Screenshot sah die Überschrift völlig normal aus, weil der Text den
 * Rahmen verlässt, ohne dass der Rahmen breiter wird.
 *
 * `hyphens: auto` trennt nach deutschen Regeln (lang="de" steht am
 * html-Element), `overflow-wrap` fängt ab, was auch dann nicht passt. */
h1, h2, h3, .page-title, .section-title, .card-title {
    overflow-wrap: break-word;
    hyphens: auto;
}

/* ── Klappmenü auf dem Handy (Korrektur in v0.12.2) ────────────────
 *
 * Der gemeldete Fehler: „Auf dem Handy ist das Drop-Down-Menü nicht zu
 * sehen." Er war schlimmer als er klang. Für Angemeldete standen die
 * Menüpunkte ausschließlich in der Leiste rechts, und die blendet die
 * Handy-Ansicht per `.btn-ghost { display: none }` aus. Das Klappmenü
 * war für sie leer – ein 25 Pixel hoher Streifen ohne Inhalt.
 *
 * Wer sich auf dem Handy anmeldete, konnte danach genau eines: sich
 * wieder abmelden. Keine Events, keine Buchungen, keine Rechnungen,
 * für Administratoren nicht einmal die Verwaltung.
 *
 * Die Punkte werden jetzt aus einer Liste zweimal gezeichnet. Damit sie
 * auf dem Desktop nicht doppelt dastehen – einmal als Menü, einmal als
 * Knöpfe –, verschwindet die Menüfassung dort. */
@media (min-width: 1181px) {
    .main-nav.is-account { display: none; }
}

/* ── Wann die Leiste zum Klappmenü wird ────────────────────────────
 *
 * Für Gäste bei 860 Pixeln – sechs kurze Punkte passen bis dahin.
 *
 * Für Angemeldete schon bei 1180. Ihre Leiste trägt bis zu acht
 * Knöpfe (Verwaltung, Events, Dein DJ, Buchungen, Rechnungen,
 * Anfragen, Konto, Abmelden) und braucht dafür 1162 Pixel. Auf einem
 * iPad quer und auf einem kleinen Notebook stand sie deshalb über den
 * Rand hinaus – jede Seite des Kundenbereichs ließ sich dort seitwärts
 * schieben. Gemessen, nicht geschätzt: 1162 von 1024 verfügbaren. */
@media (max-width: 1180px) {
    .site-header.is-account .main-nav {
        display: none;
        position: absolute;
        top: 68px; left: 0; right: 0;
        flex-direction: column;
        gap: 0;
        background: var(--bg);
        border-bottom: 1px solid var(--border);
        padding: 8px 22px 16px;
        max-height: calc(100vh - 68px);
        overflow-y: auto;
    }
    .site-header.is-account .main-nav.open { display: flex; }
    .site-header.is-account .main-nav a { padding: 12px 0; border-bottom: 1px dashed var(--border); }
    .site-header.is-account .main-nav a:last-of-type { border-bottom: none; }
    .site-header.is-account .nav-toggle { display: inline-flex; }
    .site-header.is-account .header-actions .btn-ghost,
    .site-header.is-account .header-actions .inline-form { display: none; }
    .site-header.is-account .nav-logout { display: block; margin: 0; }
    .site-header.is-account .nav-logout button {
        appearance: none;
        background: none;
        border: none;
        padding: 12px 0;
        width: 100%;
        text-align: left;
        font: inherit;
        font-weight: 500;
        font-size: 0.98rem;
        color: var(--muted);
        cursor: pointer;
    }
    .site-header.is-account .nav-logout button:hover { color: var(--heading); }
}

@media (max-width: 860px) {
    /* Sieben Menüpunkte plus Abmelden passen auf ein liegendes Handy
     * nicht mehr. Ohne diese beiden Zeilen wären die letzten Punkte
     * unter dem unteren Bildschirmrand – sichtbar wäre das Menü dann
     * zwar, benutzbar nicht. */
    .main-nav {
        max-height: calc(100vh - 68px);
        overflow-y: auto;
    }

    /* Abmelden sieht im Klappmenü aus wie ein Menüpunkt, nicht wie ein
     * Fremdkörper – es steht dort in derselben Spalte wie alles andere. */
    .nav-logout { margin: 0; }
    .nav-logout button {
        appearance: none;
        background: none;
        border: none;
        padding: 12px 0;
        width: 100%;
        text-align: left;
        font: inherit;
        font-weight: 500;
        font-size: 0.98rem;
        color: var(--muted);
        cursor: pointer;
    }
    .nav-logout button:hover { color: var(--heading); }
}

/* Auf dem Desktop steht Abmelden als Knopf in der Leiste – die Fassung
 * im Klappmenü wäre dort die zweite. */
@media (min-width: 1181px) {
    .nav-logout { display: none; }
}

/* ── Verwaltung auf dem Handy (Korrektur in v0.12.2) ───────────────
 *
 * Der ganze Verwaltungsbereich ließ sich auf jedem Handy seitwärts
 * schieben – bei 320 wie bei 768 Pixeln, auf jeder Unterseite.
 *
 * Zwei Ursachen:
 *
 * 1. Die Kopfleiste (Titel, „Live", Stilwelt-Chips, Konto) stand in
 *    einer Zeile ohne Umbruch und brauchte 439 Pixel.
 * 2. Jedes Raster war mit `minmax(340px, 1fr)` gebaut. Das liest sich
 *    wie „mindestens 340 breit", heißt aber: NIE schmaler als 340 –
 *    auch nicht, wenn der Bildschirm nur 358 Pixel Platz hat. Behoben
 *    mit `minmax(min(340px, 100%), 1fr)`: unter 340 gewinnt die
 *    Bildschirmbreite. Betrifft 16 Raster im ganzen Programm, nicht
 *    nur die Verwaltung. */
@media (max-width: 900px) {
    .admin-topbar { flex-wrap: wrap; row-gap: 8px; }

    /* Der Titel darf die ganze erste Zeile haben, die Chips rutschen
     * darunter. Sonst bricht mitten zwischen zwei Chips um und der
     * Titel steht allein neben einem halben Statuszeichen. */
    .admin-topbar-title { flex-basis: calc(100% - 52px); }
}

/* ── Tippziele auf Geräten ohne Maus (v0.12.2) ─────────────────────
 *
 * Gemessen auf 390 Pixeln: Die Links im Seitenfuß waren 25 Pixel hoch
 * und lagen 8 Pixel auseinander – vier Ziele in 132 Pixeln
 * übereinander. Wer mit dem Daumen „Impressum" trifft, landet ebenso
 * oft auf „Datenschutz". Das Auge sagt „ja"; der Daumen ist 45 bis 57
 * Pixel breit.
 *
 * Die Abfrage geht bewusst über `pointer: coarse` und nicht über die
 * Bildschirmbreite. Es geht nicht um schmale Fenster, sondern um
 * Finger: Ein schmales Browserfenster auf dem Notebook braucht keine
 * größeren Ziele, ein Tablet mit 1024 Pixeln sehr wohl. */
@media (pointer: coarse) {
    .footer-nav { gap: 0; }
    .footer-nav a { padding: 11px 0; }

    /* Das Auge im Passwortfeld war 28 Pixel breit. Es sitzt im Feld,
     * also wächst es nach innen statt über den Rand. */
    .password-toggle { padding: 12px; }

    /* Chips und Textknöpfe bekommen Höhe, ohne ihre Form zu verlieren. */
    .motion-phase,
    .status-chip,
    .tab { min-height: 40px; }

    .link-btn { padding: 9px 0; }

    /* Der Schließen-Knopf eines Fensters ist der, den man am
     * schnellsten trifft – oder eben daneben. */
    .modal-close { width: 44px; height: 44px; }

    /* Ein Link in einem Hinweiskasten ist eine Aufforderung, kein
     * Fließtext („Fertige DJs ansehen"). Er bekommt deshalb Fläche –
     * anders als ein Name in einer Tabellenzeile, den man als Wort
     * antippt. */
    .msg a,
    .notice-warning a,
    .notice-danger a,
    .notice-info a {
        display: inline-block;
        padding: 8px 0;
    }
}

/* ── Eventkarte auf schmalen Geräten (v0.12.2) ─────────────────────
 *
 * „Testfeier" stand als „Testfei / er" da, „Sommerfest" als
 * „Somm / erfest". Nicht die Worttrennung war schuld, sondern die
 * Aufteilung: Datum, Titel, Statusschild und Countdown standen auch
 * auf 390 Pixeln nebeneinander. Für den Titel blieben rund 60 Pixel,
 * und `overflow-wrap` tat, was es soll – irgendwo brechen, damit
 * nichts über den Rand läuft.
 *
 * Die Notbremse bleibt (sie hat die AGB-Überschrift gerettet). Behoben
 * wird die Ursache: Der Titel bekommt Platz, Schild und Countdown
 * rutschen in eine zweite Zeile. */
@media (max-width: 560px) {
    .event-card { flex-wrap: wrap; gap: 12px 14px; padding: 14px 16px; }

    /* 140 Pixel Mindestbreite: Darunter bricht die Karte lieber um,
     * als den Titel zu zerlegen. */
    .event-body { flex: 1 1 140px; }

    .event-side {
        flex: 1 1 100%;
        display: flex;
        flex-direction: row;
        align-items: center;
        gap: 10px;
        justify-items: start;
        text-align: left;
    }
}

/* ── Überschriften auf schmalen Geräten (v0.12.2) ──────────────────
 *
 * „Datenschutzerklärung" brach auf dem Handy als „Datenschutzerklär /
 * ung" um – ohne Trennstrich, mitten in der Silbe.
 *
 * Schuld war nicht die Notbremse `overflow-wrap`, sondern die Größe:
 * Das Wort braucht bei 30 Pixeln Schriftgröße 375 Pixel, verfügbar
 * sind auf einem 390er Bildschirm 346. Also bricht es. Auf einen
 * Trennstrich ist kein Verlass – `hyphens: auto` setzt voraus, dass
 * der Browser deutsche Trennregeln mitbringt, und manche tun das nicht.
 *
 * Nachgemessen statt geschätzt: „Datenschutzerklärung" passt ab 27,5
 * Pixeln, „Verbraucherstreitbeilegung" als Zwischenüberschrift ab 21.
 * Die Werte unten liegen darunter. */
@media (max-width: 560px) {
    .page-title { font-size: 1.6rem; }
    .section-title { font-size: 1.5rem; margin-bottom: 28px; }
    .legal h2 { font-size: 1.1rem; }
}

/* Auf 320 Pixeln (iPhone SE der ersten Reihe, ältere Android-Geräte)
 * bleiben nur 276 Pixel Textbreite. Dort muss auch die
 * „Datenschutzerklärung" noch in eine Zeile. */
@media (max-width: 380px) {
    .page-title { font-size: 1.35rem; }
    .section-title { font-size: 1.3rem; }
}

/* ══════════════════════════════════════════════════════════════════
 * KACHEL-DASHBOARD UND PLAYLISTEN (ab v0.14.0)
 *
 * Alles hier folgt den vorhandenen Farbtokens. Kein einziger fester
 * Farbwert: Die drei Erscheinungsbilder (Salon, Nachtclub, Studio) und
 * der Hell-Dunkel-Schalter müssen weiter greifen, ohne dass jemand
 * daran denkt.
 * ══════════════════════════════════════════════════════════════════ */

/* Für Überschriften, die es geben muss, damit die Gliederung stimmt,
 * die aber niemand sehen soll. `display: none` wäre falsch – ein
 * Screenreader liest sie dann auch nicht. */
.visually-hidden {
    position: absolute;
    width: 1px;
    height: 1px;
    padding: 0;
    margin: -1px;
    overflow: hidden;
    clip: rect(0 0 0 0);
    white-space: nowrap;
    border: 0;
}

/* ── Kacheln ──────────────────────────────────────────────────────
 *
 * Das Raster ist bewusst `auto-fit` mit einer Mindestbreite und nicht
 * eine feste Spaltenzahl je Bildschirmgröße: Die Zahl der Kacheln
 * wächst mit den Modulen, und eine Regel „drei nebeneinander" wäre
 * beim übernächsten Modul falsch.
 *
 * min(260px, 100%) statt 260px: Auf einem 320er Bildschirm bliebe
 * sonst eine Spalte von 260 Pixeln neben 22 Pixeln Rand stehen und
 * die Seite ließe sich seitlich schieben. */
.tile-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(260px, 100%), 1fr));
    gap: 18px;
    margin: 26px 0 34px;
}

.tile {
    display: flex;
    flex-direction: column;
    gap: 10px;
    padding: 22px;
    border: 1px solid var(--border);
    border-radius: var(--radius);
    background: var(--surface);
    color: var(--text);
    text-decoration: none;
    transition: transform 0.18s ease, box-shadow 0.18s ease, border-color 0.18s ease;
    /* Auf dem Handy soll die ganze Fläche mit dem Daumen zu treffen
     * sein, nicht nur die Beschriftung. */
    min-height: 168px;
}

.tile:hover {
    transform: translateY(-3px);
    box-shadow: var(--shadow-lg);
    border-color: var(--secondary);
}

/* Der Fokusrahmen ist nicht dekorativ. Wer die Seite mit der Tastatur
 * bedient, sieht sonst nicht, wo er steht. */
.tile:focus-visible {
    outline: 3px solid var(--secondary);
    outline-offset: 3px;
}

.tile.is-highlight {
    border-color: var(--secondary);
    box-shadow: var(--shadow);
}

.tile-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 10px;
}

.tile-icon-wrap {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 44px;
    height: 44px;
    border-radius: 12px;
    background: color-mix(in srgb, var(--secondary) 14%, transparent);
    color: var(--secondary);
}

.tile-title { font-size: 1.15rem; font-weight: 600; color: var(--heading); }
.tile-text { font-size: 0.94rem; color: var(--muted); flex: 1; }

.tile-cta {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    font-weight: 600;
    color: var(--heading);
}

.tile:hover .tile-cta svg { transform: translateX(3px); }
.tile-cta svg { transition: transform 0.18s ease; }

/* Wer „reduzierte Bewegung" eingestellt hat, hat das aus einem Grund
 * getan. */
@media (prefers-reduced-motion: reduce) {
    .tile, .tile-cta svg { transition: none; }
    .tile:hover { transform: none; }
}

/* ── Titel-Listen ─────────────────────────────────────────────────*/

.track-list { list-style: none; margin: 12px 0 0; padding: 0; display: grid; gap: 8px; }
.track-list.is-numbered { counter-reset: track; }

.track-row {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 10px 12px;
    border: 1px solid var(--border);
    border-radius: 12px;
    background: var(--surface-alt);
    flex-wrap: wrap;
}

.track-list.is-numbered .track-row::before {
    counter-increment: track;
    content: counter(track);
    min-width: 1.6em;
    text-align: right;
    color: var(--muted);
    font-variant-numeric: tabular-nums;
}

.track-row.is-done { opacity: 0.55; }
.track-body { display: flex; flex-direction: column; gap: 2px; flex: 1 1 200px; min-width: 0; }
.track-body strong { overflow-wrap: anywhere; }
.track-cover { border-radius: 8px; object-fit: cover; flex: none; }
.track-actions { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; }

/* Auf der Live-Ansicht zählt Treffsicherheit mehr als Dichte: Die Seite
 * wird im Halbdunkeln mit einer Hand bedient. */
.track-list.is-live .track-row { padding: 14px; gap: 14px; }
.track-list.is-live .btn { min-height: 44px; }

.vote-count {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 44px;
    height: 44px;
    border-radius: 12px;
    background: color-mix(in srgb, var(--secondary) 16%, transparent);
    color: var(--secondary);
    font-weight: 700;
    font-variant-numeric: tabular-nums;
    flex: none;
}

.track-list.is-guest .btn { min-height: 40px; }
.track-list.is-compact .track-row { padding: 8px 12px; }

/* ── Listen des Anbieters beim Anmelden ───────────────────────────*/

.remote-list { list-style: none; margin: 12px 0 0; padding: 0; display: grid; gap: 8px; }

.remote-item {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 10px 12px;
    border: 1px solid var(--border);
    border-radius: 12px;
    flex-wrap: wrap;
}

.remote-body { display: flex; flex-direction: column; gap: 2px; flex: 1 1 160px; min-width: 0; }
.remote-cover { border-radius: 8px; object-fit: cover; flex: none; }
.remote-cover.is-empty { width: 48px; height: 48px; background: var(--surface-alt); }

/* ── Kleinkram ────────────────────────────────────────────────────*/

.numbered-list { margin: 0 0 18px; padding-left: 1.3em; display: grid; gap: 6px; }
.soft-divider { border: 0; border-top: 1px solid var(--border); margin: 18px 0; }
.inline-actions { display: inline-flex; gap: 8px; flex-wrap: wrap; }

.qr-stage {
    display: flex;
    justify-content: center;
    padding: 14px;
    background: #fff;
    border-radius: var(--radius);
    margin-bottom: 14px;
}

/* Der Gästelink wird abgetippt, abfotografiert und weitergeschickt.
 * `anywhere` statt `break-word`, weil eine Adresse ohne Leerzeichen
 * sonst aus dem Kasten läuft. */
.link-box code {
    display: block;
    padding: 10px 12px;
    background: var(--surface-alt);
    border-radius: 10px;
    overflow-wrap: anywhere;
    font-size: 0.92rem;
}

@media (max-width: 560px) {
    .tile { min-height: 150px; padding: 18px; }
    .track-actions { width: 100%; justify-content: flex-start; }
}

/* Das Symbol in der Kachel. Eigene Klasse, damit die Form nicht an der
 * Schriftgröße hängt: In der Kachel steht sie neben einem Kennzeichen,
 * und ein Symbol, das mit dem Text mitwächst, verrutscht dabei. */
.tile-icon { display: block; }

/* Sprachwahl auf der Gästeseite. Sie steht ganz unten und darf so
 * aussehen: eine Zeile, zwei Wörter, kein Menü. */
.lang-switch { display: flex; gap: 10px; align-items: baseline; flex-wrap: wrap; }

/* ══════════════════════════════════════════════════════════════════
 * PLAYER UND LICHTSZENEN (ab v0.15.0)
 * ══════════════════════════════════════════════════════════════════ */

.player-now { display: flex; align-items: center; gap: 14px; margin: 14px 0; min-height: 64px; }
.player-cover { border-radius: 10px; object-fit: cover; flex: none; }
.player-meta { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.player-meta strong { overflow-wrap: anywhere; }

/* Die drei Knöpfe stehen mittig und sind groß: Diese Seite wird im
 * Halbdunkeln mit einer Hand bedient, und ein danebengegriffener
 * „Weiter" ist auf einer Feier sofort hörbar. */
.player-controls {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 12px;
    margin: 10px 0 18px;
}

.player-controls .btn { min-width: 64px; min-height: 48px; }
.player-controls .btn-lg { min-width: 88px; min-height: 56px; font-size: 1.3rem; }

/* Ein Lautstärkeregler, der nur so breit ist wie ein Textfeld, lässt
 * sich mit dem Daumen nicht genau treffen. Er nimmt die ganze Breite. */
.volume-row input[type="range"] { width: 100%; accent-color: var(--secondary); height: 32px; }
.volume-row .form-label { display: flex; justify-content: space-between; gap: 10px; }

/* Auswahl mit Knopf daneben – „nimm diese Liste". */
.inline-select { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; margin-bottom: 18px; }
.inline-select select { flex: 1 1 220px; }

/* Lichtszenen. Der Farbtupfer steht links und ist das Einzige an der
 * Zeile, das man aus zwei Metern Entfernung erkennt. */
.scene-row { position: relative; padding-left: 26px; }

.scene-swatch {
    position: absolute;
    left: 0;
    top: 6px;
    width: 14px;
    height: 44px;
    border-radius: 7px;
    border: 1px solid var(--border);
}

.scene-actions { margin: 0 0 18px; }
.scene-row input[type="color"] { width: 100%; height: 42px; padding: 4px; }

@media (max-width: 560px) {
    .player-controls .btn { min-width: 56px; }
    .scene-row { padding-left: 0; }
    .scene-swatch { position: static; width: 100%; height: 8px; margin-bottom: 10px; display: block; }
}

/* ══════════════════════════════════════════════════════════════════
 * PROZESS-SCHRITTE AUF DER STARTSEITE (ab v0.16.0)
 *
 * Nach der Vorlage: drei freistehende Liniensymbole, dazwischen eine
 * dünne Linie, darunter die Beschriftung in Serifen. Keine Kästen,
 * keine Nummernkreise, viel Luft.
 *
 * Kein einziger fester Farbwert. Im Salon wird daraus Terrakotta auf
 * Beige wie in der Vorlage, bei DJ Dirk Magenta auf Dunkel – dieselbe
 * Zeichnung, andere Welt.
 * ══════════════════════════════════════════════════════════════════ */

.process {
    /* Der Abstand steht als Variable, weil die Verbindungslinie mit
     * ihm rechnet: Sie reicht von der Mitte eines Symbols bis zur
     * Mitte des nächsten und muss den Zwischenraum überbrücken. */
    --process-gap: 26px;
    --process-icon: 72px;

    list-style: none;
    margin: 42px 0 0;
    padding: 0;
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: var(--process-gap);
}

.process-step {
    position: relative;
    display: flex;
    flex-direction: column;
    align-items: center;
    text-align: center;
    gap: 12px;
    padding: 0 6px;
}

.process-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: var(--process-icon);
    height: var(--process-icon);
    color: var(--secondary);
}

.process-glyph { display: block; }

/* Die Linie zum nächsten Schritt.
 *
 * Sie beginnt rechts neben diesem Symbol und endet links neben dem
 * nächsten. Da alle Spalten gleich breit sind, ist der Abstand von
 * Mitte zu Mitte genau „Spaltenbreite + Abstand" – daher die
 * Rechnung: 100 % der eigenen Breite plus der Zwischenraum, minus
 * einmal Symbolbreite und zweimal Luft. */
.process-connector {
    position: absolute;
    top: calc(var(--process-icon) / 2);
    left: calc(50% + var(--process-icon) / 2 + 16px);
    width: calc(100% + var(--process-gap) - var(--process-icon) - 32px);
    height: 1.5px;
    background: var(--secondary);
    opacity: 0.5;
    transform-origin: left center;
}

/* Hinter dem letzten Schritt kommt nichts mehr. Eine Linie, die ins
 * Nichts zeigt, sieht nach vergessenem vierten Schritt aus. */
.process-step:last-child .process-connector { display: none; }

.process-title {
    font-family: var(--font-heading);
    font-weight: 700;
    font-size: clamp(1.25rem, 2.4vw, 1.6rem);
    color: var(--heading);
    margin: 6px 0 0;
    letter-spacing: var(--heading-tracking);
}

.process-text {
    color: var(--muted);
    font-size: 0.94rem;
    margin: 0;
    max-width: 30ch;
}

/* ── Die Animation ────────────────────────────────────────────────
 *
 * Greift ausschließlich, wenn das Skript `is-animated` gesetzt hat.
 * Ohne JavaScript trifft keine der folgenden Regeln zu, und oben
 * steht bereits alles sichtbar da.
 *
 * `--step` staffelt die Verzögerung. Eine vierte Kachel würde sich
 * ohne weiteres Zutun einreihen – es gibt keine Regel je Schritt. */
.process.is-animated .process-step {
    opacity: 0;
    transform: translateY(12px);
    transition:
        opacity 0.5s ease calc(var(--step, 0) * 0.16s),
        transform 0.5s ease calc(var(--step, 0) * 0.16s);
}

/* Das Symbol kommt eine Spur später und etwas kleiner herein – so
 * wirkt es gezeichnet statt eingeblendet. */
.process.is-animated .process-glyph {
    opacity: 0;
    transform: scale(0.86);
    transition:
        opacity 0.45s ease calc(var(--step, 0) * 0.16s + 0.08s),
        transform 0.45s ease calc(var(--step, 0) * 0.16s + 0.08s);
}

/* Die Linie wächst nach dem Symbol von links nach rechts – so liest
 * man die Reihenfolge, ohne dass Nummern dastehen müssen. */
.process.is-animated .process-connector {
    transform: scaleX(0);
    transition: transform 0.5s ease calc(var(--step, 0) * 0.16s + 0.26s);
}

.process.is-animated.is-visible .process-step {
    opacity: 1;
    transform: none;
}

.process.is-animated.is-visible .process-glyph {
    opacity: 1;
    transform: none;
}

.process.is-animated.is-visible .process-connector { transform: scaleX(1); }

/* Wer „reduzierte Bewegung" eingestellt hat, hat das meist aus einem
 * gesundheitlichen Grund getan. Dann steht alles sofort da. */
@media (prefers-reduced-motion: reduce) {
    .process.is-animated .process-step,
    .process.is-animated .process-glyph,
    .process.is-animated .process-connector {
        opacity: 1;
        transform: none;
        transition: none;
    }
}

/* Auf dem Handy stehen die Schritte untereinander. Die Linie wandert
 * unter das Symbol und wächst nach unten – dieselbe Bewegung,
 * gedrehte Achse. */
@media (max-width: 760px) {
    .process {
        --process-gap: 34px;
        grid-template-columns: 1fr;
    }

    .process-connector {
        top: auto;
        bottom: calc(var(--process-gap) * -1);
        left: 50%;
        width: 1.5px;
        height: var(--process-gap);
        transform-origin: center top;
    }

    .process.is-animated .process-connector { transform: scaleY(0); }
    .process.is-animated.is-visible .process-connector { transform: scaleY(1); }

    .process-text { max-width: 34ch; }
}

/* ══════════════════════════════════════════════════════════════════
 * IPAD UND TOUCH (ab v0.17.0)
 *
 * Die Seite lief auf dem iPad schon vorher – aber mit vier Ecken, an
 * denen man hängen bleibt. Sie sind hier abgeräumt, in der Reihenfolge,
 * in der sie beim Ausprobieren auffallen.
 * ══════════════════════════════════════════════════════════════════ */

/* 1. Safari zoomt beim Antippen eines Eingabefelds, dessen Schrift
 *    kleiner als 16 Pixel ist. Danach steht die Seite verschoben und
 *    der Besucher muss von Hand herauszoomen – er hält das für einen
 *    Fehler der Seite, und er hat recht.
 *
 *    `pointer: coarse` trifft Finger, nicht Maus: Am Schreibtisch
 *    bleiben die kleineren Größen erhalten. */
@media (pointer: coarse) {
    input[type="text"], input[type="email"], input[type="password"],
    input[type="tel"], input[type="search"], input[type="number"],
    input[type="date"], input[type="time"], select, textarea,
    .filter-bar input[type="search"], .filter-bar select,
    .track-actions select {
        font-size: 16px;
    }

    /* 2. Alles, was man antippt, mindestens 44 Punkte hoch – das Maß,
     *    das Apple seit Jahren nennt und das ungefähr einer
     *    Fingerkuppe entspricht. Darunter trifft man daneben, und auf
     *    einer Feier ist „daneben" ein abgelehnter Wunsch. */
    .btn, .icon-btn, .badge[href], .nav-logout button {
        min-height: 44px;
        display: inline-flex;
        align-items: center;
        justify-content: center;
    }

    .btn-sm { min-height: 44px; padding-top: 8px; padding-bottom: 8px; }

    /* 3. Doppeltipp-Zoom kostet Safari 300 ms Wartezeit vor jedem
     *    Klick. Ohne ihn reagiert die Seite sofort. */
    a, button, summary, label, .tile, .track-row { touch-action: manipulation; }

    /* 4. Der graue Kasten, den iOS beim Antippen über Links legt,
     *    passt in keine der vier Welten. Der Fokusrahmen bleibt – er
     *    ist kein Schmuck, sondern die einzige Rückmeldung für alle,
     *    die mit Tastatur arbeiten. */
    a, button { -webkit-tap-highlight-color: transparent; }
}

/* 5. Auf einem Touchgerät bleibt ein Hover-Zustand „kleben": Man tippt
 *    eine Kachel an, kommt zurück – und sie steht immer noch angehoben
 *    da, als wäre der Finger noch drauf. Deshalb greifen die
 *    Bewegungen nur, wo es einen Zeiger gibt, der schweben kann. */
@media (hover: none) {
    .btn:hover, .tile:hover, .card:hover {
        transform: none;
        box-shadow: none;
    }

    .tile:hover { border-color: var(--border); }
}

/* 6. Der Bildschirmrand des iPad Pro ist rund, und unten liegt der
 *    Home-Balken. Ohne diese Abstände steht der letzte Knopf darunter.
 *    Wirkt nur mit `viewport-fit=cover` im Kopf der Seite. */
body {
    padding-left: env(safe-area-inset-left);
    padding-right: env(safe-area-inset-right);
}

.site-footer { padding-bottom: calc(28px + env(safe-area-inset-bottom)); }

/* 7. Quer und hoch: Auf dem iPad (768–1024 Punkte) stehen die sechs
 *    Kacheln in zwei Spalten statt in einer schmalen Reihe. Bei
 *    `auto-fit` allein käme dort je nach Zoomstufe mal zwei, mal drei
 *    heraus – das sieht bei jedem Aufklappen anders aus. */
@media (min-width: 700px) and (max-width: 1024px) {
    .tile-grid { grid-template-columns: repeat(2, 1fr); }
    .card-grid { grid-template-columns: repeat(2, 1fr); }
}

/* ══════════════════════════════════════════════════════════════════
 * KIOSK-MODUS (ab v0.17.0)
 *
 * Für ein iPad, das im Saal steht. Zwei Betriebsarten, dieselbe Hülle:
 * keine Kopfzeile, kein Menü, kein Weg hinaus, große Flächen.
 *
 * Zum Sperren dient „Geführter Zugriff" von iOS – das ist eine
 * Einstellung des Geräts, keine der Website. Diese Seiten sorgen nur
 * dafür, dass es innerhalb der App nichts gibt, was jemand versehentlich
 * anfassen könnte.
 * ══════════════════════════════════════════════════════════════════ */

.kiosk-body {
    min-height: 100dvh;
    display: flex;
    flex-direction: column;
    /* Kein Textmarkieren, kein Lupen-Popup beim Halten. Gilt NICHT für
     * Eingabefelder – dort braucht man beides. */
    -webkit-user-select: none;
    user-select: none;
    -webkit-touch-callout: none;
}

.kiosk-body input, .kiosk-body textarea {
    -webkit-user-select: text;
    user-select: text;
}

.kiosk-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 16px;
    padding: calc(18px + env(safe-area-inset-top)) 26px 14px;
    border-bottom: 1px solid var(--border);
}

.kiosk-title { font-size: 1.3rem; margin: 0; color: var(--heading); }
.kiosk-sub { color: var(--muted); font-size: 0.95rem; margin: 2px 0 0; }

.kiosk-main {
    flex: 1;
    padding: 26px;
    padding-bottom: calc(26px + env(safe-area-inset-bottom));
    width: 100%;
    max-width: 1100px;
    margin: 0 auto;
}

/* Auf dem Gäste-iPad steht das Formular groß und mittig: Wer davor
 * steht, hat eine Aufgabe, und die soll die ganze Fläche einnehmen. */
.kiosk-guest .form-label { font-size: 1.05rem; }
.kiosk-guest input[type="text"] { padding: 18px 18px; font-size: 18px; }
.kiosk-guest .btn { font-size: 1.1rem; padding: 18px 30px; }

/* Die Dankesmeldung nach einem Wunsch. Groß genug, dass man sie aus
 * zwei Metern liest, und sie verschwindet von selbst wieder. */
.kiosk-thanks {
    text-align: center;
    padding: 22px;
    border-radius: var(--radius);
    background: color-mix(in srgb, var(--success) 14%, transparent);
    color: var(--success);
    font-size: 1.15rem;
    font-weight: 600;
    margin-bottom: 22px;
}

/* Am Pult zählt Treffsicherheit: zwei Knöpfe, so groß wie möglich. */
.kiosk-wish {
    display: flex;
    align-items: center;
    gap: 18px;
    padding: 18px;
    border: 1px solid var(--border);
    border-radius: var(--radius);
    background: var(--surface);
    margin-bottom: 14px;
    flex-wrap: wrap;
}

.kiosk-wish .track-body { flex: 1 1 220px; }
.kiosk-wish strong { font-size: 1.15rem; }
.kiosk-wish .btn { min-width: 132px; min-height: 60px; font-size: 1.05rem; }

.kiosk-empty {
    text-align: center;
    color: var(--muted);
    padding: 60px 20px;
    font-size: 1.1rem;
}

/* Der Weg hinaus liegt klein unten rechts und fragt nach. Ein Knopf
 * „Beenden" in Daumennähe wäre auf einer Feier eine Zeitfrage. */
.kiosk-exit {
    text-align: right;
    padding: 0 26px calc(18px + env(safe-area-inset-bottom));
}

.kiosk-exit a, .kiosk-exit button {
    color: var(--muted);
    font-size: 0.85rem;
    background: none;
    border: 0;
    text-decoration: underline;
    cursor: pointer;
}

/* Anleitung für den Geführten Zugriff – steht auf der Startseite des
 * Kiosk-Bereichs, nicht im Kiosk selbst. */
.kiosk-steps { counter-reset: kiosk; list-style: none; padding: 0; margin: 0; display: grid; gap: 12px; }

.kiosk-steps li {
    counter-increment: kiosk;
    display: flex;
    gap: 14px;
    align-items: flex-start;
}

.kiosk-steps li::before {
    content: counter(kiosk);
    flex: none;
    width: 30px;
    height: 30px;
    border-radius: 999px;
    background: color-mix(in srgb, var(--secondary) 16%, transparent);
    color: var(--secondary);
    font-weight: 700;
    display: inline-flex;
    align-items: center;
    justify-content: center;
}
