/* ==========================================================================
   Meteor-AI Website — eigenstaendiges Stylesheet.

   Die Website lebt in einem eigenen Ordner und laeuft ohne die App: keine
   Verweise nach ../css der App, alles Noetige liegt hier daneben. Tokens
   und Schriften sind deshalb eine Kopie aus css/theme.css der App
   (shadcn/ui "neutral", DM Sans, Geist Mono). Aendert sich dort ein Wert,
   wird er hier nachgezogen. Was gilt, steht in DESIGN.md dieses Repos;
   die Grundlagen dort verweisen auf DESIGN.md der App.

   Hell/Dunkel wie in der App ueber die Klasse .dark am <html>. Ein kleines
   Skript im <head> setzt sie vor dem ersten Paint: gewaehlt per Umschalter
   (localStorage 'meteor-ai.theme'), sonst nach dem System. Ohne Skript hell.

   Ohne JavaScript bleibt alles lesbar: die Navigation steht dann offen
   unter dem Logo (Klasse .js wird erst im <head> gesetzt).

   Keine Frameworks, keine Utility-Klassen, kein Build.

   Inhalt:  Schriften · Tokens · Grundlagen · Knoepfe · Kopfzeile · Hero ·
            Abschnitte · Karten · Kachel-Icons · Bildkarten · Funktionsblock · Diagramme · Rechner · Ablauf · Tabellen · FAQ ·
            Preise · Text (Rechtliches) · Aufruf · Fusszeile · Bewegung · Responsive
   ========================================================================== */

/* ---------- Schriften (Kopie in assets/fonts, nichts wird nachgeladen) ---- */

@font-face {
  font-family: "DM Sans";
  src: url("../assets/fonts/DMSans-Variable-latin.woff2") format("woff2");
  font-weight: 100 1000;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;
}
@font-face {
  font-family: "DM Sans";
  src: url("../assets/fonts/DMSans-Variable-latin-ext.woff2") format("woff2");
  font-weight: 100 1000;
  font-style: normal;
  font-display: swap;
  unicode-range: U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;
}
@font-face {
  font-family: "DM Sans";
  src: url("../assets/fonts/DMSans-Italic-Variable-latin.woff2") format("woff2");
  font-weight: 100 1000;
  font-style: italic;
  font-display: swap;
  unicode-range: U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;
}
@font-face {
  font-family: "Geist Mono";
  src: url("../assets/fonts/GeistMono-Variable.woff2") format("woff2");
  font-weight: 100 900;
  font-style: normal;
  font-display: swap;
}

/* ---------- Tokens ------------------------------------------------------- */

/* Kopie aus css/theme.css der App, mit einer Ausnahme: Schwarz ist hier
   wirklich Schwarz (oklch(0 0 0) / #000000) statt shadcn 0.145 bzw. 0.205 —
   hell --foreground, --card-foreground, --primary, --secondary-foreground,
   dunkel --background und --primary-foreground. Das Logo ist schwarz; Text
   und Knöpfe daneben wirkten sonst grau ausgewaschen. --success gibt es nur
   hier (Preisvergleich), die App kennt kein Grün. Siehe DESIGN.md. */

:root {
  --radius: 0.625rem;
  --radius-sm: calc(var(--radius) - 4px);
  --radius-md: calc(var(--radius) - 2px);
  --radius-lg: var(--radius);
  --radius-xl: calc(var(--radius) + 4px);

  --background: oklch(1 0 0);
  --foreground: oklch(0 0 0);
  --card: oklch(1 0 0);
  --card-foreground: oklch(0 0 0);
  --primary: oklch(0 0 0);
  --primary-foreground: oklch(0.985 0 0);
  --secondary: oklch(0.97 0 0);
  --secondary-foreground: oklch(0 0 0);
  --muted: oklch(0.97 0 0);
  --muted-foreground: oklch(0.556 0 0);
  --warning: oklch(0.646 0.161 73.4);
  --warning-foreground: oklch(0.42 0.12 73.4);
  --destructive: oklch(0.577 0.245 27.325);
  --success: oklch(0.527 0.154 150.069);
  --border: oklch(0.922 0 0);
  --input: oklch(0.922 0 0);
  --ring: oklch(0.708 0 0);

  --shadow-xs: 0 1px 2px 0 oklch(0 0 0 / 0.05);
  --shadow-sm: 0 1px 3px 0 oklch(0 0 0 / 0.1), 0 1px 2px -1px oklch(0 0 0 / 0.1);
  --shadow-lg: 0 10px 15px -3px oklch(0 0 0 / 0.1), 0 4px 6px -4px oklch(0 0 0 / 0.1);

  --font-sans: "DM Sans", ui-sans-serif, system-ui, -apple-system, "Segoe UI Variable Text",
    "Segoe UI", Roboto, "Helvetica Neue", Arial, "Noto Sans", sans-serif,
    "Apple Color Emoji", "Segoe UI Emoji";
  --font-mono: "Geist Mono", ui-monospace, "Cascadia Mono", "Segoe UI Mono", "JetBrains Mono",
    Menlo, Consolas, "Liberation Mono", monospace;

  --page-width: 75rem;
  --text-width: 50rem;
  --gutter: 1.5rem;
  --header-h: 4.25rem;
}

:root { color-scheme: light; }

.dark {
  color-scheme: dark;
  --background: oklch(0 0 0);
  --foreground: oklch(0.985 0 0);
  --card: oklch(0.205 0 0);
  --card-foreground: oklch(0.985 0 0);
  --primary: oklch(0.922 0 0);
  --primary-foreground: oklch(0 0 0);
  --secondary: oklch(0.269 0 0);
  --secondary-foreground: oklch(0.985 0 0);
  --muted: oklch(0.269 0 0);
  --muted-foreground: oklch(0.708 0 0);
  --warning: oklch(0.769 0.144 73.4);
  --warning-foreground: oklch(0.879 0.089 73.4);
  --destructive: oklch(0.704 0.191 22.216);
  --success: oklch(0.792 0.209 151.711);
  --border: oklch(1 0 0 / 10%);
  --input: oklch(1 0 0 / 15%);
  --ring: oklch(0.556 0 0);
  --shadow-lg: 0 10px 15px -3px oklch(0 0 0 / 0.4), 0 4px 6px -4px oklch(0 0 0 / 0.4);
}

/* Fallback fuer Browser ohne oklch(), wie in css/theme.css der App. */
@supports not (color: oklch(0 0 0)) {
  :root {
    --background: #ffffff; --foreground: #000000;
    --card: #ffffff; --card-foreground: #000000;
    --primary: #000000; --primary-foreground: #fafafa;
    --secondary: #f5f5f5; --secondary-foreground: #000000;
    --muted: #f5f5f5; --muted-foreground: #737373;
    --warning: #d08700; --warning-foreground: #894b00;
    --destructive: #e7000b; --success: #008236;
    --border: #e5e5e5; --input: #e5e5e5; --ring: #a1a1a1;
  }
  .dark {
    --background: #000000; --foreground: #fafafa;
    --card: #171717; --card-foreground: #fafafa;
    --primary: #e5e5e5; --primary-foreground: #000000;
    --secondary: #262626; --secondary-foreground: #fafafa;
    --muted: #262626; --muted-foreground: #a1a1a1;
    --warning: #ffb900; --warning-foreground: #ffd48a;
    --destructive: #ff6467; --success: #05df72;
    --border: rgba(255, 255, 255, 0.1); --input: rgba(255, 255, 255, 0.15); --ring: #737373;
  }
}

/* ---------- Grundlagen --------------------------------------------------- */

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

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: smooth;
  scroll-padding-top: calc(var(--header-h) + 1rem);
}

body {
  margin: 0;
  background: var(--background);
  color: var(--foreground);
  font-family: var(--font-sans);
  font-size: 1rem;
  line-height: 1.65;
  font-optical-sizing: auto;
  -webkit-font-smoothing: antialiased;
  overflow-wrap: break-word;
}

img, svg { display: block; max-width: 100%; }

a { color: inherit; text-underline-offset: 0.2em; }

p, ul, ol, dl { margin: 0 0 1.25rem; }
ul, ol { padding-left: 1.25rem; }
li + li { margin-top: 0.5rem; }

h1, h2, h3, h4 { margin: 0; font-weight: 600; line-height: 1.2; letter-spacing: 0; }

code, kbd {
  padding: 0.1em 0.35em;
  background: var(--muted);
  border-radius: var(--radius-sm);
  font-family: var(--font-mono);
  font-size: 0.875em;
}

:focus-visible {
  outline: 3px solid color-mix(in oklab, var(--ring) 50%, transparent);
  outline-offset: 1px;
  border-radius: var(--radius-sm);
}

.container {
  width: 100%;
  max-width: var(--page-width);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

.skip-link {
  position: absolute;
  left: var(--gutter);
  top: -4rem;
  z-index: 100;
  padding: 0.5rem 0.875rem;
  background: var(--primary);
  color: var(--primary-foreground);
  border-radius: 999px;
  font-size: 0.875rem;
  font-weight: 500;
}
.skip-link:focus { top: 0.5rem; }

.nowrap { white-space: nowrap; }

.visually-hidden {
  position: absolute;
  width: 1px; height: 1px;
  margin: -1px; padding: 0;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
  border: 0;
}

.icon {
  flex: none;
  width: 1.25rem;
  height: 1.25rem;
  fill: none;
  stroke: currentColor;
  stroke-width: 2;
  stroke-linecap: round;
  stroke-linejoin: round;
}

/* ---------- Knoepfe ------------------------------------------------------ */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5rem;
  height: 2.5rem;
  padding: 0 1.25rem;
  border: 1px solid transparent;
  border-radius: 999px;
  font: inherit;
  font-size: 0.875rem;
  font-weight: 500;
  white-space: nowrap;
  text-decoration: none;
  cursor: pointer;
  box-shadow: var(--shadow-xs);
  transition: background-color 0.15s, border-color 0.15s;
}
.btn .icon { width: 1rem; height: 1rem; }
.btn-icon { width: 2.5rem; padding: 0; flex: none; }

.btn-lg { height: 2.875rem; padding: 0 1.75rem; font-size: 0.9375rem; }

/* Hover wie in der App: hell zu 75 % aufgehellt, dunkel zu 90 %. Auf echtem
   Schwarz ergaben 90 % nur Helligkeit 0.1 — der Hover war kaum zu sehen. */
.btn-primary { --primary-hover: 75%; background: var(--primary); color: var(--primary-foreground); }
.dark .btn-primary { --primary-hover: 90%; }
.btn-primary:hover { background: color-mix(in oklab, var(--primary) var(--primary-hover), var(--background)); }

/* Drei Stufen der durchscheinenden Tönung, wie in der App (dort an .btn).
   Dunkel stärker: Weiß zu 6 % auf Schwarz ergibt kaum einen Ton. */
