/* Grundlagen. Farben und Größen stammen ausschließlich aus theme.json. */

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

img,
video {
	max-width: 100%;
	height: auto;
}

:where(.wp-block-group) {
	min-width: 0;
}

/* Wide-Inhalte dürfen die Textspalte überschreiten, aber nie ihren Container.
   Das min() ist der eigentliche Schutz: wide-size deckelt nach oben, 100%
   verhindert den Überlauf in einer Spalte, die schmaler ist als wide-size. */
.wp-block-post-content > .alignwide {
	max-width: min(var(--wp--style--global--wide-size), 100%);
}

/*
 * Tabellenziffern.
 *
 * Bei Messwerten stehen die Stellen sonst nicht untereinander — 142,3 über
 * 98,1 lässt sich dann nicht vergleichen, ohne zu lesen. Genau dafür sind
 * Tabellen da.
 *
 * `font-variant-numeric` wirkt nur, wenn die Schrift den Satz mitbringt; tut
 * sie es nicht, bleibt es folgenlos. Kein Grund, es zu unterlassen.
 */
:where( table, .gw-procon, time, .g-post-meta ) {
	font-variant-numeric: tabular-nums;
}

/*
 * Wortumbruch fuer lange Produktnamen und deutsche Komposita.
 *
 * Gemessen, nicht vermutet. Bei 320 px Viewport ist die Inhaltsspalte
 * 278 px breit (320 minus zweimal Root-Padding `sm`), die H2 traegt keine
 * eigene Groesse und laeuft deshalb mit der Browser-Vorgabe 1.5em auf
 * 25,5 px. Aus den Schriftdateien ausgemessen (Bricolage, wght 800):
 *
 *   Verbraucherstreitbeilegung   348 px bei opsz 25 / 317 px bei opsz 96
 *   Identifikationsnummer        289 px bei opsz 25
 *
 * Das erste Wort steht als H2 im Impressum und laeuft um 39 bis 70 px aus
 * der Spalte. Kartentitel laufen im heutigen Bestand noch **nicht** ueber
 * (laengstes unumbrechbares Stueck „Arbeitsspeicher", 182 px in einer
 * 294 px breiten Karte) — dort ist die Regel Vorsorge. Eine Hardware-Seite
 * schreibt „Durchstroemungskuehler" und „Rueckwaertskompatibel"; der
 * naechste Beitrag bringt das laengere Wort.
 *
 * `hyphens: auto` braucht eine Sprachangabe am Dokument. Geprueft an der
 * laufenden Instanz: `<html lang="de">` ist gesetzt (nicht `de-DE`), also
 * greift die deutsche Silbentrennung. Faellt die Angabe je weg, trennt
 * nichts mehr — der harte Umbruch darunter bleibt dann als Auffangnetz.
 *
 * `hyphenate-limit-chars` verhindert Bruchstuecke wie „Ar-beitsspeicher".
 * Browser ohne Unterstuetzung ignorieren die Zeile, die Trennung bleibt.
 *
 * **Bewusst nicht global.** Eine Regel auf `body` bricht Fliesstext an
 * Stellen, an denen niemand sie erwartet. Umgebrochen wird nur dort, wo die
 * Spalte schmal und der Begriff lang ist: Ueberschriften, Kartentitel,
 * Tabellenzellen.
 */
:where( h1, h2, h3, h4, h5, h6, .wp-block-heading, .wp-block-post-title ) {
	overflow-wrap: break-word;
	-webkit-hyphens: auto;
	hyphens: auto;
	hyphenate-limit-chars: 8 4 4;
}

