/* ---------------------------------------------------------------------------
   Schriften des Gestaltungskonzepts (docs/konzept/11-design.md)

   Inter fuer die Oberflaeche, IBM Plex Mono fuer Daten. Beide liegen als woff2
   unter "schriften/" im Repository - die Anwendung ruft zur Laufzeit KEINEN
   fremden Server auf, auch nicht fonts.googleapis.com. Lizenzen und Herkunft:
   schriften/LIZENZ.md.

   "font-display: swap": Bis die Datei da ist, wird der Fallstapel gezeigt,
   statt den Text unsichtbar zu lassen. Bei 126 KB ueber denselben Server ist
   das ein kurzer Moment - aber kein leerer Bildschirm.
   --------------------------------------------------------------------------- */
@font-face {
    font-family: "Inter";
    font-style: normal;
    font-weight: 400;
    font-display: swap;
    src: url("schriften/inter-400.woff2") format("woff2");
}

@font-face {
    font-family: "Inter";
    font-style: normal;
    font-weight: 500;
    font-display: swap;
    src: url("schriften/inter-500.woff2") format("woff2");
}

@font-face {
    font-family: "Inter";
    font-style: normal;
    font-weight: 600;
    font-display: swap;
    src: url("schriften/inter-600.woff2") format("woff2");
}

@font-face {
    font-family: "Inter";
    font-style: normal;
    font-weight: 700;
    font-display: swap;
    src: url("schriften/inter-700.woff2") format("woff2");
}

@font-face {
    font-family: "IBM Plex Mono";
    font-style: normal;
    font-weight: 400;
    font-display: swap;
    src: url("schriften/plex-mono-400.woff2") format("woff2");
}

@font-face {
    font-family: "IBM Plex Mono";
    font-style: normal;
    font-weight: 500;
    font-display: swap;
    src: url("schriften/plex-mono-500.woff2") format("woff2");
}

/* ---------------------------------------------------------------------------
   Textvarianten der Akzentfarben.

   Brass und Moss sind FLAECHENfarben: Als Untergrund eines Knopfes mit Ink-Schrift
   tragen sie muehelos. Als SCHRIFT auf hellem Grund verfehlen beide die 4,5 der
   WCAG-Stufe AA - Brass kommt auf 2,57, Moss auf 4,28 (beides nachgemessen an der
   laufenden Anwendung, nicht geschaetzt).

   Deshalb je eine abgedunkelte Fassung, die 4,5 sowohl auf Weiss als auch auf Paper
   erreicht und noch als dieselbe Farbe zu erkennen ist. Sie gilt NUR fuer Schrift;
   Flaechen, Rahmen und Balken behalten den vollen Ton, denn dort gilt die
   Textschwelle nicht.

   Warum nicht gleich im Theme: MudBlazor kennt je Farbe nur EINEN Wert plus eine
   Kontrastfarbe fuer gefuellte Flaechen - eine getrennte Textfassung sieht die
   Palette nicht vor. */
:root {
    --fs-brass-text: #8B6B30;
    --fs-moss-text: #54785F;
}

/* MudBlazors Textfarb-Klassen umbiegen. Das "!important" ist nicht Bequemlichkeit:
   MudBlazor schreibt die Regeln selbst mit !important
   (".mud-primary-text { color: var(--mud-palette-primary) !important }"), und dagegen
   kommt eine gewoehnliche Regel nicht an, wie spezifisch sie auch ist.

   Betroffen sind Verweise im Fliesstext ("In meinen Kalender uebernehmen") und
   Erfolgsmeldungen ("Zugesagt"). Beide stehen immer auf hellem Grund. */
.mud-primary-text {
    color: var(--fs-brass-text) !important;
}

.mud-success-text {
    color: var(--fs-moss-text) !important;
}

/* Ziffern in Tabellen stehen untereinander, statt zu tanzen: Inter bringt dafuer
   Tabellenziffern mit (alle gleich breit). Betrifft jede Liste der Anwendung und
   kostet keine einzige Aenderung an den 34 Seiten.

   Das ist NICHT dasselbe wie die IBM Plex Mono des Konzepts - die ist fuer
   Spalten gedacht, die wirklich nur Zahlen tragen (Betraege, Seriennummern).
   Welche Spalte das ist, weiss "Spalte<T>" heute nicht; bis dahin gilt die
   Klasse "fs-mono" unten fuer Stellen, an denen die Anwendung es sicher weiss. */
.mud-table .mud-table-cell {
    font-variant-numeric: tabular-nums;
}

/* Der Monospace-Stapel als Variable - er stand vorher siebenmal abgeschrieben in dieser
   Datei, und alle sieben zeigten auf die Systemschrift statt auf die des Konzepts. */
:root {
    --fs-schrift-mono: "IBM Plex Mono", ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
}

/* Daten in Monospace, wo die Anwendung sicher weiss, dass es Zahlen sind. */
.fs-mono {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
}

/* Spalteninhalte werden gekuerzt, nicht umgebrochen - eine Zeile je Datensatz haelt
   lange Listen ueberschaubar. */
.fs-nowrap {
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    max-width: 24rem;
}

/* In der Kartenansicht (Telefon) steht eine Zelle als Zeile "Titel ... Wert". Dort kuerzt
   text-overflow nichts (die Zelle ist ein Flex-Container), und ein langer Wert schob die
   Karte ueber den Rand hinaus - sichtbar bei "Offen" auf /termine/pruefung. Hier wird
   deshalb umgebrochen, und der Wert steht rechts. */
@media (max-width: 599.98px) {
    .mud-table-cell.fs-nowrap {
        white-space: normal;
        max-width: none;
        text-align: right;
        overflow-wrap: break-word;
    }
}

/* Die untere Leiste liegt fest am Rand, ueber dem Sicherheitsbereich moderner Telefone.
   Jeder Reiter ist mindestens 44 Punkte hoch - kleiner trifft man mit dem Daumen nicht. */
/* Hoehe der unteren Reiterleiste im Mitgliederbereich - EINE Zahl fuer zwei Stellen:
   die Leiste selbst und die Polsterung des Inhalts darueber, der sonst darunter
   verschwindet.

   45px sind nicht gegriffen: 44px Tippziel je Reiter (docs/konzept/19) plus die 1px
   Trennlinie oben. Die Zahl bleibt stabil, weil die Leiste NICHT umbricht - sie steht
   auf "flex-wrap: nowrap" und rollt bei fuenf Reitern waagerecht (Begruendung unten).
   Braeche sie um, muesste diese Zahl mitwachsen, und genau das kann CSS nicht. */
:root {
    --fs-tableiste-hoehe: 45px;
}

.fs-tableiste {
    min-height: var(--fs-tableiste-hoehe);
    position: fixed;
    left: 0;
    right: 0;
    bottom: 0;
    z-index: 1200;
    display: flex;
    padding-bottom: env(safe-area-inset-bottom);
    background: var(--mud-palette-surface);
    border-top: 1px solid var(--mud-palette-lines-default);
    /* Rollt waagerecht, wenn fuenf Reiter mit Text nicht nebeneinander passen - siehe die
       Begruendung an .fs-reiter. "overscroll-behavior-x: contain" haelt die Wischbewegung
       in der Leiste, statt sie an die Seite weiterzureichen; die Rollleiste selbst bleibt
       unsichtbar, sie waere auf 44px Hoehe nur im Weg. */
    overflow-x: auto;
    overscroll-behavior-x: contain;
    scrollbar-width: none;
}

.fs-tableiste::-webkit-scrollbar {
    display: none;
}

/* Korrekturrunde 1 zu Blazor-Plan 4b/Aufgabe 10: Mit dem fuenften Reiter ("Verwaltung")
   lief die Leiste bei Telefonbreite ueber - gemessen bei 390px: nav.scrollWidth 611px
   gegen clientWidth 390px, der fuenfte Reiter komplett ausserhalb des Sichtbereichs
   (x=474-611). Ursache war die klassische Flexbox-Falle: ein Flex-Kind schrumpft ohne
   "min-width: 0" nicht unter seine Inhaltsbreite, MudBlazors Standard-Reiter (Icon neben
   Text, 8px/16px Innenabstand, 14px Schrift) ist dafuer schlicht zu breit. Keine
   Inline-Styles standen dabei im Weg (nachgesehen: weder <nav>, noch der MudNavLink-
   Wrapper, noch <a>/<svg>/<div> tragen ein style-Attribut) - die Klassenregeln unten
   greifen also ungehindert. */
.fs-reiter {
    /* Kein "flex: 1" und kein "min-width: 0" mehr: Der Reiter soll seine Inhaltsbreite
       behalten, damit Symbol und Text nebeneinander Platz haben. Passt die Reihe nicht,
       rollt die Leiste (siehe .fs-tableiste) - sie schrumpft die Reiter nicht mehr. */
    flex: 0 0 auto;
    /* "width: auto" ist noetig, nicht schmueckend: MudBlazor setzt auf .mud-nav-link ein
       "width: 100%". Ohne diese Zeile misst jeder Reiter die volle Leistenbreite - bei
       1440px nachgemessen: scrollWidth 7200 statt der Summe der Inhalte. */
    width: auto;
    min-height: 44px;
    text-align: center;
}

.fs-reiter .mud-nav-link {
    width: auto;
}

/* SECHS Reiter seit dem 2026-09-19 (der Notenreiter kam dazu), und der Nutzer: "in der
   Mein-Bereich-Ansicht ist das Menü zu breit geworden - entweder müssen wir die Begriffe
   kürzen oder nur mit Symbolen arbeiten."

   Beides, in dieser Reihenfolge: Die Aufschriften sind kurz ("Post" statt "Nachrichten",
   "Verw." statt "Verwaltung"), und unterhalb von 600px tritt die Aufschrift UNTER das
   Symbol statt daneben. Damit misst ein Reiter nur noch die Breite seines längsten Wortes
   (~54px) statt Symbol + Abstand + Wort (~100px); sechs davon passen auf 390px.

   Die Aufschrift wird NICHT ausgeblendet. Ein Symbol allein deutet nur, wer die Anwendung
   oft benutzt - und display:none nähme den Text auch Vorleseprogrammen. */
