/*
   Kalonaut - Gestaltungsrichtung A.
   Warmes Beigegrau, gedeckte Makrofarben (design\kalonaut-entwurf2.html).

   HELL UND DUNKEL SIND BEIDE VOLLSTAENDIG.
   Jede Farbe ist ein Merkmal auf :root und wird unter
   [data-thema="dunkel"] und unter prefers-color-scheme:dark neu gesetzt.
   Es gibt keine Farbe, die nur in einem der beiden Blocks definiert ist -
   sonst faellt sie im anderen auf den Vorgabewert des Browsers zurueck,
   und das sieht man erst auf einem fremden Geraet.

   Drei Zustaende, nicht zwei: ohne data-thema gilt die Einstellung des
   Geraets; data-thema="hell" und "dunkel" setzen sie ausser Kraft. Der
   Schalter oben rechts schreibt das Merkmal, und er muss in BEIDE
   Richtungen gewinnen - deshalb die :not()-Bedingung im Medienblock.

   SCHRIFT: die des Geraets. Eine geladene Schrift waere ein zusaetzlicher
   Abruf beim Kaltstart (die gemessene Kennzahl) und auf dem iPhone ein
   Schriftbild, das gerade NICHT nach App aussieht. -apple-system ist dort
   SF Pro - also genau die Schrift, die jede andere App auch benutzt.

   400 px: alle Maszе in rem/%, kein festes min-width, nichts breiter als
   der Bildschirm. Der Rumpf scrollt nie seitlich.
*/

:root {
  --grund:      #efece5;
  --karte:      #fbf9f5;
  --flaeche:    #e8e4db;
  --rand:       #e6e1d7;
  --randfein:   #ece7dd;
  --text:       #201e1b;
  /* KONTRAST: GEMESSEN, NICHT GESCHAETZT (Nachtrag N1 zu Auftrag 22).
     WCAG 2.1 AA verlangt 4,5:1 fuer normalen Text. Nachgerechnet
     wurden ALLE Text-auf-Flaeche-Paare in beiden Farbmodi; hell fielen
     SECHS von vierzehn durch, dunkel drei. Die Web-Leitung hatte zwei
     davon gemeldet - die anderen vier standen daneben und waren
     niemandem aufgefallen.

     --stumm  #726c63  ->  4,10:1 auf --flaeche, 4,41:1 auf --grund
     --blass  #a39d93  ->  2,12:1 auf --flaeche  (in ALLEN sieben
                           Verwendungen ist es Text, keine Zierde)

     Gerechnet wurde die HELLSTE Fassung, die die Schwelle noch
     schafft - Farbton und Saettigung bleiben, nur die Helligkeit
     bewegt sich. So bleibt der Eindruck der Gestaltung erhalten und
     die Schrift wird trotzdem lesbar.

     Der Pruefpunkt dazu steht in pruefen.php ("Kontrast nach
     WCAG AA"). Ein gemessener Kontrast, den niemand prueft, faellt
     beim naechsten Farbwechsel wieder durch. */
  --stumm:      #5d5851;   /* 5,55:1 auf --flaeche (vorher 4,10) */
  --blass:      #6b655b;   /* 4,55:1 auf --flaeche (vorher 2,12) */
  --knopf:      #201e1b;
  --knopftext:  #fefdfb;
  /* MAKROFARBEN - in Farbton UND Helligkeit gestaffelt (Auftrag 11, 2.1).
     Die alten (#5d7f9e / #c08a4a / #8a7a9e) waren zu aehnlich: Protein und
     Kohlenhydrate lagen beide im gedaempften Blau-Violett und hatten
     gegeneinander ein Kontrastverhaeltnis von 1,27 - auf einem Ringsegment
     von wenigen Millimetern ist das kein Unterschied.
     Jetzt drei verschiedene Farbtoene (Blau, Oliv, Gold) UND drei
     verschiedene Helligkeiten, damit sie auch in Graustufen und bei einer
     Farbsehschwaeche auseinanderfallen. Gemessen wird das - nicht
     behauptet: oberflaeche-browser.mjs rechnet die paarweisen Kontraste
     in hell UND dunkel und meldet unter 1,5 rot. */
  --protein:    #2f6b8f;
  --kh:         #6f9a4a;
  --fett:       #e0a955;
  --warngrund:  #f4ead9;
  --warnrand:   #e6d6ba;
  /* GEMESSEN, BEVOR SIE STAND (Auftrag 23, Abschnitt 7).
     #84652d trug 4,54:1 auf --warngrund und war dort in Ordnung - auf
     --flaeche aber nur 4,27:1, und dort steht sie seit dem Restbalken
     ("passt knapp"). Vier Hundertstel unter der Grenze sind trotzdem
     darunter. Derselbe Farbton, nur dunkler:
       --flaeche 4,67  --karte 5,64  --grund 5,02  --warngrund 4,97 */
  --warntext:   #7d5f2a;
  --fehler:     #8f3140;
  --fehlergrund:#f7e3e6;
  --fehlerrand: #e6c3c9;
  --gut:        #2f6b46;
  --schatten:   0 1px 2px rgba(32,30,27,.05);
  /* Der Lichtschein am Ring - coretica.de in der Farbe von --fett. */
  --schein:     rgba(224, 169, 85, .20);
  --fussgrund:  #fbf9f5;

  --rundung:    22px;
  --rundungklein: 14px;
  --spalte:     min(100%, 34rem);
  --luft:       14px;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-thema="hell"]) {
    --grund:      #141416;
    --karte:      #1d1d21;
    --flaeche:    #27272c;
    --rand:       #2a2a30;
    --randfein:   #26262b;
    --text:       #ece8e2;
    /* Dunkel fiel nur --blass durch (2,61:1 auf --flaeche). --stumm
       lag mit 5,01:1 knapp darueber und wird trotzdem etwas heller:
       sonst waeren --stumm und --blass im dunklen Modus praktisch
       derselbe Ton, und die Staffelung der Gestaltung waere weg. */
    --stumm:      #a9a49c;   /* 6,00:1 auf --flaeche (vorher 5,01) */
    --blass:      #938d85;   /* 4,52:1 auf --flaeche (vorher 2,61) */
    --knopf:      #ece8e2;
    --knopftext:  #141416;
    --protein:    #3d7ba5;
    --kh:         #7fae55;
    --fett:       #f0c27a;
    --warngrund:  #2b2418;
    --warnrand:   #3f3524;
    --warntext:   #d4b478;
    --fehler:     #ff9aa8;
    --fehlergrund:#2d1a1e;
    --fehlerrand: #4a2a30;
    --gut:        #7cd992;
    --schatten:   0 1px 2px rgba(0,0,0,.4);
    /* Im Dunkeln traegt der Schein mehr - dort ist er der einzige
       warme Fleck auf dem Bildschirm. */
    --schein:     rgba(240, 194, 122, .17);
    --fussgrund:  #1d1d21;
  }
}

:root[data-thema="dunkel"] {
  --grund:      #141416;
  --karte:      #1d1d21;
  --flaeche:    #27272c;
  --rand:       #2a2a30;
  --randfein:   #26262b;
  --text:       #ece8e2;
  --stumm:      #9b958c;
  --blass:      #6b665f;
  --knopf:      #ece8e2;
  --knopftext:  #141416;
  --protein:    #3d7ba5;
  --kh:         #7fae55;
  --fett:       #f0c27a;
  --warngrund:  #2b2418;
  --warnrand:   #3f3524;
  --warntext:   #d4b478;
  --fehler:     #ff9aa8;
  --fehlergrund:#2d1a1e;
  --fehlerrand: #4a2a30;
  --gut:        #7cd992;
  --schatten:   0 1px 2px rgba(0,0,0,.4);
  --schein:     rgba(240, 194, 122, .17);
  --fussgrund:  #1d1d21;
}

:root[data-thema="dunkel"] { color-scheme: dark; }
:root[data-thema="hell"]   { color-scheme: light; }

* { box-sizing: border-box; }

html, body {
  margin: 0;
  padding: 0;
  background: var(--grund);
  color: var(--text);
  /* Keine Browser-Optik: kein Ueberdehnen, keine Textvergroeszerung beim
     Drehen, keine blaue Markierung beim Tippen. */
  overscroll-behavior-y: none;
  -webkit-text-size-adjust: 100%;
  -webkit-tap-highlight-color: transparent;
}

body {
  font: 15px/1.5 -apple-system, BlinkMacSystemFont, "Segoe UI", system-ui, Roboto, sans-serif;
  min-height: 100vh;
  /* Nichts darf seitlich herauslaufen - der Nachweispunkt bei 400 px. */
  overflow-x: hidden;
}

button, input, select, textarea { font: inherit; color: inherit; }
button { cursor: pointer; }
:focus-visible { outline: 2px solid var(--protein); outline-offset: 2px; }

.stumm { color: var(--stumm); }
.klein { font-size: 12.5px; }
.gut   { color: var(--gut); }

/* ---------------------------------------------------------------
   Startbild - da, bevor irgendetwas anderes da ist.
   --------------------------------------------------------------- */
#startbild {
  position: fixed; inset: 0; z-index: 60;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 14px; background: var(--grund); color: var(--text);
}
#startbild svg { color: var(--fett); }
#startbild.weg { opacity: 0; pointer-events: none; transition: opacity .18s ease; }
.startname { font-size: 17px; font-weight: 700; letter-spacing: -.02em; }
.startnot  { color: var(--fehler); font-size: 13px; margin: 0; padding: 0 20px; text-align: center; }

/* ---------------------------------------------------------------
   Anmeldung
   --------------------------------------------------------------- */
#anmeldung { min-height: 100vh; display: grid; place-items: center; padding: 24px 16px; }
.anmeldekasten { width: var(--spalte); }
.anmeldekasten h1 { font-size: 24px; margin: 0 0 2px; letter-spacing: -.03em; }
.anmeldekasten p  { margin: 0 0 20px; }
.anmeldekasten label { display: block; font-size: 12.5px; color: var(--stumm); margin: 12px 0 5px; }

input[type=text], input[type=email], input[type=password], input[type=number], textarea, select {
  width: 100%;
  padding: 12px 13px;
  border: 1px solid var(--rand);
  border-radius: var(--rundungklein);
  background: var(--karte);
  color: var(--text);
  -webkit-appearance: none;
  appearance: none;
}
textarea { resize: vertical; min-height: 78px; }

button.gross {
  width: 100%; margin-top: 18px; padding: 15px 16px;
  border: 0; border-radius: 16px;
  background: var(--knopf); color: var(--knopftext);
  font-weight: 700; font-size: 15.5px;
}
button.gross[disabled] { opacity: .5; }
button.alslink {
  background: none; border: 0; padding: 0;
  color: var(--stumm); text-decoration: underline; text-underline-offset: 3px;
  font-size: 13px;
}
.fehlertext {
  margin: 12px 0 0; padding: 10px 12px; font-size: 13.5px;
  color: var(--fehler); background: var(--fehlergrund);
  border: 1px solid var(--fehlerrand); border-radius: var(--rundungklein);
}

/* ---------------------------------------------------------------
   Geruest
   --------------------------------------------------------------- */
.kopf {
  display: flex; align-items: flex-start; justify-content: space-between; gap: 10px;
  width: var(--spalte); margin: 0 auto;
  padding: calc(env(safe-area-inset-top, 0px) + 18px) var(--luft) 10px;
}
.kopfgrusz { font-size: 20px; font-weight: 800; letter-spacing: -.03em; }
.kopfdatum { font-size: 12.5px; margin-top: 1px; }
.kopfknoepfe { display: flex; gap: 7px; flex: none; }

button.rund {
  width: 34px; height: 34px; flex: none;
  border: 1px solid var(--rand); border-radius: 17px;
  background: var(--karte); color: var(--stumm);
  display: grid; place-items: center; padding: 0;
}
button.rund svg { width: 16px; height: 16px; fill: none; stroke: currentColor;
                  stroke-width: 1.9; stroke-linecap: round; stroke-linejoin: round; }

main {
  width: var(--spalte); margin: 0 auto;
  padding: 0 var(--luft) calc(env(safe-area-inset-bottom, 0px) + 104px);
}

.karte {
  background: var(--karte); border: 1px solid var(--rand);
  border-radius: var(--rundung); padding: 16px;
  margin-bottom: 10px; box-shadow: var(--schatten);
}
.kartenkopf {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  font-size: 13px; font-weight: 700; margin-bottom: 10px;
}
.kartenkopf.auszen { margin: 18px 2px 8px; }
.kartenkopf span + span { font-weight: 500; text-align: right; }

/* ---------------------------------------------------------------
   Ring nach Makro-Herkunft
   --------------------------------------------------------------- */
/* ---------------------------------------------------------------
   Der Ring und die drei Zahlen (Auftrag 11, Punkt 1 und 2)

   DER RING LIEGT HINTER DER ZAHL, nicht neben ihr. Die Zahl "noch
   offen" ist der Inhalt; der Ring ist die Form, die zeigt, wie weit
   der Tag gefuellt ist. Vorher stand die Zahl IM SVG als <text> und
   war damit nicht auswaehlbar, nicht skalierbar und nicht von einem
   Vorleseprogramm zu lesen - jetzt ist es gewoehnlicher Text, der
   ueber dem Ring liegt.
   --------------------------------------------------------------- */