/*
 * Kartentitel und Rubrik: hier `anywhere`, nicht `break-word`.
 *
 * Der Unterschied ist nicht kosmetisch. Beide brechen ein zu langes Wort,
 * aber nur `anywhere` senkt auch die min-content-Breite des Kastens.
 * Das Beitragsraster ist inhaltsbemessen
 * (`repeat(auto-fill, minmax(min(18rem, 100%), 1fr))`, `layout.css`): mit
 * `break-word` haelt der Titel die Spur weiterhin auf seine Wortbreite auf
 * und sprengt das Raster, statt umzubrechen. Deshalb steht `anywhere`
 * bereits an `.g-post-card__mark` — hier aus demselben Grund.
 *
 * Klassenselektor mit Absicht: `:where()` waere spezifitaetsfrei und wuerde
 * von jeder Element-Regel eines Child-Themes ueberschrieben. Dann stuende
 * am Kartentitel wieder `break-word`, und das Raster waere ungeschuetzt.
 */
.g-post-card__title,
.g-post-card__kicker {
	overflow-wrap: anywhere;
}

/*
 * Tabellenzellen: `break-word`, und hier ist `anywhere` **falsch**.
 *
 * Die Vergleichstabelle des Content-Vertrags soll seitlich scrollen, nicht
 * umbrechen — `gw-table-scroll` liefert `overflow-x: auto` auf der `figure`.
 * Der Bildlauf entsteht nur, solange die min-content-Breite der Tabelle
 * groesser ist als die der `figure`. `anywhere` senkt genau diese Breite und
 * loescht damit den Bildlauf; `break-word` laesst sie unberuehrt und bricht
 * erst, wenn die Zelle ohnehin schon feststeht.
 *
 * Fuer `has-fixed-layout` bringt Core schon
 * `word-break: break-word` mit (`wp-block-table` Stylesheet). Diese Regel
 * greift also vor allem bei Tabellen mit automatischem Layout, die von Core
 * nichts bekommen. `word-break: break-word` selbst wird hier nicht benutzt:
 * die Eigenschaft ist fuer diesen Wert veraltet und nur ein Alias auf
 * `overflow-wrap`, waehrend `word-break: break-all` mitten im Wort ohne
 * Ruecksicht auf die Sprache trennen wuerde.
 *
 * Keine Silbentrennung in Zellen: in 35 px schmalen Spalten einer
 * achtspaltigen Tabelle erzeugt sie mehr Trennstriche als Text.
 */
:where( th, td ) {
	overflow-wrap: break-word;
}

/*
 * Bewegung.
 *
 * Der Token-Satz steht in `theme.json` unter `custom.motion`. Wer eine Dauer
 * hart hinschreibt, koppelt sie von jeder späteren Entscheidung ab.
 *
 * `prefers-reduced-motion` ist keine Kür: Für einen Teil der Nutzer ist
 * Bewegung ein körperliches Problem, kein Geschmacksthema. Die Dauern werden
 * hier zentral auf nahezu null gesetzt, statt in jeder Regel erneut.
 */
/*
 * Sanftes Scrollen.
 *
 * **Es fehlte, und das ist gemessen:** Die Ruecknahme fuer
 * `prefers-reduced-motion` unten setzt `scroll-behavior: auto !important` —
 * sie hat bis zum 2026-09-02 etwas zurueckgenommen, das nirgends gesetzt war.
 * Jeder Sprung aus dem Inhaltsverzeichnis war ein harter Schnitt.
 *
 * **Eine Zeile CSS, kein JavaScript.** Alle aktuellen Browser tragen es
 * (Safari seit 15.4). Eine Skriptloesung waere nicht nur ueberfluessig,
 * sondern schlechter: Sie muesste `scrollTo` je Sprungziel selbst rechnen und
 * dabei `scroll-padding-top` nachbauen, das der Browser hier schon
 * beruecksichtigt.
 *
 * Es gilt fuer **alle** Sprungziele: Inhaltsverzeichnis, Sprunglinks des
 * Formulars, „Nach oben", und den Sprunglink zum Inhalt.
 *
 * `scroll-padding-top` steht in `layout.css` bei der Kopfleiste, weil der Wert
 * dort hingehoert. Ohne ihn schneidet die fixierte Pille die angesprungene
 * Ueberschrift ab.
 */
:root {
	scroll-behavior: smooth;
}