@media (max-width: 599px) {
    /* **Die Leistenhöhe muss mitwachsen.** Gestapelt misst ein Reiter 49px statt 45 -
       gemessen am 2026-09-19. Die Variable speist BEIDE Stellen: die Mindesthöhe der Leiste
       und den unteren Innenabstand des Inhalts darüber (`.fs-mein`). Bliebe sie bei 45px,
       verschwänden die letzten 4px jeder Seite unter der Leiste - derselbe Fehler, der am
       2026-09-15 den Abmelden-Knopf verschluckt hat.

       52px statt der gemessenen 49: drei Pixel Reserve für eine größere Schriftgröße im
       Betriebssystem. */
    :root {
        --fs-tableiste-hoehe: 52px;
    }

    .fs-reiter {
        /* Jetzt schrumpfen sie doch: Mit gestapeltem Inhalt passen sie, und gleich breite
           Reiter treffen sich mit dem Daumen besser als verschieden breite. */
        flex: 1 1 0;
        min-width: 0;
    }

    /* DREI Klassen im Selektor, nicht zwei: MudBlazors eigene Regel für `.mud-nav-link`
       kommt später im Stylesheet und gewänne bei gleicher Spezifität. Nachgemessen am
       2026-09-19 - mit `.fs-reiter .mud-nav-link` blieb `flex-direction` auf `row`, die
       Aufschriften standen weiter neben den Symbolen und wurden abgeschnitten. Dieselbe
       Falle wie bei MudBlazors Abstandsklassen, nur über Spezifität statt `!important`. */
    .fs-tableiste .fs-reiter .mud-nav-link {
        flex-direction: column;
        gap: 2px;
        padding-left: 4px;
        padding-right: 4px;
        justify-content: center;
    }

    /* MudBlazor setzt am Symbol einen rechten Abstand für "Symbol neben Text" - gestapelt
       schöbe er die Spalte aus der Mitte. */
    .fs-tableiste .fs-reiter .mud-nav-link .mud-icon-root {
        margin-right: 0;
    }

    .fs-tableiste .fs-reiter .mud-nav-link-text {
        font-size: 0.7rem;
        line-height: 1.1;
        text-align: center;
        /* Ohne das schneidet MudBlazor den Text mit `text-overflow` ab, statt ihn zu
           zeigen - bei 65px Reiterbreite traf das jedes Wort ("Termir…"). */
        overflow: visible;
        text-overflow: clip;
        white-space: nowrap;
    }
}


/* Symbol NEBEN dem Text, nicht darueber - Nutzervorgabe vom 2026-09-13. Die vorige
   Fassung stellte das Symbol ueber das Label, weil fuenf Reiter nebeneinander auf 360px
   nicht nebeneinander passen. Das stimmt weiterhin: "Nachrichten" allein braucht mehr
   Platz, als ein Fuenftel von 360px hergibt. Geloest wird es jetzt nicht durch Stapeln,
   sondern durch waagerechtes Rollen der Leiste (siehe .fs-tableiste) - die ersten
   Reiter sind sofort da, die letzten eine Wischbewegung entfernt.

   Zielt auf den MudNavLink innerhalb von .fs-reiter, nicht auf .mud-nav-link global: Die
   Seitenleiste der Verwaltung nutzt MudNavLink ebenfalls. */
.fs-reiter .mud-nav-link {
    display: flex;
    flex-direction: row;
    align-items: center;
    justify-content: center;
    gap: 8px;
    padding: 6px 12px;
    white-space: nowrap;
}

.fs-reiter .mud-nav-link-icon {
    width: 22px;
    height: 22px;
}

/* Bewusst kein text-overflow: ellipsis - ein zu "Verwalt…" abgeschnittenes Label waere
   nicht mehr bedienbar. Stattdessen so klein, dass "Nachrichten" und "Verwaltung" (die
   laengsten der fuenf Beschriftungen) bei 360px Geraetebreite noch vollstaendig auf eine
   Zeile passen, mit Luft - nachgemessen, siehe Aufgabe-10-Bericht. 0,69rem (11px) statt
   vormals 0,6rem (9,6px): Die Vorlage loest dieselbe Aufgabe mit 11px
   (frontend/src/components/MitgliedTabBar.tsx) - Schrift ist der falsche Hebel fuer
   Breite (Abschlusspruefung 4b, KLEIN 7). Bei 360px reicht der Platz weiterhin, siehe
   Abschlussfixbericht fuer die nachgemessenen Werte. */
.fs-reiter .mud-nav-link-text {
    font-size: 0.69rem;
    line-height: 1.1;
    white-space: nowrap;
}

/* Das echte <button> in Tabelle.razor (siehe dort) braucht eigene Regeln: Ohne sie sieht
   es aus wie ein Standard-Browser-Knopf statt wie ein Spaltenkopf, und ohne den
   focus-visible-Ring waere es mit der Tastatur erreichbar, aber unsichtbar fokussiert -
   ein globaler Reset irgendwo in MudBlazor nimmt einem rohen <button> den Browser-eigenen
   Fokusring wieder weg. */
.fs-sortknopf {
    background: none;
    border: none;
    padding: 0;
    font: inherit;
    color: inherit;
    cursor: pointer;
}

.fs-sortknopf:focus-visible {
    outline: 2px solid var(--mud-palette-primary);
    outline-offset: 2px;
}

/* Der Datumsblock der Terminkarte (siehe TerminKarte.razor): dunkler Block mit Tag und
   Monat, wie im TS-Original (TerminKarte.tsx). Rein dekorativ (aria-hidden) - das Datum
   steht daneben nochmal ausgeschrieben (TagesdatumLang). */
.fs-datumsblock {
    flex: 0 0 auto;
    width: 52px;
    text-align: center;
    background: var(--mud-palette-dark);
    color: var(--mud-palette-dark-text);
    border-radius: var(--mud-default-borderradius);
    padding: 6px 0 5px;
    line-height: 1;
}

.fs-datumsblock-tag {
    font-size: 22px;
    font-weight: 700;
}

.fs-datumsblock-monat {
    font-size: 11px;
    font-weight: 600;
    margin-top: 3px;
    letter-spacing: 0.06em;
    text-transform: uppercase;
}

/* Der Detailtext eines Protokolleintrags ist meist ein JSON-Rumpf oder ein Stapelabzug:
   Festbreitenschrift, umgebrochen statt gekuerzt (hier ausdruecklich anders als in den
   Tabellenzellen, .fs-nowrap) und in der Hoehe begrenzt, damit der Dialog auf dem Telefon
   nicht ins Endlose waechst. */
.fs-protokoll-details {
    margin: 0;
    padding: 12px;
    background: var(--mud-palette-background-gray);
    border: 1px solid var(--mud-palette-lines-default);
    border-radius: var(--mud-default-borderradius);
    font-family: var(--fs-schrift-mono);
    font-size: 12px;
    white-space: pre-wrap;
    overflow-wrap: break-word;
    max-height: 50vh;
    overflow-y: auto;
}

/* Ein natives <fieldset>/<legend> statt einer MudText-Ueberschrift ueber einer
   Kaestchengruppe (InstrumententypDialog): Nur so sagt ein Vorleseprogramm die Gruppe samt
   Namen an. MudBlazor kennt kein eigenes fieldset, deshalb der Reset hier statt einer
   MudBlazor-Komponente - der Browser-Rahmen und die Standardabstaende sollen nicht
   anders aussehen als die bisherige MudText-Ueberschrift (Abschlusspruefung 4b, KLEIN 6). */
/* Die beschriftete Gruppe eines Formulars (Bausteine/Feldgruppe.razor auf MudField-Basis).
   MudField ist eigentlich fuer ANZEIGEwerte gedacht und gibt seinem Inhalt deshalb eine
   Mindesthoehe und einen Zeigefinger-Mauszeiger; beides stoert, sobald echte Eingabefelder
   darin stehen. Der Innenabstand kommt hier statt ueber InnerPadding, damit die Felder am
   Rahmen nicht kleben. */
.fs-feldgruppe > .mud-input-control-input-container > div {
    min-height: 0;
    cursor: auto;
    padding: 12px 12px 4px;
}

/* Eine Gruppe im Formular hat keinen eigenen Klickzweck - der Zeigefinger von MudField
   verspraeche einen. */
.fs-feldgruppe {
    cursor: auto;
}

/* Die Stellenangabe der Blaettern-Pfeile: dicktengleich, damit "9 / 105" und
   "10 / 105" gleich breit sind und die Pfeile beim Blaettern nicht wandern. */
.fs-blaettern-stand {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
}

/* Die Kennzahl ist die Zahl, nicht der Text daneben: gross, dicktengleich, damit eine
   Reihe von Kacheln nicht wackelt.

   `overflow-wrap: anywhere` ist das Netz fuer lange Betraege. In der Handpruefung von
   Teilplan 4e bei 360 px gemessen: "175.722,90 EUR" ist in 27px-Dickengleich 164 px breit,
   die Kachel bot 126 px - der Betrag ragte auf /statistik in die Nachbarkachel und auf
   /statistik/termine ueber den Seitenrand (scrollWidth 366 > clientWidth 360, also
   waagerechtes Rollen der ganzen Seite; CLAUDE.md verbietet genau das). Eine Zahl ohne
   Leerzeichen bietet von sich aus keine Umbruchstelle, deshalb `anywhere` statt
   `break-word`. Auf breiten Schirmen aendert die Regel nichts: Sie greift nur, wenn es
   sonst ueberliefe. Kein bUnit-Test kann das sehen - bUnit rechnet kein CSS. */
.fs-kennzahl-wert {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
    font-size: 27px;
    font-weight: 500;
    line-height: 1.1;
    overflow-wrap: break-word;
}

/* Der Balken einer BalkenListe. Die Rinne traegt die 100-%-Marke, die Fuellung den
   Anteil - beide ohne feste Breite, damit sie sich der Spalte anpassen. */