/* DIE BEIDEN SEITEN LIEGEN UEBEREINANDER, NICHT NEBENEINANDER.
   Die erste Fassung war ein Karussell: beide Seiten in einer Reihe,
   die inaktive rechts auszerhalb, abgeschnitten von overflow:hidden.
   Das sieht beim Wischen schoener aus und hat zwei echte Nachteile -
   die Browserprobe meldete bei 400 px vier Elemente "ueber den Rand"
   (r-seite-makros 369..707), und ein Vorleseprogramm liest die
   unsichtbare Seite trotzdem vor.
   Jetzt liegt beides im selben Rasterfeld, und die inaktive Seite ist
   per hidden weg: nichts ragt hinaus, nichts wird vorgelesen, was
   niemand sieht. Die Wischbewegung bleibt - sie wechselt die Seite,
   nur ohne Gleitbewegung. */
/* DIE SEITE ENDET VOR DEM STREIFEN, nicht darunter.
   Ohne diese Einrueckung lag das Ringstueck der naechsten Ansicht mitten
   auf dem Wort "25 %" der Makroseite - gefunden auf dem ersten
   Bildschirmfoto, nicht im Kopf. Der Ring rutscht dadurch ein paar
   Pixel nach links; genau so sieht ein Streifen aus, hinter dem es
   weitergeht. */
/* Der Platz rechts war fuer den Streifen (.ringlug). Der ist mit
   Auftrag 22, 2.3 weggefallen; geblieben ist der Pfeil, und der
   braucht schmaler. */
.ringbuehne { overflow: hidden; touch-action: pan-y; position: relative;
              padding-right: 26px; }
.ringseiten { display: grid; position: relative; z-index: 1; }
.ringseite  { grid-area: 1 / 1; min-width: 0; }

/* Der Einladungscode steht im Klartext und soll abgeschrieben werden -
   also in einer Schrift, in der 0 und O verschieden aussehen. Das
   Alphabet der Codes vermeidet beide zwar (Einladung::ZEICHEN), aber
   wer ihn vorliest, liest ihn hier ab. */
.einladungcode {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 15px; font-weight: 700; letter-spacing: .06em;
}

/* ---------------------------------------------------------------
   DIE KOERPER-SEITE (Auftrag 14, Abschnitt 2)

   Eine Zeile je Wert: Name links, Zahl rechts, darunter das Feld zum
   Eintragen. "wird nicht gerechnet" steht als WORT daneben und nicht
   als Grauton - Farbe ist nie das einzige Merkmal (Auftrag 11, 2.1),
   und hier traegt sie eine Aussage, die man lesen koennen muss.
   --------------------------------------------------------------- */
.wertzeile {
  display: flex; align-items: center; gap: 10px;
  padding: 10px 0 2px;
}
.wertzeile .was { flex: 1 1 auto; min-width: 0; }
.wertzeile .name { font-size: 14px; font-weight: 700; }
.wertzahl { flex: none; font-size: 17px; font-weight: 800; }

/* DIE ZEILE KLAPPT AUF (Auftrag 22, Nachtrag N9).

   R hielt das "-" neben Koerperfett fuer ein Bedienelement und fand,
   dass es nicht reagiert. Es war der Platzhalter fuer einen fehlenden
   Wert. Jetzt ist die ganze ZEILE das Bedienelement - und das Zeichen
   dafuer steht rechts daneben, wo er es vermutet hat.

   ES IST EIN WINKEL UND KEIN MINUS. Ein Minus sagt "wegnehmen"; der
   Winkel sagt, in welche Richtung sich etwas oeffnet, und dreht sich
   mit dem Zustand. Der Zustand haengt an aria-expanded und nicht an
   einer Klasse daneben - damit koennen Aussehen und Vorlesetext nicht
   auseinanderlaufen (dieselbe Regel wie beim Info-Knopf, 1.1). */
.wertzeile[aria-expanded]::after {
  content: ''; flex: none; width: 7px; height: 7px; margin-left: 2px;
  border-right: 2px solid var(--stumm); border-bottom: 2px solid var(--stumm);
  transform: rotate(45deg) translate(-2px, -2px);
  transition: transform .16s ease;
}
.wertzeile[aria-expanded="true"]::after {
  transform: rotate(-135deg) translate(-2px, -2px);
}
.wertzeile .zeile,
.wertauf .zeile { font-size: 12px; color: var(--stumm); margin-top: 2px; }
.wertauf { padding-bottom: 4px; }
.nichtgerechnet {
  margin-left: 7px; font-size: 10.5px; font-weight: 600;
  color: var(--stumm); background: var(--flaeche);
  border-radius: 999px; padding: 2px 7px; vertical-align: middle;
}
/* Die Linie: Richtung, nicht Praezision. Keine Achsen - bei drei
   Messungen waeren sie eine Behauptung ueber Genauigkeit. */
.verlauf { margin: 6px 0 12px; }
.verlaufsvg {
  width: 100%; height: 54px; display: block;
  overflow: visible; margin-bottom: 4px;
}
.verlaufsvg polyline {
  fill: none; stroke: var(--protein); stroke-width: 2;
  vector-effect: non-scaling-stroke;
  stroke-linejoin: round; stroke-linecap: round;
}

/* Wochentrend und Monatstrend (Auftrag 14, 2.2).

   DIE ZEILE FAERBT NICHT. "Runter" ist beim Gewicht das Erwuenschte,
   bei der Muskelmasse nicht - eine Farbe muesste je Wert das Gegenteil
   bedeuten und waere damit keine Auskunft, sondern ein Urteil. Der
   Pfeil zeigt die Richtung, bewerten darf der Nutzer selbst.

   Er bricht bei schmalem Bildschirm um, statt seitlich hinauszulaufen. */
.trendzeile {
  display: flex; align-items: baseline; gap: 6px;
  flex-wrap: wrap; margin: 0 0 4px; line-height: 1.35;
}
.trendwann {
  flex: 0 0 auto; font-size: 11px; font-weight: 700;
  color: var(--stumm); text-transform: uppercase; letter-spacing: .04em;
  min-width: 42px;
}
.trendpfeil { flex: 0 0 auto; font-size: 13px; color: var(--text); }
.trendzeile .klein { flex: 1 1 140px; min-width: 0; }

/* ---------------------------------------------------------------
   DER VORSCHLAGSBEREICH (Auftrag 13, umgebaut mit Nachtrag N5)

   DREI FRAGEN, ALLE DREI GLEICH. Bis zum 15.09.2026 war die erste
   grosz, farbig und trug einen erklaerenden Satz im Knopf - R's
   Befund: *"die erste Kachel sieht anders aus als die beiden
   darunter."* Was gerade dran ist, sagt jetzt die REIHENFOLGE (der
   Server dreht sie nach Tageszeit), nicht die Gestaltung. Eine Kachel,
   die anders aussieht, liest sich wie eine andere Art von Ding.

   KEIN SCHLOSS (Abschnitt 6). Es gibt hier keine Sperrgestaltung, kein
   Schloss-Zeichen und keine ausgegraute Flaeche - wer eine Funktion
   nie erlebt hat, kauft sie nicht.
   --------------------------------------------------------------- */
.fragenknopf {
  display: flex; flex-direction: column; align-items: flex-start; gap: 3px;
  width: 100%; margin-top: 8px; padding: 11px 13px; text-align: left;
  border: 1px solid var(--rand); border-radius: var(--rundungklein);
  background: var(--karte); color: var(--text);
}
.fragenknopf.ist-an { border-color: var(--stumm); }
.fragenknopf:active { opacity: .7; }
/* DER KOPF EINER FRAGE (Auftrag 22, 4.1): der Knopf nimmt die Breite,
   daneben stehen das i und der Premium-Schriftzug. Beide sind eigene
   Treffflaechen - ein i IM Knopf waere ein Knopf im Knopf. */
.fragenkopf { display: flex; align-items: center; gap: 8px; }
.fragenkopf .fragenknopf { flex: 1 1 auto; min-width: 0; }
.fragenzeichen {
  display: flex; align-items: center; gap: 6px; flex: none;
  margin-top: 8px; align-self: flex-start; padding-top: 11px;
}
.fragename { font-size: 14.5px; font-weight: 700; }
.vorschlagraus { margin-top: 10px; }

/* ---------------------------------------------------------------
   DIE REIHE ALS ZEILE (Auftrag 12, Punkt 3)

   Eine Zeile, kein Kasten: kein Rahmen, kein Hintergrund, keine
   Ueberschrift. Sie steht ueber dem Ring und soll dort nicht mit ihm
   um Aufmerksamkeit ringen - deshalb kleine Schrift und gedaempfte
   Farbe, und die Zahl traegt das Gewicht.

   Sie ist ein Knopf und sieht nicht danach aus. Das ist Absicht: das
   Blatt dahinter ist eine Zugabe, kein Weg, den jemand finden muss.
   --------------------------------------------------------------- */
.reihezeile {
  display: flex; align-items: center; gap: 7px;
  width: var(--spalte); margin: 0 auto;
  padding: 2px var(--luft) 8px;
  background: none; border: 0; text-align: left;
  color: var(--stumm); font-size: 13px;
}
.reihezeile:active { opacity: .6; }
.reihezahl { font-weight: 700; color: var(--text); }
.reihename { color: var(--stumm); }
.reihename::before { content: "\00b7"; margin-right: 7px; }
/* Der Wink auf den Joker - dieselbe warme Farbe wie der Schein am Ring,
   damit "hier ist noch etwas" ueberall dasselbe aussieht. */
.reihewink {
  margin-left: auto; font-size: 11.5px; font-weight: 700;
  color: var(--warntext); background: var(--warngrund);
  border: 1px solid var(--warnrand); border-radius: 999px; padding: 2px 8px;
}
.reihestufe { font-size: 15px; line-height: 1; }
/* Die fuenfte Stufe: dasselbe Zeichen, mit dem Schein dahinter. */
.reihestufe.leuchtet {
  border-radius: 50%;
  box-shadow: 0 0 10px 4px var(--schein);
}

/* ---------------------------------------------------------------
   DASS ES WEITERGEHT, MUSS MAN SEHEN (Auftrag 12, Punkt 2)

   DER SCHEIN ist der Lichteffekt von coretica.de - R's eigener, mit
   seiner Erlaubnis uebernommen. Dort:

       background: radial-gradient(ellipse at center,
                   rgba(224, 169, 109, 0.16), transparent 65%);
       filter: blur(30px);

   Hier dieselbe Form in der Farbwelt von Richtung A: --fett ist
   #e0a955 und damit fast derselbe Ton wie coretica's #e0a96d. Ein
   eigener Farbwert fuer einen Effekt waere ein Farbwert, den niemand
   pflegt.

   ER IST IMMER DA, NICHT BEI BERUEHRUNG. Auf dem iPhone gibt es kein
   Hover; ein Hinweis, der eine Beruehrung braucht, ist fuer genau die
   Nutzer unsichtbar, fuer die er gebaut ist. Und er bewegt sich nicht:
   was blinkt, wird nach drei Tagen ignoriert.
   --------------------------------------------------------------- */
.ringbuehne::before {
  content: "";
  position: absolute; left: 50%; top: 44%;
  width: 280px; height: 200px;
  transform: translate(-50%, -50%);
  background: radial-gradient(ellipse at center, var(--schein), transparent 65%);
  filter: blur(26px);
  z-index: 0; pointer-events: none;
}

/* Der Knopf am rechten Rand: Streifen der naechsten Ansicht plus Pfeil.
   Er ist ein ECHTER Knopf - wischen allein ist eine versteckte Geste,
   und auf einem Rechner gibt es keinen Finger. */
.ringweiter {
  position: absolute; right: 0; top: 0; bottom: 0; z-index: 2;
  width: 46px; padding: 0; border: 0; background: none;
  display: flex; align-items: center; justify-content: flex-end;
  gap: 4px;
}
.ringweiter:active { opacity: .6; }

/* DAS LEUCHTEN AM PFEIL - und warum es aufhoert (Auftrag 22, 2.5).
   Es laeuft, solange noch nie umgeschaltet wurde, und endet mit dem
   ersten Mal. Ein Element, das dauernd pulsiert, ist nach drei Tagen
   das, was man wegklicken moechte.
   Bewegt wird die DECKKRAFT, nicht die Groesze: eine Pulsation ueber
   transform zieht bei jedem Schritt das Layout mit. */
.ringweiter.winkt .ringpfeil svg { animation: pfeilwink 2.2s ease-in-out infinite; }
@keyframes pfeilwink {
  0%, 100% { opacity: .45; }
  50%      { opacity: 1; }
}
/* Eine Systemeinstellung, die Menschen aus einem Grund setzen: der
   Pfeil steht dann einfach da - sichtbar, aber still. */
@media (prefers-reduced-motion: reduce) {
  .ringweiter.winkt .ringpfeil svg { animation: none; opacity: 1; }
}