@media ( prefers-reduced-motion: reduce ) {
	:root {
		--wp--custom--motion--schnell: 1ms;
		--wp--custom--motion--normal: 1ms;
		--wp--custom--motion--ruhig: 1ms;
	}

	*,
	*::before,
	*::after {
		animation-duration: 1ms !important;
		animation-iteration-count: 1 !important;
		transition-duration: 1ms !important;
		scroll-behavior: auto !important;
	}
}

/*
 * Schaltflaechen, die kein Block erzeugt.
 *
 * Die Kurzfassung in der Seitenleiste (`.g-toc__current`) kommt aus
 * `goblin-toolkit` — also nicht aus einem Core-Block, der eine Gestaltung
 * mitbraechte. Ohne diese Regel traegt sie die Grundgestalt des Browsers:
 * graue Flaeche, Systemrahmen, Systemschrift. In einem Entwurf, dessen
 * Kontraste auf zwei Stellen gemessen sind, faellt genau das sofort auf.
 *
 * Farbe kommt aus den Rollen, nicht von hier — `goblin-base` schreibt keinen
 * Farbwert. Was hier steht, ist die Struktur einer Schaltflaeche.
 *
 * HIER STANDEN `.g-toc-toggle` UND `.g-toc-overlay__close`. Beide gehoerten
 * zum modalen Inhaltsverzeichnis, das am 2026-09-01 durch die mobile Leiste
 * (`.g-toc-bar*`) ersetzt wurde; seither gibt sie keine PHP- und keine
 * JS-Datei mehr aus. Entfernt am 2026-09-02 (BL65), belegt an der laufenden
 * Instanz: null Treffer auf einem Beitrag MIT und einem OHNE
 * Inhaltsverzeichnis, waehrend `.g-toc__current` und `.g-toc-bar*` auf dem
 * Beitrag mit Verzeichnis je einmal vorkamen. Die Klammer bleibt einelementig
 * stehen — `:where()` haelt die Spezifitaet bei null, und das ist hier der
 * Punkt: Der Skin soll ohne Muehe dagegen ankommen.
 */
:where( .g-toc__current ) {
	font: inherit;
	color: inherit;
	background-color: var( --wp--preset--color--surface );
	border: var( --wp--custom--border--width, 1px ) solid var( --wp--preset--color--muted );
	border-radius: var( --wp--custom--radius--sm, 2px );
	padding: var( --wp--preset--spacing--2-xs ) var( --wp--preset--spacing--xs );
	cursor: pointer;
	transition: background-color var( --wp--custom--motion--schnell ) var( --wp--custom--motion--kurve );
}

/*
 * Sichtbarer Fokus. Der weggeblendete Fokusring ist der haeufigste Fehler
 * ueberhaupt — hier wird er gar nicht erst weggeblendet.
 */
:where( .g-toc__current ):focus-visible {
	outline: var( --wp--custom--border--accent-width, 3px ) solid var( --wp--preset--color--primary );
	outline-offset: 2px;
}

/*
 * ---------------------------------------------------------------------------
 * Icons.
 * ---------------------------------------------------------------------------
 *
 * Der Satz liegt im Child, der Mechanismus in `inc/icons.php`. Hier steht nur,
 * wie ein Zeichen sich verhaelt.
 *
 * **Die Groesse kommt von hier und nicht aus der Datei.** `inc/icons.php`
 * entfernt `width` und `height` am Wurzelelement, weil ein Attribut gegen jede
 * Regel gewinnen wuerde — ein aus einem Zeichenprogramm exportiertes Icon
 * braechte sonst seine eigene Groesse mit.
 *
 * `1.5em` als Standard: Damit haengt das Zeichen an der Schriftgroesse seiner
 * Umgebung und passt in eine Textzeile, ohne dass jemand rechnet. Der Entwurf
 * nennt 20, 24 und 36 px; alle drei sind ueber `--g-icon-size` erreichbar.
 *
 * `stroke: currentColor` steht in den Dateien selbst. Hier wird es NICHT
 * wiederholt: Sonst gaebe es zwei Orte, an denen die Farbe herkommt, und der
 * eine wuerde irgendwann den anderen ueberholen.
 */
