/* Dev-Konsole - die Schale.
   Gehoert zu public/devkonsole-schale.js. Alle Klassen tragen das Praefix dks-.

   WAS DAS IST: Ein Werkzeug fuer die beiden Menschen, die dieses Programm
   bauen - ein Overlay IN der laufenden Anwendung, nur fuer Administratoren.
   Es ist NICHT Teil des Dienstes. Genau daraus folgt jede Entscheidung hier:
   Im Ernstfall bedient jemand mit dieser Anwendung einen Notruf. Ein
   Entwicklerwerkzeug, das dabei im Weg liegt, ist ein Sicherheitsproblem und
   keine Unbequemlichkeit.

   ------------------------------------------------------------------------
   DIE FORM: EINE WERKBANK, KEINE REITER.

     +--------------------------------+--------------+
     |  Dev-KI   Name    [Verlauf][Changelog]   [x]  |
     +--------------------------------+--------------+
     |                                | Wuensche     |
     |   DAS GESPRAECH                | [x] ...      |
     |   (Hauptflaeche)               | [ ] ...      |
     |                                +--------------+
     |                                | 2 gewaehlt   |
     |                                | [Paket]      |
     |                                | Ausgegeben   |
     |                                +--------------+
     |   [Eingabe]                    | Ideen        |
     +--------------------------------+--------------+

   Die Leiste steht NEBEN dem Gespraech und nicht dahinter. Das ist der ganze
   Zweck des Umbaus: Ein Wunsch entsteht aus dem Gespraech, und man muss
   sehen, dass er entsteht. Die Kaestchen in der Leiste SIND die Paketauswahl,
   der Knopf steht direkt darunter, die ausgegebenen Pakete darunter.

   Verlauf und Changelog TAUSCHEN die Hauptflaeche und legen sich nicht
   darueber. Eine Lade, die ueber dem Inhalt liegt, verdeckt ihn - genau die
   Beschwerde, die zu diesem Umbau gefuehrt hat. Beim Tausch bleibt die Leiste
   stehen; man verliert die Wuensche nicht aus den Augen, waehrend man
   nachschlaegt.

   ------------------------------------------------------------------------
   DER PLATZ AM RECHTEN RAND IST SCHON VERGEBEN. Das kommt nicht aus einer
   Annahme, sondern aus notfall.css:

     @media screen and (min-width: 861px) {
       .nf-leiste { right: 18px; top: 50%; transform: translateY(-50%); ... }
       .hat-notfallleiste main { padding-right: 104px; }
     }

   Am Rechner steht die Notfallgruppe (Notruf, Hilfe und die zwei anderen
   Knoepfe) senkrecht am rechten Rand, mittig, 68px breit - und der Inhalt
   bekommt dafuer 104px Polster. Es gibt am rechten Rand also bereits eine
   freigehaltene Gasse UND ein Element, das man niemals verdecken darf.

   Daraus folgt beides auf einmal:
     - Der zugeklappte Griff lebt IN dieser Gasse (rechts, buendig, 28px
       breit). Er kostet damit keinen einzigen Pixel Inhalt.
     - Das aufgeklappte Panel beginnt LINKS der Gasse (right: var(--dks-rand),
       also 104px) und laesst die Notfallgruppe frei stehen.

   ------------------------------------------------------------------------
   VERDECKEN GILT NICHT, AUCH NICHT EIN BISSCHEN. Ein Panel, das ueber der
   Anwendung liegt, verdeckt sie zwangslaeufig - es sei denn, man reserviert
   den Platz, den man einnimmt. Genau das machen die Regeln unter "Der Inhalt
   macht Platz": Solange die Konsole offen ist, bekommt <main> Polster in
   ihrer Breite. Dieselbe Loesung wie in notfall.css - das Haus kennt sie
   schon.

   Am Handy geht das nicht nach rechts: 375px Breite haben keine Spalte
   uebrig. Dort faehrt die Konsole von OBEN herein, und <main> bekommt
   Polster oben. Der untere Rand bleibt vollstaendig frei - dort liegen die
   Fussleiste (styles.css, .sidebar unter 860px), die Notfallgruppe und die
   Meldungen. Das ist die Zone, in der im Ernstfall gedrueckt wird.

   ------------------------------------------------------------------------
   WANN NEBENEINANDER, WANN UNTEREINANDER: entschieden an der PANELBREITE
   (@container, 560px), nicht an der Fensterbreite. Wer die Konsole am
   grossen Schirm auf 400px zusammenschiebt, hat denselben Platz wie am Handy
   und bekommt darum dieselbe Form. Untereinander heisst: Gespraech oben,
   Leiste unten, beide mit eigenem Rollbereich und beide gleichzeitig
   sichtbar - kein Reiter, keine Schublade, nichts Schwebendes. Der Teiler
   dazwischen ist derselbe wie in der Breite, nur quer.

   Die Zahl 560 steht auch in devkonsole-schale.js (FORM_UMBRUCH). Wer eine
   aendert, aendert beide.

   ------------------------------------------------------------------------
   EBENEN (z-index). Bewusst NIEDRIG, naemlich 45:
     .overlay (Dialoge)      50   - ein Dialog deckt die Konsole zu, richtig so
     .nf-leiste (Notfall)    88   - liegt immer oben
     .hilfe-fenster          95
     .nf-grund (Notrufdialog) 300
   Die Konsole liegt ueber dem Inhalt und ueber der Seitenleiste (30), aber
   unter allem, was jemand im Dienst braucht. Ein Entwicklerwerkzeug gewinnt
   keinen einzigen Streit gegen den Betrieb.

   ------------------------------------------------------------------------
   KONTRAST, mit der WCAG-Formel nachgerechnet (Zahlen hell/dunkel), und zwar
   fuer die Paare, die diese Datei WIRKLICH setzt:
     text-primary   auf surface-2       16,78:1 / 14,65:1   (Titel, Blattkopf)
     text-primary   auf surface-1       16,40:1 / 16,06:1
     text-secondary auf surface-2        7,95:1 /  8,90:1   (Nachschlag-Knoepfe)
     text-secondary auf surface-1        7,77:1 /  9,76:1   (Griffwort)
     text-muted     auf surface-2        5,65:1 /  4,71:1   (Name)
     text-muted     auf surface-1        5,52:1 /  5,16:1   (Notiz)
     accent-fg      auf accent-soft      6,16:1 /  8,82:1   (gedrueckter Knopf)
     accent-fg      auf surface-2        6,67:1 /  8,80:1   (Zeichen im Griff)
     text-muted     auf surface-0        5,16:1 /  5,55:1   (Rand des Griffs)
   Alle Textpaare liegen ueber 4,5:1; der niedrigste ist 4,71:1.

   Und die Werte, die NICHT bestehen, samt Begruendung:
     --border      als Trennlinie       1,3:1 – 1,4:1
     --border-strong gegen surface-1    1,95:1 /  1,78:1
   Das sind Kanten von Flaechen, keine Bedienelemente und kein Text. WCAG
   1.4.11 verlangt 3:1 nur dort, wo eine Linie das EINZIGE Merkmal eines
   Bedienelements ist. Der Teiler ist ein solches Element - er bekommt darum
   bei Beruehrung und bei Tastaturfokus eine Flaeche in --accent-soft und
   einen Umriss in --accent-fg (6,16:1 gegen die Flaeche), und er ist
   ausserdem ueber die Tabulatortaste erreichbar. Der GRIFF ist der zweite
   Fall: Er IST seine Umrisslinie, und darum traegt er --text-muted statt
   --border-strong (5,16:1 hell / 5,55:1 dunkel gegen den Seitengrund). */