:is(.btn, .nav-links a, .lang-switch, .nav-toggle) { --tint-1: 6%; --tint-2: 10%; --tint-3: 14%; }
.dark :is(.btn, .nav-links a, .lang-switch, .nav-toggle) { --tint-1: 10%; --tint-2: 14%; --tint-3: 18%; }

/* Wie in der App ohne Rahmen und mit einer leichten, durchscheinenden
   Fläche in --foreground: Er steht meist neben dem primären Knopf im Hero
   oder im Aufruf; eine weiße Fläche wirkte dort wie ein zweiter
   Hauptknopf. Hover und Druck tönen je eine Stufe stärker. */
.btn-outline {
  background: color-mix(in oklab, var(--foreground) var(--tint-1), transparent);
  box-shadow: none;
  color: var(--foreground);
}
.btn-outline:hover { background: color-mix(in oklab, var(--foreground) var(--tint-2), transparent); }
.btn-outline:active { background: color-mix(in oklab, var(--foreground) var(--tint-3), transparent); }

.btn-ghost { background: transparent; box-shadow: none; color: var(--foreground); }

/* Alles Klickbare ohne eigene Fläche — Kopfzeile, Sprachwechsel, Menüknopf —
   tönt bei Hover und Druck wie .btn-ghost der App nur durchscheinend in
   --foreground, damit alles Klickbare ohne Fläche gleich antwortet. */
:is(.btn-ghost, .nav-links a, .lang-switch, .nav-toggle):hover {
  background: color-mix(in oklab, var(--foreground) var(--tint-1), transparent);
  color: var(--foreground);
}
:is(.btn-ghost, .nav-links a, .lang-switch, .nav-toggle):active {
  background: color-mix(in oklab, var(--foreground) var(--tint-2), transparent);
}

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

.site-header {
  position: sticky;
  top: 0;
  z-index: 50;
  background: var(--background);
}

.header-bar {
  display: flex;
  align-items: center;
  gap: 1rem;
  min-height: var(--header-h);
}

.brand {
  display: inline-flex;
  align-items: center;
  gap: 0.625rem;
  font-weight: 600;
  letter-spacing: -0.01em;
  text-decoration: none;
  white-space: nowrap;
}
.brand img { width: 1.625rem; height: 1.625rem; }

/* Das Logo gibt es nur schwarz; dunkel wird es umgekehrt — weißes Sechseck,
   schwarzes Zeichen, genau wie die weiße Fassung der App. */
.dark .logo { filter: invert(1); }

/* Umschalter hell/dunkel: zeigt, wohin er schaltet (Mond hell, Sonne dunkel),
   wie in der App. Ohne Skript schaltet er nichts und fehlt. */
.theme-sun, .dark .theme-moon { display: none; }
.dark .theme-sun { display: block; }
.no-js .theme-toggle { display: none; }

.site-nav {
  display: flex;
  flex: 1;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
}

/* Die Leiste bricht nie um: Wird sie zu eng, klappt die Navigation hinter
   den Knopf (62 rem). Ausgeschrieben braucht sie deutsch rund 60 rem; die
   Abstände sind darum knapp gehalten. Vorher (Lücke 0,5 rem, Innenrand
   0,875 rem) brauchte sie 65 rem, klappte aber erst bei 56 rem ein —
   dazwischen brachen Logo und Links um und rechts lief die Leiste aus der
   Seite, ohne Menüknopf. */
.nav-links {
  display: flex;
  align-items: center;
  gap: 0.25rem;
  margin: 0;
  padding: 0;
  list-style: none;
}
.nav-links li + li { margin: 0; }
.nav-links a {
  display: block;
  padding: 0.5rem 0.75rem;
  white-space: nowrap;
  border-radius: 999px;
  color: var(--muted-foreground);
  font-size: 0.875rem;
  font-weight: 500;
  text-decoration: none;
}
.nav-links a[aria-current="page"] { color: var(--foreground); }

.nav-actions { display: flex; align-items: center; gap: 0.75rem; white-space: nowrap; }

.lang-switch {
  display: inline-flex;
  align-items: center;
  height: 2.5rem;
  padding: 0 0.625rem;
  border-radius: 999px;
  color: var(--muted-foreground);
  font-size: 0.8125rem;
  font-weight: 500;
  text-decoration: none;
}
.lang-switch b { color: var(--foreground); font-weight: 600; }

.nav-toggle {
  display: none;
  margin-left: auto;
  width: 2.5rem;
  height: 2.5rem;
  padding: 0;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: 0;
  border-radius: 999px;
  color: var(--foreground);
  cursor: pointer;
}
.nav-toggle .icon-close { display: none; }
.nav-toggle[aria-expanded="true"] .icon-open { display: none; }
.nav-toggle[aria-expanded="true"] .icon-close { display: block; }

/* ---------- Wolken ------------------------------------------------------- */

/* Jede Fläche mit data-clouds trägt Wolken als Standbild: Vorführfläche,
   Bildkarten, Bento und Funktionsflächen. js/clouds.js
   malt sie mit einem Shader auf ein <canvas> hinter dem Inhalt. Dekoration,
   keine Tokens: Die Paletten stehen nur hier, je fünf Farben von dunkel nach
   hell; das Skript liest sie aus --cloud-1 … --cloud-5. Fehlen Skript oder
   WebGL, bleibt der Verlauf aus denselben Farben stehen. Darüber liegt ein
   Schleier in --background, hell 35 %, dunkel 50 % (Vorführfläche hell
   20 %, siehe dort). Mehrere Paletten, damit
   nicht jede Fläche gleich blau ist; außer "Aurora" alle entsättigt und
   hell, damit die Seite nicht bunt wird. */