/* Der Streifen. Schmal genug, um nicht zu stoeren, breit genug, um
   gesehen zu werden - und am Rand abgeschnitten, damit er aussieht wie
   etwas, das dahinter weitergeht. */
/* DER STREIFEN (.ringlug) IST WEG - Auftrag 22, 2.3.
   R hat die angeschnittenen Farbflaechen rechts nicht als Andeutung
   gelesen, sondern als etwas, das nicht dazugehoert. Was eine
   Andeutung sein soll und als Fehler ankommt, ist keine. Die zwei
   Punkte unter dem Ring sagen dasselbe und sind sofort verstaendlich. */

/* DIE LEGENDE LINKS VOM RING (Auftrag 22, 2.3).
   Sie darf schrumpfen (min-width: 0, Zeilenumbruch erlaubt), der Ring
   nicht - deshalb flex: none am Ring und flex: 0 1 auto an der
   Legende. Auf 390 px muessen Legende + Ring + Rand ohne seitlichen
   Ueberlauf passen; gemessen wird das in der Browserprobe. */
.ringzeile {
  display: flex; align-items: center; justify-content: center;
  gap: 12px; min-width: 0;
}
.ringzeile > .ringmitte { flex: none; }
.ringlegende {
  display: flex; flex-direction: column; gap: 7px;
  flex: 0 1 auto; min-width: 0;
}
.legendezeile {
  display: flex; align-items: center; gap: 6px;
  font-size: 11.5px; color: var(--stumm); line-height: 1.2;
  min-width: 0;
}
.legendezeile span { overflow: hidden; text-overflow: ellipsis; }
.legendezeile .punkt { width: 9px; height: 9px; border-radius: 3px; flex: none; }
.legendezeile .p-protein { background: var(--protein); }
.legendezeile .p-kh      { background: var(--kh); }
.legendezeile .p-fett    { background: var(--fett); }
@media (max-width: 360px) {
  .legendezeile { font-size: 10.5px; }
  .ringzeile { gap: 8px; }
}

.ringpfeil { display: grid; place-items: center; width: 22px; }
.ringpfeil svg {
  width: 18px; height: 18px; fill: none; stroke: var(--stumm);
  stroke-width: 2.4; stroke-linecap: round; stroke-linejoin: round;
}

.ringmitte { position: relative; display: grid; place-items: center; }
.ring { width: 168px; height: 168px; display: block; }
@media (max-width: 360px) { .ring { width: 140px; height: 140px; } }

.ringinhalt {
  position: absolute; inset: 0;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 1px; pointer-events: none; text-align: center;
}
.ringzahl    { font-size: 34px; font-weight: 800; letter-spacing: -1.5px; line-height: 1.02; }
.ringwort    { font-size: 11.5px; font-weight: 600; color: var(--stumm); }
.ringprozent { font-size: 12.5px; font-weight: 700; color: var(--stumm); margin-top: 4px; }

.ringgrund { fill: none; stroke: var(--flaeche); stroke-width: 14; }
/* DER OFFENE TEIL: dieselbe Farbe, blass (Auftrag 14, 1).
   Blass darf nicht unsichtbar heiszen - die Deckkraft ist so gewaehlt,
   dass sich der Bogen messbar vom Ringgrund abhebt. Das prueft
   oberflaeche-browser.mjs in hell UND dunkel; eine Zahl, die nur
   dasteht, waere eine Behauptung. */
.ringteil.blass { opacity: .34; }
/* Der aeuszere Kalorienring der Form "zwei": gegessen in der stummen
   Textfarbe, offen als ruhige Spur. Keine Makrofarbe - sonst konkurriert
   er mit den Boegen innen, und genau das soll diese Form vermeiden. */
#r-kcal-voll  { stroke: var(--stumm); }
#r-kcal-offen { stroke: var(--rand); }
/* In der Form "zwei" ist das Loch in der Mitte kleiner - die Zahl auch.
   Sonst liegt sie auf dem Bogen, und das sieht man erst auf dem Bild. */
[data-ringform="zwei"] .ringzahl { font-size: 28px; }
[data-ringform="zwei"] .ringwort { font-size: 10.5px; }
/* Der Prozentsatz entfaellt in dieser Form: der aeuszere Ring IST der
   Prozentsatz. Zweimal dieselbe Auskunft, und die zweite liegt auf dem
   Bogen - auf dem Bild sofort zu sehen. */
[data-ringform="zwei"] .ringprozent { display: none; }
.ringteil  { fill: none; stroke-width: 14; transition: stroke-dasharray .35s ease; }
#r-protein, #r-offen-protein { stroke: var(--protein); }
#r-fett,    #r-offen-fett    { stroke: var(--fett); }
#r-kh,      #r-offen-kh      { stroke: var(--kh); }

/* Die zwei Punkte unter dem Ring. Sie sind Knoepfe und keine Grafik:
   wischen ist auf einem Rechner keine Bedienung, und ein Merkmal, das
   nur mit dem Finger erreichbar ist, sperrt Nutzer aus. */
.ringpunkte { display: flex; justify-content: center; gap: 7px; margin-top: 10px; }
.ringpunkte button {
  width: 26px; height: 18px; padding: 0; border: 0; background: none;
  display: grid; place-items: center;
}
.ringpunkte button::after {
  content: ""; width: 7px; height: 7px; border-radius: 4px;
  background: var(--rand); transition: background .15s ease, width .15s ease;
}
.ringpunkte button.ist-an::after { background: var(--stumm); width: 18px; }

/* Das i am Ring (Auftrag 11, Punkt 3).

   NUR NOCH DER ORT, NICHT MEHR DAS AUSSEHEN. Seit Auftrag 22, 1.1
   gibt es den Info-Knopf genau einmal - Form, Farbe und Zustand
   stehen im Bauteilblock weiter unten. Hier bleibt, was wirklich
   nur den Ring betrifft: er sitzt in der Ecke der Ringkarte und ist
   dort etwas groeszer als neben einer Ueberschrift.

   Zwei Auslegungen desselben Knopfes waeren genau das, wogegen
   Stufe 1 dieses Auftrags gebaut ist. */
.ringkarte { position: relative; }
.ringkarte > .infoknopf {
  position: absolute; top: 12px; right: 12px;
  width: 26px; height: 26px; border-radius: 13px; font-size: 13px;
}
.infokasten {
  margin-top: 12px; padding: 12px 13px;
  background: var(--flaeche); border: 1px solid var(--randfein);
  border-radius: var(--rundungklein); font-size: 12.5px; line-height: 1.55;
}
.infokasten b { display: block; margin-bottom: 4px; font-size: 13px; color: var(--text); }
.infozeile { display: flex; justify-content: space-between; gap: 10px; padding: 3px 0; }
.infozeile span:last-child { font-weight: 700; color: var(--text); white-space: nowrap; }

.makrotitel { font-size: 12px; font-weight: 700; color: var(--stumm);
              text-transform: uppercase; letter-spacing: .06em;
              margin: 4px 0 12px; text-align: center; }
.makros { display: flex; flex-direction: column; gap: 11px; min-width: 0; }
.makro .kopfzeile { display: flex; align-items: center; gap: 6px; }
.makro .punkt { width: 10px; height: 10px; border-radius: 3px; flex: none; }
.makro .name  { font-size: 12px; color: var(--stumm); font-weight: 600; }
/* FARBE IST NIE DAS EINZIGE MERKMAL (Auftrag 11, 2.1). Der Prozentsatz
   steht als Zahl rechts, der Name links - wer Farben schlecht
   unterscheidet, liest beides. */
.makro .anteil { margin-left: auto; font-size: 12.5px; font-weight: 700; }
.makro .wert  { font-size: 14.5px; font-weight: 700; margin-top: 1px; }
.makro .wert span { color: var(--blass); font-weight: 500; }
.makro .balken { height: 7px; border-radius: 4px; background: var(--flaeche);
                 margin-top: 5px; overflow: hidden; }
.makro .balken i { display: block; height: 100%; border-radius: 4px; }

/* ---------------------------------------------------------------
   DIE DREI ZAHLEN (Auftrag 11, Punkt 1)

   Ziel, gegessen, offen - und "offen" ist die groesste. Sie steht
   zusaetzlich im Ring; hier steht sie im Zusammenhang, aus dem sie
   sich ergibt. Ohne Scrollen sichtbar: die Karte ist die erste.
   --------------------------------------------------------------- */
.dreizahl {
  display: grid; grid-template-columns: 1fr auto 1fr; align-items: end; gap: 8px;
  border-top: 1px solid var(--randfein); margin-top: 16px; padding-top: 13px;
}
.dreizahl .feld { min-width: 0; }
.dreizahl .feld.mitte { text-align: center; }
.dreizahl .feld.rechts { text-align: right; }
.dreizahl .wort { font-size: 11.5px; color: var(--stumm); font-weight: 600; }
.dreizahl .zahl { font-size: 17px; font-weight: 700; letter-spacing: -.02em; margin-top: 1px; }
.dreizahl .feld.gross .zahl { font-size: 23px; font-weight: 800; }
.dreizahl .zahl small { font-size: 11.5px; font-weight: 600; color: var(--stumm); }
.dreizahl .zahl.drueber { color: var(--warntext); }
.ringtext { margin: 12px 0 0; font-size: 13px; color: var(--stumm); }

.warnkasten {
  margin-top: 12px; padding: 11px 12px;
  background: var(--warngrund); border: 1px solid var(--warnrand);
  border-radius: var(--rundungklein); color: var(--warntext); font-size: 12.5px;
}
.warnkasten b { display: block; margin-bottom: 3px; }
.warnkasten button.alslink { color: var(--warntext); }

/* DER PFLICHTHINWEIS - in normaler Textfarbe (Nachtrag N1).
   Gleiche Form wie der Warnkasten, damit er als abgesetzter Block
   erkennbar bleibt, aber ohne die gedaempfte Warnfarbe: eine
   Pflichtangabe, die zuruecktritt, arbeitet gegen ihren Zweck. */
.pflichtkasten {
  margin-top: 12px; padding: 11px 12px;
  background: var(--flaeche); border: 1px solid var(--rand);
  border-radius: var(--rundungklein); color: var(--text); font-size: 12.5px;
}

/* ---------------------------------------------------------------
   Gewicht
   --------------------------------------------------------------- */
.gewichtsreihe { display: flex; align-items: center; gap: 8px; }
.gewichtsreihe input { flex: 1 1 auto; min-width: 0; font-size: 17px; font-weight: 700; }
.gewichtsreihe .einheit { color: var(--stumm); font-size: 13px; flex: none; }
.gewichtsreihe button {
  flex: none; padding: 12px 15px; border: 0; border-radius: var(--rundungklein);
  background: var(--knopf); color: var(--knopftext); font-weight: 700; font-size: 14px;
}
.gewichtsfeld .gewichtsstand { margin-bottom: 7px; }
.gewichtsfeld p { margin: 8px 0 0; }

/* ---------------------------------------------------------------
   DIE GEWICHTSLINIE (Auftrag 11, KORREKTUR 13)

   Startgewicht - Punkt - Zielgewicht, direkt unter dem Ring. Sie
   ersetzt zwei Eingabekarten, die den Startbildschirm ueberladen
   haben, und ist selbst ein Knopf: ein Tipp oeffnet die Eingabe.

   SCHMAL HEISST SCHMAL. Die ganze Zeile ist niedriger als eine der
   beiden Karten, die sie ersetzt - sonst waere nichts gewonnen.
   --------------------------------------------------------------- */
.gewichtslinie {
  display: block; width: 100%; text-align: left; margin-top: 14px;
  padding: 11px 0 0; border: 0; border-top: 1px solid var(--randfein);
  background: none; color: inherit; font: inherit;
}
.gewichtslinie .linieenden {
  display: flex; justify-content: space-between; gap: 10px;
  font-size: 11.5px; font-weight: 600; color: var(--stumm);
}
.gewichtslinie .liniebahn {
  display: block; position: relative; height: 6px; margin: 7px 0 0;
  border-radius: 4px; background: var(--flaeche);
}
.gewichtslinie .liniebahn i {
  display: block; height: 100%; border-radius: 4px; background: var(--gut);
}
/* Der Punkt sitzt AUF dem Fuellstand, nicht daneben: er ist "wo du
   stehst", und das ist dasselbe Ende. */
.gewichtslinie .liniebahn b {
  position: absolute; top: 50%; width: 12px; height: 12px; border-radius: 50%;
  transform: translate(-50%, -50%); background: var(--karte);
  border: 2.5px solid var(--gut);
}
.gewichtslinie .linietext {
  display: block; margin-top: 7px; font-size: 12.5px; color: var(--stumm);
}
/* Der Druckzustand, nicht Hover (Auftrag 11, 16): auf dem iPhone gibt
   es kein Hover, und genau dort wird die App benutzt. */
.gewichtslinie:active { opacity: .6; }

/* ---------------------------------------------------------------
   Mahlzeiten
   --------------------------------------------------------------- */