/* ------------------------------------------------------------- Grundmasse */

/* Die Werte stehen auf <html> und NICHT auf dev-konsole - das ist keine
   Geschmacksfrage. Die Regeln unter "Der Inhalt macht Platz" weiter unten
   rechnen mit --dks-rand und --dks-breite an <main>, und <main> ist kein Kind
   der Konsole. Eine Variable auf dev-konsole waere dort schlicht nicht
   sichtbar, das Polster fiele aus, und das Panel laege wieder auf dem Inhalt -
   also genau der Fehler, den diese Datei verhindern soll.

   Am Attribut data-dks="1" und nicht an :root, damit die Namen nur existieren,
   solange die Konsole wirklich haengt. devkonsole-schale.js setzt das Attribut
   beim Aufhaengen und nimmt es beim Abbauen wieder weg; die Zahlen hier sind
   der Rueckfall, bis das Skript gemessen hat. */
html[data-dks="1"] {
  --dks-rand: 16px;
  --dks-zu-rand: 44px;
  --dks-breite: 620px;
  --dks-hoehe: 55dvh;
  --dks-leiste: 260px;
  --dks-leiste-hoehe: 170px;
  --dks-griff-oben: 50%;
  --dks-griff-breite: 28px;
  --dks-ebene: 45;
  --dks-ecke: 14px;
}