[data-clouds="aurora"] { --cloud-1: #1a6fe3; --cloud-2: #6699e6; --cloud-3: #80b3ff; --cloud-4: #b3d9ff; --cloud-5: #e6f2ff; }
[data-clouds="iris"]   { --cloud-1: #6f78d8; --cloud-2: #9196e6; --cloud-3: #b0b4f2; --cloud-4: #d7d8fa; --cloud-5: #f3f3ff; }
[data-clouds="lagoon"] { --cloud-1: #3f8fc4; --cloud-2: #62aec6; --cloud-3: #93cfd6; --cloud-4: #c6e9ea; --cloud-5: #eef9f9; }
[data-clouds="dusk"]   { --cloud-1: #8a78d0; --cloud-2: #a996dc; --cloud-3: #c6b3e6; --cloud-4: #e3d8f2; --cloud-5: #f8f4fc; }
[data-clouds="mist"]   { --cloud-1: #6f87a8; --cloud-2: #8fa3bf; --cloud-3: #b2c2d6; --cloud-4: #d6e0eb; --cloud-5: #f3f6f9; }

[data-clouds] {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  background: linear-gradient(0deg, var(--cloud-2), var(--cloud-4) 70%, var(--cloud-5));
}
[data-clouds]::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  background: color-mix(in oklab, var(--background) 35%, transparent);
}
.dark [data-clouds]::before { background: color-mix(in oklab, var(--background) 50%, transparent); }
.clouds {
  position: absolute;
  inset: 0;
  z-index: -2;
  width: 100%;
  height: 100%;
  opacity: 0;
  transition: opacity 0.6s ease;
}
.clouds[data-ready] { opacity: 1; }
@media (prefers-reduced-motion: reduce) {
  .clouds { transition: none; }
}

/* ---------- Hero --------------------------------------------------------- */

/* Kopf der Startseite: mittig auf Weiß wie jeder Abschnitt. Farbe trägt erst
   die Vorführfläche darunter. */
.hero { padding-block: 6.5rem 4.5rem; }

/* Jeder Kopf steht mittig — der Startseite wie der Unterseiten, mit
   Brotkrumen, Einleitung und Knöpfen. Vorher standen die Unterseiten links
   und ihr Kopf sah anders aus als jeder Abschnittskopf darunter. */
.hero, .page-hero { text-align: center; }
:is(.hero, .page-hero) :is(h1, .hero-lead) { margin-inline: auto; }
:is(.hero, .page-hero) :is(.hero-actions, .trust-row, .breadcrumb ol) { justify-content: center; }

/* Über dem Titel steht allein das EU-Abzeichen, mittig. */
.hero .eu-badge { margin: 0 auto 1.75rem; }

.hero h1 {
  max-width: 20ch;
  margin: 0 auto 1.5rem;
  font-size: clamp(2.25rem, 5.5vw, 3.75rem);
  line-height: 1.05;
  letter-spacing: -0.01em;
  text-wrap: balance;
}

.hero-lead {
  max-width: 42rem;
  margin-bottom: 2.5rem;
  color: var(--muted-foreground);
  font-size: clamp(1.0625rem, 2vw, 1.1875rem);
}

.hero-actions { display: flex; flex-wrap: wrap; gap: 1rem; }

.hero-note { margin: 1.25rem 0 0; color: var(--muted-foreground); font-size: 0.8125rem; }

.trust-row {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem 1.5rem;
  margin: 2.75rem 0 0;
  padding: 0;
  list-style: none;
  color: var(--muted-foreground);
  font-size: 0.8125rem;
}
.trust-row li { display: inline-flex; align-items: center; gap: 0.4375rem; margin: 0; }
.trust-row .icon { width: 1rem; height: 1rem; color: var(--foreground); }

/* EU-Abzeichen: EU-Sterne und die zwei wichtigsten Zusagen als Pille, Rand
   in --border wie .btn-outline. Steht auf der Startseite über dem Titel
   und auf jeder Seite in der Fußzeile. Die Sterne stehen
   für EU-Hosting, nicht für eine Zulassung. */
.eu-badge {
  display: flex;
  align-items: center;
  gap: 0.625rem;
  width: fit-content;
  margin: 0;
  padding: 0.3125rem 1rem 0.3125rem 0.3125rem;
  border: 1px solid var(--border);
  border-radius: 999px;
  color: var(--foreground);
  font-size: 0.875rem;
  font-weight: 500;
}
.eu-badge img { width: 1.75rem; height: 1.75rem; border-radius: 50%; }
.eu-badge span + span { padding-left: 0.625rem; border-left: 1px solid var(--border); }

/* Seitenkopf der Unterseiten */
.page-hero { padding-block: 5.5rem 3.5rem; }
.page-hero h1 {
  max-width: 24ch;
  margin-bottom: 1.25rem;
  font-size: clamp(2rem, 4.5vw, 3rem);
  line-height: 1.08;
  letter-spacing: -0.01em;
  text-wrap: balance;
}
.page-hero .hero-lead { margin-bottom: 0; }
.page-hero .hero-actions { margin-top: 2.5rem; }
.steps + .lead-box, .grid + .lead-box { margin-top: 2.5rem; margin-bottom: 0; }
/* Unter einem Raster mit mittigem Kopf steht der Hinweis ebenfalls mittig. */
.grid + .lead-box { margin-inline: auto; }

.breadcrumb {
  margin: 0 0 1.25rem;
  color: var(--muted-foreground);
  font-size: 0.8125rem;
}
.breadcrumb ol { display: flex; flex-wrap: wrap; gap: 0.25rem; margin: 0; padding: 0; list-style: none; }
.breadcrumb li { display: inline-flex; gap: 0.25rem; margin: 0; }
.breadcrumb li + li::before { content: "/"; opacity: 0.6; }
.breadcrumb a { text-decoration: none; }
.breadcrumb a:hover { color: var(--foreground); text-decoration: underline; }

/* Vorführfläche unter dem Hero: ein Screenshot der App, eine echte Aufnahme
   der Chatseite mit erfundenen Beispieldaten. Er steht auf einer Fläche mit
   stillen Wolken in "Aurora" (.showcase-panel), Innenrand wie beim
   Funktionsblock. Die Fläche ist das einzige Blau im Kopf der Startseite. */
.showcase { padding-block: 0 5rem; }
.showcase-panel { padding: 3.5rem; border-radius: var(--radius-xl); }
/* Hell nur 20 % Schleier wie früher auf der Bühne: Hier steht kein Text,
   und das Blau soll so kräftig stehen wie dort. Dunkel bleibt es bei 50 %. */
.showcase-panel::before { background: color-mix(in oklab, var(--background) 20%, transparent); }
.dark .showcase-panel::before { background: color-mix(in oklab, var(--background) 50%, transparent); }
.showcase-frame {
  max-width: 66rem;
  margin: 0 auto;
  overflow: hidden;
  background: var(--card);
  border: 1px solid oklch(1 0 0 / 0.55);
  border-radius: var(--radius-xl);
  box-shadow: 0 30px 60px -20px oklch(0 0 0 / 0.45), 0 10px 20px -10px oklch(0 0 0 / 0.3);
}
.showcase-figure { margin: 0; }
.showcase-frame img { width: 100%; height: auto; }

/* Über dem Screenshot die aufgeklappte Modellauswahl der App
   (js/model-picker.js) — dieselben Einträge, Maße und Farben wie dort, nur
   in em statt rem. Die Grundgröße folgt der Breite des Screenshots (1080 px
   aufgenommen, daher 100cqi / 1080 * 16 = 1,4815cqi) — so groß wie die App
   im Bild; größer deckte sie den halben Screenshot zu. Sie sitzt rechts
   unten am Rand und ragt um 4 % in die Wolkenfläche hinaus, damit der Chat
   in der Mitte frei bleibt. Dekoration (aria-hidden): Das Bild beschreibt
   der alt-Text. */
.showcase-stage { position: relative; max-width: 66rem; margin: 0 auto; container-type: inline-size; }
.showcase-pop {
  position: absolute;
  right: -4%;
  bottom: 7%;
  z-index: 1;
  width: 17em;
  padding: 0.25em;
  background: var(--card);
  color: var(--foreground);
  border: 1px solid var(--border);
  border-radius: 0.625em;
  box-shadow: 0 24px 48px -16px oklch(0 0 0 / 0.4), var(--shadow-lg);
  font-size: 1.4815cqi;
  line-height: 1.4;
  text-align: left;
}
.pop-item { display: flex; align-items: center; gap: 0.625em; padding: 0.4375em 0.625em; border-radius: 0.5em; }
.pop-item.is-active { background: var(--secondary); }
.showcase-pop .icon { width: 1em; height: 1em; }
.pop-item > span { flex: 1; min-width: 0; }
.pop-item b { display: block; font-size: 0.8125em; font-weight: 500; }
.pop-item small { display: block; margin-top: 0.0625em; color: var(--muted-foreground); font-size: 0.6875em; }
.showcase-pop .pop-check { width: 0.9375em; height: 0.9375em; }
.pop-search {
  display: flex;
  align-items: center;
  gap: 0.5em;
  padding: 0.5em 0.625em 0.625em;
  border-bottom: 1px solid var(--border);
  color: var(--muted-foreground);
}
.pop-search span { font-size: 0.8125em; }
.pop-group {
  padding: 0.75em 0.5em 0.375em;
  color: var(--muted-foreground);
  font-size: 0.6875em;
  font-weight: 600;
  letter-spacing: 0.04em;
  text-transform: uppercase;
}
.showcase-caption {
  margin: 1.25rem 0 0;
  color: var(--muted-foreground);
  font-size: 0.8125rem;
  text-align: center;
}

/* Bild unter dem Kopf der Compliance-Seite: dieselbe Fläche wie die
   Vorführfläche, in der Mitte die EU-Sterne groß als Plakette, links und
   rechts die Zusagen als Kärtchen (wie .media-icons: --card, Schatten).
   Aurora, weil das Blau zur EU passt. Dekoration (aria-hidden): Die
   Zusagen stehen darunter im Überblick als Text. */
.eu-visual {
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  grid-template-rows: repeat(3, auto);
  align-items: center;
  gap: 1rem 3rem;
  max-width: 54rem;
  margin: 0 auto;
  padding-block: 1.5rem;
}
.eu-visual-emblem {
  grid-column: 2;
  grid-row: 1 / -1;
  width: 9rem;
  height: 9rem;
  border-radius: 50%;
  box-shadow: 0 0 0 0.5rem var(--card), 0 24px 48px -16px oklch(0 0 0 / 0.45);
}
.eu-chip {
  display: inline-flex;
  align-items: center;
  gap: 0.625rem;
  padding: 0.75rem 1.125rem;
  background: var(--card);
  color: var(--foreground);
  border-radius: var(--radius-lg);
  box-shadow: 0 12px 24px -12px oklch(0 0 0 / 0.35);
  font-size: 0.9375rem;
  font-weight: 500;
  white-space: nowrap;
}
.eu-chip:nth-child(-n+3) { grid-column: 1; justify-self: end; }
.eu-chip:nth-child(n+5) { grid-column: 3; justify-self: start; }
.eu-chip:is(:nth-child(1), :nth-child(5)) { grid-row: 1; }
.eu-chip:is(:nth-child(2), :nth-child(6)) { grid-row: 2; }
.eu-chip:is(:nth-child(3), :nth-child(7)) { grid-row: 3; }

/* Modellanbieter unter dem Screenshot: gefüllte Markenzeichen (LobeHub,
   Symbole brand-*), Zeichen und Name einfarbig in --foreground, damit keine
   fremde Markenfarbe neben dem Screenshot laut wird. Das Zeichen 20 px wie
   jedes Icon frei im Text, der Name 500 wie die Titel der Bildkarten — so
   steht beides gleich schwer. Nur Anbieter, die im Katalog belegt sind. */
.model-makers { margin-top: 4rem; text-align: center; }
.model-makers-label {
  margin: 0 0 1.25rem;
  color: var(--muted-foreground);
  font-size: 0.8125rem;
}
.model-makers-list {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: 1rem 2rem;
  margin: 0;
  padding: 0;
  list-style: none;
  color: var(--foreground);
  font-size: 1.0625rem;
  font-weight: 500;
  letter-spacing: -0.01em;
}
.model-makers-list li { display: inline-flex; align-items: center; gap: 0.5rem; margin: 0; }
.model-makers-list .icon { width: 1.25rem; height: 1.25rem; }

/* ---------- Abschnitte --------------------------------------------------- */

/* Alle Abschnitte stehen weiß in --background, ohne Linie dazwischen: Sie
   trennt der Weißraum. Farbe tragen nur die Wolkenflächen und der Aufruf. */
.section { padding-block: 5.5rem; }
.section-tight { padding-block: 0 4.5rem; }

/* Der Abschnittskopf steht mittig über seinem Inhalt. */
.section-head { max-width: 46rem; margin: 0 auto 3.5rem; text-align: center; }

.section-label {
  margin: 0 0 1rem;
  color: var(--muted-foreground);
  font-size: 0.6875rem;
  font-weight: 600;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

.section h2 {
  margin-bottom: 1.125rem;
  font-size: clamp(1.875rem, 4vw, 2.75rem);
  line-height: 1.1;
  letter-spacing: -0.01em;
  text-wrap: balance;
}
.section h3 { font-size: 1.0625rem; }

.section-lead { margin: 0; color: var(--muted-foreground); font-size: 1.0625rem; }

.lead-box {
  max-width: var(--text-width);
  margin-bottom: 2.5rem;
  padding: 1.5rem 1.75rem;
  border-left: 3px solid var(--foreground);
  background: var(--secondary);
  border-radius: 0 var(--radius-lg) var(--radius-lg) 0;
  font-size: 1.0625rem;
}
.lead-box p:last-child { margin-bottom: 0; }

/* ---------- Karten ------------------------------------------------------- */

.grid {
  display: grid;
  gap: 1.5rem;
  grid-template-columns: repeat(auto-fit, minmax(16rem, 1fr));
}
.grid-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.grid-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.grid-2 { grid-template-columns: repeat(2, minmax(0, 1fr)); }

/* Karte der Website: eine graue Fläche ohne Rahmen und Schatten, statt der
   weißen Karte mit Rand aus der App — auf der weißen Seite steht sie so
   ruhiger. Hell --secondary, dunkel --card (dort wäre --secondary zu hell).
   --muted-foreground erreicht auf dem Grau keine 4,5 : 1, darum steht der
   Text in --foreground zu 72 %. */
.card, .steps li {
  --surface: var(--secondary);
  background: var(--surface);
  color: var(--card-foreground);
  border-radius: var(--radius-xl);
}
.dark :is(.card, .steps li) { --surface: var(--card); }
.card {
  display: flex;
  flex-direction: column;
  gap: 0.75rem;
  padding: 2rem;
}
.card h3 { margin: 0.5rem 0 0; font-size: 1.0625rem; }
:is(.card, .steps li) :is(p, ul) {
  margin: 0;
  color: color-mix(in oklab, var(--foreground) 72%, transparent);
  font-size: 0.9375rem;
}
/* Tasten und Code hätten auf der grauen Karte dieselbe Fläche wie sie. */
:is(.card, .steps li) :is(code, kbd) { background: var(--background); }
a.card { text-decoration: none; transition: background-color 0.15s; }
a.card:hover { background: color-mix(in oklab, var(--foreground) 5%, var(--surface)); }
.card-link {
  display: inline-flex;
  align-items: center;
  gap: 0.375rem;
  margin-top: auto;
  padding-top: 0.25rem;
  color: var(--foreground);
  font-size: 0.875rem;
  font-weight: 500;
}
.card-link .icon { width: 1rem; height: 1rem; }

/* Offenes Raster: dieselben Karten ohne graue Fläche — Kachel, Titel und
   Text frei auf der Seite, oben eine Linie in --border. Für Raster zwischen
   anderen grauen Flächen: mehrere graue Raster hintereinander wirkten wie
   eine Wand aus Kästen. Auf Weiß reicht --muted-foreground für 4,5 : 1. */
.grid-open { gap: 2.5rem 2rem; }
.grid-open > .card, .dark .grid-open > .card {
  --surface: transparent;
  padding: 1.5rem 0 0;
  border-top: 1px solid var(--border);
  border-radius: 0;
}
.grid-open > .card :is(p, ul) { color: var(--muted-foreground); }
.grid-open > .card .tile { background: var(--secondary); }

/* Zusagen-Raster (Compliance-Überblick): offenes Raster aus neun Zusagen in
   Kurzform. Es bleibt bis zum Handy dreispaltig — zweispaltig stünde die
   neunte allein —, und einspaltig steht die Kachel neben Titel und Text;
   untereinander wären neun Zusagen über 1.600 px hoch. Regeln unter
   Responsive. */

/* Kachel-Icon: flach und ohne eigene Farbe — eine neutrale Fläche, das
   Zeichen in --foreground. Auf weißem Grund (Funktionsköpfe, Fenster)
   --secondary, auf der grauen Karte --background, damit sie sich abhebt.
   Anders als der Mesh-Verlauf der App: Farbige Kacheln auf den Karten und
   neben den Wolkenflächen machten die Seite zu bunt (DESIGN.md). */
.tile {
  display: grid;
  flex: none;
  align-self: flex-start;
  place-items: center;
  width: 2.5rem;
  height: 2.5rem;
  background: var(--secondary);
  color: var(--foreground);
  border-radius: var(--radius-lg);
}
.card .tile { background: var(--background); }
.tile .icon { width: 1.25rem; height: 1.25rem; }

/* Bildkarte: oben eine quadratische Fläche mit Wolken (data-clouds) und einem Motiv
   aus der App, darunter Titel und Text frei auf der Seite. Das Motiv ist
   Dekoration (aria-hidden); was zählt, steht im Text darunter. */
.media-card { display: flex; flex-direction: column; gap: 0.625rem; }
.media-card h3 { margin: 1rem 0 0; font-size: 1.25rem; font-weight: 500; letter-spacing: -0.01em; }
.media-card p { margin: 0; color: var(--muted-foreground); }
.media {
  position: relative;
  display: grid;
  place-items: center;
  aspect-ratio: 1;
  overflow: hidden;
  border-radius: var(--radius-xl);
}
/* Motive: Icons auf Kärtchen (Markenzeichen der Modellanbieter, Bereiche der
   Library) und ein Fenster mit Statistik und Budget. Icons auf einer
   Wolkenfläche stehen flach, ohne eigene Farbe: --card als Kärtchen, Zeichen
   in --foreground — farbige Kacheln auf den Wolken wirkten zu bunt. */
.media-icons { display: grid; grid-template-columns: repeat(3, auto); gap: 1rem; }
.media-icons span {
  display: grid;
  place-items: center;
  width: 4.5rem;
  height: 4.5rem;
  background: var(--card);
  color: var(--foreground);
  border-radius: var(--radius-xl);
  box-shadow: 0 12px 24px -12px oklch(0 0 0 / 0.35);
}
.media-icons .icon { width: 2rem; height: 2rem; }
.media-window {
  position: absolute;
  top: 16%;
  left: 14%;
  width: 100%;
  height: 100%;
  background: var(--card);
  border-radius: var(--radius-xl) 0 0 0;
  box-shadow: 0 20px 40px -12px oklch(0 0 0 / 0.35);
  font-size: 0.8125rem;
  font-weight: 500;
}
.media-window-bar {
  display: flex;
  gap: 0.375rem;
  padding: 0.875rem 1rem;
  border-bottom: 1px solid var(--border);
}
.media-window-bar span { width: 0.5rem; height: 0.5rem; background: var(--border); border-radius: 999px; }
.media-window-body { width: 72%; padding: 1.25rem; }
.media-window-body p { margin: 0 0 0.75rem; }
.media-bars {
  display: flex;
  align-items: flex-end;
  gap: 0.5rem;
  height: 6rem;
  margin-bottom: 1.5rem;
}
.media-bars span {
  flex: 1;
  height: 40%;
  background: color-mix(in oklab, var(--foreground) 12%, transparent);
  border-radius: var(--radius-sm) var(--radius-sm) 0 0;
}
.media-bars span:nth-child(2) { height: 65%; }
.media-bars span:nth-child(3) { height: 50%; }
.media-bars span:nth-child(4) { height: 80%; }
.media-bars span:nth-child(5) { height: 55%; }
.media-bars span:nth-child(6) { height: 70%; }
.media-bars span:nth-child(7) { height: 95%; background: var(--primary); }
.media-meter { height: 0.5rem; background: var(--secondary); border-radius: 999px; }
.media-meter span { display: block; width: 62%; height: 100%; background: var(--primary); border-radius: inherit; }

/* ---------- Bento -------------------------------------------------------- */

/* Karten mit Motiv: graue Karten (wie .card), oben je eine Wolkenfläche mit
   einem Motiv aus der App — einem Fenster, das unten aus der Fläche läuft.
   Das Motiv ist Dekoration (aria-hidden) und zeigt keine Zahlen; was zählt,
   steht im Text darunter. Drei Spalten mit breiten Feldern (.bento-wide) im
   Wechsel, oder zwei gleiche (.bento-2). Ist die Karte ein Verweis (a), wird
   sie im Hover dunkler und das Fenster hebt sich; als article steht sie
   still. Im Einsatz: Hauptfunktionen und „Für wen" (Start), „Drei Regeln"
   (Preise), „Vier Dinge" und „Wirtschaftlichkeit" (Unternehmen). */
.bento { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.bento-wide { grid-column: span 2; }
.bento-2 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
.bento-card {
  --surface: var(--secondary);
  display: flex;
  flex-direction: column;
  padding: 0.5rem;
  background: var(--surface);
  color: var(--card-foreground);
  border-radius: var(--radius-xl);
  text-decoration: none;
  transition: background-color 0.15s;
}
.dark .bento-card { --surface: var(--card); }
a.bento-card:hover { background: color-mix(in oklab, var(--foreground) 5%, var(--surface)); }
.bento-visual {
  display: flex;
  align-items: flex-end;
  justify-content: center;
  height: 17rem;
  padding: 2.25rem 2rem 0;
  border-radius: var(--radius-lg);
  container-type: inline-size;
}
.bento-body { display: flex; flex: 1; flex-direction: column; gap: 0.625rem; padding: 1.5rem 1.5rem 1.25rem; }
.bento-body h3 { margin: 0; font-size: 1.25rem; font-weight: 500; letter-spacing: -0.01em; }
.bento-body :is(p, ul) {
  margin: 0;
  color: color-mix(in oklab, var(--foreground) 72%, transparent);
  font-size: 0.9375rem;
}
.bento-body .card-link { padding-top: 0.5rem; }
/* Knopf (und Verweis) am Fuß einer Bento-Karte, unten bündig. */
.bento-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 0.75rem 1.25rem; margin-top: auto; padding-top: 0.75rem; }
.bento-actions .card-link { margin-top: 0; padding-top: 0; }
.bento-more { margin-top: 3rem; text-align: center; }

/* Das Fenster im Motiv: --card, oben gerundet, unten angeschnitten. Hebt
   sich im Hover leicht, damit die Karte auf den Zeiger antwortet. */
.ui {
  display: flex;
  flex-direction: column;
  width: 100%;
  max-width: 21rem;
  height: 100%;
  overflow: hidden;
  background: var(--card);
  color: var(--card-foreground);
  border-radius: var(--radius-lg) var(--radius-lg) 0 0;
  box-shadow: 0 20px 40px -12px oklch(0 0 0 / 0.35);
  font-size: 0.8125rem;
  font-weight: 500;
  line-height: 1.4;
  transition: transform 0.4s cubic-bezier(0.16, 1, 0.3, 1);
}
.bento-wide .ui { max-width: 38rem; }
.bento-2 .ui { max-width: 28rem; }
a.bento-card:hover .ui { transform: translateY(-0.375rem); }
.ui-bar {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  padding: 0.75rem 1rem;
  border-bottom: 1px solid var(--border);
}
.ui-bar b { font-weight: 600; }
.ui-bar .ui-chip { margin-left: auto; }
.ui-dots { display: flex; gap: 0.375rem; margin-right: 0.25rem; }
.ui-dots span { width: 0.5rem; height: 0.5rem; background: var(--border); border-radius: 999px; }
.ui-body { display: flex; flex-direction: column; gap: 0.75rem; padding: 1rem; }
.ui .icon { width: 1rem; height: 1rem; }
.ui .tile { width: 2rem; height: 2rem; border-radius: var(--radius-md); }
.ui-muted { color: var(--muted-foreground); font-weight: 400; }
/* Platzhalter für Text, der nichts behaupten soll. */
.ui-line {
  display: block;
  height: 0.5rem;
  background: color-mix(in oklab, var(--foreground) 10%, transparent);
  border-radius: 999px;
}
.ui-line.w-90 { width: 90%; }
.ui-line.w-75 { width: 75%; }
.ui-line.w-60 { width: 60%; }
.ui-line.w-40 { width: 40%; }
.ui-chips { display: flex; flex-wrap: wrap; gap: 0.375rem; }
.ui-chip {
  display: inline-flex;
  align-items: center;
  gap: 0.375rem;
  padding: 0.25rem 0.625rem;
  background: var(--secondary);
  border-radius: 999px;
  font-size: 0.75rem;
  white-space: nowrap;
}
.ui-chip .icon { width: 0.875rem; height: 0.875rem; }
.ui-chip.is-active { background: var(--primary); color: var(--primary-foreground); }

/* Chat: Modellwechsel, eine Frage, eine Antwort, das Eingabefeld. */
.ui-msg-user {
  align-self: flex-end;
  max-width: 75%;
  padding: 0.5rem 0.875rem;
  background: var(--secondary);
  border-radius: var(--radius-lg);
}
.ui-msg-ai { display: flex; flex-direction: column; gap: 0.5rem; }
.ui-input {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 0.5rem;
  padding: 0.5rem 0.5rem 0.5rem 0.875rem;
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
}
.ui-send {
  display: grid;
  flex: none;
  place-items: center;
  width: 1.75rem;
  height: 1.75rem;
  background: var(--primary);
  color: var(--primary-foreground);
  border-radius: 999px;
}
.ui-send .icon { width: 0.875rem; height: 0.875rem; }

/* Bild: eine Landschaft aus den Farben der Wolkenfläche, darunter die
   Ansage für die nächste Runde. */
.ui-image {
  position: relative;
  overflow: hidden;
  aspect-ratio: 16 / 10;
  background: linear-gradient(180deg, var(--cloud-2), var(--cloud-4) 60%, var(--cloud-5));
  border-radius: var(--radius-md);
}
.ui-image::before {
  content: "";
  position: absolute;
  top: 22%;
  left: 62%;
  width: 18%;
  aspect-ratio: 1;
  background: var(--cloud-5);
  border-radius: 999px;
  box-shadow: 0 0 2rem 0.5rem color-mix(in oklab, var(--cloud-5) 70%, transparent);
}
.ui-image::after, .ui-image span {
  content: "";
  position: absolute;
  inset: 45% 0 0;
  background: color-mix(in oklab, var(--cloud-1) 70%, var(--cloud-3));
  clip-path: polygon(0 60%, 18% 25%, 32% 50%, 52% 5%, 72% 45%, 86% 30%, 100% 55%, 100% 100%, 0 100%);
}
.ui-image span {
  inset: 62% 0 0;
  background: color-mix(in oklab, var(--cloud-1), oklch(0 0 0) 25%);
  clip-path: polygon(0 40%, 22% 70%, 45% 20%, 65% 60%, 82% 35%, 100% 65%, 100% 100%, 0 100%);
}

/* Assistent: Kopf mit Kachel, darunter, was er mitbringt. */
.ui-head { display: flex; align-items: center; gap: 0.75rem; }
.ui-head b { display: block; font-weight: 600; }
.ui-rows { display: grid; grid-template-columns: auto 1fr; gap: 0.5rem 1rem; align-items: center; }

/* Flow: Eingabe, drei Schritte, Antwort — als Diagramm wie im Editor. */
.ui-flow { display: flex; flex: 1; align-items: center; padding: 1.25rem 1rem 2rem; }
.ui-node {
  display: grid;
  flex: 1 1 0;
  grid-template-columns: auto minmax(0, 1fr);
  align-items: center;
  gap: 0.5rem;
  min-width: 0;
  padding: 0.625rem 0.75rem;
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-xs);
}
.ui-node b { overflow: hidden; font-weight: 600; text-overflow: ellipsis; white-space: nowrap; }
.ui-node .icon { width: 1.125rem; height: 1.125rem; }
.ui-node .ui-line { grid-column: 1 / -1; width: 80%; }
.ui-end { flex: none; padding: 0.375rem 0.75rem; background: var(--secondary); border-radius: 999px; font-size: 0.75rem; }
.ui-link { flex: 0 0 1.25rem; height: 2px; background: var(--border); }
.ui-stack { display: flex; flex: 1.4 1 0; flex-direction: column; gap: 0.75rem; min-width: 0; }
.ui-stack .ui-node { flex: none; }

/* HTML App: links der Code, rechts die laufende App. */
.ui-pair { display: flex; align-items: flex-end; gap: 1rem; width: 100%; max-width: 38rem; height: 100%; }
.ui-pair .ui { flex: 1 1 0; max-width: none; }
.ui-pair .ui-code { flex: 0.8 1 0; height: 85%; }
.ui-code .ui-body { gap: 0.5rem; font-family: var(--font-mono); font-size: 0.75rem; font-weight: 400; }
.ui-code .ui-body span { color: var(--muted-foreground); }
.ui-code .ui-line { margin-left: 1rem; }
.ui-field { display: flex; flex-direction: column; gap: 0.375rem; }
.ui-field .ui-input { padding-block: 0.625rem; }
.ui-button {
  padding: 0.5rem;
  background: var(--primary);
  color: var(--primary-foreground);
  border-radius: 999px;
  text-align: center;
}

/* Library: die sieben Bereiche als Liste. */
.ui-list { display: flex; flex-direction: column; gap: 0.25rem; padding: 0.5rem; }
.ui-list > span { display: flex; align-items: center; gap: 0.75rem; padding: 0.375rem 0.5rem; border-radius: var(--radius-md); }
.ui-list > span:first-child { background: var(--secondary); }
.ui-list > span:first-child .tile { background: var(--background); }
.ui-list .tile { width: 1.75rem; height: 1.75rem; }
.ui-list .icon { width: 0.875rem; height: 0.875rem; }

/* Tabelle im Fenster: Modelle mit Preis, Buchungen, Konten mit Budget.
   Werte stehen als Platzhalter (.ui-line, Balken), nie als Zahl. */
.ui-label { color: var(--muted-foreground); font-size: 0.75rem; font-weight: 400; }
.ui-table {
  display: grid;
  grid-template-columns: minmax(0, 1.4fr) repeat(2, minmax(0, 1fr));
  align-items: center;
  gap: 0.875rem 1rem;
  padding: 1rem;
}
.ui-table.cols-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.ui-table.cols-accounts { grid-template-columns: minmax(0, 1.2fr) minmax(0, 1.6fr) auto; }
.ui-table > span { display: flex; align-items: center; gap: 0.5rem; min-width: 0; }
.ui-table > span > .ui-line { width: 70%; }
.ui-table .media-meter { flex: 1; }
.ui-avatar {
  display: grid;
  flex: none;
  place-items: center;
  width: 1.75rem;
  height: 1.75rem;
  background: var(--secondary);
  border-radius: 999px;
  font-size: 0.6875rem;
  font-weight: 600;
}
.media-meter.is-low span { width: 35%; }
.media-meter.is-high span { width: 85%; }
.ui .media-bars { margin: 0.25rem 0 0; }

/* Prüfliste: Zusagen mit Haken. */
.ui-checks { display: flex; flex-direction: column; gap: 0.75rem; }
.ui-checks > span { display: flex; align-items: center; gap: 0.625rem; }
.ui-check {
  display: grid;
  flex: none;
  place-items: center;
  width: 1.25rem;
  height: 1.25rem;
  background: var(--primary);
  color: var(--primary-foreground);
  border-radius: 999px;
}
.ui .ui-check .icon { width: 0.75rem; height: 0.75rem; }
.ui-chips.is-large { gap: 0.5rem; }
.ui-chips.is-large .ui-chip { padding: 0.375rem 0.75rem; font-size: 0.8125rem; }
.ui-chips.is-large .ui-chip .icon { width: 1rem; height: 1rem; }

/* Offene Fläche: Trägt das Fenster echten Inhalt (Diagramm mit Quellen,
   Rechner), steht es ganz auf der Wolke, wächst mit dem Inhalt und läuft
   nicht aus — abgeschnitten wäre es nicht mehr zu lesen oder zu bedienen. */
.bento-visual.is-open { height: auto; align-items: center; padding: 2rem; }
.ui.is-open { height: auto; max-width: none; border-radius: var(--radius-lg); }
.ui .bars { padding: 1.25rem; color: var(--foreground); font-weight: 400; }
.ui .bar-track { background: var(--secondary); }
.ui .bar-metric { margin: 0.375rem 0 0; color: var(--muted-foreground); font-size: 0.8125rem; }
.ui .calc-fields { margin-top: 0; }
.bento-body .sources { margin-top: 0.25rem; }
.bento-body p.sources { padding-left: 0; }

/* Vergleich „Ein Konto statt vier Abos": links die Einzelabos mit belegten
   Listenpreisen und ihrer Summe, rechts Meteor-AI. Die Preise sind echter
   Inhalt (Quelle und Stand darunter), darum offene Fläche. */
.ui-table.cols-price { grid-template-columns: minmax(0, 1fr) auto; }
.ui-table > .ui-cell-stack { flex-direction: column; align-items: flex-start; gap: 0; }
.ui-table > .ui-num { justify-content: flex-end; font-variant-numeric: tabular-nums; }
.ui-total {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  margin: 0 1rem;
  padding: 0.875rem 0 1rem;
  border-top: 1px solid var(--border);
  font-size: 1rem;
  font-weight: 600;
  font-variant-numeric: tabular-nums;
}
.ui-total span:first-child { font-weight: 500; }
/* Rot die Kosten der Einzelabos, grün der Preis von Pro bei Meteor-AI: Der
   Unterschied soll auf einen Blick lesbar sein, bevor man Zahlen vergleicht. */
.is-cost .ui-num, .ui-total.is-cost span:last-child { color: var(--destructive); }
.ui-total.is-gain span:last-child { color: var(--success); }
.ui-logo { flex: none; width: 1.25rem; height: 1.25rem; }
/* Hervorgehobene Karte: Rahmen und Abzeichen in --success, das Abzeichen
   ragt über die Oberkante. Text in --background, damit er hell auf dem
   dunklen Grün und dunkel auf dem hellen Grün des dunklen Designs steht. */
.bento-card.is-highlight { position: relative; box-shadow: 0 0 0 2px var(--success); }
.bento-badge {
  position: absolute;
  top: 0;
  left: 50%;
  z-index: 1;
  padding: 0.25rem 0.875rem;
  background: var(--success);
  color: var(--background);
  border-radius: 999px;
  font-size: 0.8125rem;
  font-weight: 600;
  white-space: nowrap;
  transform: translate(-50%, -50%);
}

/* Hinweis über dem Rechner: Ohne ihn las sich der Rechner wie ein Bild mit
   Zahlen. Er steht frei über der grauen Karte, ohne Fläche, und nimmt ihr
   keine Höhe — so bleiben Studien und Rechner gleich hoch. Der Pfeil wippt
   und das erste Feld trägt einen pulsierenden Hof, bis jemand ein Feld
   anfasst (data-touched aus js/site.js) — dann ist klar, dass man rechnen
   kann, und die Bewegung hört auf. Ohne Skript gibt es keine Felder und
   darum auch keinen Hinweis. */
.calc { position: relative; }
.calc-cue {
  position: absolute;
  bottom: calc(100% + 0.5rem);
  left: 50%;
  display: inline-flex;
  align-items: center;
  gap: 0.375rem;
  margin: 0;
  transform: translateX(-50%);
  color: var(--foreground);
  font-size: 0.9375rem;
  font-weight: 500;
  white-space: nowrap;
}
.calc-cue .icon { width: 1rem; height: 1rem; }
.no-js .calc-cue { display: none; }
@media (prefers-reduced-motion: no-preference) {
  .calc:not([data-touched]) .calc-cue .icon { animation: cue-bob 1.4s ease-in-out infinite; }
  .calc:not([data-touched]) .calc-fields label:first-child .input { animation: cue-ring 2s ease-out infinite; }
}
@keyframes cue-bob {
  0%, 100% { transform: translateY(-2px); }
  50% { transform: translateY(3px); }
}
@keyframes cue-ring {
  0% { box-shadow: 0 0 0 0 color-mix(in oklab, var(--ring) 60%, transparent); }
  70%, 100% { box-shadow: 0 0 0 8px color-mix(in oklab, var(--ring) 0%, transparent); }
}
.bento-body .calc-note { font-size: 0.8125rem; }

/* Schmale Flächen: Nebensachen fallen weg, damit das Motiv lesbar bleibt. */
@container (max-width: 26rem) {
  .ui-end, .ui-end + .ui-link, .ui-flow > .ui-link:nth-last-child(2) { display: none; }
  .ui-pair .ui-code { display: none; }
  /* Der Flow steht senkrecht, ein Schritt je Zeile. */
  .ui-flow { flex-direction: column; align-items: stretch; padding: 1rem 1.25rem; }
  .ui-flow > .ui-node, .ui-stack { flex: none; }
  .ui-stack .ui-node + .ui-node, .ui-node .ui-line { display: none; }
  .ui-link { flex: 0 0 0.75rem; align-self: center; width: 2px; height: auto; }
  .ui-bar .ui-chips .ui-chip:nth-child(n+4) { display: none; }
}
@media (prefers-reduced-motion: reduce) {
  .ui { transition: none; }
  a.bento-card:hover .ui { transform: none; }
}

/* Funktionsblock: Text links, rechts eine Fläche mit Wolken (data-clouds),
   darauf die Liste als Fenster. */
.feature {
  display: grid;
  gap: 2.5rem 4.5rem;
  grid-template-columns: minmax(0, 2fr) minmax(0, 3fr);
  align-items: center;
}
.feature-head { display: flex; flex-direction: column; align-items: flex-start; gap: 1.125rem; }
.feature-head h2, .feature-head .section-label { margin: 0; }
.feature-head h2 { font-size: clamp(1.625rem, 3vw, 2.25rem); }
.feature-head p { margin: 0; color: var(--muted-foreground); }
.feature-head .btn { margin-top: 0.875rem; }
.feature-panel { padding: 3.5rem; border-radius: var(--radius-xl); }
.feature .feature-panel > :is(ul, figure) {
  margin: 0;
  padding: 2rem;
  background: var(--card);
  color: var(--card-foreground);
  border-radius: var(--radius-xl);
  box-shadow: 0 20px 40px -12px oklch(0 0 0 / 0.35);
}
/* Zusagen als Liste im Fenster: Kachel links, Titel und Text daneben. */
.promise-list { list-style: none; }
.promise-list li { display: flex; gap: 1rem; margin: 0; }
.promise-list li + li { margin-top: 1rem; padding-top: 1rem; border-top: 1px solid var(--border); }
.promise-list h3 { margin: 0 0 0.25rem; font-size: 0.9375rem; }
.promise-list p { margin: 0; color: var(--muted-foreground); font-size: 0.9375rem; }
.checklist { margin: 0; padding: 0; list-style: none; }
.checklist li {
  position: relative;
  padding-left: 1.75rem;
  margin: 0;
}
.checklist li + li { margin-top: 0.875rem; }
.checklist li::before {
  content: "";
  position: absolute;
  left: 0;
  top: 0.4em;
  width: 0.9rem;
  height: 0.9rem;
  background: currentColor;
  -webkit-mask: url("../assets/check.svg") center / contain no-repeat;
  mask: url("../assets/check.svg") center / contain no-repeat;
}

/* Funktionsblock mit App-Fenster (Funktionsseite): Text und Liste links,
   rechts auf der Wolke ein Fenster aus der App, das unten aus der Fläche
   läuft — wie das Motiv einer Bento-Karte. Jeder zweite Block steht
   gespiegelt (.is-reversed). Vorher trug jede Fläche nur die Liste; zehn
   gleiche Textfenster hintereinander zeigten nicht, wie die App aussieht. */
.feature-app { grid-template-columns: repeat(2, minmax(0, 1fr)); align-items: stretch; }
/* Die Fläche wächst mit dem Text: Ist die Liste lang, stand der Text sonst
   über die Fläche hinaus. Kürzerer Text steht mittig daneben. */
.feature-app .feature-head { align-self: center; }
.feature-app.is-reversed .feature-panel { order: -1; }
.feature-app .feature-panel {
  display: flex;
  align-items: flex-end;
  justify-content: center;
  min-height: 28rem;
  padding: 3rem 3rem 0;
  container-type: inline-size;
}
/* Das Fenster bestimmt die Höhe nicht mit (contain): Es füllt die Fläche
   und läuft unten aus, statt sie aufzudrücken. */
.feature-app .ui { max-width: 28rem; contain: size; }
.feature-head .checklist { margin-top: 0.375rem; color: var(--muted-foreground); font-size: 0.9375rem; }
.feature-head .checklist li::before { color: var(--foreground); }
.feature-head .checklist strong { color: var(--foreground); font-weight: 600; }

/* Bausteine der Fenster auf der Funktionsseite. Wie bei Bento: keine
   Zahlen, Werte als Platzhalter (.ui-line, Balken). */
.ui-tiles { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0.75rem; }
.ui-tiles > span {
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
  padding: 0.75rem;
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
}
.ui-tiles .tile { width: 1.75rem; height: 1.75rem; }
.ui-tiles .icon { width: 0.875rem; height: 0.875rem; }
/* Ein Absatz im Fenster, abgesetzt: Gedankengang, Anhang, Ausgabe. */
.ui-box {
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
  padding: 0.625rem 0.75rem;
  background: var(--secondary);
  border-radius: var(--radius-md);
}
.ui-box > b { display: flex; align-items: center; gap: 0.375rem; font-weight: 500; }
.ui-file { display: flex; align-items: center; gap: 0.625rem; min-width: 0; padding: 0.5rem 0.75rem 0.5rem 0.5rem; border: 1px solid var(--border); border-radius: var(--radius-lg); }
.ui-file .tile { width: 1.75rem; height: 1.75rem; }
.ui-file b { display: block; font-weight: 600; }
.ui-files { display: flex; flex-wrap: wrap; gap: 0.5rem; }
.ui-thumb {
  width: 3.125rem;
  aspect-ratio: 1;
  background: linear-gradient(180deg, var(--cloud-2), var(--cloud-5));
  border-radius: var(--radius-lg);
}
.ui-image.is-small { width: 70%; align-self: flex-start; }
.ui-image.is-clear { background: linear-gradient(180deg, var(--cloud-4), var(--cloud-5) 70%); }
/* Schalter und Regler wie in der App: Schiene in --secondary, an in --primary. */
.ui-switch {
  display: inline-flex;
  flex: none;
  width: 1.875rem;
  height: 1.125rem;
  padding: 0.125rem;
  background: var(--primary);
  border-radius: 999px;
}
.ui-switch::after { content: ""; width: 0.875rem; height: 0.875rem; margin-left: auto; background: var(--primary-foreground); border-radius: 999px; }
.ui-switch.is-off { background: color-mix(in oklab, var(--foreground) 14%, transparent); }
.ui-switch.is-off::after { margin-left: 0; background: var(--card); box-shadow: var(--shadow-xs); }
.ui-range { position: relative; height: 0.375rem; background: var(--secondary); border-radius: 999px; }
.ui-range span { position: absolute; inset: 0 auto 0 0; width: 40%; background: var(--primary); border-radius: inherit; }
.ui-range span::after {
  content: "";
  position: absolute;
  top: 50%;
  right: -0.5rem;
  width: 1rem;
  height: 1rem;
  background: var(--card);
  border: 2px solid var(--primary);
  border-radius: 999px;
  transform: translateY(-50%);
}
.ui-split { display: flex; align-items: center; justify-content: space-between; gap: 0.75rem; }
/* Speicher: ein Balken aus drei Teilen. */
.ui-stacked { display: flex; gap: 2px; height: 0.5rem; overflow: hidden; border-radius: 999px; background: var(--secondary); }
.ui-stacked span { background: var(--primary); }
.ui-stacked span:nth-child(1) { width: 34%; }
.ui-stacked span:nth-child(2) { width: 22%; background: color-mix(in oklab, var(--primary) 55%, transparent); }
.ui-stacked span:nth-child(3) { width: 12%; background: color-mix(in oklab, var(--primary) 25%, transparent); }
/* Flow im Editor: Schritte untereinander, je mit Ziel der Ausgabe. */
.ui-steps { display: flex; flex-direction: column; align-items: stretch; }
.ui-steps .ui-node { grid-template-columns: auto minmax(0, 1fr) auto; }
.ui-steps .ui-link { flex: none; align-self: center; width: 2px; height: 0.75rem; }
.ui-steps .ui-end { align-self: center; }
.ui kbd { padding: 0.125rem 0.375rem; background: var(--secondary); font-size: 0.6875rem; }
.ui-bar .is-right { display: flex; gap: 0.25rem; margin-left: auto; }
.ui-chip .ui-line { width: 2.5rem; height: 0.375rem; }
.ui-files { justify-content: flex-end; }
.ui-check.is-off { background: var(--card); box-shadow: inset 0 0 0 1.5px var(--border); }

/* Stufen im Kopf eines Funktionsblocks: nummeriert, Titel fett davor. */
.stage-list { margin: 0.25rem 0 0; padding-left: 1.25rem; color: var(--muted-foreground); }
.stage-list li + li { margin-top: 0.75rem; }
.stage-list strong { color: var(--foreground); font-weight: 600; }

/* ---------- Diagramme ---------------------------------------------------- */

/* Einfarbig in --foreground: Ein Diagramm mit einer Reihe braucht keine
   Farbe, und die Seite soll ruhig bleiben. Linien 2 px (vector-effect, damit
   sie beim Skalieren nicht dicker werden), Punkte mit Ring in --card, Raster
   in --border. Beschriftungen als HTML statt im SVG, damit sie auf dem
   Telefon nicht mitschrumpfen. Ein Schema sagt, dass es eines ist. */
.chart { margin: 0; }
.chart-head { display: flex; flex-wrap: wrap; align-items: baseline; justify-content: space-between; gap: 0.5rem 1rem; margin-bottom: 1rem; }
.chart-title { margin: 0 0 1rem; color: var(--foreground); font-size: 0.9375rem; font-weight: 600; }
.chart-head .chart-title { margin: 0; }
.chart-legend { display: flex; gap: 1rem; margin: 0; padding: 0; list-style: none; color: var(--muted-foreground); font-size: 0.8125rem; }
.chart-legend li { display: inline-flex; align-items: center; gap: 0.375rem; margin: 0; }
.chart-key { width: 1rem; border-top: 2px solid var(--foreground); }
.chart-key-base { border-top-style: dashed; border-color: var(--muted-foreground); }
.chart svg { width: 100%; height: auto; overflow: visible; }
.chart-grid { stroke: var(--border); stroke-width: 1; vector-effect: non-scaling-stroke; }
.chart-axis { stroke: var(--muted-foreground); stroke-width: 1; vector-effect: non-scaling-stroke; }
.chart-area { fill: color-mix(in oklab, var(--foreground) 7%, transparent); }
.chart-line { fill: none; stroke: var(--foreground); stroke-width: 2; stroke-linecap: round; vector-effect: non-scaling-stroke; }
.chart-base { stroke: var(--muted-foreground); stroke-width: 2; stroke-dasharray: 6 6; vector-effect: non-scaling-stroke; }
.chart-dot { fill: var(--card); stroke: var(--foreground); stroke-width: 2; vector-effect: non-scaling-stroke; }
.chart-x { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 0.5rem; margin-top: 0.75rem; color: var(--muted-foreground); font-size: 0.8125rem; text-align: center; }
.chart-x b { color: var(--foreground); font-weight: 500; }
.chart-note { margin: 1rem 0 0; color: var(--muted-foreground); font-size: 0.8125rem; }

/* Balken: eine Reihe, Länge = Wert auf einer Skala von 0 bis 100 %; Zahl
   rechts in tabular-nums, Messgröße darunter. Auf der grauen Karte läuft die
   Spur in --background. */
.bars { display: grid; gap: 1.25rem; margin: 0; padding: 0; list-style: none; }
.bars li { margin: 0; }
.card .bars { color: var(--foreground); }
.bar-label { display: flex; justify-content: space-between; gap: 1rem; font-size: 0.9375rem; }
.bar-label b { font-weight: 600; font-variant-numeric: tabular-nums; }
.bar-track { height: 0.625rem; margin-top: 0.5rem; overflow: hidden; background: var(--background); border-radius: 999px; }
.bar-fill { display: block; width: var(--v); height: 100%; background: var(--foreground); border-radius: 0 4px 4px 0; }
.card .bar-metric { margin-top: 0.375rem; font-size: 0.8125rem; }
.bar-metric sup a { color: inherit; }
.sources { margin: 1.75rem 0 0; padding-left: 1.25rem; color: var(--muted-foreground); font-size: 0.75rem; }
.sources li + li { margin-top: 0.25rem; }
.sources a { color: inherit; }

/* ---------- Rechner ------------------------------------------------------ */

/* Eingabefeld wie .input der App (Rand --input, Fokus mit Hof in --ring),
   aber 40 px hoch wie die Knöpfe der Website. Der Rechner rechnet mit
   js/site.js; ohne Skript fehlen die Felder und das Beispiel steht fest da. */
.input {
  width: 100%;
  height: 2.5rem;
  padding: 0 0.875rem;
  border: 1px solid var(--input);
  border-radius: var(--radius-md);
  background: var(--background);
  color: var(--foreground);
  box-shadow: var(--shadow-xs);
  font: inherit;
  font-size: 0.9375rem;
  font-variant-numeric: tabular-nums;
  transition: border-color 0.15s, box-shadow 0.15s;
}
.input:focus { outline: none; border-color: var(--ring); box-shadow: 0 0 0 3px color-mix(in oklab, var(--ring) 40%, transparent); }
.calc-fields { display: grid; gap: 1rem; margin-top: 0.75rem; }
.calc-fields label { display: grid; gap: 0.375rem; font-size: 0.875rem; font-weight: 500; }
.calc-result { display: grid; grid-template-columns: repeat(auto-fit, minmax(10rem, 1fr)); gap: 1rem; margin: 1rem 0 0; padding-top: 1.25rem; border-top: 1px solid var(--border); }
.calc-result dt { color: color-mix(in oklab, var(--foreground) 72%, transparent); font-size: 0.8125rem; }
.calc-result dd { margin: 0.125rem 0 0; font-size: 1.75rem; font-weight: 600; letter-spacing: -0.02em; font-variant-numeric: tabular-nums; }
.card .calc-note { font-size: 0.8125rem; }
.js .calc-defaults, .no-js .calc-fields { display: none; }

/* ---------- Ablauf ------------------------------------------------------- */

.steps { display: grid; gap: 1.5rem; margin: 0; padding: 0; list-style: none; counter-reset: step; grid-template-columns: repeat(3, minmax(0, 1fr)); }
.steps li {
  position: relative;
  margin: 0;
  padding: 2rem;
  counter-increment: step;
}
.steps li::before {
  content: counter(step);
  display: grid;
  place-items: center;
  width: 1.75rem;
  height: 1.75rem;
  margin-bottom: 1rem;
  background: var(--primary);
  color: var(--primary-foreground);
  border-radius: 999px;
  font-size: 0.8125rem;
  font-weight: 600;
}
.steps h3 { margin-bottom: 0.375rem; font-size: 1.0625rem; }

/* ---------- Tabellen ----------------------------------------------------- */

.table-wrap {
  overflow-x: auto;
  background: var(--card);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
}
table { width: 100%; border-collapse: collapse; font-size: 0.9375rem; }
th, td { padding: 0.75rem 1rem; border-bottom: 1px solid var(--border); text-align: left; vertical-align: top; }
tr:last-child > th, tr:last-child > td { border-bottom: 0; }
thead th {
  background: var(--secondary);
  color: var(--muted-foreground);
  font-size: 0.75rem;
  font-weight: 600;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  white-space: nowrap;
}
tbody th { width: 34%; font-weight: 500; }
td { color: var(--muted-foreground); }
td strong { color: var(--foreground); font-weight: 500; }

/* ---------- FAQ ---------------------------------------------------------- */

.faq { max-width: var(--text-width); margin-inline: auto; }
.faq details { border-bottom: 1px solid var(--border); }
.faq summary {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding: 1.5rem 0;
  font-size: 1.0625rem;
  font-weight: 500;
  cursor: pointer;
  list-style: none;
}
.faq summary::-webkit-details-marker { display: none; }
.faq summary::after {
  content: "";
  flex: none;
  width: 1rem;
  height: 1rem;
  background: var(--muted-foreground);
  -webkit-mask: url("../assets/chevron-down.svg") center / contain no-repeat;
  mask: url("../assets/chevron-down.svg") center / contain no-repeat;
  transition: transform 0.15s;
}
.faq details[open] summary::after { transform: rotate(180deg); }
.faq .answer { padding-bottom: 1.5rem; color: var(--muted-foreground); }
.faq .answer p:last-child { margin-bottom: 0; }

/* ---------- Preise ------------------------------------------------------- */

.notice {
  display: flex;
  gap: 0.75rem;
  padding: 1.25rem 1.5rem;
  background: color-mix(in oklab, var(--warning) 12%, var(--background));
  border: 1px solid color-mix(in oklab, var(--warning) 35%, var(--background));
  border-radius: var(--radius-lg);
  color: var(--foreground);
  font-size: 0.9375rem;
}
.notice .icon { color: var(--warning-foreground); margin-top: 0.125rem; }
.notice p:last-child { margin-bottom: 0; }
.notice-narrow { max-width: var(--text-width); margin-bottom: 2.5rem; }

/* Tarifkarten: graue Karten wie .card, Name, Preis, ein Satz, Prüfliste und
   der Knopf unten bündig. Nur Pro trägt .btn-primary (einer je Fläche), die
   übrigen .btn-outline. Pro ist hervorgehoben wie die Meteor-AI-Karte im
   Vergleich (Rahmen 2 px, Abzeichen über der Oberkante), aber in --primary
   statt --success: Das Grün bleibt dem Vergleich, Schwarz passt zum Knopf.
   Vier Tarife stehen in .grid-4, mit 1.5rem Innenrand statt 2rem, damit
   vier Spalten nebeneinander Platz für die Prüflisten lassen. */
.plan.is-highlight { position: relative; box-shadow: 0 0 0 2px var(--primary); }
.plan .bento-badge { background: var(--primary); color: var(--primary-foreground); }
.plans > .plan { padding: 1.5rem; }
.plan h2 { margin: 0; font-size: 1.25rem; font-weight: 500; letter-spacing: 0; }
.card .plan-price { margin: 0; color: var(--foreground); font-size: 2.25rem; font-weight: 600; line-height: 1.2; letter-spacing: -0.01em; font-variant-numeric: tabular-nums; }
.card .plan-price small { color: color-mix(in oklab, var(--foreground) 72%, transparent); font-size: 0.9375rem; font-weight: 400; letter-spacing: 0; }
.plan .checklist { margin: 0.5rem 0 1rem; }
.plan .checklist li + li { margin-top: 0.625rem; }
.plan .btn { margin-top: auto; }
.plans-note { margin: 1.5rem 0 0; color: var(--muted-foreground); font-size: 0.8125rem; text-align: center; }

/* ---------- Text (Rechtliches) ------------------------------------------- */

/* Mittig unter dem mittigen Seitenkopf, wie die FAQ; der Text selbst bleibt
   linksbündig. */
.prose { max-width: var(--text-width); margin-inline: auto; }
.prose h2 { margin: 3rem 0 1rem; font-size: 1.375rem; }
.prose h3 { margin: 2rem 0 0.625rem; font-size: 1.0625rem; }
.prose h2:first-child { margin-top: 0; }
.prose p, .prose li { color: color-mix(in oklab, var(--foreground) 82%, transparent); }
.prose a { text-decoration: underline; }
.prose .meta { color: var(--muted-foreground); font-size: 0.875rem; }
.prose .todo {
  padding: 0.125rem 0.375rem;
  background: color-mix(in oklab, var(--warning) 18%, var(--background));
  border-radius: var(--radius-sm);
  color: var(--warning-foreground);
}

/* ---------- Aufruf ------------------------------------------------------- */

/* Aufruf am Seitenende: ein graues Band über die ganze Breite, dieselbe
   Fläche wie die Karten (hell --secondary, dunkel --card) — schlicht, ohne
   Verlauf oder Wolken; die bleiben den Flächen vorbehalten. Der Text
   steht wie auf der Karte in --foreground zu 72 % (--muted-foreground
   reicht auf dem Grau nicht für 4,5 : 1), der zweite Knopf in --background,
   damit er sich vom Grau abhebt. */
.cta {
  --surface: var(--secondary);
  padding-block: 7rem;
  background: var(--surface);
  text-align: center;
}
.dark .cta { --surface: var(--card); }
.cta h2 {
  margin-bottom: 1.125rem;
  font-size: clamp(2rem, 5vw, 3.25rem);
  line-height: 1.08;
  letter-spacing: -0.01em;
  text-wrap: balance;
}
.cta p { max-width: 40rem; margin: 0 auto 2.25rem; color: color-mix(in oklab, var(--foreground) 72%, transparent); font-size: 1.0625rem; }
.cta .btn-outline { background: var(--background); }
.cta .btn-outline:hover { background: color-mix(in oklab, var(--foreground) 5%, var(--background)); }
.cta .btn-outline:active { background: color-mix(in oklab, var(--foreground) 10%, var(--background)); }
.cta-actions { display: flex; flex-wrap: wrap; justify-content: center; gap: 1rem; }

/* ---------- Fusszeile ---------------------------------------------------- */

.site-footer {
  padding-block: 5rem 2.5rem;
  border-top: 1px solid var(--border);
  background: var(--background);
  font-size: 0.875rem;
}
/* Unter dem grauen Aufruf ist die Kante schon da. */
main:has(> .cta:last-child) + .site-footer { border-top: 0; }
.footer-grid {
  display: grid;
  gap: 2.5rem;
  grid-template-columns: minmax(0, 1.4fr) repeat(3, minmax(0, 1fr));
}
.footer-about p { max-width: 22rem; margin: 0.75rem 0 0; color: var(--muted-foreground); }
/* Dasselbe EU-Abzeichen wie im Hero, hier linksbündig unter dem Satz zu
   EU-Hosting. Die Regel für Absätze darüber (grau, 22 rem) gilt hier nicht. */
.footer-about .eu-badge { max-width: none; margin: 1.25rem 0 0; color: var(--foreground); }
.site-footer h2 {
  margin-bottom: 0.75rem;
  color: var(--muted-foreground);
  font-size: 0.6875rem;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}
.site-footer ul { margin: 0; padding: 0; list-style: none; }
.site-footer li + li { margin-top: 0.4375rem; }
.site-footer a { text-decoration: none; }
.site-footer a:hover { text-decoration: underline; }
.footer-bottom {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: 0.5rem 1.5rem;
  margin-top: 3.5rem;
  padding-top: 1.5rem;
  border-top: 1px solid var(--border);
  color: var(--muted-foreground);
  font-size: 0.8125rem;
}
/* „Made in Germany" mit Streifen in Schwarz-Rot-Gold. Die Farben der
   Bundesflagge sind Dekoration wie die Wolken, keine Tokens. Der Hof hält
   das Schwarz im dunklen Design sichtbar. */
.made-in {
  --flag-black: #000;
  --flag-red: #d00;
  --flag-gold: #ffce00;
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
}
.made-in::before {
  content: "";
  width: 1.25rem;
  height: 0.75rem;
  border-radius: 2px;
  background: linear-gradient(var(--flag-black) 0 33.34%, var(--flag-red) 0 66.67%, var(--flag-gold) 0);
  box-shadow: 0 0 0 1px color-mix(in oklab, var(--foreground) 14%, transparent);
}

/* ---------- Sprachwahl und 404 ------------------------------------------- */

.chooser {
  display: grid;
  place-items: center;
  min-height: 100vh;
  padding-block: 3rem;
  text-align: center;
}
.chooser-logo { margin: 0 auto 1.25rem; }
.chooser h1 { margin-bottom: 1rem; font-size: clamp(2rem, 6vw, 3rem); letter-spacing: -0.01em; }
.chooser-lead { max-width: 30rem; margin: 0 auto 0.5rem; color: var(--muted-foreground); }
.chooser-actions { display: flex; flex-wrap: wrap; justify-content: center; gap: 0.75rem; margin-top: 2rem; }

/* ---------- Bewegung ----------------------------------------------------- */

/* Inhalte erscheinen, statt einfach dazustehen: leicht von unten (1 rem),
   ausblendend in .7s mit der Kurve der App-Dialoge. Länger als die .15s der
   App, weil hier ein ganzer Block auftaucht und kein Zustand wechselt.
   Der Kopf jeder Seite steigt beim Laden der Reihe nach auf (nur CSS, mit
   .js aus dem <head>). Was weiter unten steht, blendet js/site.js beim
   Hineinscrollen ein (.reveal → .is-visible), mehrere zugleich nacheinander;
   was beim Laden schon zu sehen ist, fasst es nicht an. Ohne Skript oder bei
   prefers-reduced-motion steht alles sofort da. */
@keyframes rise {
  from { opacity: 0; transform: translateY(1rem); }
}
.js .page-hero .container > * {
  animation: rise 0.7s cubic-bezier(0.16, 1, 0.3, 1) both;
}
.js .page-hero .container > :nth-child(2) { animation-delay: 0.06s; }
.js .page-hero .container > :nth-child(n+3) { animation-delay: 0.12s; }

/* Die Startseite tritt deutlicher auf: weiter von unten (2 rem), aus der
   Unschärfe, in 1s und je .12s versetzt — der Kopf ist das Erste, was man
   sieht, und soll als Auftritt wirken. Der Screenshot kommt danach aus 4 rem
   und leicht verkleinert herauf. */
@keyframes hero-rise {
  from { opacity: 0; transform: translateY(2rem); filter: blur(8px); }
}
@keyframes showcase-rise {
  from { opacity: 0; transform: translateY(4rem) scale(0.96); }
}
.js .hero .container > * {
  animation: hero-rise 1s cubic-bezier(0.16, 1, 0.3, 1) 0.1s both;
}
.js .hero .container > :nth-child(2) { animation-delay: 0.22s; }
.js .hero .container > :nth-child(3) { animation-delay: 0.34s; }
.js .hero .container > :nth-child(4) { animation-delay: 0.46s; }
.js .hero .container > :nth-child(n+5) { animation-delay: 0.58s; }
.js .showcase-figure {
  animation: showcase-rise 1.2s cubic-bezier(0.16, 1, 0.3, 1) 0.7s both;
}
/* Die Modellauswahl klappt nach dem Screenshot auf: kurz, von leicht unten und
   leicht verkleinert, wie die Menüs der App (dialog-in). */
@keyframes pop-in {
  from { opacity: 0; transform: translateY(0.75rem) scale(0.96); }
}
.js .showcase-pop { animation: pop-in 0.6s cubic-bezier(0.16, 1, 0.3, 1) 1.5s both; }

/* Der Übergang hängt nur am Erscheinen: Das Verstecken beim Laden geschieht
   sofort, sonst blendete ein Block erst aus, bevor er einblendet. */
.reveal { opacity: 0; transform: translateY(1rem); }
.reveal.is-visible {
  opacity: 1;
  transform: none;
  transition: opacity 0.7s cubic-bezier(0.16, 1, 0.3, 1), transform 0.7s cubic-bezier(0.16, 1, 0.3, 1);
  transition-delay: var(--reveal-delay, 0s);
}
/* Balken wachsen mit, kurz nach ihrer Karte. */
.reveal .bar-fill { transform: scaleX(0); transform-origin: left; }
.reveal.is-visible .bar-fill {
  transform: none;
  transition: transform 1s cubic-bezier(0.16, 1, 0.3, 1) calc(var(--reveal-delay, 0s) + 0.2s);
}

/* ---------- Responsive --------------------------------------------------- */

@media (max-width: 62rem) {
  .grid-3, .bento { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  /* Vier Tarife zu zweit nebeneinander: Free neben Pro, Ultimate neben
     Enterprise. Vier schmale Spalten ließen die Prüflisten zerfallen. */
  .grid-4 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .grid-3.grid-facts { grid-template-columns: repeat(3, minmax(0, 1fr)); }
  .bento-wide { grid-column: auto; }
  .feature { grid-template-columns: minmax(0, 1fr); }
  .feature-panel, .showcase-panel { padding: 2.5rem; }
  /* Einspaltig steht das Fenster immer unter dem Text. */
  .feature-app.is-reversed .feature-panel { order: 0; }
  .feature-app .feature-panel { min-height: 0; height: 25rem; padding: 2.5rem 2.5rem 0; }
  .footer-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .footer-about { grid-column: 1 / -1; }
  /* Acht Anbieter passen hier nicht mehr in eine Zeile; schmaler gefasst
     bricht die Liste in 4 + 4 statt in 7 + 1 um. */
  .model-makers-list { max-width: 33rem; margin-inline: auto; }
}

@media (max-width: 62rem) {
  /* Ab hier klappt die Navigation hinter den Knopf — aber nur mit Skript.
     Eigener Block, aber derselbe Umbruch wie oben; vorher 56 rem, da passte
     die ausgeschriebene Leiste schon nicht mehr (siehe .nav-links). */
  .js .nav-toggle { display: inline-flex; }
  .js .site-nav {
    position: absolute;
    top: 100%;
    left: 0;
    right: 0;
    display: none;
    flex-direction: column;
    align-items: stretch;
    gap: 1rem;
    max-height: calc(100vh - var(--header-h));
    overflow-y: auto;
    padding: 1rem var(--gutter) 1.5rem;
    background: var(--background);
    border-bottom: 1px solid var(--border);
    box-shadow: var(--shadow-lg);
  }
  .js .site-header[data-open="true"] .site-nav { display: flex; }
  .js .nav-links { flex-direction: column; align-items: stretch; }
  .js .nav-links a { padding: 0.75rem; font-size: 1rem; }
  .js .nav-actions { flex-wrap: wrap; }
  .js .nav-actions .btn { flex: 1; }
  .js .nav-actions .btn-icon { flex: none; }

  /* Ohne Skript: Kopf bricht um, Navigation steht offen darunter. */
  .no-js .header-bar { flex-wrap: wrap; padding-block: 0.75rem; }
  .no-js .site-nav { flex-basis: 100%; flex-wrap: wrap; }
  .no-js .nav-links { flex-wrap: wrap; }
}

@media (max-width: 42rem) {
  :root { --gutter: 1.25rem; }
  .hero { padding-block: 4.5rem 3rem; }
  .showcase { padding-block: 0 3rem; }
  .showcase-panel { padding: 1rem; }
  .showcase .container { padding-inline: 0.75rem; }
  .model-makers { margin-top: 3rem; }
  .model-makers-list { gap: 0.75rem 1.5rem; font-size: 1rem; }
  .page-hero { padding-block: 3.5rem 2.5rem; }
  .section { padding-block: 4rem; }
  .grid-3, .grid-4, .grid-2, .steps, .bento, .bento-2 { grid-template-columns: minmax(0, 1fr); }
  .grid-3.grid-facts { grid-template-columns: minmax(0, 1fr); gap: 1.25rem; }
  .grid-facts > .card {
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    gap: 0.25rem 1rem;
    padding-top: 1.25rem;
  }
  .grid-facts > .card .tile { grid-row: span 2; }
  .grid-facts > .card h3 { margin: 0; }
  .bento-visual { height: 15rem; padding: 1.75rem 1.25rem 0; }
  .bento-visual.is-open { padding: 1rem; }
  .calc { margin-top: 1.75rem; }
  .feature-panel { padding: 1rem; }
  .feature .feature-panel > :is(ul, figure) { padding: 1.5rem 1.25rem; }
  .feature-app .feature-panel { height: 22rem; padding: 1.75rem 1.25rem 0; }
  .media-icons span { width: 3.75rem; height: 3.75rem; }
  /* Auf dem Handy wäre die Modellauswahl über dem kleinen Screenshot nicht zu
     lesen und verdeckte ihn fast ganz. */
  .showcase-pop { display: none; }
  /* Schmal steht die Plakette oben, die Zusagen zu zweit darunter. */
  .eu-visual { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0.625rem; padding-block: 1.25rem 0.5rem; }
  .eu-visual-emblem { grid-column: 1 / -1; grid-row: 1; justify-self: center; width: 6.5rem; height: 6.5rem; margin-bottom: 1.25rem; }
  .eu-chip, .eu-chip:nth-child(n) { grid-column: auto; grid-row: auto; justify-self: stretch; gap: 0.5rem; padding: 0.625rem 0.75rem; font-size: 0.8125rem; white-space: normal; }
  .eu-chip .icon { flex: none; }
  .cta { padding-block: 4.5rem; }
  .hero-actions .btn, .cta-actions .btn { flex: 1 1 100%; }
  .footer-grid { grid-template-columns: minmax(0, 1fr); }
  tbody th { width: auto; }
}

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  .btn, a.card, .faq summary::after, .input { transition: none; }
  .js :is(.hero, .page-hero) .container > *, .js .showcase-figure, .js .showcase-pop { animation: none; }
}

@media print {
  .site-header, .site-footer, .cta, .skip-link { display: none; }
  .reveal, .reveal .bar-fill { opacity: 1; transform: none; }
  body { background: #fff; color: #000; }
}