/* DIE MAHLZEITEN SIND SICHTBAR EIN MODUL (Auftrag 22, 2.8).

   R's Befund: *"die Bloecke Mittag / Abend / Snack sehen voneinander
   losgeloest aus."* Sie waren drei Karten mit eigenem Rahmen und
   eigenem Abstand - drei Orte statt einer Liste.

   Jetzt: EINE Flaeche mit EINEM Rahmen, darin die Mahlzeiten durch
   feine Linien getrennt. Der Tagesabschluss liegt in derselben
   Flaeche und ist damit sichtbar der letzte Schritt derselben Sache.

   #m-liste und #alltag stehen im Markup nebeneinander; der Rahmen
   liegt deshalb auf einem gemeinsamen Elternteil (#mahlzeitenmodul). */
#mahlzeitenmodul {
  background: var(--karte); border: 1px solid var(--rand);
  border-radius: var(--rundung); overflow: hidden;
}
.mahlzeit {
  background: none; border: 0; border-radius: 0;
  padding: 12px 12px; margin-bottom: 0;
}
.mahlzeit + .mahlzeit { border-top: 1px solid var(--randfein); }
.mahlzeit.leer .titel { color: var(--stumm); }
.mahlzeitkopf { display: flex; align-items: center; gap: 9px; }
.mahlzeitkopf .titel { flex: 1 1 auto; min-width: 0; font-size: 13px; font-weight: 700; }
.mahlzeitkopf .titel span { color: var(--blass); font-weight: 500; }
.mahlzeitkopf button {
  flex: none; width: 32px; height: 32px; padding: 0;
  border: 0; border-radius: 10px; background: var(--flaeche); color: var(--stumm);
  display: grid; place-items: center;
}
.mahlzeitkopf button.voll { background: var(--knopf); color: var(--knopftext); }
.mahlzeitkopf button svg { width: 16px; height: 16px; fill: none; stroke: currentColor;
                           stroke-width: 2.2; stroke-linecap: round; }

.posten { display: flex; align-items: center; gap: 8px; width: 100%;
          background: none; border: 0; text-align: left;
          padding: 8px 0 0; color: inherit; }
/* DER TRENNSTRICH SITZT AM UMSCHLAG, NICHT AN DER ZEILE.
   Seit dem Wischen (app-35, 3.1) steckt jede .posten-Zeile in einem
   .postenwisch - `.posten + .posten` traf danach nichts mehr, und die
   Striche zwischen den Eintraegen waren lautlos weg. */
.postenwisch + .postenwisch { border-top: 1px solid var(--randfein); margin-top: 6px; }

/* ---------------------------------------------------------------
   NACH LINKS WISCHEN (Auftrag app-35, 3.1)

   Der Loeschknopf liegt UNTER der Zeile und wird von ihr verdeckt;
   das Wischen schiebt die Zeile zur Seite. Zwei Vorteile gegenueber
   einem Knopf, der erst eingefuegt wird: nichts springt in der Hoehe,
   und der Knopf ist schon da, wenn der Finger ankommt.

   `touch-action: pan-y` gibt das senkrechte Scrollen an den Browser
   ab und behaelt nur die waagerechte Geste. Ohne das kaempfen die
   Zeile und die Liste um denselben Finger - und die Liste gewinnt,
   weil sie zuerst da war.
   --------------------------------------------------------------- */
.postenwisch { position: relative; overflow: hidden; }
.postenwisch .posten { position: relative; z-index: 1;
                       background: var(--flaeche); touch-action: pan-y; }
.wischgrund {
  position: absolute; z-index: 0; top: 0; right: 0; bottom: 0;
  display: flex; align-items: stretch;
}
.wischweg {
  border: 0; border-radius: var(--rundungklein);
  padding: 0 14px; min-width: 88px;
  background: var(--warngrund); color: var(--warntext);
  font-size: 12.5px; font-weight: 700;
}
.wischweg:active { opacity: .7; }
.posten .was  { flex: 1 1 auto; min-width: 0; }
.posten .name { font-size: 13px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.posten .menge{ font-size: 11.5px; color: var(--stumm); margin-top: 1px; }
.posten .kcal { flex: none; font-size: 13px; font-weight: 700; }
.mahlzeit .leerzeile { font-size: 12px; color: var(--blass); margin-top: 3px; }


/* ---------------------------------------------------------------
   DIE DREI MODELLFUNKTIONEN (Auftrag 10, A7 bis A9)

   "Was passt jetzt?" steht ueber der Vorschlagsliste und ist von ihr
   abgesetzt: es ist dieselbe Frage aus der anderen Richtung, nicht ein
   Filter derselben Liste.
   --------------------------------------------------------------- */
.wasjetzt {
  margin: 2px 0 14px; padding-bottom: 12px;
  border-bottom: 1px solid var(--randfein);
}
.wasjetzt .suchreihe { margin-bottom: 6px; }
/* Das Mengenfeld in der Foto-Schaetzung: schmal, damit Name und Zahl
   bei 400 px nebeneinander passen. */
.mengenfeld { flex: none; width: 72px; text-align: right; padding: 8px 9px; }

/* ---------------------------------------------------------------
   FORTSCHRITTSFOTOS (Auftrag 10, A4)

   Zwei nebeneinander, nie drei: bei 400 px waeren drei Bilder drei
   Briefmarken, und der Vergleich ist genau das, was diese Ansicht
   leisten soll.
   --------------------------------------------------------------- */
.fotovergleich { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; margin: 10px 0; }
.fotospalte img {
  display: block; width: 100%; height: auto; margin-top: 4px;
  border-radius: var(--rundungklein); background: var(--flaeche);
}
.fotogitter {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(88px, 1fr));
  gap: 7px; margin: 8px 0;
}
.fotokachel {
  position: relative; padding: 0; border: 1px solid var(--rand);
  border-radius: var(--rundungklein); overflow: hidden; background: var(--flaeche);
  aspect-ratio: 3 / 4;
}
.fotokachel img { display: block; width: 100%; height: 100%; object-fit: cover; }
.fotokachel .wann {
  position: absolute; left: 0; right: 0; bottom: 0; padding: 3px 5px;
  font-size: 10.5px; font-weight: 700; color: #fff;
  background: linear-gradient(transparent, rgba(0,0,0,.62));
}
.fotokachel.gewaehlt { outline: 2px solid var(--knopf); outline-offset: -2px; }
.fotokachel:active { opacity: .7; }
/* Ein Bild, das sich mit diesem Passwort nicht oeffnen laesst, bleibt
   sichtbar leer - kein stiller Platzhalter, der wie ein Bild aussieht. */
img.fehlt { min-height: 40px; border: 1px dashed var(--rand); }

/* ---------------------------------------------------------------
   WISSENSKARTEN (Auftrag 10, A2 - Konzept 50)

   Sie sehen aus wie eine Karte und nicht wie ein Warnkasten: es ist
   eine Erklaerung, keine Meldung. Die Quellen stehen klein darunter -
   sie gehoeren dazu (50.4), duerfen die Aussage aber nicht erschlagen.
   --------------------------------------------------------------- */
.wissenkarte { border-left: 3px solid var(--protein); }
.wissenkarte p { margin: 6px 0 0; font-size: 14px; }
.wissenkarte.weggeklickt { opacity: .62; }
.wissenzu {
  flex: none; width: 30px; height: 30px; margin: -4px -4px -4px 0; padding: 0;
  border: 0; border-radius: 10px; background: none; color: var(--stumm);
  font-size: 19px; line-height: 1;
}
.wissenzu:active { background: var(--flaeche); }
/* Die Quellenliste selbst ist schon gestaltet (Belegseite) - hier wird
   sie nur nicht ein zweites Mal erfunden. */

/* ---------------------------------------------------------------
   REITER UEBER DEN MAHLZEITEN (Auftrag 11, 15)

   Supplemente sind ein Reiter hier und kein eigener Bereich in der
   Navigation. Die Zeile ist gar nicht da, wenn der Schalter aus ist -
   ein Reiter, der taeglich ueber den Mahlzeiten steht, fragt taeglich,
   ob man nicht doch etwas nehmen sollte.
   --------------------------------------------------------------- */
.mahlzeitreiter { display: flex; flex-wrap: wrap; gap: 5px; margin: 0 0 9px; }
.mahlzeitreiter button {
  flex: none; padding: 8px 13px; border-radius: 999px;
  border: 1px solid var(--rand); background: var(--karte); color: var(--stumm);
  font-size: 12.5px; font-weight: 600;
}
.mahlzeitreiter button.ist-an {
  background: var(--knopf); color: var(--knopftext); border-color: var(--knopf);
}
.mahlzeitreiter button:active { opacity: .6; }

/* Die verbreiteten Stoffe zum Antippen. Gleiche Groesze, gleiche Farbe,
   gleiche Reihenfolge wie im Code - eine hervorgehobene Kachel waere
   eine Empfehlung, und die gibt diese App nicht ab (Konzept 43.2). */
.stoffe { display: flex; flex-wrap: wrap; gap: 6px; margin: 6px 0 8px; }
.stoff {
  flex: none; padding: 9px 13px; border-radius: 999px;
  border: 1px dashed var(--rand); background: none; color: var(--stumm);
  font-size: 12.5px; font-weight: 600;
}
.stoff:active { opacity: .6; }

/* ---------------------------------------------------------------
   Fussleiste - fest unten, wie in einer App
   --------------------------------------------------------------- */
.fussleiste {
  position: fixed; left: 0; right: 0; bottom: 0; z-index: 30;
  display: flex; align-items: center; justify-content: space-around; gap: 6px;
  padding: 9px 12px calc(env(safe-area-inset-bottom, 0px) + 11px);
  background: var(--fussgrund); border-top: 1px solid var(--rand);
}
.fussknopf {
  background: none; border: 0; padding: 4px 10px;
  display: flex; flex-direction: column; align-items: center; gap: 3px;
  color: var(--blass); width: 84px;
}
.fussknopf svg { width: 21px; height: 21px; fill: none; stroke: currentColor;
                 stroke-width: 2; stroke-linecap: round; stroke-linejoin: round; }
.fussknopf span { font-size: 10px; font-weight: 600; }
.fussknopf.ist-an { color: var(--text); }
.fussknopf.ist-an span { font-weight: 700; }

/* ---------------------------------------------------------------
   ZUSTAND BEIM BERUEHREN (Auftrag 11, 16)

   AUF DEM IPHONE GIBT ES KEIN HOVER. Ein reiner Hover-Effekt waere
   genau dort unsichtbar, wo R die App benutzt. Gebaut ist deshalb der
   DRUCKZUSTAND (:active); Hover kommt nur zusaetzlich fuer den
   Schreibtisch dazu, und auch nur dort, wo ein Zeiger wirklich schwebt
   (@media (hover: hover)) - ohne diese Bedingung bleibt der
   Hover-Zustand auf Touch-Geraeten nach dem Tippen kleben.

   KEIN RUCKELN: der Schein laeuft ueber Deckkraft, nicht ueber Groesze
   oder Position. transform und width loesen ein Neuberechnen des
   Layouts aus; opacity wird vom Bildwerk allein erledigt.

   Ein weicher Lichtschein, kein harter Farbwechsel: der Kreis liegt
   HINTER dem Symbol und blendet auf, statt die Farbe umzuschalten.
   --------------------------------------------------------------- */
.fussknopf { position: relative; }
.fussknopf::before {
  content: ''; position: absolute; top: 0; left: 50%; width: 46px; height: 46px;
  margin-left: -23px; border-radius: 23px; background: var(--flaeche);
  opacity: 0; transition: opacity .16s ease; pointer-events: none;
}
.fussknopf:active::before { opacity: 1; }
.fussrund { transition: box-shadow .16s ease, opacity .16s ease; }
.fussrund:active { opacity: .82; box-shadow: 0 2px 8px rgba(32,30,27,.26); }

@media (hover: hover) and (pointer: fine) {
  .fussknopf:hover::before { opacity: .7; }
}

/* Wer "Bewegung reduzieren" eingestellt hat, bekommt den Zustand ohne
   Uebergang - er bleibt sichtbar, er blendet nur nicht mehr auf. */
@media (prefers-reduced-motion: reduce) {
  .fussknopf::before, .fussrund { transition: none; }
}

.fussrund {
  width: 52px; height: 52px; margin-top: -18px; flex: none;
  border: 0; border-radius: 26px; padding: 0;
  background: var(--knopf); color: var(--knopftext);
  display: grid; place-items: center; box-shadow: 0 4px 14px rgba(32,30,27,.18);
}
.fussrund svg { width: 23px; height: 23px; fill: none; stroke: currentColor;
                stroke-width: 2.5; stroke-linecap: round; }

/* ---------------------------------------------------------------
   Kontomenue am Kopf-Symbol (Auftrag 11, Punkt 9)

   Es sitzt UEBER der Fussleiste, nicht daneben: bei 400 px ist
   rechts neben dem Knopf kein Platz fuer drei Eintraege.
   --------------------------------------------------------------- */