dev-konsole {
  /* Das Element selbst ist kein Kasten - es traegt nur seine zwei Kinder,
     die beide fuer sich fest positioniert sind. Ohne display:contents haette
     es als Block eine eigene Zeile im Fluss und wuerde ganz unten am
     Dokument Platz kosten. */
  display: contents;
}

/* Auf Papier hat ein Entwicklerwerkzeug nichts verloren. */
@media print {
  dev-konsole { display: none; }
}

/* ---------------------------------------------------------------- Der Griff

   Zugeklappt ist die Konsole ein schmaler Reiter am rechten Rand - kein
   Balken, kein runder Knopf, der irgendwo daraufliegt. Er ist buendig
   angelegt (right: 0) und nach links gerundet, damit er wie eine Lasche am
   Fensterrand aussieht und nicht wie ein weiterer schwebender Knopf.

   28px breit: Das ist bewusst schmaler als eine Trefflaeche fuer Handschuhe
   (44px). Es ist kein Bedienelement des Dienstes - es ist der Griff eines
   Werkzeugs, das nur zwei Menschen benutzen, und Zurueckhaltung wiegt hier
   schwerer als Treffsicherheit. Die HOEHE gleicht es aus: 96px. */

.dks-griff {
  position: fixed;
  right: 0;
  top: var(--dks-griff-oben);
  transform: translateY(-50%);
  z-index: var(--dks-ebene);
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 7px;
  width: var(--dks-griff-breite);
  height: 96px;
  padding: 0;
  border: 1px solid var(--text-muted);
  border-right: 0;
  border-radius: var(--dks-ecke) 0 0 var(--dks-ecke);
  background: var(--surface-2);
  color: var(--text-secondary);
  cursor: pointer;
  box-shadow: var(--shadow);
  /* Waehrend des Ziehens darf der Browser nicht scrollen wollen. */
  touch-action: none;
  transition:
    background var(--dur-schnell) var(--easing),
    border-color var(--dur-schnell) var(--easing);
}

.dks-griff:hover { background: var(--surface-sunken); }
.dks-griff:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: 2px; }

/* Waehrend gezogen wird, verschwindet der Zeiger nicht aus dem Griff. */
.dks-griff[data-zieht="1"] { cursor: grabbing; }

/* Das Zeichen im Griff: zwei spitze Klammern, wie sie jeder Entwickler kennt.
   Es traegt den Akzent - damit ist das Bedienelement auch dann noch als
   solches erkennbar, wenn jemand die Umrisslinie uebersieht. */
.dks-griff-zeichen {
  font-size: var(--fs-sm);
  font-weight: 700;
  letter-spacing: -.04em;
  color: var(--accent-fg);
  line-height: 1;
}

/* Die senkrechte Beschriftung. Sie sagt, was der Reiter ist - ein Griff ohne
   Wort wird zum Raetsel, und Raetsel loest niemand im Dienst. */
.dks-griff-wort {
  writing-mode: vertical-rl;
  text-orientation: mixed;
  font-size: var(--fs-xs);
  font-weight: 600;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--text-secondary);
  user-select: none;
}

/* ---------------------------------------------------------------- Das Panel */

.dks-panel {
  position: fixed;
  z-index: var(--dks-ebene);
  display: flex;
  flex-direction: column;
  min-height: 0;
  background: var(--surface-1);
  border: 1px solid var(--border-strong);
  box-shadow: var(--shadow);
  /* Am Rechner: eine Spalte links der Notfall-Gasse, volle Hoehe minus Luft. */
  top: 12px;
  bottom: 12px;
  right: var(--dks-rand);
  width: var(--dks-breite);
  border-radius: var(--dks-ecke);
  overflow: hidden;
  /* Der Bezugsrahmen fuer die Formfrage weiter unten. inline-size und nicht
     size: Die Hoehe des Panels haengt an top/bottom, und eine Groessen-
     Einschliessung in beide Richtungen wuerde sie auf null rechnen. */
  container-type: inline-size;
  container-name: dkspanel;
}