.fs-balken {
    height: 8px;
    border-radius: 4px;
    background: var(--mud-palette-lines-default);
    overflow: hidden;
}

.fs-balken-fuellung {
    height: 100%;
    border-radius: 4px;
    background: var(--mud-palette-primary);
}

.fs-balken-zahl {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
    white-space: nowrap;
    flex-shrink: 0;
}

/* Die Werteangabe neben einem Jahresbalken ist ein ganzer Satz ("16 teilgenommen ·
   15 zugesagt · 20 moeglich"), keine kurze Zahl - sie traegt darum NICHT `fs-balken-zahl`.
   Mit dessen `white-space: nowrap; flex-shrink: 0` schob die Zeile die ganze Seite
   waagerecht: scrollWidth 439 bei clientWidth 400 bzw. 360 (Befund B1 der Handpruefung),
   und der Seitenrumpf darf bei 400 px nicht waagerecht scrollen. Ziffernstellung wie bei
   `fs-balken-zahl`, aber umbrechend und schrumpffaehig - `min-width: 0` hebt die Vorgabe
   `min-width: auto` eines Flex-Elements auf, ohne die ein Flex-Element nicht unter seine
   Inhaltsbreite schrumpft. */
.fs-jahresbalken-werte {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
    min-width: 0;
    text-align: right;
}

/* Geschichtete Jahresbalken (Mitgliedsstatistik): die Rinne `fs-balken` ist "moeglich",
   darueber liegen Zusagen und Teilnahmen als Anteile daran. Beide absolut positioniert,
   damit sie uebereinander liegen statt nebeneinander - teilgenommen steht im Markup
   hinter zugesagt und liegt darum obenauf. */
.fs-jahresbalken .fs-balken {
    position: relative;
}

.fs-jahresbalken-zugesagt,
.fs-jahresbalken-teilgenommen {
    position: absolute;
    top: 0;
    bottom: 0;
    left: 0;
    border-radius: 4px;
}

.fs-jahresbalken-zugesagt {
    background: var(--mud-palette-primary);
}

.fs-jahresbalken-teilgenommen {
    background: var(--mud-palette-success);
}

/* Die Legende benutzt dieselben Farbklassen wie die Balken - "position: static" holt die
   Kaestchen aus der absoluten Lage zurueck (sie steht hier bewusst NACH den beiden Regeln
   oben, damit sie bei gleicher Spezifitaet gewinnt). */
.fs-legende {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    font-size: 0.8rem;
}

.fs-legende-farbe {
    position: static;
    width: 11px;
    height: 11px;
    border-radius: 3px;
}

.fs-legende-moeglich {
    background: var(--mud-palette-lines-default);
}

/* Kennzahlen-Reihe und Diagrammgitter: so viele Spalten, wie nebeneinander passen, und
   auf dem Telefon eine. Kein Breakpoint von Hand - auto-fit erledigt genau das. */
.fs-kennzahlen {
    display: grid;
    /* 150px waren zu wenig: "Einnahmen" mit einem Eurobetrag darunter brach um. 220px
       traegt die laengste Beschriftung des Projekts samt Wert in einer Zeile; passt die
       Reihe nicht mehr, wandert eine Kachel in die naechste - genau das soll auto-fit. */
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: 12px;
}

/* Der Wert in einer Kennzahlenkachel bricht nicht um - lieber schrumpft die Schrift, als
   dass "1.234,56 €" auf zwei Zeilen steht. */
.fs-kennzahlen .fs-kennzahl-wert {
    white-space: nowrap;
}

.fs-diagrammgitter {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
    gap: 16px;
}

/* Der Dateiname in der Anhangsliste ist ein echtes <button> (nur so ist er per Tabulator
   erreichbar - siehe die Begruendung in Dateiliste.razor), und MudBlazor gibt jedem Knopf
   `text-transform: uppercase`. Auf einem Dateinamen verfaelscht das den Eigennamen:
   "Wegweiser D1-D2-D3.pdf" stand als "WEGWEISER D1-D2-D3.PDF" da (Befund B3 der
   Handpruefung). Die Vorgabe "Material wie es kommt" gilt weiter - sie wird hier an genau
   einer Stelle abgeschaltet, und das ist der Grund dafuer. */
.fs-dateiname {
    text-transform: none;
}

/* Die Filterschalter der Mitgliederliste: ein echtes <button> mit aria-pressed, damit der
   Zustand nicht nur an der Farbe haengt. 44px Hoehe - kleiner trifft man mit dem Daumen
   nicht (globale Vorgabe). */
/* Die Schalter einer Vorauswahl (/mitglieder, /musikstuecke, Agenda/Tabelle auf
   /termine). Sie sehen aus wie die Reiter der Statistik und sind auch genauso gross -
   Nutzervorgabe vom 2026-09-16, zweimal: erst die Form, dann ausdruecklich auch die Hoehe
   ("die sind zu hoch - ich sagte extra so wie in Statistik").

   Die Werte sind nicht gegriffen, sondern an einem Statistikreiter gemessen (Chromium,
   2026-09-16): MudButton mit Size.Small ergibt 30,75 px Hoehe aus "padding: 3px 9px" und
   13 px Schrift, dazu die Themerundung. Feste Zahlen, weil MudBlazor seine Groessenstufen
   nicht als CSS-Variablen herausgibt - der Kommentar haelt fest, woher sie stammen.

   **Ausnahme von "Bedienziele sind 44 px"** (19-frontend-referenz, Gestaltung): Die
   Statistikreiter selbst sind seit jeher 30 px und werden auch auf dem Telefon bedient;
   eine Vorauswahl, die hoeher waere als die Reiter daneben, faellt im Vergleich staerker
   auf als die fehlenden 13 px. Die Entscheidung liegt beim Nutzer, nicht in dieser Datei. */
.fs-filterschalter {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    padding: 3px 9px;
    border: 1px solid var(--mud-palette-lines-default);
    border-radius: var(--mud-default-borderradius);
    background: var(--mud-palette-surface);
    color: var(--mud-palette-text-primary);
    font-family: inherit;
    font-size: 0.8125rem;
    line-height: 1.75;
    cursor: pointer;
}

.fs-filterschalter[aria-pressed="true"] {
    border-color: var(--mud-palette-primary);
    background: var(--mud-palette-primary);
    color: var(--mud-palette-primary-text);
    font-weight: 600;
}

.fs-filterschalter:focus-visible {
    outline: 2px solid var(--mud-palette-primary);
    outline-offset: 2px;
}

/* Die Werkzeugleiste der Tabelle DARF umbrechen. MudToolBar steht auf "nowrap" und einer
   festen Hoehe von 64 px - mit der Vorauswahl darin (seit v3.1.16) reichte das nicht mehr:
   Bei 1400 px gemessen summierten sich Suche, vier Schalter, Trenner und vier Knoepfe auf
   1067 px in einer 1108 px breiten Leiste. Die Leiste selbst blieb einzeilig, dafuer brach
   der Inhalt auf: "Alle 105" rutschte unter die uebrigen Schalter und "Neues Mitglied"
   wurde zweizeilig - genau das, was die Vorauswahl aus dem eigenen Kasten heraus vermeiden
   sollte.

   Umgekehrt herum ist es richtig: Die LEISTE bricht um, ihre Teile bleiben ganz. */
.mud-table .mud-toolbar {
    flex-wrap: wrap;
    height: auto;
    min-height: 64px;
    /* Waagerecht wie senkrecht derselbe Abstand. Vorher stand hier nur "row-gap", und
       "column-gap" blieb auf "normal", also 0 - am Dateibrowser nachgemessen klebten alle
       vier Luecken der Leiste auf 0 px, Suchfeld an Kategorie an Knopf an Menue. Was
       dazwischen Luft hatte, hatte sie nur zufaellig aus einem Margin der jeweiligen
       MudBlazor-Komponente (Nutzerbefund vom 2026-09-16). */
    gap: 8px;
}

/* Eine Knopfaufschrift bricht nicht mitten im Wort um - der Knopf geht lieber in die
   naechste Zeile der Leiste. */
.mud-table .mud-toolbar .mud-button-root {
    white-space: nowrap;
}

/* Die Gruppe der Vorauswahl-Schalter in der Werkzeugleiste (/mitglieder) oder im
   Seitenkopf (/termine). "flex-shrink: 0" ist das Entscheidende: Ohne es staucht die
   Leiste zuerst diese Gruppe, und sie bricht intern um, statt dass die Leiste umbricht.
   Auf dem Telefon darf sie das weiterhin - dann ist sie das Breiteste der Zeile. */
.fs-vorauswahl {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
    flex-shrink: 0;
    /* "flex-shrink: 0" allein setzt die Breite auf die aller vier Schalter nebeneinander
       (378 px gemessen) - bei 390 px Schirmbreite lief die Seite damit waagerecht ueber
       (411 gegen 390, mit scrollWidth nachgemessen). "max-width: 100%" deckelt sie auf den
       vorhandenen Platz; dann greift das eigene flex-wrap der Gruppe und sie bricht intern
       um. Beides zusammen ergibt die gewuenschte Reihenfolge: Erst bricht die LEISTE um,
       und erst wenn auch das nicht mehr reicht, die Gruppe selbst. */
    max-width: 100%;
}

/* Der senkrechte Strich zwischen dem Eingrenzen und dem Anlegen. Genau EIN Nutzer: der
   Seitenkopf von /termine, wo Jahr, Ansichtsumschalter und "Neuer Termin" nebeneinander
   stehen. In der Werkzeugleiste der Tabelle braucht es ihn nicht - dort trennt der
   MudSpacer die beiden Seiten. MudDivider bringt Farbe und Staerke mit; hier steht nur, wie
   hoch er sein darf und wie viel Luft er braucht.

   "align-self: stretch" allein ergaebe die volle Zeilenhoehe einschliesslich des Umbruchs -
   auf Telefonbreite also einen Strich quer durch zwei Knopfreihen. Die feste Hoehe haelt ihn
   an der Hoehe eines Knopfes. */