#kontomenue { position: fixed; inset: 0; z-index: 45; }
.menuegrund { position: absolute; inset: 0; background: rgba(24,22,20,.32); }
.menuekasten {
  position: absolute; right: 10px; max-width: calc(100vw - 20px); min-width: 190px;
  bottom: calc(env(safe-area-inset-bottom, 0px) + 74px);
  background: var(--karte); border: 1px solid var(--rand);
  border-radius: var(--rundung); box-shadow: 0 10px 30px rgba(24,22,20,.22);
  padding: 6px; display: flex; flex-direction: column;
}
.menuekasten button {
  background: none; border: 0; text-align: left;
  padding: 13px 14px; border-radius: var(--rundungklein);
  font-size: 14.5px; font-weight: 600; color: var(--text);
}
.menuekasten button + button { border-top: 1px solid var(--rand); border-radius: 0; }
.menuekasten button:last-child { border-radius: 0 0 var(--rundungklein) var(--rundungklein); }
.menuekasten button.gefahr { color: var(--fehler); }

/* ---------------------------------------------------------------
   Rueckfrage (Auftrag 11, Punkt 8)
   --------------------------------------------------------------- */
#frage { position: fixed; inset: 0; z-index: 60; }
.fragegrund { position: absolute; inset: 0; background: rgba(24,22,20,.45); }
.fragekasten {
  position: absolute; left: 50%; top: 50%; transform: translate(-50%, -50%);
  width: min(340px, calc(100vw - 32px));
  background: var(--karte); border: 1px solid var(--rand);
  border-radius: var(--rundung); box-shadow: 0 14px 40px rgba(24,22,20,.28);
  padding: 18px;
}
.fragekasten strong { font-size: 15px; display: block; }
.fragekasten p { font-size: 13px; color: var(--stumm); line-height: 1.5; margin: 8px 0 14px; }
.fragekasten .knopfreihe { flex-wrap: wrap; }

/* ---------------------------------------------------------------
   Der Speichern-Balken der Profileinstellungen (Auftrag 11, Punkt 8)

   Kein fester Knopf: dieser Balken ist verborgen, bis wirklich etwas
   geaendert wurde. Er liegt UNTER der Fussleiste in der Stapelfolge,
   damit er sie nie verdeckt.
   --------------------------------------------------------------- */
#ich-speichern {
  position: fixed; left: 0; right: 0; z-index: 29;
  bottom: calc(env(safe-area-inset-bottom, 0px) + 72px);
  width: var(--spalte); margin: 0 auto;
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  padding: 10px 12px; border-radius: var(--rundung);
  background: var(--karte); border: 1px solid var(--rand);
  box-shadow: 0 8px 24px rgba(24,22,20,.20);
}
#ich-offen { font-size: 12.5px; color: var(--stumm); line-height: 1.4; min-width: 0; }
#ich-speichern-knopf {
  flex: none; border: 0; padding: 12px 18px; border-radius: var(--rundungklein);
  background: var(--knopf); color: var(--knopftext); font-weight: 700;
}

/* Eine durchgehende Seite statt Karten (Auftrag 11, Punkt 8). Die
   Abschnitte trennt eine Linie, kein Kasten - sie sind Wegmarken im
   Fluss, keine eigenen Orte. */
.seitenteil { padding: 18px 0 4px; border-top: 1px solid var(--rand); }
.seitenteil:first-child { border-top: 0; padding-top: 4px; }
.seitenteil > h2 {
  font-size: 13px; font-weight: 700; margin: 0 2px 10px;
  letter-spacing: .01em;
}

/* EIN MINDESTABSTAND ZWISCHEN ZWEI ZEILEN EINES ABSCHNITTS
   (Auftrag 22, 0.3).

   R's Befund vom 14.09.2026: "maennlich / weiblich und das
   Geburtsjahr so dicht beieinander, dass sich die Texte
   ueberschneiden." Nachgemessen ueberlappen sie nicht - sie
   BERUEHREN sich: der Abstand war an drei Stellen exakt 0 px. Fuer
   den Leser ist das dasselbe.

   Der Grund war jedesmal derselbe: die Zeile darueber traegt ihren
   Abstand als `margin-bottom`, die Zeile darunter bringt keinen mit,
   und wo die erste keinen hat, bleibt nichts.

   DESHALB EIN BODEN UND KEINE EINZELKORREKTUR. `margin-top` benachbarter
   Bloecke FAELLT MIT dem `margin-bottom` des Vorgaengers ZUSAMMEN -
   es gilt der groeszere der beiden. Diese Regel addiert also nichts,
   wo schon genug Luft ist; sie fuellt nur die Stellen, an denen gar
   keine ist. Eine Liste einzelner Selektoren waere beim naechsten
   neuen Abschnitt wieder unvollstaendig.

   Gemessen wird das ab jetzt: "keine Formularzeile klebt an der
   naechsten" in der Browserprobe, mit dem engsten Abstand als
   Messwert. */
.seitenteil > * + * { margin-top: 10px; }

/* ===============================================================
   DIE VIER BAUTEILE AUS AUFTRAG 22, STUFE 1

   Ein Bauteil, eine Gestaltung, ein Verhalten. Wer eines davon
   aendert, aendert es fuer alle zwanzig Stellen - und genau das ist
   der Zweck.
   =============================================================== */

/* 1.1 DER INFO-KNOPF - ein kleines i NEBEN der Ueberschrift.
   Nicht davor (dann liest man erst das Zeichen und dann das Thema)
   und nicht als eigene Zeile (dann ist es wieder Text, den niemand
   angefordert hat). */
.mit-info { display: flex; align-items: center; gap: 7px; }
.infoknopf {
  flex: none; width: 18px; height: 18px; padding: 0;
  border: 1px solid var(--rand); border-radius: 9px;
  background: var(--karte); color: var(--stumm);
  font-size: 11px; font-weight: 700; font-style: italic; line-height: 1;
  display: grid; place-items: center;
  transition: background .16s ease, color .16s ease, border-color .16s ease;
}
/* DER ZUSTAND HAENGT AN aria-expanded UND NICHT AN EINER KLASSE.
   Damit kann das Aussehen nicht mehr von dem abweichen, was ein
   Screenreader vorliest - vorher waren es zwei Angaben, die von Hand
   gleichgehalten werden mussten. */
.infoknopf[aria-expanded="true"] {
  background: var(--knopf); color: var(--knopftext); border-color: var(--knopf);
}

/* Der Text, den das i aufklappt. Er sitzt eingerueckt unter der
   Ueberschrift, damit sichtbar bleibt, WOZU er gehoert. */
.infotext {
  font-size: 12px; line-height: 1.55; color: var(--stumm);
  margin: 0 2px 4px; padding-left: 10px;
  border-left: 2px solid var(--randfein);
}
.infotext > div + div { margin-top: 6px; }

/* 1.2 DAS AUF- UND ZUKLAPPEN.
   BEWEGUNG UEBER HOEHE UND DECKKRAFT, NIE UEBER POSITION - eine
   Position, die wandert, laesst die ganze Seite unter dem Finger
   rutschen. overflow: hidden ist noetig, sonst steht der Inhalt bei
   max-height: 0 trotzdem da. */
.klappinhalt {
  overflow: hidden;
  transition: max-height .2s ease, opacity .2s ease;
}

/* 1.3 DIE PREMIUM-KENNZEICHNUNG - ein Schriftzug, klein, immer
   gleich. KEIN SCHLOSS, KEINE SPERRE, KEIN VERDUNKELN (Auftrag 13,
   Abschnitt 6). Er steht auch dann da, wenn die Funktion offen ist:
   taucht das Wort erst beim Verkaufsstart auf, wirkt es wie eine
   nachtraegliche Sperre statt wie etwas, das man schon kannte. */
.premiumzeichen {
  flex: none; display: inline-block; vertical-align: middle;
  font-size: 9.5px; font-weight: 700; letter-spacing: .08em;
  text-transform: uppercase; color: var(--fett);
  border: 1px solid var(--fett); border-radius: 999px;
  padding: 1px 6px; margin-left: 7px; white-space: nowrap;
  opacity: .9;
}

/* WO ER STEHT - UEBERALL GLEICH (Auftrag 22, Nachtrag N6).

   R: *"Oben rechts, auf der Hoehe der Ueberschrift der Funktion.
   Nicht mitten in der Kachel, nicht neben dem Text. Ein Schriftzug,
   der mal hier und mal dort steht, wird nicht wiedererkannt."*

   Vorher klebte er unmittelbar hinter dem Ueberschriftstext - also an
   fuenf Stellen an fuenf verschiedenen Punkten der Zeile, je nachdem
   wie lang die Ueberschrift war.

   ZWEI EIGENSCHAFTEN, UND BEIDE WERDEN GEBRAUCHT:
   - `margin-left: auto` schiebt ihn an den rechten Rand. Es ueberschreibt
     das margin-left: 7px von oben; das bleibt fuer den Fall stehen, dass
     er einmal auszerhalb eines Flexkastens steht.
   - `order: 9` setzt ihn ans ENDE der Zeile, auch wenn er im Dokument
     vor dem i steht. Das ist an vier der fuenf Stellen so, und es ohne
     `order` zu loesen hiesze, fuenf Aufrufstellen gleichzuhalten -
     also genau die Bauart, aus der "[object Object]" entstanden ist.
     Unbedenklich, weil der Schriftzug NICHTS BEDIENT: ein Vorleser
     liest die Dokumentreihenfolge, und die bleibt richtig.

   EINE REGEL FUER ALLE ORTE. `.mit-info` traegt jede Ueberschrift mit
   Zusatzzeichen - Tellerfoto, Etikett, Fotovergleich,
   Koerperfettschaetzung -, `.fragenzeichen` die drei Fragen. Wer eine
   sechste Stelle baut, bekommt die Lage geschenkt, statt sie
   nachzubauen. */
.mit-info > .premiumzeichen,
.fragenzeichen > .premiumzeichen {
  margin-left: auto; order: 9;
}

/* Der unsichtbare Zwilling (siehe premiumPlatz() in app.js). Er haelt
   den Platz frei, damit alle drei Fragen gleich breit sind - gemessen
   am 15.09.2026: ohne ihn war die Premium-Kachel 241 px breit und die
   beiden anderen 312 px.

   visibility statt display: nur so nimmt er seinen Platz ein. */
.premiumzeichen.platzhalter { visibility: hidden; }

/* 1.4 DIE GESTALTUNGSSCHICHT - Zustaende und Bewegung.

   R's Befund, woertlich: "sonst sieht es alles sehr, sehr schwach
   aus." Das betrifft nicht einen Knopf, sondern alle.

   HOVER NUR BEI ECHTEM ZEIGER. Auf dem Telefon gibt es kein Hover,
   und ein Hover-Zustand, der dort am Antippen haengenbleibt, sieht
   aus wie ein Fehler.

   DRUCK UEBER DECKKRAFT UND SCHATTEN, NIE UEBER GROESZE ODER
   POSITION (Auftrag 11, Abschnitt 16 - gilt weiter). transform und
   width loesen ein Neuberechnen des Layouts aus.

   HOCHWERTIGER HEISZT HIER: ruhiger, klarere Zustaende - NICHT mehr
   Farbe und nicht mehr Bewegung. */
.wahl, .wahlzeile, .knopfreihe button, .schalter, .infoknopf,
.suchreihe button, .geraet button {
  transition: background .16s ease, border-color .16s ease,
              box-shadow .16s ease, opacity .16s ease;
}
@media (hover: hover) and (pointer: fine) {
  .wahl:hover, .knopfreihe button:hover, .suchreihe button:hover,
  .infoknopf:hover, .geraet button:hover {
    border-color: var(--knopf);
    box-shadow: 0 0 0 1px var(--knopf);
  }
  .wahlzeile:hover .haken { border-color: var(--knopf); }
  .schalter:hover { box-shadow: 0 0 0 1px var(--knopf); }
}
/* Der Druck ist deutlicher als bisher - vorher war er an mehreren
   Stellen gar nicht da. */
.wahl:active, .knopfreihe button:active, .suchreihe button:active,
.infoknopf:active, .geraet button:active {
  opacity: .78; box-shadow: inset 0 1px 3px rgba(32,30,27,.16);
}

/* ALLES STEHT SOFORT DA. Das ist keine Kuer - es ist eine
   Systemeinstellung, die Menschen aus einem Grund setzen. Der
   Zustand bleibt sichtbar, er blendet nur nicht mehr auf. */
@media (prefers-reduced-motion: reduce) {
  .wahl, .wahlzeile, .knopfreihe button, .schalter, .infoknopf,
  .suchreihe button, .geraet button, .klappinhalt, .ringteil,
  /* Der Winkel der Wertzeile dreht sich ebenfalls nicht mehr - er
     steht sofort richtig herum (Nachtrag N9 mit 1.4). */
  .wertzeile[aria-expanded]::after {
    transition: none !important;
  }
  .klappinhalt { max-height: none !important; }
}

/* ---------------------------------------------------------------
   Blatt von unten
   --------------------------------------------------------------- */