/* Zugeklappt ist das Panel wirklich weg und nicht nur unsichtbar: [hidden]
   nimmt es aus dem Fluss UND aus der Tabulatorreihenfolge. Ein Panel, durch
   das man mit der Tabulatortaste laeuft, ohne es zu sehen, ist eine Falle. */
.dks-panel[hidden] { display: none; }

/* ---- Kopfzeile ---- */

.dks-kopf {
  display: flex;
  align-items: center;
  gap: var(--luft-eng);
  flex: none;
  padding: 8px 8px 8px 14px;
  background: var(--surface-2);
  border-bottom: 1px solid var(--border);
}

/* flex: none und nowrap sind hier kein Feinschliff, sondern die Lehre aus
   einer Messung: Bei 320px Panelbreite schrumpfte die Kopfzeile ihre eigenen
   Kinder, bis "Dev-KI" auf 30px Breite in zwei Zeilen umbrach und der Name
   auf 16px stand. Die Kopfzeile war dadurch 113px hoch - ein Viertel des
   Panels fuer drei Woerter, und dem Gespraech blieben 99px. */
.dks-titel {
  flex: none;
  white-space: nowrap;
  font-size: var(--fs-md);
  font-weight: 600;
  color: var(--text-primary);
  letter-spacing: -.01em;
}

/* Wessen Wunschbuch gerade offen ist. Die Buecher sind je Person getrennt -
   wer das nicht sieht, laedt irgendwann das Paket des anderen herunter. */
.dks-wer {
  flex: 0 1 auto;
  min-width: 0;
  font-size: var(--fs-xs);
  color: var(--text-muted);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 14ch;
}

.dks-schub { flex: 1 1 0; min-width: 0; }

/* Ganz schmal faellt "Dev-KI" weg und der NAME bleibt. Herum entschieden:
   Der Titel ist Zierde - der Griff sagt bereits "Konsole", und das Panel
   traegt sein aria-label. Wessen Wunschbuch offen ist, sagt sonst nichts. */
@container dkspanel (max-width: 400px) {
  .dks-titel { display: none; }
}

/* ---- Die zwei Nachschlagewerke ----

   SCHALTER, KEINE REITER - und das ist an der Form ablesbar: Sie stehen
   rechts oben in der Kopfzeile bei den Werkzeugen und nicht in einer Reihe
   unter dem Kopf, wo eine Reiterleiste stuende. Ein gedrueckter Knopf bleibt
   gedrueckt, solange sein Blatt offen ist; noch einmal druecken fuehrt
   zurueck. Damit ist der Weg zurueck derselbe wie der Weg hin. */

.dks-nach {
  display: flex;
  flex: none;
  gap: 2px;
}

.dks-nach-knopf {
  appearance: none;
  border: 1px solid transparent;
  border-radius: 8px;
  background: transparent;
  padding: 5px 9px;
  color: var(--text-secondary);
  font-size: var(--fs-xs);
  font-weight: 600;
  white-space: nowrap;
  cursor: pointer;
}
.dks-nach-knopf:hover { background: var(--surface-sunken); color: var(--text-primary); }
.dks-nach-knopf:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: 1px; }
.dks-nach-knopf[aria-pressed="true"] {
  background: var(--accent-soft);
  border-color: var(--accent-fg);
  color: var(--accent-fg);
}

.dks-zu {
  display: grid;
  place-items: center;
  flex: none;
  width: 30px;
  height: 30px;
  padding: 0;
  border: 1px solid transparent;
  border-radius: 8px;
  background: transparent;
  color: var(--text-secondary);
  font-size: var(--fs-lg);
  line-height: 1;
  cursor: pointer;
}
.dks-zu:hover { background: var(--surface-sunken); color: var(--text-primary); }
.dks-zu:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: 2px; }