.fs-werkzeugtrenner {
    height: 24px;
    align-self: center;
    margin: 0 4px;
}

/* "3 ausgewählt" vor den Sammelaktionen des Dateibrowsers. Gedaempft und klein: Die Zahl
   ist eine Auskunft ueber den Zustand, kein Bedienelement - sie darf neben den Knoepfen
   nicht um Aufmerksamkeit ringen. `white-space: nowrap` haelt sie beim Umbruch der Leiste
   zusammen, sonst stuende "3" am Ende der einen und "ausgewählt" am Anfang der naechsten
   Zeile. */
.fs-auswahlzahl {
    font-size: 0.875rem;
    color: var(--mud-palette-text-secondary);
    white-space: nowrap;
    align-self: center;
    margin-right: 4px;
}

.fs-filterzahl {
    font-family: var(--fs-schrift-mono);
    font-variant-numeric: tabular-nums;
    font-size: 0.8em;
}

/* Die Unterlisten am Mitglied (Instrumente, Erziehungsberechtigte): eine schlichte Liste
   aus Zeilen, kein MudTable - es gibt nichts zu sortieren und nichts zu durchsuchen. */
.fs-schlichteliste {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 8px;
}

.fs-schlichteliste > li {
    display: flex;
    align-items: center;
    gap: 12px;
    flex-wrap: wrap;
    min-height: 44px;
    padding: 4px 12px;
    border: 1px solid var(--mud-palette-lines-default);
    border-radius: var(--mud-default-borderradius);
}

/* Eine Zeile der Terminagenda. Ein echtes <a> statt eines <button> (siehe
   Terminagenda.razor): per Tabulator erreichbar, im Kontextmenue zu oeffnen - und ein
   <button> duerfte die Statusmarke nicht enthalten. */
.fs-agendazeile {
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
  padding: 10px 14px;
  border: 1px solid var(--mud-palette-lines-default);
  border-radius: var(--mud-default-borderradius);
  background: var(--mud-palette-surface);
  color: inherit;
  text-decoration: none;
}

.fs-agendazeile:hover {
  background: var(--mud-palette-action-default-hover);
}

.fs-agendazeile:focus-visible {
  outline: 2px solid var(--mud-palette-primary);
  outline-offset: 2px;
}

/* Stornierte Termine werden zurueckgenommen, nicht bunter gemacht. Der Klartext der
   Statusmarke steht trotzdem da - der Zustand haengt nie allein an der Darstellung. */
.fs-agenda-storniert {
  opacity: 0.6;
}

.fs-agenda-storniert .fs-agendatitel {
  text-decoration: line-through;
}

/* Datumsblock links - der Anker der Zeile. Feste Breite, damit die Titel untereinander
   fluchten; dicktengleiche Ziffern, damit "9." und "30." gleich breit stehen. */
.fs-agendatag {
  flex: 0 0 2.75rem;
  display: flex;
  flex-direction: column;
  align-items: center;
  border-right: 1px solid var(--mud-palette-lines-default);
  padding-right: 12px;
}

.fs-agendatag-wochentag {
  font-size: 0.7rem;
  text-transform: uppercase;
  color: var(--mud-palette-text-secondary);
}

.fs-agendatag-tag {
  font-variant-numeric: tabular-nums;
  font-size: 1.25rem;
  line-height: 1.1;
}

/* min-width: 0 ist nicht schmueckend: Ohne es waechst ein langer Titel ueber die
   Flexzeile hinaus, statt zu kuerzen - und die Seite scrollt waagerecht. */
.fs-agendatext {
  flex: 1 1 10rem;
  min-width: 0;
  display: flex;
  flex-direction: column;
}

.fs-agendatitel {
  font-weight: 600;
}

.fs-agendazweit {
  font-size: 0.85rem;
  color: var(--mud-palette-text-secondary);
}

.fs-agendamarken {
  flex: 0 0 auto;
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
}

/* Die Statusmarke: ein <span> mit Klasse, kein MudChip - ein MudChip in einem <a> waere
   ein Bedienelement im Bedienelement. Der Text traegt die Bedeutung, die Farbe verstaerkt
   sie nur (globale Vorgabe: Zustand nie allein ueber Farbe). */
.fs-agendastatus {
  border: 1px solid currentColor;
  border-radius: 999px;
  padding: 2px 9px;
  font-size: 0.75rem;
  white-space: nowrap;
}

/* Statusfarben als SCHRIFT - deshalb die abgedunkelten Textfassungen, siehe oben.
   "fs-status-offen" nimmt Signal, weil das Konzept nur einen Akzent kennt und eine
   zweite Goldnuance neben Brass nicht zu unterscheiden waere. */
.fs-status-gut { color: var(--fs-moss-text); }
.fs-status-offen { color: var(--mud-palette-warning); }
.fs-status-kritisch { color: var(--mud-palette-error); }
.fs-status-neutral { color: var(--mud-palette-text-secondary); }

.fs-agendazusagen {
  font-variant-numeric: tabular-nums;
  font-size: 0.8rem;
  color: var(--mud-palette-text-secondary);
  white-space: nowrap;
}

/* Alle Zusagen da: gruen statt gedaempft - dieselbe Auskunft wie in der Vorlage
   (TerminAgenda.tsx faerbt den Zaehler, sobald `offen === 0`). Die Zahl "12/12 zugesagt"
   steht in beiden Faellen da, die Farbe ist nur die Verstaerkung. */
.fs-agendazusagen-voll {
  /* Textfassung von Moss - als Schrift reicht der volle Ton nicht, siehe oben. */
  color: var(--fs-moss-text);
}

/* Hier stand eine Regel `.fs-besetzungszeile` fuer die Zeilen der Mindestbesetzung im
   Terminformular - ENTFERNT, weil sie nachweislich nichts tat. Die Zeilen sind <li> in
   einer `ul.fs-schlichteliste`, und `.fs-schlichteliste > li` (0,1,1) schlaegt eine blosse
   `.fs-besetzungszeile` (0,1,0) bei JEDER ihrer Erklaerungen - dieselbe Fehlerklasse wie
   bei `fs-zustellzeile` und `fs-besetzungsstand` weiter unten, die den Listenselektor
   deshalb mittragen.

   Nachgemessen im Browser, nicht ueberlegt: dasselbe <li> einmal mit und einmal ohne die
   Klasse in derselben Liste ergab Zeichen fuer Zeichen dieselben errechneten Werte
   (display flex, align-items center, gap 12px, padding 4px 12px, Rahmen 1px, Radius 6px,
   min-height 44px). Die Klasse bleibt am Markup: Sie ist der Testhaken auf die Zeilen
   (`li.fs-besetzungszeile` in TerminBearbeitenTests) und traegt dort keine Gestaltung.

   Denselben Namen trug bis dahin auch die Anzeige unter dem Formular - zwei Regelbloecke
   fuer eine Klasse in zwei verschiedenen Bausteinen. Die Anzeige ist inzwischen eine
   Tabelle mit eigenen Namen (`fs-besetzungstabelle`, siehe unten), damit ist der Name
   wieder eindeutig. */

/* Die Zusagenfarben der Zusagenliste am Termin - Gegenstueck zu `zusageZeilenStil` in
   frontend/src/components/zusageDarstellung.ts, und zwar wortgleich in der Absicht:
   Abgesagte werden ZURUECKGENOMMEN (gedaempft, Name durchgestrichen) statt rot
   angestrichen, damit Farbe ein Signal fuer das bleibt, was Aufmerksamkeit braucht;
   Zugesagte heben sich dezent gruen ab, mit einem Balken links als zweitem Merkmal
   neben der Flaechenfarbe; Offene bleiben neutral und tragen deshalb gar keine Klasse.

   Der Klartext steht in beiden Faellen in der Spalte "Zusage" daneben - der Zustand
   haengt nie allein an der Farbe (globale Vorgabe). Die Klassen gehen ueber
   `Tabelle<T>.ZeilenKlasse` an MudTable.RowClassFunc und landen auf dem <tr>. */
tr.fs-zusage-abgesagt {
  opacity: 0.55;
}

tr.fs-zusage-abgesagt td[data-label="Musiker"] {
  text-decoration: line-through;
}

/* box-shadow statt border-left: Ein Rahmen an der ersten Zelle verschoebe die Spalte
   gegenueber den uebrigen Zeilen; der Schatten liegt darueber und kostet keine Breite. */
tr.fs-zusage-zugesagt {
  background: var(--mud-palette-success-hover);
  box-shadow: inset 3px 0 0 0 var(--mud-palette-success);
}

/* Die beiden Kartenknoepfe von Bausteine/Kartenlinks (Befund L1 der Handpruefung von
   Teilplan 4d). Sie standen mit MudBlazors kleiner Groessenstufe bei 26 x 26 px - das
   kleinste Bedienziel des Projekts, ausgerechnet auf /mein/termine, das man am
   Strassenrand mit dem Daumen bedient. Die Groessenstufe ist weg; die 44px stehen hier,
   damit sie nicht an einem Vorgabewert des Pakets haengen, der sich mit dem naechsten
   Paket verschieben kann (globale Vorgabe: kleiner trifft man mit dem Daumen nicht). */
.fs-kartenknopf {
  min-width: 44px;
  min-height: 44px;
}

/* Die Vorschau im VorschauDialog. Die Hoehen stehen hier und nicht als Inline-Stil, weil
   ein `style="…"` an einem Element eine CSS-Klasse nicht ueberschreiben LAESST (die
   Umkehrung der Lehre aus CLAUDE.md) - und weil drei Zahlen an einem Ort besser zu finden
   sind als in drei Zweigen eines switch.

   `70vh` statt einer festen Pixelhoehe: Auf dem Telefon ist der Dialog ohnehin
   bildschirmfuellend, auf dem PC soll das PDF so hoch sein, wie das Fenster hergibt. Die
   Breite regelt MudBlazor ueber MaxWidth.Large + FullWidth. */