#blatt { position: fixed; inset: 0; z-index: 40; }
.blattgrund { position: absolute; inset: 0; background: rgba(24,22,20,.45); }
.blattkasten {
  position: absolute; left: 0; right: 0; bottom: 0;
  max-height: 92vh; display: flex; flex-direction: column;
  background: var(--grund);
  border-radius: 22px 22px 0 0;
  border-top: 1px solid var(--rand);
  /* Nativer Uebergang statt Seitenwechsel. */
  animation: hoch .22s cubic-bezier(.2,.8,.3,1);
}
@keyframes hoch { from { transform: translateY(100%); } to { transform: none; } }
@media (prefers-reduced-motion: reduce) { .blattkasten { animation: none; } }

.blattgriff { width: 38px; height: 4px; border-radius: 2px; background: var(--rand);
              margin: 8px auto 2px; flex: none; }
.blattkopf { display: flex; align-items: center; justify-content: space-between;
             padding: 8px var(--luft) 6px; flex: none; }
.blattkopf strong { font-size: 15px; }
.blattinhalt {
  overflow-y: auto; -webkit-overflow-scrolling: touch;
  padding: 4px var(--luft) calc(env(safe-area-inset-bottom, 0px) + 20px);
}

/* Die Reiter des Eintragen-Blatts.

   SIE BRECHEN UM, STATT ZU SCROLLEN. Mit dem Vorschlag sind es fuenf,
   und bei 400 px Breite passten sie in einer Zeile nicht mehr - der
   letzte ("Von Hand") stand dann rechts auszerhalb des Bildes. Genau
   der ist der Rueckfallweg, wenn Suche und Barcode nichts liefern; ihn
   hinter einer waagerechten Scrollbewegung zu verstecken waere die
   schlechteste Stelle dafuer. Gefunden hat es die Browserprobe bei
   400 px ("ueber den Rand: BUTTON 345..431"). */
.reiter { display: flex; flex-wrap: wrap; gap: 5px; padding: 4px var(--luft) 10px;
          flex: none; }
.reiter button {
  flex: none; padding: 8px 11px; border-radius: 999px;
  border: 1px solid var(--rand); background: var(--karte); color: var(--stumm);
  font-size: 12.5px; font-weight: 600;
}
.reiter button.ist-an { background: var(--knopf); color: var(--knopftext); border-color: var(--knopf); }

/* Die Bruchteile aus Auftrag 11, Abschnitt 12.2: 1/4 bis 3.
   Gleich breit, damit die Reihe beim Umschalten nicht springt - und
   breit genug zum Treffen mit dem Daumen (44 px ist das Mass aus den
   Apple-Richtlinien, an dem sich auch der Rest dieser App orientiert). */
/* IM BLATTINHALT OHNE SEITENLUFT. .blattinhalt bringt sie schon mit;
   zweimal var(--luft) haette die Reihe bei 400 px ueber den Rand
   geschoben - genau der Fehler, den die Browserprobe bei den Reitern
   oben schon einmal gefunden hat. */
.blattinhalt .reiter { padding-left: 0; padding-right: 0; }
.reiter.bruch { padding-top: 0; }
.reiter.bruch button { min-width: 44px; text-align: center; padding: 9px 8px; }

/* "1 Stueck - 360 g - 1040 kcal". Die Zeile steht gross, weil sie die
   Antwort auf die Frage ist, die der Nutzer sich gerade stellt: was
   steckt hinter dieser Portion? */
.portionzeile {
  padding: 10px 0 2px; font-size: 15px; font-weight: 700;
}
.merkfeld { margin-top: 8px; }
.merkfeld input {
  width: 100%; padding: 10px 11px; border-radius: var(--rundungklein);
  border: 1px solid var(--rand); background: var(--karte);
}
button.merken { margin-top: 10px; }