/* ---- Die Buehne: Hauptflaeche, Teiler, Leiste ----

   Grundform ist UNTEREINANDER. Das ist Absicht: Die enge Form ist die
   schwierigere, also ist sie der Ausgangspunkt und die breite die Zugabe.
   Wer es andersherum baut, liefert am Handy den Rest der Regeln aus. */

.dks-buehne {
  flex: 1;
  min-height: 0;
  display: flex;
  flex-direction: column;
}

.dks-haupt {
  flex: 1 1 auto;
  min-height: 0;
  min-width: 0;
  display: flex;
  overflow: hidden;
}
.dks-haupt:focus { outline: none; }

.dks-blatt {
  flex: 1;
  min-height: 0;
  min-width: 0;
  display: flex;
  flex-direction: column;
}
.dks-blatt[hidden] { display: none; }
.dks-blatt:focus { outline: none; }

/* Der Blattkopf sagt, WO man ist.

   Er ist die Antwort auf einen gemeldeten Fehler: Die Verlaufs-Fuellung nennt
   sich selbst "Werkstattgespraech", und die einzigen sichtbaren Stellen mit
   dem Wort "Verlauf" standen im Changelog ("Im Verlauf suchen"). Wer den
   Verlauf suchte, fand ihn dort, wo er nicht war. Die Schale beschriftet die
   Flaeche darum selbst - ein Wort, unabhaengig davon, wie sich eine Fuellung
   nennt. */
.dks-blattkopf {
  display: flex;
  align-items: center;
  gap: var(--luft-eng);
  flex: none;
  padding: 8px 10px 8px 14px;
  border-bottom: 1px solid var(--border);
}
.dks-blattkopf h2 {
  flex: 1;
  min-width: 0;
  margin: 0;
  font-size: var(--fs-md);
  font-weight: 600;
  color: var(--text-primary);
}
.dks-zurueck {
  appearance: none;
  flex: none;
  border: 1px solid var(--border-strong);
  border-radius: 8px;
  background: var(--surface-2);
  padding: 4px 10px;
  color: var(--text-secondary);
  font-size: var(--fs-xs);
  font-weight: 600;
  cursor: pointer;
}
.dks-zurueck:hover { background: var(--surface-sunken); color: var(--text-primary); }
.dks-zurueck:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: 1px; }

/* Die Andockstellen. Jede rollt fuer sich - das ist die Bedingung dafuer,
   dass die Leiste stehen bleibt, waehrend man im Gespraech nach unten geht. */
.dks-andock {
  flex: 1;
  min-height: 0;
  min-width: 0;
  overflow: auto;
  overscroll-behavior: contain;
  padding: var(--luft-block);
}

/* Eine kurze Notiz, wenn ein Platz leer geblieben ist. Kein Aufsatz und kein
   Ladezustand - ein Befund und ein zweiter Versuch. */
.dks-notiz {
  display: flex;
  align-items: center;
  gap: var(--luft-eng);
  flex-wrap: wrap;
  padding: var(--luft-block);
  border: 1px dashed var(--border-strong);
  border-radius: var(--radius);
  background: var(--surface-sunken);
  color: var(--text-muted);
  font-size: var(--fs-sm);
}
.dks-notiz button {
  appearance: none;
  border: 1px solid var(--border-strong);
  border-radius: 8px;
  background: var(--surface-2);
  padding: 4px 10px;
  color: var(--text-secondary);
  font-size: var(--fs-xs);
  font-weight: 600;
  cursor: pointer;
}
.dks-notiz button:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: 1px; }

/* ---- Die Leiste ---- */

.dks-leiste {
  flex: none;
  height: var(--dks-leiste-hoehe);
  /* In der gestapelten Form darf die Leiste die Hauptflaeche nie erdruecken -
     auch dann nicht, wenn ein gemerkter Wert aus einem hoeheren Fenster
     stammt. 60 Prozent der Buehne sind die Grenze, 90px der Boden. */
  min-height: 90px;
  max-height: 60%;
  overflow: auto;
  overscroll-behavior: contain;
  background: var(--surface-2);
}
.dks-leiste-teil + .dks-leiste-teil { border-top: 1px solid var(--border); }
.dks-leiste .dks-andock { padding: 12px 14px; }