.fs-vorschau-pdf {
  width: 100%;
  height: 70vh;
  border: none;
  display: block;
}

.fs-vorschau-video {
  width: 100%;
  max-height: 70vh;
  display: block;
}

.fs-vorschau-audio {
  width: 100%;
}

/* Das Bild passt sich dem Fenster an, statt es zu sprengen: `max-width`/`max-height` statt
   fester Masse, damit ein Vereinslogo (120 x 120) nicht hochskaliert und ein Foto mit
   4000 Pixeln Breite nicht ueber den Rand laeuft. Der karierte Hintergrund macht
   durchsichtige Bereiche eines PNG oder GIF sichtbar - sonst steht ein weisses Logo auf
   weissem Grund und sieht aus wie ein Ladefehler. */
.fs-vorschau-bild {
    display: block;
    margin: 0 auto;
    max-width: 100%;
    max-height: 70vh;
    object-fit: contain;
    background-color: var(--mud-palette-background-grey);
    background-image:
        linear-gradient(45deg, rgba(0, 0, 0, .06) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, .06) 75%),
        linear-gradient(45deg, rgba(0, 0, 0, .06) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, .06) 75%);
    background-size: 16px 16px;
    background-position: 0 0, 8px 8px;
}

/* Der Nachrichtentext behaelt seine Absaetze: Er wurde in ein Textfeld getippt, und ein
   Zeilenumbruch darin ist Absicht. `overflow-wrap`, damit eine lange Adresse ohne
   Leerzeichen die Seite bei 360 px nicht waagerecht schiebt. */
.fs-nachrichtentext {
  white-space: pre-wrap;
  overflow-wrap: break-word;
}

/* Eine Zeile des Zustellprotokolls. `.fs-schlichteliste > li` ist eine Flex-Zeile (siehe
   oben); hier soll der Fehlertext UNTER der Zeile stehen, zu der er gehoert, nicht daneben.
   `display: block` statt einer zweiten Listenklasse: Die gemeinsame Liste bleibt damit die
   bestehende `fs-schlichteliste` (Befund S2-2), nur diese eine Zeile richtet sich anders
   aus. Die 44-px-Mindesthoehe der Liste gilt weiter.

   QUALIFIZIERT geschrieben, und das ist der ganze Punkt: `.fs-zustellzeile` allein wiegt
   (0,1,0) und verlor gegen `.fs-schlichteliste > li` (0,1,1) - die Regel war wirkungslos,
   der Fehlertext stand weiter NEBEN seiner Zeile (Befund aus Aufgabe 8, dieselbe
   Fehlerklasse wie M-1/M-2). `.fs-schlichteliste > li.fs-zustellzeile` wiegt (0,2,1) und
   schlaegt sie. bUnit rechnet kein CSS - kein Test kann das fangen, die Spezifitaet ist
   beim Schreiben nachgerechnet und in der Handpruefung mit `getComputedStyle` zu messen. */
.fs-schlichteliste > li.fs-zustellzeile {
  display: block;
}

/* Der Fehlertext eines gescheiterten Versands ("550 unbekannter Empfaenger") ist eine
   Serverantwort und kann beliebig lang sein. */
.fs-fehlertext {
  font-size: 0.75rem;
  overflow-wrap: break-word;
}

/* -- Diagramme der Statistik (Teilplan 4e) ------------------------------------------- */

/* Die Farbfolge der Diagramme, in ZWEI getrennten Familien. Acht Stufen, damit auch acht
   Instrumententypen in einer Torte unterscheidbar bleiben; darueber hinaus beginnt die
   Folge von vorn (`i % 8`). Sie sind aus der MudBlazor-Palette gezogen, nicht aus den
   Markenfarben der Vorlage - "Material wie es kommt".

   Als KLASSEN, nicht als `stroke`/`fill`-Attribute: Ein Attribut im Markup liesse sich
   nicht in einem spaeteren Farbschema-Durchgang austauschen (Merker
   `fortissimo-blazor-ui-qualitaet-unzureichend`), und es stuende achtmal im Markup statt
   einmal hier.

   **Warum getrennt und nicht eine Klasse, die beides setzt** (Befund S2-4 der
   Vorabpruefung): `fill="none"` am <circle> des Rings ist ein PRAESENTATIONSATTRIBUT, und
   jede CSS-Deklaration schlaegt es (in der Kaskade zaehlt es wie eine Autorenregel mit
   Spezifitaet 0 ganz am Anfang des Stylesheets):

     eine Klasse mit stroke UND fill -> fill: rgb(25,118,210)   <- der Ring wird eine SCHEIBE
     nur-stroke-Klasse              -> fill: none, stroke: rgb(25,118,210)   <- richtig
     nur-fill-Klasse (Torte)        -> fill: rgb(25,118,210), stroke: none   <- richtig

   Kein bUnit-Test haette das gesehen: `stroke-dasharray`, `stroke-dashoffset` und die
   Klasse bleiben in beiden Fassungen richtig.

   Die beiden zweifelhaften Stufen sind 5 (`--mud-palette-tertiary`) und 7
   (`--mud-palette-dark`): Sie stehen NICHT in MudBlazor.min.css, weil der
   MudThemeProvider die Palettenvariablen erst zur Laufzeit aus dem `MudTheme` erzeugt.
   Nachgesehen wurde deshalb am Typ: `MudBlazor.Palette` traegt in 9.9 sowohl `Tertiary`
   (samt `TertiaryDarken`/`TertiaryLighten`/`TertiaryContrastText`) als auch `Dark` -
   beide Variablen werden also gesetzt. **Gegen das Paket geprueft, nicht im Browser
   gemessen**; ein Balken ohne Farbe waere unsichtbar und kein Test saehe es, deshalb
   steht die Farbprobe im Browser als Merker fuer die Handpruefung (Aufgabe 10). */
.fs-strichfarbe-0 { stroke: var(--mud-palette-primary); }
.fs-strichfarbe-1 { stroke: var(--mud-palette-success); }
.fs-strichfarbe-2 { stroke: var(--mud-palette-info); }
.fs-strichfarbe-3 { stroke: var(--mud-palette-warning); }
.fs-strichfarbe-4 { stroke: var(--mud-palette-secondary); }
.fs-strichfarbe-5 { stroke: var(--mud-palette-tertiary); }
.fs-strichfarbe-6 { stroke: var(--mud-palette-error); }
.fs-strichfarbe-7 { stroke: var(--mud-palette-dark); }

.fs-fuellfarbe-0 { fill: var(--mud-palette-primary); }
.fs-fuellfarbe-1 { fill: var(--mud-palette-success); }
.fs-fuellfarbe-2 { fill: var(--mud-palette-info); }
.fs-fuellfarbe-3 { fill: var(--mud-palette-warning); }
.fs-fuellfarbe-4 { fill: var(--mud-palette-secondary); }
.fs-fuellfarbe-5 { fill: var(--mud-palette-tertiary); }
.fs-fuellfarbe-6 { fill: var(--mud-palette-error); }
.fs-fuellfarbe-7 { fill: var(--mud-palette-dark); }

/* Ein Legendenkaestchen ist ein <span> und hat kein `fill` - diese Regel uebersetzt die
   Fuellfamilie in einen Hintergrund. Zwei Klassen als Selektor, damit sie die Grundfarbe
   wirklich ueberschreibt. */
.fs-legende-farbe.fs-fuellfarbe-0 { background: var(--mud-palette-primary); }
.fs-legende-farbe.fs-fuellfarbe-1 { background: var(--mud-palette-success); }
.fs-legende-farbe.fs-fuellfarbe-2 { background: var(--mud-palette-info); }
.fs-legende-farbe.fs-fuellfarbe-3 { background: var(--mud-palette-warning); }
.fs-legende-farbe.fs-fuellfarbe-4 { background: var(--mud-palette-secondary); }
.fs-legende-farbe.fs-fuellfarbe-5 { background: var(--mud-palette-tertiary); }
.fs-legende-farbe.fs-fuellfarbe-6 { background: var(--mud-palette-error); }
.fs-legende-farbe.fs-fuellfarbe-7 { background: var(--mud-palette-dark); }

/* Die Summe in der Mitte des Rings. */
.fs-ringmitte {
    font-family: var(--fs-schrift-mono);
    font-size: 20px;
    font-weight: 500;
    fill: var(--mud-palette-text-primary);
}

/* Die Legende neben Ring und Torte. */
.fs-legendenliste {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 4px;
}

/* Die Trennlinie zwischen zwei Tortensegmenten - in der Hintergrundfarbe der Karte, damit
   sie als Spalt wirkt statt als Rahmen. Eigene Klasse statt eines `stroke`-Attributs am
   <path>: Ein Praesentationsattribut traegt keine CSS-Variable des Themes.

   Nur `stroke`, getrennt von der Fuellfamilie (`.fs-fuellfarbe-N`, die nur `fill` setzt) -
   dieselbe Trennung wie beim Ring, wo eine Klasse mit beidem aus dem Ring eine gefuellte
   Scheibe machte. Beide Klassen stehen am selben <path> und wiegen gleich viel (0,1,0);
   weil sie verschiedene Eigenschaften setzen, gibt es nichts zu ueberschreiben. */
.fs-tortensegment { stroke: var(--mud-palette-surface); }

/* Die Bereichskarten auf /statistik: Die ganze Karte ist das Klickziel. `display: block`
   und `height: 100%`, damit der MudLink die MudPaper wirklich umschliesst und alle sechs
   Karten in einer Gitterzeile gleich hoch sind.

   Die Textfarbe steht hier bewusst NICHT: `color: inherit` war wirkungslos, weil MudBlazor
   dem Verweis `mud-primary-text` mit `!important` gibt und eine Autorenregel ohne
   `!important` das nie schlaegt (Befund M-1). Geregelt wird sie stattdessen am Bauteil
   selbst - `Color="Color.Inherit"` am MudLink. */
.fs-bereichskarte {
    display: block;
    height: 100%;
}

