﻿/* ============================================================
   TopNavLayout – Kopfzeile mit Navigation oben, Inhalt darunter über die volle Breite; schmal mit eingeklappter Navigation.

   CSS-Variablen:
     --oo-tnl-header-height    Mindesthöhe der Kopfzeile, eingeklappt genau ihre Höhe, Standard 3rem
     --oo-tnl-backdrop         Farbe des Schleiers hinter der geöffneten Navigation, Standard rgb(0 0 0 / 0.2)
   Für den Inhalt, gesetzt am Inhaltsbereich:
     --oo-tnl-header-offset    Höhe der oben klebenden Kopfzeile, wenn die Seite scrollt, sonst 0
     --oo-tnl-content-height   sichtbare Höhe des Inhalts (für height/min-height einer Seite, die den Bildschirm füllt)
   ============================================================ */

/* Es scrollt nur der Inhalt, nie die Seite (außer am Handy, siehe unten). Sonst bekäme das Dokument einen zweiten
   Scrollbalken, sobald etwas ans Ende des body gehängt wird (etwa der Tooltip-Container von Mermaid). */
html:has(.oo-tnl) body {
    overflow: hidden;
}

/* Kopfzeile und Inhalt untereinander; der Inhalt nimmt, was die Kopfzeile übrig lässt. Keine feste Höhe der Kopfzeile:
   Bricht die Navigation um, wird sie höher und der Inhalt entsprechend niedriger.
   Container-Abfrage statt Media-Abfrage: Entscheidend ist die Breite des Layouts, nicht die des Fensters. */
.oo-tnl {
    --oo-tnl-header-height: 3rem;
    --oo-tnl-backdrop: rgb(0 0 0 / 0.2);
    position: relative;
    display: flex;
    flex-direction: column;
    height: 100dvh;
    background: var(--oo-color-surface);
    color: var(--oo-color-text);
    container-type: inline-size;
}

/* Über dem Inhalt und dem Schleier, damit Flyouts und die geöffnete Navigation darüber liegen. */
.oo-tnl__header {
    position: relative;
    z-index: 2;
    flex-shrink: 0;
    box-sizing: border-box;
    background: var(--oo-color-background);
    border-bottom: var(--oo-border-width) solid var(--oo-color-border);
}

.oo-tnl__bar {
    box-sizing: border-box;
    min-height: var(--oo-tnl-header-height);
    padding: var(--oo-space-1) var(--oo-space-3);
}

.oo-tnl__brand {
    flex-shrink: 0;
    white-space: nowrap;
}

/* Nimmt die Mitte ein; min-width 0, damit umbrechende Navigation (etwa ein FlyoutMenu) schmaler werden darf als ihr Inhalt. */
.oo-tnl__nav {
    flex: 1 1 auto;
    min-width: 0;
}

/* Der Menüknopf setzt den Fokus auf die Navigation selbst (tabindex -1); sie ist ein Bereich, kein Bedienelement. */
.oo-tnl__nav:focus {
    outline: none;
}

.oo-tnl__actions {
    flex-shrink: 0;
}

/* Zwei Klassen, damit die Regel die Anzeige des Buttons sicher überschreibt. */
.oo-tnl .oo-tnl__menu-button {
    display: none;
}

.oo-tnl__backdrop {
    display: none;
}

/* min-height 0, sonst wächst der Inhalt mit, und er scrollt nicht. isolation: Was im Inhalt übereinander liegt,
   bleibt unter Kopfzeile und Schleier. */
.oo-tnl__main {
    --oo-tnl-header-offset: 0px;
    --oo-tnl-content-height: 100%;
    flex: 1 1 0;
    min-height: 0;
    overflow: auto;
    isolation: isolate;
}

/* Eingeklappt (schmal): Die Kopfzeile ist genau eine Zeile hoch, links der Menüknopf. Die Navigation liegt unsichtbar unter
   der Kopfzeile und schiebt sich geöffnet über den Inhalt. visibility, damit Tab die eingeklappten Einträge überspringt;
   beim Einblenden sofort sichtbar, sonst ginge der Fokus, den der Menüknopf setzt, im ersten Bild ins Leere.
   Kindkombinatoren am offenen Zustand: Ein verschachteltes TopNavLayout öffnet sich nicht mit dem äußeren.
   Dieselben Regeln stehen unten noch einmal für das Handy, wo die Navigation immer eingeklappt ist. */