/* ---- Der Teiler zwischen Hauptflaeche und Leiste ----

   Er ist beides: die sichtbare Kante und die Greifzone. Die Kante ist eine
   1px-Linie in der Mitte einer 9px breiten Flaeche - so sieht man die Grenze,
   ohne dass ein Balken im Bild steht, und trifft sie trotzdem mit dem Finger. */
.dks-teiler {
  appearance: none;
  flex: none;
  padding: 0;
  border: 0;
  height: 9px;
  background: linear-gradient(var(--border), var(--border)) center / 100% 1px no-repeat;
  cursor: ns-resize;
  touch-action: none;
}
.dks-teiler:hover,
.dks-teiler:focus-visible { background: var(--accent-soft); }
.dks-teiler:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: -2px; }

/* ---- Der Griff zum Groesseaendern des ganzen Panels ----

   Links am Panel (am Handy: unten). Eine 8px schmale Zone; sichtbar wird sie
   erst bei Beruehrung, damit sie im Ruhezustand keine zweite Kante zeichnet. */
.dks-groesse {
  position: absolute;
  z-index: 1;
  left: 0;
  top: 0;
  bottom: 0;
  width: 8px;
  padding: 0;
  border: 0;
  background: transparent;
  cursor: ew-resize;
  touch-action: none;
}
.dks-groesse:hover,
.dks-groesse:focus-visible { background: var(--accent-soft); }
.dks-groesse:focus-visible { outline: 2px solid var(--accent-fg); outline-offset: -2px; }

/* ------------------------------------------------- Nebeneinander ab 620px

   @container und nicht @media: Entschieden wird an der Breite des PANELS.
   Wer die Konsole am 27-Zoll-Schirm auf 400px zusammenschiebt, hat denselben
   Platz wie am Handy - und bekommt darum dieselbe Form. Eine Abfrage auf die
   Fensterbreite haette ihm zwei Spalten zu je 190px gegeben. */

@container dkspanel (min-width: 560px) {
  .dks-buehne { flex-direction: row; }
  .dks-leiste {
    width: var(--dks-leiste);
    height: auto;
    min-height: 0;
    max-height: none;
  }
  .dks-teiler {
    width: 9px;
    height: auto;
    background: linear-gradient(var(--border), var(--border)) center / 1px 100% no-repeat;
    cursor: ew-resize;
  }
  .dks-teiler:hover,
  .dks-teiler:focus-visible { background: var(--accent-soft); }
}

/* ------------------------------------------- Der Inhalt macht Platz (Rechner)

   Hier steht der eigentliche Anspruch dieser Datei: Die Konsole nimmt sich
   keinen Platz, den sie nicht bezahlt.

   Die Spezifitaet ist Absicht. styles.css setzt "main { padding: ... }"
   (0,0,1) und notfall.css setzt ".hat-notfallleiste main" (0,1,1). Diese
   Regeln hier haben zwei Attribute und eine Klasse - sie gewinnen gegen
   beide, und zwar unabhaengig von der Ladereihenfolge. */

@media screen and (min-width: 861px) {
  /* Offen: Polster fuer die Gasse UND fuer das Panel. */
  html[data-dks="1"][data-dks-offen="1"] .app > main {
    padding-right: calc(var(--dks-rand) + var(--dks-breite) + 12px);
  }
  /* Zugeklappt: nur so viel, wie der Griff wirklich braucht. Steht die
     Notfallgruppe da, sind das null zusaetzliche Pixel - der Griff sitzt in
     ihrer Gasse. devkonsole-schale.js rechnet das aus. */
  html[data-dks="1"][data-dks-offen="0"] .app > main {
    padding-right: var(--dks-zu-rand);
  }
}

/* --------------------------------------------------- Handy und schmale Fenster

   Nach rechts ist kein Platz. Also von oben - und der untere Rand bleibt
   unangetastet: Fussleiste, Notfallgruppe und Meldungen liegen dort, und das
   ist die Zone, in der im Ernstfall gedrueckt wird.

   Der Griff wandert dabei nicht mit nach oben: Er bleibt am rechten Rand, wo
   er senkrecht verschiebbar ist - nur seine Gasse ist hier 28px statt 104px
   breit, weil es am Handy keine Notfall-Gasse gibt. */

