Design-System: Button-Varianten konsolidieren, 44px-Trefferflächen

Dritter Teil. .btn hatte nur primary + outline + sm/lg, daneben lebten mehrere
Controls als Eigenbau — teils zeichengleich dupliziert.

Tabs: .group-tabs__tab und .filter-bar__tab waren bis auf flex-shrink und 4px
Innenabstand identisch. Beide laufen jetzt über eine gemeinsame .tab-Basis, die
aria-pressed (Filter) und aria-selected (Tabs) gleich behandelt; von den
BEM-Klassen bleibt nur das jeweilige Delta. Innenabstand vereinheitlicht auf
--space-m, die Gruppen-Tabs verlieren dadurch 4px pro Seite.

Icon-Buttons: .ad-banner__nav-btn und .ad-banner__toggle waren vollständige
Duplikate voneinander. Sie tragen jetzt .btn .btn--icon und behalten nur die
Glas-Optik als Delta. Der Selektor schreibt .btn mit — utilities.css lädt nach
components.css, bei gleicher Spezifität gewänne sonst die rote .btn-Fläche.

Trefferflächen auf 44px (WCAG 2.5.5): .btn bekommt min-height und wird
inline-flex, damit Icon und Label ohne Zusatz-Markup zentriert liegen.
Bezeichnend auch hier — .department-choice__btn hatte inline-flex, align-items
und exakt denselben gap bereits selbst deklariert und gibt sie jetzt ab.
Controls, die optisch klein bleiben sollen, strecken die Fläche stattdessen
unsichtbar per Pseudo-Element (.tap-target, automatisch auch für .btn--sm) —
gewertet wird die Trefferfläche, nicht die gezeichnete.

Der Banner-Indikator brauchte einen anderen Weg: er trug overflow: hidden, um
den Fortschrittsbalken zu beschneiden, was jede Erweiterung wieder abgeschnitten
hätte. Der sichtbare 6px-Balken liegt jetzt im ::before, der Fortschritt ist
selbst rund — overflow entfällt, der Button ist 48x44px.

Haupt-Nav-Links, Dropdown-Trigger und Footer-Social-Links bekommen min-height
statt einer Pseudo-Erweiterung: sie stehen in Reihen, wo überlappende
Trefferflächen den Nachbarn verdecken würden. In der 60px hohen Kopfleiste ist
die Höhe ohnehin nicht sichtbar.

Bewusst unverändert: die Formular-Checkbox bleibt bei 24px (WCAG 2.5.8).
<input> ist ein Replaced Element, dort greift ::after nicht zuverlässig — und
das zugehörige <label> ist klickbar und liefert die große Fläche.

.btn--ghost ist angelegt, hat aber aktuell keinen Abnehmer: die vermuteten
nackten Links sind bei näherem Hinsehen Bildkarten (.instagram__link),
Wrapper (.split__cta) oder eigenständige Karten-Affordanzen (.team-card__cta),
keine tertiären Buttons.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01MSsVdooFLgPA8gPFp7HwZU
This commit is contained in:
2026-07-27 10:28:02 +02:00
parent 3fa521eaf1
commit eacf9449e0
13 changed files with 304 additions and 93 deletions

View File

@@ -98,7 +98,7 @@ $total = count($banners);
<?php if ($total > 1): ?>
<?php /* Ohne JS verborgen (Steuerung wäre funktionslos); carousel.js blendet sie ein. */ ?>
<div class="ad-banner__controls" data-carousel-controls hidden>
<button class="ad-banner__nav-btn" type="button" data-carousel-prev aria-label="Vorherige Anzeige">
<button class="btn btn--icon ad-banner__nav-btn" type="button" data-carousel-prev aria-label="Vorherige Anzeige">
<?= icon('chevron-left') ?>
</button>
<div class="ad-banner__indicators" role="group" aria-label="Anzeige wählen">
@@ -108,11 +108,11 @@ $total = count($banners);
</button>
<?php endforeach; ?>
</div>
<button class="ad-banner__nav-btn" type="button" data-carousel-next aria-label="Nächste Anzeige">
<button class="btn btn--icon ad-banner__nav-btn" type="button" data-carousel-next aria-label="Nächste Anzeige">
<?= icon('chevron-right') ?>
</button>
<?php /* Pause/Play — WCAG 2.2.2. Nur bei aktiver Auto-Rotation sichtbar. */ ?>
<button class="ad-banner__toggle" type="button" data-carousel-toggle aria-pressed="false" aria-controls="ad-banner-track" hidden>
<button class="btn btn--icon ad-banner__toggle" type="button" data-carousel-toggle aria-pressed="false" aria-controls="ad-banner-track" hidden>
<?= icon('pause-fill', 'ad-banner__toggle-icon ad-banner__toggle-icon--pause') ?>
<?= icon('play-fill', 'ad-banner__toggle-icon ad-banner__toggle-icon--play') ?>
<span class="visually-hidden" data-carousel-toggle-label>Automatischen Wechsel pausieren</span>