@container (max-width: 48rem) {
    .oo-tnl__header {
        height: var(--oo-tnl-header-height);
    }

    .oo-tnl__bar {
        height: 100%;
        min-height: 0;
        padding-block: 0;
    }

    .oo-tnl .oo-tnl__menu-button {
        display: inline-flex;
    }

    .oo-tnl__brand {
        flex-shrink: 1;
        min-width: 0;
        overflow: hidden;
    }

    .oo-tnl__nav {
        position: absolute;
        top: 100%;
        left: 0;
        right: 0;
        padding: var(--oo-space-3);
        background: var(--oo-color-background);
        border-bottom: var(--oo-border-width) solid var(--oo-color-border);
        visibility: hidden;
        opacity: 0;
        transform: translateY(-0.5rem);
        transition: transform var(--oo-transition), opacity var(--oo-transition), visibility var(--oo-transition);
    }

    .oo-tnl--open > .oo-tnl__header > .oo-tnl__bar > .oo-tnl__nav {
        visibility: visible;
        opacity: 1;
        transform: none;
        box-shadow: var(--oo-shadow-lg);
        transition: transform var(--oo-transition), opacity var(--oo-transition);
    }

    .oo-tnl--open > .oo-tnl__backdrop {
        display: block;
        position: absolute;
        inset: 0;
        z-index: 1;
        background: var(--oo-tnl-backdrop);
    }
}

/* Handy: Die Seite scrollt, nicht der Inhaltsbereich. Nur so klappt der Browser die Adressleiste ein, aktualisiert beim
   Herunterziehen und hält das fokussierte Eingabefeld über der Tastatur; bei festem Grundgerüst schiebt er stattdessen die
   ganze Seite hoch. Abfrage nach Fenster und Eingabeart statt Container-Abfrage: Ein schmales Panel neben einer Anwendung
   scrollt weiter in seinem Bereich. Auch im Querformat (niedrig, aber breiter als 48rem), bis 60rem Breite, damit ein Tablet
   im Querformat nicht umschaltet, sobald seine Tastatur das Fenster niedrig macht.
   Die Navigation ist hier immer eingeklappt: So ist die klebende Kopfzeile genau --oo-tnl-header-height hoch, und
   --oo-tnl-header-offset stimmt. Die Seiten mit diesem Layout sollten im viewport-Meta interactive-widget=resizes-content setzen. */
@media (pointer: coarse) and ((max-width: 48rem) or ((max-height: 30rem) and (max-width: 60rem))) {
    html:has(.oo-tnl) body {
        overflow: visible;
        background: var(--oo-color-surface);
    }

    .oo-tnl {
        height: auto;
        min-height: 100dvh;
    }

    .oo-tnl__header {
        position: sticky;
        top: 0;
        height: var(--oo-tnl-header-height);
    }

    .oo-tnl__main {
        --oo-tnl-header-offset: var(--oo-tnl-header-height);
        --oo-tnl-content-height: calc(100dvh - var(--oo-tnl-header-height));
        overflow: visible;
    }

    .oo-tnl__bar {
        height: 100%;
        min-height: 0;
        padding-block: 0;
    }

    .oo-tnl .oo-tnl__menu-button {
        display: inline-flex;
    }

    .oo-tnl__brand {
        flex-shrink: 1;
        min-width: 0;
        overflow: hidden;
    }

    .oo-tnl__nav {
        position: absolute;
        top: 100%;
        left: 0;
        right: 0;
        padding: var(--oo-space-3);
        background: var(--oo-color-background);
        border-bottom: var(--oo-border-width) solid var(--oo-color-border);
        visibility: hidden;
        opacity: 0;
        transform: translateY(-0.5rem);
        transition: transform var(--oo-transition), opacity var(--oo-transition), visibility var(--oo-transition);
    }

    .oo-tnl--open > .oo-tnl__header > .oo-tnl__bar > .oo-tnl__nav {
        visibility: visible;
        opacity: 1;
        transform: none;
        box-shadow: var(--oo-shadow-lg);
        transition: transform var(--oo-transition), opacity var(--oo-transition);
    }

    .oo-tnl--open > .oo-tnl__backdrop {
        display: block;
        position: fixed;
        inset: 0;
        z-index: 1;
        background: var(--oo-tnl-backdrop);
    }
}

/* Am Ende, damit es die Übergänge beider Blöcke oben überschreibt. */
@media (prefers-reduced-motion: reduce) {
    .oo-tnl__nav,
    .oo-tnl--open > .oo-tnl__header > .oo-tnl__bar > .oo-tnl__nav {
        transition: none;
    }
}