/* Ein Eintrag zum Antippen - Favorit, Treffer, Zuletzt */
.wahl {
  display: flex; align-items: center; gap: 10px; width: 100%; text-align: left;
  background: var(--karte); border: 1px solid var(--rand);
  border-radius: var(--rundungklein); padding: 11px 12px; margin-bottom: 7px;
  color: inherit;
}
.wahl:active { background: var(--flaeche); }
.wahl .was  { flex: 1 1 auto; min-width: 0; }
.wahl .name { font-size: 13.5px; font-weight: 700;
              overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.wahl .zeile{ font-size: 11.5px; color: var(--stumm); margin-top: 2px;
              overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.wahl .kcal { flex: none; font-size: 13px; font-weight: 700; }
.wahl[disabled] { opacity: .55; }

/* Ein Vorschlag traegt seine Begruendung mit. Sie darf umbrechen -
   anders als die Zeile darueber, die eine Zeile bleiben soll: die
   Begruendung IST der Inhalt, nicht das Beiwerk (Konzept 57.5). */
.wahl.vorschlag { align-items: flex-start; }
.wahl.vorschlag .grund {
  font-size: 11.5px; line-height: 1.45; color: var(--stumm); margin-top: 4px;
  white-space: normal;
}
.wahl.vorschlag .kcal { margin-top: 1px; }

/* Die Gerichte unter einer tragenden Zutat (Auftrag 22, 0.2).
   Sie haengen sichtbar am Knopf darueber: eingerueckt, ohne eigenen
   Rahmen - sonst sehen sie nach einer zweiten Liste aus statt nach der
   Antwort auf den Knopf. */
.zutatgerichte {
  margin: -3px 2px 9px 14px; padding-left: 10px;
  border-left: 2px solid var(--randfein);
}
.zutatgerichte .zeile {
  font-size: 12px; line-height: 1.5; color: var(--stumm); padding: 1px 0;
}
.zutatgerichte .zeile.stumm { font-style: italic; }

/* Die Restluecke ueber der Liste - die Zahl, gegen die gerechnet wurde. */
.lueckenkopf {
  background: var(--flaeche); border: 1px solid var(--randfein);
  border-radius: var(--rundungklein); padding: 10px 12px; margin: 6px 0 2px;
}
.lueckenkopf .name  { font-size: 13.5px; font-weight: 700; }
.lueckenkopf .zeile { font-size: 11.5px; line-height: 1.45; color: var(--stumm); margin-top: 3px; }

.gruppe { font-size: 11.5px; font-weight: 700; color: var(--stumm);
          text-transform: uppercase; letter-spacing: .06em; margin: 14px 2px 7px; }
.leerhinweis { color: var(--stumm); font-size: 13px; padding: 10px 2px; }

.suchreihe { display: flex; gap: 8px; margin-bottom: 4px; }
.suchreihe input { flex: 1 1 auto; min-width: 0; }
.suchreihe button { flex: none; padding: 12px 15px; border: 0; border-radius: var(--rundungklein);
                    background: var(--knopf); color: var(--knopftext); font-weight: 700; }

.feldpaar { display: flex; gap: 8px; }
.feldpaar > label { flex: 1 1 0; min-width: 0; }
label.feld { display: block; margin-bottom: 10px; }
label.feld > span { display: block; font-size: 12.5px; color: var(--stumm); margin-bottom: 5px; }

/* ---------------------------------------------------------------
   Einstellungen
   --------------------------------------------------------------- */
.wahlzeile {
  display: flex; align-items: flex-start; gap: 11px; width: 100%; text-align: left;
  background: none; border: 0; padding: 11px 2px; color: inherit;
  border-bottom: 1px solid var(--randfein);
}
.wahlzeile:last-child { border-bottom: 0; }
.wahlzeile .haken { width: 20px; height: 20px; flex: none; margin-top: 1px;
                    border: 1.5px solid var(--rand); border-radius: 10px;
                    display: grid; place-items: center; }
.wahlzeile.ist-an .haken { background: var(--knopf); border-color: var(--knopf); }
.wahlzeile .haken svg { width: 12px; height: 12px; fill: none; stroke: var(--knopftext);
                        stroke-width: 3; stroke-linecap: round; stroke-linejoin: round;
                        visibility: hidden; }
.wahlzeile.ist-an .haken svg { visibility: visible; }
.wahlzeile .was { flex: 1 1 auto; min-width: 0; }
.wahlzeile .name { font-size: 13.5px; font-weight: 700; }
.wahlzeile .zeile { font-size: 12px; color: var(--stumm); margin-top: 2px; }

/* Die Reihe (Konzept 44). Eine Zahl und ein Satz - keine Farbe, die
   Druck macht, und kein Ausrufezeichen. Gezaehlt wird "eingetragen",
   nicht "Ziel erreicht"; eine Anzeige, die wie eine Belohnung aussieht,
   wuerde genau das wieder zu einer Bewertung machen. */
.streakreihe { display: flex; align-items: center; gap: 13px; padding: 4px 0 8px; }
.streakzahl {
  flex: none; min-width: 46px; text-align: center;
  font-size: 30px; font-weight: 800; line-height: 1.05;
}
.streakreihe .was   { flex: 1 1 auto; min-width: 0; }
.streakreihe .name  { font-size: 13.5px; font-weight: 700; }
.streakreihe .zeile { font-size: 12px; line-height: 1.45; color: var(--stumm); margin-top: 3px; }

/* Die Tagesleiste (Auftrag 11, 11.4).
   GRUEN HEISST ABGESCHLOSSEN, NICHT "ZIEL ERREICHT" - deshalb gibt es
   hier kein Rot. Ein Feld, das bei Zieluebertretung rot wird, bestraft
   ehrliches Eintragen und erzeugt geschoente Eintraege; genau davon
   lebt der adaptive TDEE. */
/* ---------------------------------------------------------------
   TAG ABSCHLIESZEN UND KALENDER (Auftrag 11, 14)

   Der Abschluss traegt die Gestalt einer Mahlzeitenzeile: er ist der
   letzte Schritt derselben Liste - Fruehstueck, Mittag, Abend, Snack,
   dann der Abschluss -, kein neues Thema in einem eigenen Kasten.
   --------------------------------------------------------------- */
/* "TAG ABSCHLIESZEN" IST EIN KNOPF (Auftrag 22, 2.8).
   Zentriert unter den Mahlzeiten, im selben Modul - kein eigener
   Block, kein Erklaertext daneben. Der stand vorher da und hat R den
   Bildschirm zugestellt. */
.abschluss {
  display: flex; flex-direction: column; align-items: center;
  gap: 6px; padding: 12px 12px 4px;
}
/* KLEIN, ABER NICHT VERSTECKT (Befund R, 15.09.2026, app-35 Stufe 7.1).
   R: *"Tag abschlieszen - einfach wesentlich kleiner den Button. Der
   muss nicht so praesent sein."*

   Ein Knopf, der so grosz ist wie die Hauptfunktion, behauptet, genauso
   wichtig zu sein. Der Tagesabschluss ist ein Vermerk, keine Leistung,
   und nach Konzept 62 wird er nicht gefeiert.

   DIE UNTERGRENZE IST DER FINGER, NICHT DIE OPTIK: 44 px Hoehe sind
   die kleinste Flaeche, die sich sicher treffen laesst (Apple HIG,
   WCAG 2.5.5). Deshalb `min-height` und nicht nur weniger Polsterung -
   wer den Knopf allein ueber `padding` verkleinert, macht ihn
   unbedienbar, ohne dass es in einem Bildschirmfoto auffaellt.
   Er bleibt an seiner Stelle und behaelt seinen Rand. */
.abschlussknopf {
  padding: 7px 14px; min-height: 44px; border: 1px solid var(--rand);
  border-radius: 999px; background: var(--karte); color: var(--text);
  font-weight: 600; font-size: 12.5px; opacity: .85;
}
/* `voll` faerbt ihn nicht mehr wie die Hauptfunktion ein - das war der
   Grund, warum er so laut war. Die Regel bleibt stehen, damit eine
   aeltere Zeichnung nicht ins Leere greift. */
.abschlussknopf.voll {
  background: var(--karte); color: var(--text); border-color: var(--rand);
}
.abschlusskopf {
  display: flex; align-items: center; gap: 7px;
  font-size: 13px; font-weight: 700; color: var(--gut);
}
.abschluss .klein { text-align: center; max-width: 30rem; }
.abschluss.zu .haken { font-size: 15px; }

/* Der Kalender ersetzt die fruehere 30-Felder-Leiste. GRUEN HEISZT
   ABGESCHLOSSEN, NICHT "ZIEL ERREICHT" - es gibt hier deshalb keine
   Warnfarbe fuer einen ueberschrittenen Tag. */
.kalenderkopf { display: flex; align-items: center; gap: 8px; margin-top: 10px; }
.kalendertitel { flex: 1 1 auto; text-align: center; font-size: 13px; font-weight: 700; }
.kalenderkopf button {
  flex: none; width: 32px; height: 32px; padding: 0; border: 0; border-radius: 10px;
  background: var(--flaeche); color: var(--stumm); font-size: 17px; line-height: 1;
}
.kalenderkopf button:disabled { opacity: .35; }
.kalenderkopf button:active { background: var(--rand); }

.kalender {
  display: grid; grid-template-columns: repeat(7, 1fr); gap: 4px; margin: 9px 0 8px;
}
/* KLEIN IST DIE VORGABE (Auftrag 22, 2.7): heute und die Woche davor,
   in EINER Reihe. Acht Felder nebeneinander sind schmaler als sieben
   und passen auch auf 320 px - deshalb kein aspect-ratio hier. */
.kalender.klein { grid-template-columns: repeat(8, 1fr); }
.kalender.klein .kalendertag { aspect-ratio: auto; height: 34px; }

/* DIE LEGENDE STATT DES SATZES (Auftrag 22, 2.7).
   Je Farbe ein Wort, von links nach rechts. Die Marken sind DIESELBEN
   Klassen wie die Felder darueber - eine zweite Farbtabelle waere eine
   zweite Meinung darueber, was "abgeschlossen" aussieht. */
.kalenderlegende {
  display: flex; flex-wrap: wrap; gap: 4px 12px; margin: 2px 0 4px;
  font-size: 11px; color: var(--stumm);
}
.legendemarke { display: inline-flex; align-items: center; gap: 5px; }
.legendemarke .kalendertag {
  width: 12px; height: 12px; aspect-ratio: auto; border-radius: 4px;
  display: block; flex: none; pointer-events: none;
}
.kalenderwtag { font-size: 10.5px; font-weight: 700; color: var(--blass);
                text-align: center; padding-bottom: 2px; }
.kalenderleer { display: block; }
.kalendertag {
  position: relative; aspect-ratio: 1 / 1; min-width: 0; padding: 0;
  display: grid; place-items: center;
  border: 1px solid var(--randfein); border-radius: 8px;
  background: var(--flaeche); color: var(--stumm);
  font-size: 12px; font-weight: 600;
}
.kalendertag .nr { pointer-events: none; }

/* ---------------------------------------------------------------
   DIE FARBE SAGT DIE ZAHL (Auftrag app-35, Stufe 4)

   Vorher: `.zu` war gruen (abgeschlossen), `.offen` grau
   (eingetragen) und "nichts" ebenfalls grau. Zwei Zustaende in
   derselben Farbe sind keine Legende - R's Befund.

   Jetzt sagt die Farbe die Kalorien gegen das Tagesziel, und alles
   andere sagen Zeichen. Die Stufen kommen vom Server
   (rechnen\Tagesfarbe.php); hier steht nur, wie sie aussehen.

   EIN TAG OHNE EINTRAG BLEIBT NEUTRAL - er sieht aus wie vorher.
   Das ist die empfindlichste Stelle der Funktion: ein nicht
   eingetragener Tag ist kein schlechter Tag (Konzept 62.1).
   --------------------------------------------------------------- */
.kalendertag.stufe-neutral { background: var(--flaeche); color: var(--stumm); }
.kalendertag.stufe-gruen {
  background: var(--gut); border-color: var(--gut);
  /* NICHT #fff. Im dunklen Thema ist --gut ein HELLES Gruen (#7cd992),
     und Weisz darauf traegt 1,72:1 - unlesbar. Genau so stand es hier
     bis zum 15.09.2026, und der Kontrastpruefpunkt hat es nicht
     gefangen, weil dieses Paar nicht in seiner Liste stand.
     --knopftext dreht mit dem Thema: hell #fefdfb (6,34:1), dunkel
     #141416 (10,69:1). */
  color: var(--knopftext);
}
.kalendertag.stufe-leicht {
  background: var(--warngrund); border-color: var(--warnrand); color: var(--warntext);
}
.kalendertag.stufe-rot {
  background: var(--fehlergrund); border-color: var(--fehlerrand); color: var(--fehler);
}

/* ABGESCHLOSSEN IST EIN ZEICHEN, KEINE FARBE MEHR. Ein Strich unten,
   als inset-Schatten und nicht als Rahmen: ein dickerer Rahmen
   verschoebe die Zahl in der Kachel um zwei Pixel. */
.kalendertag.zu { box-shadow: inset 0 -3px 0 currentColor; }

/* DAS STERNCHEN - Eiweiszziel erreicht. Es gibt es nur im gruenen
   Bereich (die Regel steht im Server), also steht es hier immer auf
   einem Grund, auf dem currentColor traegt. */
.kalendertag.stern::before {
  content: '\2605'; position: absolute; top: 1px; right: 3px;
  font-size: 9px; line-height: 1; pointer-events: none;
}
.kalendertag.heute { outline: 1.5px solid var(--stumm); outline-offset: 1px; }
.kalendertag.gewaehlt { outline: 2px solid var(--knopf); outline-offset: 1px; }
.kalendertag.zukunft { opacity: .3; }
.kalendertag:active { opacity: .6; }
/* NACHGETRAGEN ist eine Schraffur und keine zweite Farbe: die Farbe
   sagt schon etwas anderes (offen/abgeschlossen), und zwei Aussagen in
   einem Merkmal liest niemand auseinander. */
.kalendertag.nach::after {
  content: ''; position: absolute; inset: 0; border-radius: 7px; pointer-events: none;
  background: repeating-linear-gradient(135deg,
    transparent 0 3px, currentColor 3px 4px);
  opacity: .45;
}

/* Der Haken am Gewicht (Auftrag 11, Punkt 6). */
.hakenklein { display: inline-grid; place-items: center; vertical-align: -2px; }
.hakenklein svg { width: 13px; height: 13px; fill: none; stroke: var(--gut);
                  stroke-width: 3; stroke-linecap: round; stroke-linejoin: round; }

/* Der Defizit-Regler (Auftrag 11, Punkt 4).
   Ein echtes <input type="range"> und kein Nachbau aus divs: nur das
   echte Element ist von sich aus mit der Tastatur bedienbar, und ein
   Regler, der nur mit dem Finger geht, ist fuer manche eine Sperre. */
.reglerwert { font-size: 19px; font-weight: 800; letter-spacing: -.02em;
              margin: 6px 0 2px; }
.regler { width: 100%; margin: 8px 0 2px; -webkit-appearance: none; appearance: none;
          background: none; }
.regler::-webkit-slider-runnable-track {
  height: 6px; border-radius: 3px; background: var(--flaeche); border: 1px solid var(--randfein);
}
.regler::-moz-range-track {
  height: 6px; border-radius: 3px; background: var(--flaeche); border: 1px solid var(--randfein);
}
.regler::-webkit-slider-thumb {
  -webkit-appearance: none; appearance: none; margin-top: -10px;
  width: 26px; height: 26px; border-radius: 13px;
  background: var(--knopf); border: 2px solid var(--karte); box-shadow: var(--schatten);
}
.regler::-moz-range-thumb {
  width: 26px; height: 26px; border-radius: 13px;
  background: var(--knopf); border: 2px solid var(--karte);
}
.regler:focus-visible::-webkit-slider-thumb { outline: 2px solid var(--protein); outline-offset: 2px; }
.reglermarken { display: flex; justify-content: space-between; gap: 4px; margin-top: 2px; }
.reglermarken button {
  background: none; border: 0; padding: 3px 2px;
  color: var(--blass); font-size: 11.5px; font-weight: 600;
}

.schalterzeile { display: flex; align-items: center; gap: 12px; padding: 4px 0; }
.schalterzeile .was { flex: 1 1 auto; min-width: 0; }
.schalter {
  flex: none; width: 46px; height: 28px; border-radius: 14px; padding: 0;
  border: 1px solid var(--rand); background: var(--flaeche); position: relative;
  transition: background .15s ease;
}
.schalter::after {
  content: ""; position: absolute; top: 2px; left: 2px;
  width: 22px; height: 22px; border-radius: 11px; background: var(--karte);
  box-shadow: 0 1px 3px rgba(0,0,0,.25); transition: transform .15s ease;
}
.schalter.ist-an { background: var(--knopf); border-color: var(--knopf); }
.schalter.ist-an::after { transform: translateX(18px); }

/* Oben 12, unten 10: die Reihe steht in `auswahlZeile()` INNERHALB
   eines Wrappers und ist damit kein Kind des Seitenteils - der Boden
   oben greift dort nicht. Genau diese Stelle war R's Befund. */
.knopfreihe { display: flex; gap: 8px; flex-wrap: wrap; margin: 12px 0 10px; }
.knopfreihe button {
  padding: 11px 14px; border: 1px solid var(--rand); border-radius: var(--rundungklein);
  background: var(--karte); color: var(--text); font-weight: 600; font-size: 13.5px;
}
.knopfreihe button.voll { background: var(--knopf); color: var(--knopftext); border-color: var(--knopf); }
.knopfreihe button.gefahr { background: var(--fehlergrund); color: var(--fehler); border-color: var(--fehlerrand); }
/* Der Abschicken-Knopf der Rueckmeldung (Auftrag 22, 2.9). R's Befund:
   "der Knopf geht unter". Er bekommt die Zustimmungsfarbe dieser App -
   dieselbe, die ein abgeschlossener Tag im Kalender traegt. */
.knopfreihe button.melden {
  background: var(--gut); border-color: var(--gut); color: #fff;
}

.geraet { display: flex; align-items: center; gap: 10px; padding: 11px 0;
          border-bottom: 1px solid var(--randfein); flex-wrap: wrap; }
.geraet:last-child { border-bottom: 0; }
.geraet .was { flex: 1 1 160px; min-width: 0; }
.geraet.aus .name { color: var(--blass); text-decoration: line-through; }
.geraet button { padding: 8px 11px; border: 1px solid var(--rand);
                 border-radius: 10px; background: var(--karte); font-size: 12.5px; }
.geraet button.gefahr { background: var(--fehlergrund); color: var(--fehler); border-color: var(--fehlerrand); }

.schluessel {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12.5px; word-break: break-all;
  background: var(--grund); border: 1px solid var(--warnrand);
  border-radius: var(--rundungklein); padding: 11px; margin: 10px 0;
}

/* ---------------------------------------------------------------
   Woher die Zahlen kommen
   --------------------------------------------------------------- */
.belegblock { margin-bottom: 10px; }
.belegblock h3 { font-size: 14.5px; margin: 0; }
.belegblock p  { margin: 0 0 8px; font-size: 13.5px; line-height: 1.55; }
.belegblock p:first-child { margin-top: 8px; }

/* AUF- UND ZUKLAPPBAR, VORGABE ZU (Auftrag 22, 2.10).
   Die Ueberschrift IST der Ausloeser - ein eigener kleiner Knopf
   daneben waere eine zweite Stelle zum Treffen, und die groeszere
   Flaeche ist auf dem Telefon die bessere. */
.belegkopf {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  width: 100%; padding: 0; margin: 0; text-align: left;
  background: none; border: 0; color: inherit;
}
.belegpfeil {
  flex: none; color: var(--stumm); font-size: 18px; line-height: 1;
  transition: transform .2s ease;
}
.belegkopf[aria-expanded="true"] .belegpfeil { transform: rotate(90deg); }
@media (prefers-reduced-motion: reduce) {
  .belegpfeil { transition: none; }
}
.formel {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 12px; background: var(--flaeche); border-radius: 10px;
  padding: 9px 10px; margin: 0 0 8px; overflow-x: auto; white-space: pre-wrap;
}
.einwand { border-left: 3px solid var(--fett); padding-left: 10px;
           color: var(--stumm); font-size: 13px; margin: 0 0 8px; }
.quellen { list-style: none; margin: 6px 0 0; padding: 0;
           border-top: 1px solid var(--randfein); padding-top: 8px; }
.quellen li { font-size: 12px; color: var(--stumm); margin-bottom: 7px; line-height: 1.45; }
.quellen a { color: var(--protein); word-break: break-word; }

/* ---------------------------------------------------------------
   Balken: ohne Netz, neue Fassung, Meldungen
   --------------------------------------------------------------- */
#netzbalken, #fassungsbalken {
  position: fixed; left: 0; right: 0; z-index: 50;
  bottom: calc(env(safe-area-inset-bottom, 0px) + 74px);
  width: var(--spalte); margin: 0 auto;
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  padding: 11px 13px; border-radius: var(--rundungklein);
  font-size: 13px;
}
#netzbalken { background: var(--warngrund); border: 1px solid var(--warnrand); color: var(--warntext); }
#fassungsbalken { background: var(--flaeche); border: 1px solid var(--rand); color: var(--text); }
#netzbalken span, #fassungsbalken span { flex: 1 1 150px; min-width: 0; }
#netzbalken button, #fassungsbalken button {
  flex: none; padding: 8px 12px; border: 0; border-radius: 10px;
  background: var(--knopf); color: var(--knopftext); font-weight: 700; font-size: 12.5px;
}

#melder {
  position: fixed; z-index: 55; left: 0; right: 0;
  bottom: calc(env(safe-area-inset-bottom, 0px) + 74px);
  width: fit-content; max-width: calc(100% - 28px); margin: 0 auto;
  padding: 10px 16px; border-radius: 999px;
  background: var(--knopf); color: var(--knopftext);
  font-size: 13px; font-weight: 600; text-align: center;
  animation: einblenden .16s ease;
}
@keyframes einblenden { from { opacity: 0; transform: translateY(6px); } to { opacity: 1; } }