@media screen and (max-width: 860px) {
  .dks-panel {
    top: 0;
    bottom: auto;
    left: 0;
    right: 0;
    width: auto;
    height: var(--dks-hoehe);
    max-height: 78dvh;
    border-top: 0;
    border-left: 0;
    border-right: 0;
    border-radius: 0 0 var(--dks-ecke) var(--dks-ecke);
  }
  .dks-groesse {
    left: 0;
    right: 0;
    top: auto;
    bottom: 0;
    width: auto;
    height: 10px;
    cursor: ns-resize;
  }
  html[data-dks="1"][data-dks-offen="1"] .app > main {
    padding-top: calc(var(--dks-hoehe) + 12px);
  }
  html[data-dks="1"] .app > main {
    padding-right: var(--dks-zu-rand);
  }
}

/* ------------------------------------------------------- Ruhe vor Bewegung */

@media (prefers-reduced-motion: reduce) {
  .dks-griff { transition: none; }
}

/* ==========================================================================
   NOTBEHELF: public/devkonsole.css GIBT ES NICHT.

   Der Kopf dieser Datei behauptete, die Gespraechs-Front habe "ein
   Stylesheet mit den Klassen dk-gespraech, dk-verlauf, dk-warnung, dk-leer
   und einem Dutzend weiterer bestellt". Bestellt schon - geliefert nie. Im
   ganzen Verzeichnis public/ gibt es keine einzige Regel fuer .dk-gespraech,
   .dk-verlauf, .dk-eingabe, .dk-buch, .dk-paket, .dk-wunschliste oder
   .dk-paketliste. Nur devauswahl.css deckt eine Handvoll dk-Klassen ab.

   Ohne Stylesheet ist .dk-gespraech ein gewoehnlicher Block: Der Faden rollt
   nicht, das Eingabefeld steht irgendwo und wandert beim Tippen aus dem Bild.
   Eine Werkbank, deren Hauptflaeche nicht funktioniert, ist keine Werkbank -
   also steht hier das Noetigste, und zwar AUSSCHLIESSLICH Anordnung: keine
   Farbe, keine Schriftgroesse, keine Abstaende ueber das Notwendige hinaus.
   Wer devkonsole.css nachliefert, kann diesen Block ersatzlos loeschen; er
   nimmt nichts vorweg ausser der Frage, wo etwas liegt.

   Alles unter .dks-haupt bzw. .dks-leiste eingeschlossen, damit keine dieser
   Regeln jemals ausserhalb der Konsole etwas trifft. */

/* Das Gespraech: Faden rollt, Eingabe steht unten fest. */
.dks-haupt .dks-andock[data-fach="gespraech"] { display: flex; overflow: hidden; }
.dks-haupt .dk-gespraech {
  flex: 1;
  min-height: 0;
  display: flex;
  flex-direction: column;
  gap: var(--luft-eng);
}
.dks-haupt .dk-verlauf {
  flex: 1;
  min-height: 0;
  overflow: auto;
  overscroll-behavior: contain;
  display: flex;
  flex-direction: column;
  gap: var(--luft-eng);
}
.dks-haupt .dk-eingabe {
  flex: none;
  display: flex;
  align-items: flex-end;
  gap: var(--luft-eng);
}
.dks-haupt .dk-eingabe-feld { flex: 1; min-width: 0; resize: vertical; }
.dks-haupt .dk-senden { flex: none; }

/* Die Leiste: Listen ohne Punkte und ohne Einzug - in 280px ist der
   Standard-Einzug von 40px ein Siebtel der Spalte. */
.dks-leiste .dk-wunschliste,
.dks-leiste .dk-paketliste { list-style: none; margin: 0; padding: 0; }
.dks-leiste .dk-buch-spalten { display: flex; flex-direction: column; gap: var(--luft-block); }
.dks-leiste .dk-buch,
.dks-leiste .dk-paket { display: flex; flex-direction: column; gap: var(--luft-eng); }
.dks-leiste .dk-buch h3,
.dks-leiste .dk-paket h3,
.dks-leiste .dk-auswahl h4 { margin: 0; font-size: var(--fs-md); }
.dks-leiste .dk-auswahl-knoepfe { display: flex; flex-wrap: wrap; gap: 4px; }
.dks-leiste .dk-paket-knopf { width: 100%; }