.g-icon {
	display: inline-block;
	inline-size: var(--g-icon-size, 1.5em);
	block-size: var(--g-icon-size, 1.5em);

	/*
	 * Ein Icon in einer Textzeile sitzt sonst auf der Grundlinie und drueckt
	 * die Zeilenhoehe auf. `vertical-align` statt `flex`, weil ein Icon auch
	 * mitten im Satz stehen kann.
	 */
	vertical-align: -0.125em;

	/* Nie zusammenquetschen, wenn es in einem Flex-Container steht. */
	flex-shrink: 0;
}

/*
 * ---------------------------------------------------------------------------
 * Aufzaehlungslisten im Fliesstext.
 * ---------------------------------------------------------------------------
 *
 * IN EINEM BLOCKTHEMA IST FAST JEDES BAUTEIL EINE LISTE. Navigation, Chips,
 * Kartenraster, Trefferliste, Inhaltsverzeichnis, Profillinks, Quellen,
 * Beitragsverlauf, Lesetipps und die Pro/Contra-Gegenueberstellung sind alle
 * `<ul>` oder `<ol>`. Ein `ul { list-style: disc }` haette ihnen allen
 * Aufzaehlungszeichen und einen Einzug gegeben. GEMESSEN am 2026-09-04 an
 * sechs Adressen: 15 Bauteillisten, alle auf `list-style: none` und
 * `padding-inline-start: 0` — bis auf `gw-sources-list`, die absichtlich
 * nummeriert ist.
 *
 * GEZIELT WIRD DESHALB NACH MERKMAL, NICHT NACH ORT: `wp-block-list` ist die
 * Klasse, die Cores Listenblock traegt, und nur der entsteht aus geschriebenem
 * Text. Nach Ort zu zielen (alles im Inhaltstraeger) haette nicht gereicht —
 * Quellen, Pro/Contra, Lesetipps und das Inline-Verzeichnis stehen alle IM
 * Inhalt.
 *
 * DIE AUSNAHME IST DIE HALBE REGEL. Zwei Bauteillisten tragen `wp-block-list`
 * zusaetzlich zu ihrer eigenen Klasse, weil sie aus dem Listenblock gebaut
 * sind: `gw-procon-list` und `g-pledge__list`. Ausgenommen wird deshalb nicht
 * diese Zweierliste — die wuerde beim naechsten Bauteil still unvollstaendig —
 * sondern JEDE Liste mit einer Bauteilklasse. `g-` und `gw-` sind die beiden
 * Praefixe dieses Systems; ein Attributselektor auf `"g-"` allein faengt
 * `gw-` NICHT (dort folgt auf das g ein w), beide Formen muessen also stehen.
 *
 * KEINE FARBE HIER. Das Zeichen faerbt der Skin.
 */
.wp-block-list:not([class^="g-"]):not([class*=" g-"]):not([class^="gw-"]):not([class*=" gw-"]) {
	/*
	 * Der Einzug ist kleiner als Browsers 40px und derselbe wie bei der
	 * Quellenliste des Content-Vertrags: eine Zahl fuer alle eingerueckten
	 * Listen dieses Systems. Groesser schoebe den Text sichtbar aus der
	 * Lesespalte, in der er steht.
	 */
	padding-inline-start: var(--g-list-indent, 24px);
}

/*
 * DER ABSTAND ZWISCHEN ZWEI PUNKTEN MUSS GROESSER SEIN ALS DER ZWISCHEN ZWEI
 * ZEILEN EINES PUNKTES, sonst zerfaellt die Liste in gleich weit stehende
 * Zeilen und man sieht nicht mehr, wo ein Punkt endet. Der Fliesstext laeuft
 * mit Zeilenhoehe 1,7; die Zeilen eines Punktes stehen also rund 12px
 * auseinander, zwei Punkte mit diesen 10px rund 22.
 *
 * `li + li` und nicht `li { margin-block-end }`: So haengt am letzten Punkt
 * kein Abstand, den der Abstand des Blocks darunter noch einmal mitbringt.
 */