/* DER RUECKWEG IN DER MELDUNG (app-35, 3.1). Er sitzt IN der Meldung
   und verschwindet mit ihr - ein eigenes Bauteil haette eine eigene
   Frist, und dann stuende irgendwann ein "Rueckgaengig" da, dessen
   Meldung schon weg ist. 44 px Mindesthoehe, weil auch dieser Knopf
   mit dem Finger getroffen werden muss. */
.melderknopf {
  margin-left: 12px; min-height: 44px; padding: 0 6px;
  background: none; border: 0; color: inherit;
  font-size: 13px; font-weight: 700; text-decoration: underline;
}
.melderknopf:active { opacity: .6; }

/* ---------------------------------------------------------------
   DAS PORTIONSRAEDCHEN (Auftrag app-35, 3.2)

   Die Stufen sind Knoepfe und kein <select>: ein Auswahlfeld oeffnet
   auf dem Telefon eine Systemliste und kostet zwei Griffe fuer etwas,
   das ein Griff sein soll. Die Gramm stehen darunter und rechnen mit -
   sichtbar, nicht versteckt (Auftrag: "Wer in Gramm denkt, tippt
   weiter Gramm ein").
   --------------------------------------------------------------- */
.portionsrad {
  margin-bottom: 12px; padding: 11px 12px;
  background: var(--flaeche); border: 1px solid var(--randfein);
  border-radius: var(--rundungklein);
}
.radtitel { font-size: 12px; color: var(--stumm); font-weight: 600; margin-bottom: 7px; }
.radreihe { display: flex; flex-wrap: wrap; gap: 5px; }
.radreihe button {
  min-width: 52px; min-height: 44px; padding: 0 10px;
  border: 1px solid var(--rand); border-radius: var(--rundungklein);
  background: var(--grund); color: var(--text);
  font-size: 14px; font-weight: 700;
}
/* FARBE IST NIE DAS EINZIGE MERKMAL (Konzept 51.1): die gewaehlte
   Stufe traegt zusaetzlich aria-pressed und steht im Satz darunter. */
.radreihe button.ist-an { background: var(--knopf); color: var(--knopftext);
                          border-color: var(--knopf); }
.radwert { margin-top: 8px; font-size: 13px; font-weight: 700; }

/* ---------------------------------------------------------------
   DIE SCHNELLEINGABE AM RING (Auftrag app-35, Stufe 7.2)

   Ein echtes <input type="range"> und kein Nachbau aus divs -
   dieselbe Entscheidung wie beim Defizitregler: nur das echte
   Bauteil laesst sich mit der Tastatur bedienen und wird von
   Bildschirmlesern richtig angesagt.

   DIE ZAHL STEHT GROSZ UEBER DEM SCHIEBER, nicht daneben: wer
   schiebt, verdeckt mit dem Finger die Stelle unter dem Griff.
   --------------------------------------------------------------- */
.schnellkasten {
  margin: 10px 0 0; padding: 12px 13px;
  background: var(--flaeche); border: 1px solid var(--randfein);
  border-radius: var(--rundungklein);
}
.schnellwert { font-size: 22px; font-weight: 800; letter-spacing: -.02em; margin-bottom: 6px; }
.schnellkasten input[type="range"] { width: 100%; }
.schnellkasten .knopfreihe { margin-top: 8px; }

/* ---------------------------------------------------------------
   DIE EINKAUFSLISTE (Auftrag 22, 4.3)

   KEIN EIGENES KAESTCHEN-BAUTEIL. Der Haken ist ein <button> mit
   role="checkbox" - ein nachgebautes <input type="checkbox"> haette
   auf dem Telefon eine andere Trefferflaeche als alles andere in
   dieser App, und die Trefferflaeche ist genau das, was R bemaengelt
   hat.

   ABGEHAKTES BLEIBT STEHEN und wird nur leiser (Auftrag 22, 4.3:
   "Abhaken, und Abgehaktes bleibt abgehakt"). Es verschwindet erst,
   wenn jemand ausdruecklich "Abgehaktes entfernen" drueckt -
   ein Haken, der die Zeile wegnimmt, nimmt auch die Moeglichkeit,
   ihn zurueckzunehmen.
   --------------------------------------------------------------- */
.einkaufsliste { margin-top: 14px; }
.postenzeile {
  display: flex; align-items: center; gap: 10px;
  padding: 9px 0; border-bottom: 1px solid var(--rand);
}
.postenzeile:last-of-type { border-bottom: 0; }
.postenzeile .was { flex: 1 1 auto; min-width: 0; }
.postenzeile .name { font-size: 14px; font-weight: 700; }
.postenzeile .zeile { font-size: 12px; color: var(--stumm); margin-top: 2px; }
.postenzeile.abgehakt .name { text-decoration: line-through; color: var(--stumm); }
.haken {
  flex: none; width: 26px; height: 26px; padding: 0;
  border: 2px solid var(--rand); border-radius: 8px;
  background: var(--flaeche);
}
/* DER HAKEN IST EIN ZEICHEN, NICHT NUR EINE FARBE (Konzept 51.1) -
   wer Farben nicht unterscheidet, sieht trotzdem, was erledigt ist. */
.haken.ist-an { border-color: var(--knopf); background: var(--knopf); position: relative; }
.haken.ist-an::after {
  content: ""; position: absolute; left: 7px; top: 3px;
  width: 6px; height: 12px; border: solid var(--knopftext);
  border-width: 0 2.5px 2.5px 0; transform: rotate(45deg);
}
.zusatzreihe { margin: -4px 0 8px; padding-left: 2px; }
.suchreihe input.schmal { flex: 0 0 84px; }

/* ---------------------------------------------------------------
   DER EINWILLIGUNGSBILDSCHIRM (Auftrag 26)

   ER IST ABSICHTLICH SCHLICHT. Kein Kasten, keine Farbe, kein
   Symbol - eine Einwilligung ist kein Angebot, und alles, was sie
   freundlicher aussehen laesst, als sie ist, zieht sie in die
   Richtung, aus der sie herausgehalten werden muss.

   Der Text steht in normaler Textgroesze, nicht in .klein: ein
   Einwilligungstext im Kleingedruckten ist ein Widerspruch in sich.
   --------------------------------------------------------------- */
.einwilligung h2 { margin: 0 0 10px; font-size: 17px; }
.einwilligungsatz { margin: 0; font-size: 14px; line-height: 1.55; }
.einwilligungliste { margin: 0; padding-left: 20px; font-size: 14px; line-height: 1.55; }
.einwilligungliste li { margin-bottom: 7px; }

/* Der Haken. Ein echtes <input type="checkbox"> und kein Nachbau:
   Tastatur, Screenreader und die Anzeige "an/aus" bringt es selbst
   mit, und bei einer Einwilligung ist genau das die Anforderung.
   Ausdruecklich ohne `checked` im HTML - ein vorangekreuzter Haken
   ist keine Einwilligung, sondern eine Voreinstellung, der jemand
   nicht widersprochen hat. */
.hakenzeile {
  display: flex; gap: 11px; align-items: flex-start;
  margin: 16px 0 4px; padding: 13px;
  border: 1px solid var(--rand); border-radius: var(--rundungklein);
  background: var(--flaeche); cursor: pointer;
}
.hakenzeile input[type="checkbox"] {
  flex: none; width: 22px; height: 22px; margin: 1px 0 0;
  accent-color: var(--knopf);
}
.hakentext { font-size: 13.5px; line-height: 1.5; }
.hakenzeile input[type="checkbox"]:disabled { opacity: .45; }

/* ---------------------------------------------------------------
   DER RESTBALKEN (Auftrag 23)

   ER ZEIGT DEN TAG, NICHT DAS LEBENSMITTEL - und das steckt in der
   Bauform: die Bahn IST der Tagesrest, die Fuellung ist das, was
   dieser Eintrag davon nehmen wuerde. Ein Punkt am Produkt waere ein
   Urteil ueber das Produkt; ein Balken am Rest kann keines sein.

   FARBE IST NIE DAS EINZIGE MERKMAL (Auftrag 23, 7). Jede Stufe
   traegt ein Zeichen, das sich in Schwarzweisz unterscheidet:

     passt    Haken
     knapp    halb gefuellter Kreis
     reiszt   Ausrufezeichen im Kreis

   Die Farben kommen aus Richtung A und sind die, die es schon gibt -
   `--gut`, `--warntext`, `--fehler`. Keine Ampel-Palette von auszen:
   die drei sind gemessen (pruefen.php, "Kontrast nach WCAG AA"), eine
   neue waere es nicht.
   --------------------------------------------------------------- */
.restbalken { flex: 1 1 auto; min-width: 0; }
.balkenkopf { margin: -2px 0 10px; padding-left: 2px; gap: 9px; }

/* Die Bahn IST der Tagesrest. Sie ist immer gleich lang - was sich
   aendert, ist die Fuellung. Eine Bahn, die mitwaechst, waere ein
   zweites Mass im selben Bild. */
.balkenbahn {
  height: 6px; border-radius: 3px;
  background: var(--flaeche); border: 1px solid var(--rand);
  overflow: hidden;
}
.balkenfuell { height: 100%; border-radius: 3px 0 0 3px; transition: width .12s linear; }
.stufe-passt  .balkenfuell { background: var(--gut); }
.stufe-knapp  .balkenfuell { background: var(--warntext); }
.stufe-reiszt .balkenfuell { background: var(--fehler); border-radius: 3px; }

.balkenzeile {
  display: flex; align-items: center; gap: 6px; flex-wrap: wrap;
  margin-top: 4px; font-size: 11.5px;
}
.balkenwort  { font-weight: 600; }
.stufe-passt  .balkenwort { color: var(--gut); }
.stufe-knapp  .balkenwort { color: var(--warntext); }
.stufe-reiszt .balkenwort { color: var(--fehler); }
.balkenbezug { color: var(--stumm); }

/* Die drei Zeichen - gezeichnet, nicht gefaerbt. Wer keine Farben
   unterscheidet, sieht trotzdem drei verschiedene Formen. */
.balkenzeichen {
  flex: none; width: 13px; height: 13px; border-radius: 50%;
  position: relative; border: 1.5px solid currentColor;
}
.stufe-passt  .balkenzeichen { color: var(--gut); }
.stufe-knapp  .balkenzeichen { color: var(--warntext); }
.stufe-reiszt .balkenzeichen { color: var(--fehler); }

/* Haken */
.zeichen-haken::after {
  content: ""; position: absolute; left: 3.5px; top: 1px;
  width: 3px; height: 6px; border: solid currentColor;
  border-width: 0 1.5px 1.5px 0; transform: rotate(45deg);
}
/* halb gefuellt */
.zeichen-halb::after {
  content: ""; position: absolute; left: 0; top: 0; bottom: 0; width: 50%;
  background: currentColor; border-radius: 6px 0 0 6px;
}
/* Ausrufezeichen */
.zeichen-voll::after {
  content: ""; position: absolute; left: 4.5px; top: 1.5px;
  width: 1.5px; height: 4.5px; background: currentColor;
}
.zeichen-voll::before {
  content: ""; position: absolute; left: 4.5px; bottom: 1.5px;
  width: 1.5px; height: 1.5px; background: currentColor;
}

[hidden] { display: none !important; }

/* ---- Sagen: ein ganzer Tag in einem Feld (Auftrag 27) ---------
   DIE ZEILE IST EINE .postenzeile, keine eigene Bauart. Sie sieht
   aus wie die Einkaufsliste, weil sie dasselbe ist: eine Liste, die
   man durchgeht, bevor man sie bestaetigt. Nur zwei Dinge kommen
   dazu - die kcal rechts und die Kennzeichnung "unklar". */
.freitextfeld {
  width: 100%; box-sizing: border-box; resize: vertical;
  min-height: 92px; padding: 10px 12px; margin: 10px 0 4px;
  font: inherit; font-size: 15px; line-height: 1.45;
  color: var(--text); background: var(--flaeche);
  border: 1px solid var(--rand); border-radius: 10px;
}
.freitextfeld:focus { outline: 2px solid var(--knopf); outline-offset: 1px; }
.postenkcal {
  flex: none; font-size: 13px; font-weight: 700;
  font-variant-numeric: tabular-nums; color: var(--text);
}
/* UNKLAR IST EIN ZEICHEN UND EINE LINIE, NICHT NUR EINE FARBE
   (Konzept 51.1): die Kennzeichnung "unklar" steht als Wort daneben,
   der Streifen links ist nur die zweite Spur. */
.postenzeile.ungeklaert { border-left: 3px solid var(--warnrand); padding-left: 8px; }
.postenzeile.ungeklaert .postenkcal { color: var(--stumm); }
.sagenaendern {
  padding: 4px 0 12px; border-bottom: 1px solid var(--rand);
}
.sagenaendern .feld { margin-bottom: 8px; }

/* Der wandernde Grundumsatz (Auftrag 22, 3.3).
   SOLANGE ER WANDERT, IST ES EINE ANKUENDIGUNG - danach nur noch eine
   Auskunft. Der Unterschied ist ein Streifen, keine Farbe allein: der
   Satz sagt es ohnehin (Konzept 51.1). */
.klein.wandert {
  border-left: 3px solid var(--rand);
  padding-left: 8px; margin-top: 6px;
}