/* Der Verlauf zieht sich auf die Spaltenbreite; die Hoehe setzt die Komponente inline,
   weil sie ein Parameter ist. */
.fs-verlauf { width: 100%; display: block; overflow: visible; }
.fs-verlauf-hilfslinie { stroke: var(--mud-palette-lines-default); }
.fs-verlauf-linie { stroke: var(--mud-palette-primary); }
.fs-verlauf-flaeche { fill: var(--mud-palette-primary); opacity: 0.14; }
.fs-verlauf-punkt { fill: var(--mud-palette-primary); }

/* Zwei zusaetzliche Farben fuer Balken und Verlaeufe, die neben einer anderen Reihe
   stehen und Gegenteiliges zeigen (Eintritte gegen Austritte, Zusagen gegen Ausfaelle).
   Zwei Klassen als Selektor, damit sie die Grundfarbe wirklich ueberschreiben. */
.fs-balken-fuellung.fs-farbe-gut { background: var(--mud-palette-success); }
.fs-balken-fuellung.fs-farbe-kritisch { background: var(--mud-palette-error); }
.fs-verlauf-linie.fs-farbe-gut { stroke: var(--mud-palette-success); }
.fs-verlauf-flaeche.fs-farbe-gut { fill: var(--mud-palette-success); }
.fs-verlauf-punkt.fs-farbe-gut { fill: var(--mud-palette-success); }

/* Eine Zeile der Besetzungsliste auf /statistik/termine: Trennlinien wie in der Vorlage,
   ohne eigene Tabelle. Der Selektor traegt die Liste mit, weil `.fs-schlichteliste > li`
   (0,1,1) sonst gewinnt - eine blosse `.fs-besetzungsstand`-Regel (0,1,0) waere
   wirkungslos, gleichgueltig an welcher Stelle der Datei sie steht. */
.fs-schlichteliste > li.fs-besetzungsstand {
    border: none;
    border-bottom: 1px solid var(--mud-palette-lines-default);
    border-radius: 0;
    padding: 10px 0;
}


/* Befund B-09: Im Mitgliederbereich standen die Zeilen zu weit auseinander. Gemessen an
   einer Terminkarte auf 360px: 468px Hoehe, davon allein 64px fuer eine zweizeilige
   Ueberschrift - MudBlazors h6 bringt 32px Zeilenhoehe auf 20px Schrift mit (Faktor 1,6),
   was fuer eine Ueberschrift ueber zwei Zeilen zu luftig ist.

   Nur hier und nicht global: In der Verwaltung stehen dieselben Groessen in Tabellen, wo
   der Abstand die Zeilen trennt. Diese Seiten sind Karten-Feeds, die man am Telefon
   ueberfliegt. */
/* Der Inhalt des Mitgliederbereichs endet ueber der festen Reiterleiste, nicht dahinter.

   Die Leiste liegt mit "position: fixed" ueber dem Inhalt und nimmt ihm keinen Platz weg -
   ohne diese Polsterung sitzt die unterste Bedienzeile jeder Seite unerreichbar darunter.
   Gemessen am 2026-09-15, bevor es das hier gab: der Abmelden-Knopf auf dem Profil lag
   5px unter der Leiste, "Was ist neu" 26px, auf der Terminseite die Zusagen- und
   Absagen-Knoepfe der letzten Karte.

   Drei Summanden, jeder mit einem Grund:
   - die Leistenhoehe, aus derselben Variable wie die Leiste selbst,
   - der Sicherheitsbereich moderner Telefone (die Leiste polstert sich darum ebenfalls),
   - 16px Luft, damit das letzte Element die Leiste nicht beruehrt - derselbe Wert, den
     "pa-4" ringsum gibt.

   **Ohne "!important", und das ist Absicht:** MitgliedLayout traegt deshalb "px-4 pt-4"
   statt "pa-4". MudBlazors Abstandsklassen sind "!important"; gegen "pa-4" kaeme diese
   Regel nicht an, und ein zweites "!important" waere ein Wettruesten ohne Sieger. */
.fs-mein {
    padding-bottom: calc(var(--fs-tableiste-hoehe) + env(safe-area-inset-bottom) + 16px);
}

.fs-mein .mud-typography-h6 {
    line-height: 1.3;
}

.fs-mein .mud-card-content {
    padding: 12px;
}

/* Die beschrifteten Zeilen einer Karte (Treffpunkt, Auftrittsort) ruecken enger
   zusammen - sie gehoeren zusammen und sind kein eigener Absatz.

   Diese Regel war bis zum 2026-09-15 WIRKUNGSLOS: Die Zeilen trugen im Markup eigene
   "mt-3"/"mt-2", und MudBlazors Abstandsklassen stehen in ihrer eigenen Datei weiter
   hinten - gleiche Spezifitaet, spaetere Regel, sie gewannen. Erst seit die Klassen aus
   TerminKarte.razor draussen sind, greift der Wert hier. */
.fs-mein .mud-card-content > * + * {
    margin-top: 8px;
}

/* Der Ablaufplan-Ausklapper: MudBlazor gibt seinem Kopf 48px Mindesthoehe plus Polster,
   zusammen gemessene 56px fuer eine Zeile Text. In einer Karte, die kompakt sein soll,
   ist das die teuerste Zeile ohne Inhalt. */
.fs-mein .fs-ablaufplan .mud-expand-panel-header {
    min-height: 0;
    padding-top: 6px;
    padding-bottom: 6px;
}

.fs-mein .fs-ablaufplan .mud-expand-panel-text {
    padding: 0 0 8px;
}

/* Die Handlungsleiste der Terminkarte traegt keinen eigenen Rahmen - sie gehoert zum
   Karteninhalt und nicht als abgesetzter Fuss darunter. */
.fs-mein .fs-terminkarte .mud-card-actions {
    border-top: none;
}


/* Die Ladeanzeige: das Abzeichen dreht sich, daneben steht, was gerade passiert.
   "prefers-reduced-motion" haelt das Bild still - wer Bewegung abgestellt hat, soll von
   ihr nicht bedraengt werden; der Text bleibt und sagt dasselbe. */
/* Die Spaltenauswahl der Tabelle - unterhalb von 960 px weg. Dieselbe Marke, an der die
   MudTable in die Kartenansicht faellt (Breakpoint="Sm" in Tabelle.razor): Wo es keine
   Spalten mehr gibt, ist auch nichts zu waehlen. Die Begruendung, warum das hier per CSS
   geht und nicht gerendert werden muss, steht an der Nutzungsstelle. */
@media (max-width: 959.98px) {
    .fs-spaltenwahl {
        display: none;
    }
}

.fs-laden {
    display: flex;
    align-items: center;
    /* Mittig, nicht am linken Rand: Der Ladehinweis steht dort, wo gleich der Inhalt
       steht, und nicht in der Ecke geklemmt (Wunsch des Nutzers vom 2026-09-15). */
    justify-content: center;
    gap: 12px;
}

.fs-ladekreisel {
    animation: fs-drehen 1.1s linear infinite;
}

.fs-ladetext {
    color: var(--mud-palette-text-secondary);
    font-size: 0.875rem;
}

@keyframes fs-drehen {
    to { transform: rotate(360deg); }
}

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

/* Die Werkzeugleiste der Tabelle (Suchfeld, Anlegen, Drucken, Spaltenauswahl).
   Nach unten trennt eine Linie die Leiste von den Spaltenkoepfen.

   Die 8px oben und unten sind der Abstand, den das Suchfeld braucht, seit es nicht mehr
   die ganze Leistenhoehe fuellt (Wunsch des Nutzers vom 2026-09-15). Vorher genuegten
   5px oben, weil das 56px hohe Feld den Rest von selbst auffuellte. */
.mud-table .mud-toolbar {
    padding-top: 8px;
    padding-bottom: 8px;
    margin-bottom: 2px;
    border-bottom: 1px solid var(--mud-palette-lines-default);
}

/* Das Suchfeld auf die Hoehe der Knoepfe daneben.

   37px ist nicht geraten, sondern die nachgemessene Hoehe eines MudButton in dieser
   Leiste ("Neues Mitglied", "Drucken"): 2x9px Innenabstand auf eine Zeilenhoehe von
   1,75rem. Steht hier als Variable, damit beide Werte an EINER Stelle liegen, falls
   MudBlazor seine Knopfhoehe einmal aendert.

   Warum die Hoehe ueberhaupt gesetzt werden muss: MudBlazors "Dense" verkleinert nur den
   Innenabstand des Feldes, nicht seine Mindesthoehe - gemessen kam es damit auf 40px und
   stand weiter ueber den Knoepfen. Die Hoehe gehoert auf das INPUT-Element, nicht auf den
   umgebenden Rahmen: Sonst waechst der Rahmen wieder auf den Inhalt. */
/* Die eine Hoehe fuer alles, was in einer Leiste nebeneinander steht. Sie gilt global und
   nicht mehr nur an der Werkzeugleiste der Tabelle: Seit v3.1.16 ist auch der Seitenkopf
   von /termine eine solche Leiste (Jahr, Ansichtsumschalter, "Neuer Termin"), und eine
   Variable, die dort nicht aufgeloest wird, faellt still auf ihren Anfangswert zurueck. */
:root {
    --fs-leistenhoehe: 37px;
}

/* Jedes Eingabefeld IN einer Werkzeugleiste steht auf Leistenhoehe und auf derselben
   Mittellinie wie die Knoepfe daneben. Vorher galt das nur fuer die Suche (`fs-suche`);
   der Kategoriefilter des Dateibrowsers kam auf 60 px gegen 37 px der Suche und sass
   12 px hoeher - "dem Browser ist das Suchfeld zur Kategorie auswahl unterschiedlich hoch
   und nicht ausgerichtet" (Nutzer am 2026-09-16, im Browser nachgemessen).

   Ursache waren zwei Dinge zugleich: das schwebende Label, das die Bauhoehe eines
   Outlined-Feldes hochtreibt (dieselbe Falle wie bei der Suche, siehe dort), und ein festes
   `mb-3` am Feld, das in einem Formular richtig ist und in einer Leiste nicht. Deshalb
   traegt ein Feld in der Leiste einen Platzhalter statt eines Labels - den Namen nimmt das
   aria-label auf, wie bei der Suche. */