.wp-block-list:not([class^="g-"]):not([class*=" g-"]):not([class^="gw-"]):not([class*=" gw-"]) > li + li {
	margin-block-start: var(--g-list-item-gap, 10px);
}

/*
 * VERSCHACHTELTE LISTEN. Cores Listenblock gibt auch der inneren Liste die
 * Klasse `wp-block-list`, die Regel oben trifft sie also mit.
 *
 * HIER STEHT KEIN `list-style-type`, UND DAS IST ABSICHT: Der Browser gibt der
 * ersten Ebene `disc` und der zweiten `circle`, der ersten Zahlenebene
 * `decimal` und der zweiten `lower-alpha`. Wer die erste Ebene festschreibt,
 * nimmt der zweiten ihren Unterschied und muss ihn danach von Hand
 * zurueckgeben. Die Vorgabe ist richtig; sie braucht nur eine Farbe, und die
 * setzt der Skin.
 *
 * Die zweite Ebene bekommt weniger Einzug: Sie steht ohnehin schon eingerueckt,
 * und zweimal 24px schoeben den Text aus der Lesespalte.
 */
.wp-block-list .wp-block-list:not([class^="g-"]):not([class*=" g-"]):not([class^="gw-"]):not([class*=" gw-"]) {
	padding-inline-start: var(--g-list-indent-nested, 20px);
	margin-block-start: var(--g-list-item-gap, 10px);
}

/*
 * ---------------------------------------------------------------------------
 * Das Zeichen am Affiliate-Link.
 * ---------------------------------------------------------------------------
 *
 * Gesetzt wird es vom Toolkit (`Affiliate_Links`), gestaltet hier. Zwei Teile:
 * der sichtbare Stern und daneben das Wort fuer die Sprachausgabe. Beide
 * stehen IM Link, damit die Kennzeichnung ankommt, bevor jemand ihn aktiviert.
 *
 * DAS WORT WIRD AUS DEM BILD GENOMMEN, NICHT AUS DEM BAUM. `display: none`
 * oder `visibility: hidden` naehmen es auch der Sprachausgabe — dann stuende
 * nur ein Stern da, und Sternchen werden von Vorlesern haeufig verschluckt.
 *
 * KEINE FARBE HIER. Das Zeichen faerbt der Skin.
 */
.g-affiliate-mark {
	/*
	 * `inline-block`, UND DAS IST DER GANZE PUNKT DIESER REGEL: Eine
	 * Unterstreichung wird am Vorfahren gezeichnet und laeuft ueber alle
	 * Nachfahren hinweg — ein `text-decoration: none` am Kind nimmt sie nicht
	 * zurueck. In einen atomaren Inline-Kasten laeuft sie dagegen nicht
	 * hinein. Ohne das zieht der Strich des Links unter dem Stern weiter, und
	 * der Hinweis sieht aus wie das letzte Zeichen des Linktextes. Gemessen
	 * am 2026-09-16 im Browser, nicht am Markup — im HTML ist davon nichts zu
	 * sehen.
	 */
	display: inline-block;

	/*
	 * `<sup>` bringt Hochstellung und kleinere Schrift vom Browser mit. Was
	 * fehlt, ist `line-height: 0`: Ohne das zieht die hochgestellte Zeile den
	 * Zeilenabstand im Absatz auseinander, und zwar nur in den Zeilen mit
	 * einem Link. Gemessen an einem Absatz mit und ohne Kennzeichnung.
	 */
	line-height: 0;
}

.g-affiliate-mark__text {
	position: absolute;
	width: 1px;
	height: 1px;
	margin: -1px;
	padding: 0;
	border: 0;
	overflow: hidden;
	clip-path: inset(50%);
	white-space: nowrap;
}