.fs-leistenfeld.mud-input-control {
    margin-top: 0;
    margin-bottom: 0;
    /* Bezugspunkt fuer den Helfertext darunter. */
    position: relative;
}

/* Der Helfertext haengt UNTER der Leiste, statt sie hoeher zu machen. MudBlazor legt den
   Behaelter dafuer immer an - auch bei `HelperTextOnFocus`, wo er meist leer ist -, und er
   misst 20 px: Das Suchfeld des Protokolls kam damit auf 60 px gegen 37 px der Knoepfe
   daneben, obwohl das Eingabefeld selbst 37 px hoch war (im Browser nachgemessen). Aus dem
   Fluss genommen zaehlt er nicht mehr zur Feldhoehe; sichtbar wird er ohnehin nur, solange
   das Feld den Fokus hat, und liegt dann kurz ueber der Kopfzeile der Tabelle - deshalb
   der eigene Untergrund. */
.fs-leistenfeld .mud-input-control-helper-container {
    position: absolute;
    top: 100%;
    left: 0;
    right: 0;
    z-index: 2;
    background: var(--mud-palette-surface);
}

/* Die Spaltenauswahl ist ein MudMenu mit Symbolknopf und kam auf 48 px - elf mehr als
   alles andere in der Leiste. Sie ist erst ab 960 px sichtbar (siehe `fs-spaltenwahl`),
   wird also mit der Maus bedient; die 44-px-Regel fuer Tippziele greift hier nicht. */
.mud-table .mud-toolbar .fs-spaltenwahl .mud-button-root {
    height: var(--fs-leistenhoehe);
    width: var(--fs-leistenhoehe);
}

.fs-leistenfeld .mud-input.mud-input-outlined {
    height: var(--fs-leistenhoehe);
    min-height: var(--fs-leistenhoehe);
}

.fs-leistenfeld .mud-input.mud-input-outlined > input {
    height: calc(var(--fs-leistenhoehe) - 2px);
    padding-top: 0;
    padding-bottom: 0;
}

/* Ohne schwebendes Label braucht die Umrandung keine Luecke - die legt MudBlazor sonst
   fuer die Beschriftung an, und ohne Beschriftung klafft sie leer. */
.fs-leistenfeld .mud-input-outlined-border {
    top: 0;
}

.fs-suche .mud-input.mud-input-outlined {
    height: var(--fs-leistenhoehe);
    min-height: var(--fs-leistenhoehe);
}

.fs-suche .mud-input.mud-input-outlined > input {
    /* 1px weniger als der Rahmen, sonst reibt der Textcursor an der Umrandung. */
    height: calc(var(--fs-leistenhoehe) - 2px);
    padding-top: 0;
    padding-bottom: 0;
}

/* Ohne schwebendes Label braucht die Umrandung keine Luecke mehr - die legt MudBlazor
   sonst fuer die Beschriftung an, und ohne Beschriftung klafft sie leer. */
.fs-suche .mud-input-outlined-border {
    top: 0;
}

.fs-suche.mud-input-control {
    margin-top: 0;
    margin-bottom: 0;
    /* Nicht ueber die halbe Leiste: Die Knoepfe rechts brauchen ihren Platz, und eine
       Suchbox von 800px hilft niemandem. */
    max-width: 420px;
    /* Seit v3.1.16 gibt die Suche Platz ab, statt ihn zu behaupten: MudBlazor setzt
       "flex: 1 1 auto", die Box waechst also und draengt die Werkzeuge rechts in die
       naechste Zeile - auf /mitglieder blieb bei 1400 px allein die Spaltenauswahl darin
       stehen.

       **Die BASIS ist das Entscheidende, nicht die Mindestbreite.** Eine umbrechende
       Flexbox verteilt zuerst auf Zeilen und schrumpft erst danach innerhalb einer Zeile:
       Mit einer Basis von 240 px brach /mitglieder um, obwohl die Box bis 150 px haette
       nachgeben koennen (gemessen: Leistenhoehe 99 statt 64). Mit 180 px passt die volle
       Leiste - Suche, vier Schalter, drei Knoepfe und die Spaltenauswahl - in eine Zeile.

       "flex-grow: 1" laesst sie auf Seiten mit wenig Werkzeug wieder breiter werden; den
       Rest der Zeile teilt sie sich dann mit dem MudSpacer. */
    flex: 1 1 180px;
    min-width: 150px;
}

/* Spaltennamen fett - der Kopf einer Tabelle ist keine Datenzeile. Der Selektor muss
   MudBlazors eigenen schlagen: ".mud-table .mud-table-head .mud-table-cell" setzt dort
   font-weight 500 und ist spezifischer als ein schlichtes "thead th" (nachgemessen: 500
   statt der gewuenschten 600). */
.mud-table .mud-table-head .mud-table-cell,
.mud-table .mud-table-head .mud-table-cell .mud-button-root {
    font-weight: 700;
}


/* EINE Flaechenform in der ganzen Anwendung, nach dem Vorbild der Statistikkarten:
   leichter Schatten (Elevation 1), 16px Innenabstand, die Eckenrundung aus dem Theme.
   Vorher standen drei Formen nebeneinander - umrandete Kopfleisten, umrandete Karten im
   Mitgliederbereich und beschattete Statistikkarten.

   Die Tabelle bekommt ihren Innenabstand nur oben und an den Seiten: Die Zeilen sollen
   ueber die volle Breite laufen, sonst stuende die Trennlinie zwischen ihnen in der Luft. */
.mud-table.mud-elevation-1 {
    padding: 0;
}

.mud-table .mud-toolbar {
    padding-left: 16px;
    padding-right: 16px;
}

/* Der Fuss der Seitenleiste (Bausteine/Sidebarfuss.razor): Version und Urheberrecht.

   "margin-top: auto" schiebt ihn an den unteren Rand der Schublade, wenn die Navigation
   kuerzer ist als der Schirm - und laesst ihn bei langer Navigation einfach darunter
   stehen, statt ihn mit "position: sticky" ueber die letzten Eintraege zu legen.
   Vorbedingung ist die Flex-Spalte, die MudDrawer seinem Inhalt ohnehin gibt; ohne sie
   faellt "auto" auf 0 zurueck und der Fuss steht direkt unter dem Abmelden-Knopf. */
.fs-sidebarfuss {
    margin-top: auto;
    padding: 8px 16px calc(12px + env(safe-area-inset-bottom));
    /* Nebensache, nicht Navigation: gedaempft, damit der Blick an den Eintraegen haengt. */
    opacity: 0.7;
}

/* Der aktive Eintrag der Seitenleiste.

   MudBlazor faerbt ihn in der Primaerfarbe - und die ist seit der Rueckkehr zum
   Gestaltungskonzept Brass (#C89A46). Als TEXT auf hellem Grund kommt Brass auf ein
   Kontrastverhaeltnis von 2,57 und verfehlt die 4,5 der WCAG-Stufe AA um mehr als die
   Haelfte; nachgemessen war es der einzige Ort in der Anwendung, an dem Brass als
   Schriftfarbe landet.

   Also andersherum: Die Schrift wird Ink und etwas fetter, und den Akzent traegt ein
   Balken am linken Rand. Damit steht die Markierung nicht mehr allein auf der Farbe -
   was ohnehin Vorgabe ist (Zustand nie allein ueber Farbe). */
/* Der Selektor traegt ".mud-drawer" nur der Gewichtung wegen: MudBlazors eigene Regel
   ist ".mud-navmenu.mud-navmenu-default .mud-nav-link.active:not(...)" und damit um eine
   Klasse spezifischer als ein schlichtes ".mud-navmenu ...". Ohne das dritte Glied hier
   setzte sich weiter die Primaerfarbe durch (nachgemessen: der Rahmen links kam an, die
   Schriftfarbe nicht). Beim Schriftschnitt hilft auch das nicht - MudBlazor schreibt
   "font-weight: 500 !important", dagegen kommt nur ein eigenes !important an. */
.mud-drawer .mud-navmenu .mud-nav-link.active:not(.mud-nav-link-disabled) {
    color: var(--mud-palette-text-primary);
    font-weight: 600 !important;
    border-left: 3px solid var(--mud-palette-primary);
    /* Was der Balken links einnimmt, kommt vom Innenabstand - sonst ruecken die
       Beschriftungen des aktiven und der uebrigen Eintraege gegeneinander. */
    padding-left: calc(16px - 3px);
}

.mud-drawer .mud-navmenu .mud-nav-link.active:not(.mud-nav-link-disabled) .mud-icon-root {
    color: var(--mud-palette-primary);
}

/* Die Werkzeugleiste auf dem Telefon.

   Gemessen bei 390px: Suchfeld, Anlegen-Knopf, Drucken und Spaltenauswahl teilen sich
   358px in EINER Zeile - vom Platzhalter blieb "Such" uebrig, und die Knopfaufschrift
   brach auf zwei Zeilen um und schob sich ueber den Nachbarn. MudBlazors Leiste steht auf
   "flex-wrap: nowrap".

   Unterhalb von Sm darf sie deshalb umbrechen, und das Suchfeld nimmt die erste Zeile
   ganz: Suchen ist auf einer Liste mit hundert Eintraegen die haeufigere Handlung als
   Anlegen. Der Abstandshalter zwischen beiden Zeilen faellt weg - er wuerde sonst eine
   leere dritte Zeile aufspannen. */
@media (max-width: 599.98px) {
    .mud-table .mud-toolbar {
        flex-wrap: wrap;
        row-gap: 8px;
    }

    .fs-suche.mud-input-control {
        max-width: none;
        flex: 1 0 100%;
    }

    .mud-table .mud-toolbar > .flex-grow-1 {
        display: none;
    }

    /* Die zweite Zeile muss Anlegen, Drucken UND Spaltenauswahl tragen: gemessen sind
       das 186 + 99 + 48 px auf 326 px verfuegbare Breite, die Spaltenauswahl rutschte
       allein in eine dritte Zeile. Beim Drucken-Knopf entfaellt deshalb hier die
       Aufschrift - das Druckersymbol allein ist eindeutig, und der Knopf behaelt ueber
       sein aria-label seinen Namen fuer Vorleseprogramme.

       Nur die Aufschrift wird ausgeblendet, nicht der Knopf: Ein "display: none" am
       Knopf naehme ihn auch aus der Tabulatorreihenfolge. */
    .mud-table .mud-toolbar .fs-druckknopf-text {
        display: none;
    }

    .mud-table .mud-toolbar .fs-druckknopf {
        min-width: 0;
    }

    .mud-table .mud-toolbar .fs-druckknopf .mud-button-icon-start {
        margin-right: 0;
        margin-left: 0;
    }
}

/* Das Bild auf der Anmeldeseite (Seiten/Anmelden.razor).

   Die Vorlage ist 309x480 im Hochformat; als Band ueber dem Formular braucht sie einen
   Zuschnitt. "object-fit: cover" fuellt das Band ohne zu verzerren, "object-position"
   haelt den Apfel im Bild - ohne die Angabe schnitte der Browser mittig und zeigte nur
   Klangstaebe.

   Die Hoehe ist fest, nicht am Seitenverhaeltnis ausgerechnet: Eine Anmeldekarte soll auf
   jedem Schirm gleich hoch beginnen, damit das Formular nicht wandert. */
.fs-anmeldebild {
    display: block;
    width: 100%;
    height: 150px;
    object-fit: cover;
    object-position: center 38%;
    border-radius: var(--mud-default-borderradius);
}

/* Die Antwortknoepfe der Terminkarte auf volle Zielgroesse (Bausteine/TerminKarte.razor).
   MudBlazors Vorgabe sind 37px; docs/konzept/19 fordert 44px, und hier ist die Stelle,
   an der es zaehlt. */
.fs-mein .fs-antwortknoepfe .mud-button-root {
    min-height: 44px;
}

/* Der Besetzungsblock der Terminseite (Seiten/Verwaltung/TerminBesetzung.razor).

   Vorher waren das Flex-Zeilen, in denen jede Zahl ihre eigene Beschriftung neben sich
   trug. Weil die Instrumentennamen unterschiedlich lang sind, begann jede Zeile an einer
   anderen Stelle - die Zahlen standen nirgends untereinander. Jetzt ist es eine echte
   Tabelle: Die Spalte gibt die Stelle vor, nicht der Nachbar links davon.

   Eigene Abstaende statt MudBlazors `pa-2`/`px-2`: Deren Klassen sind `!important` und
   liessen sich hier nicht mehr feiner regeln. Ausserdem faellt so die Trennlinie zwischen
   den Zeilen mit dem Innenabstand zusammen.

   Der Rahmen rollt waagerecht, wenn sechs Spalten nicht nebeneinander passen. Das ist der
   erlaubte Weg; der SEITENkoerper darf nicht waagerecht rollen (gemessen ueber
   `scrollWidth > clientWidth` bei 400 und 360 px, nicht nach Augenmass). */
/* Der Rahmen rollt waagerecht, FALLS die Tabelle nicht auf den Schirm passt. Er ist
   unsichtbar, solange sie passt - und der SEITENkoerper darf nie waagerecht rollen,
   das ist die Vorgabe. Ohne ihn schob die Tabelle auf dem Telefon die ganze Seite
   auf (vom Nutzer am 2026-09-17 gemeldet: "nicht responsive"). */
.fs-besetzung-rahmen {
    overflow-x: auto;
    overscroll-behavior-x: contain;
}

.fs-besetzung {
    border-collapse: collapse;
    max-width: 100%;
}

/* Die Spalten sind nur so breit wie ihr Inhalt - KEIN `width: 100%` auf der
   Instrumentenspalte. Die erste Fassung hatte das, und die Zahlen wurden damit an
   den rechten Rand geschoben, mit einer handbreiten Luecke hinter jedem Namen.
   Ausgerichtet waren sie zwar, lesbar nicht. */
.fs-besetzung th,
.fs-besetzung td {
    padding: 6px 0;
    text-align: left;
}

/* Nur die ZAHLEN duerfen nicht umbrechen - eine Zahl ueber zwei Zeilen ist keine Zahl
   mehr. Die Instrumentenspalte bricht dagegen um: Sie ist die einzige mit langem Text,
   und damit passt die Tabelle auf einem Telefon, statt zu rollen. "Sopran-Floete ·
   1. Stimme" steht dort dann zweizeilig - das ist besser als seitwaerts schieben. */
.fs-besetzung .fs-besetzung-zahl {
    white-space: nowrap;
}

.fs-besetzung th:not(:last-child),
.fs-besetzung td:not(:last-child) {
    padding-right: 24px;
}

/* Auf schmalen Schirmen ruecken die Spalten zusammen: 24 Pixel Abstand mal fuenf sind
   120 Pixel, die auf einem 360er Schirm der Instrumentenspalte fehlen. */
@media (max-width: 599.98px) {
    .fs-besetzung th:not(:last-child),
    .fs-besetzung td:not(:last-child) {
        padding-right: 10px;
    }
}

.fs-besetzung thead th {
    font-weight: 600;
    border-bottom: 1px solid var(--mud-palette-lines-default);
}

/* Zahlen rechtsbuendig und dicktengleich: Ohne `tabular-nums` ist die 1 schmaler
   als die 8, und die Spalte wackelt trotz fester Ausrichtung. */
.fs-besetzung .fs-besetzung-zahl {
    text-align: right;
    font-variant-numeric: tabular-nums;
}

/* Die Summenzeile wird wie der Kopf gesetzt: Strich darueber, fett. Sie schliesst die
   Tabelle ab, wie der Kopf sie eroeffnet. */
.fs-besetzung tfoot td {
    border-top: 1px solid var(--mud-palette-lines-default);
    font-weight: 600;
}

.fs-besetzung tr.fs-unterbesetzt {
    color: var(--mud-palette-error);
}

/* Nur fuer Vorleseprogramme: Text, der auf dem Schirm keinen Platz hat, aber gehoert
   werden muss - der Kopf der Markenspalte und der Satz hinter dem Gedankenstrich in der
   Spalte "Mindestanzahl". `display: none` waere falsch, das nimmt den Text auch dem
   Vorleseprogramm; deshalb der Weg ueber ein weggeschnittenes Pixel.

   AUSDRUECKLICH OHNE `position: absolute`, obwohl das die verbreitetste Fassung dieses
   Musters ist. Der Grund ist gemessen, nicht vermutet: Der Baustein steht in einem
   waagerecht rollenden Rahmen. Ein absolut gesetztes Kind sucht sich seinen Bezugsrahmen
   beim naechsten POSITIONIERTEN Vorfahren - der Rahmen ist keiner, also wird das Kind von
   dessen `overflow` auch nicht beschnitten. Bei 400 px Schirmbreite stand der unsichtbare
   Text dadurch bei x=548 und zog die GANZE SEITE auf scrollWidth 548 gegen clientWidth 400
   - genau das waagerechte Rollen des Seitenkoerpers, das hier verboten ist. Im Textfluss
   kann er nirgends hin: Er kostet ein Pixel in seiner Zelle und wird mit ihr beschnitten. */
.fs-nurvorlesen {
    display: inline-block;
    width: 1px;
    height: 1px;
    padding: 0;
    overflow: hidden;
    clip-path: inset(50%);
    white-space: nowrap;
    border: 0;
}

/* Die Eingabezeile ueber einer Zuordnungsliste: Auswahlfeld (oder Feldergruppe) und der
   Hinzufuegen-Knopf daneben, auf der Grundlinie ausgerichtet, umbrechend auf dem Telefon.

   Bis v3.1.35 stand an sieben Stellen dieselbe Kette aus vier Hilfsklassen -
   `d-flex align-end gap-2 flex-wrap` (Befund O-3). Ein Name sagt, WAS die Zeile ist; vier
   Hilfsklassen sagen nur, wie sie gesetzt wird, und wer eine achte Zeile baut, schreibt sie
   ab, statt sie wiederzuerkennen. Der Abstand nach unten bleibt an der Aufrufstelle
   (`mb-3`/`mb-4`): Er haengt davon ab, was darunter folgt, nicht von der Zeile selbst. */
.fs-eingabezeile {
    display: flex;
    align-items: flex-end;
    flex-wrap: wrap;
    gap: 8px;
}

/* Repertoire-Stücke im Notenarchiv des Mitgliederbereichs (Nutzer am 2026-09-19: "es sollte
   angezeigt werden - evtl. durch Titelfarbe o. Ä., welche Stücke zum Repertoire gehören").

   Farbe UND Schriftschnitt, dazu ein Stern davor: Eine Aussage, die allein an der Farbe
   hängt, ist für rund jeden zwölften Mann nicht lesbar - und auf einem ausgedruckten
   Schwarzweißbild für niemanden. */
.fs-repertoire {
    color: var(--mud-palette-primary);
    font-weight: 600;
}

/* Der Knopf einer Notendatei: linksbuendig und umbrechend.

   MudButton zentriert seinen Inhalt und haelt ihn in einer Zeile. Bei einem langen
   Dateinamen ("Exercise Book - Pipa Szesny.pdf") rutschte der Name dadurch in die Mitte und
   die Groesse allein auf die naechste Zeile - nachgemessen bei 390px. Namen sind hier lang
   und sollen von links gelesen werden. */
.fs-notendatei {
    justify-content: flex-start;
    text-align: left;
    flex: 1 1 auto;
    min-width: 0;
}

.fs-notendatei .mud-button-label {
    justify-content: flex-start;
    text-align: left;
    /* Umbrechen statt abschneiden: Ein halber Dateiname hilft niemandem bei der Frage,
       ob es die richtige Stimme ist. */
    white-space: normal;
    word-break: break-word;
}
