/* Kurato Cockpit - Designsystem (UX-Konzept Kap. 8/9).
   Tagwache (hell) / Nachtwache (dunkel): automatisch nach System, per
   data-theme im Profil umschaltbar. Statusfarben immer doppelt kodiert
   (Farbe + Text/Symbol). Systemschrift, keine Dritt-Fonts zur Laufzeit. */

:root {
	--font: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif;
	--radius: 10px;
	--radius-sm: 6px;
	--gap: 16px;
	--motion: 180ms;

	/* Tagwache (hell) */
	--bg: #eef2f5;
	--surface: #ffffff;
	--surface-2: #f6f8fa;
	--text: #16232e;
	--muted: #5b6b78;
	--border: #d5dde3;
	--primary: #0f6e8c;
	--primary-ink: #ffffff;
	--primary-weak: #d9eef4;
	--focus: #1189ad;

	--gruen: #1f8a4c;
	--gruen-bg: #e2f4e9;
	--gelb: #9a6b00;
	--gelb-bg: #fbefcf;
	--rot: #b3261e;
	--rot-bg: #f8e0de;
}

@media (prefers-color-scheme: dark) {
	:root {
		/* Nachtwache (dunkel) */
		--bg: #0d151b;
		--surface: #14212b;
		--surface-2: #1b2b37;
		--text: #e7eef3;
		--muted: #9db0bd;
		--border: #29404f;
		--primary: #3fb3d4;
		--primary-ink: #05222c;
		--primary-weak: #143642;
		--focus: #6fd0ec;

		--gruen: #57c98a;
		--gruen-bg: #123021;
		--gelb: #e0b459;
		--gelb-bg: #33280d;
		--rot: #f0857e;
		--rot-bg: #3a1613;
	}
}

/* Explizite Umschaltung im Profil gewinnt in beide Richtungen. */
:root[data-theme='tag'] {
	--bg: #eef2f5; --surface: #ffffff; --surface-2: #f6f8fa; --text: #16232e;
	--muted: #5b6b78; --border: #d5dde3; --primary: #0f6e8c; --primary-ink: #ffffff;
	--primary-weak: #d9eef4; --focus: #1189ad;
	--gruen: #1f8a4c; --gruen-bg: #e2f4e9; --gelb: #9a6b00; --gelb-bg: #fbefcf; --rot: #b3261e; --rot-bg: #f8e0de;
}
:root[data-theme='nacht'] {
	--bg: #0d151b; --surface: #14212b; --surface-2: #1b2b37; --text: #e7eef3;
	--muted: #9db0bd; --border: #29404f; --primary: #3fb3d4; --primary-ink: #05222c;
	--primary-weak: #143642; --focus: #6fd0ec;
	--gruen: #57c98a; --gruen-bg: #123021; --gelb: #e0b459; --gelb-bg: #33280d; --rot: #f0857e; --rot-bg: #3a1613;
}

* { box-sizing: border-box; }
html, body { margin: 0; padding: 0; }
body { font-family: var(--font); background: var(--bg); color: var(--text); line-height: 1.5; -webkit-font-smoothing: antialiased; }
h1 { font-size: 1.5rem; margin: 0 0 .25rem; }
h2 { font-size: 1.05rem; margin: 0 0 .6rem; }
h3 { font-size: 1rem; margin: 0 0 .4rem; }
p { margin: 0 0 .5rem; }
.muted { color: var(--muted); font-size: .9rem; }
code { font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: .85em; word-break: break-all; }

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

/* Fokus-Ringe sichtbar (A11y). */
a:focus-visible, button:focus-visible, input:focus-visible, select:focus-visible, [tabindex]:focus-visible {
	outline: 3px solid var(--focus); outline-offset: 2px; border-radius: var(--radius-sm);
}

/* --- Buttons --- */
.btn { font: inherit; padding: .55rem .95rem; border-radius: var(--radius-sm); border: 1px solid var(--border);
	background: var(--surface); color: var(--text); cursor: pointer; transition: background var(--motion) ease-out, transform var(--motion) ease-out; }
.btn:hover { background: var(--surface-2); }
.btn:active { transform: translateY(1px); }
.btn[disabled] { opacity: .55; cursor: not-allowed; }
.btn-primary { background: var(--primary); color: var(--primary-ink); border-color: var(--primary); }
.btn-primary:hover { filter: brightness(1.07); background: var(--primary); }
.btn-ghost { background: transparent; }
.btn-danger { color: var(--rot); border-color: var(--rot); }
.btn-primary.btn-danger { background: var(--rot); color: #fff; border-color: var(--rot); }

/* --- Fields --- */
.field { margin-bottom: .9rem; }
.field label { display: block; font-weight: 600; font-size: .9rem; margin-bottom: .3rem; }
input, select { font: inherit; width: 100%; padding: .55rem .7rem; border: 1px solid var(--border);
	border-radius: var(--radius-sm); background: var(--surface); color: var(--text); }
input[type='checkbox'], input[type='radio'] { width: auto; }
.field-hint { color: var(--muted); font-size: .82rem; margin: .3rem 0 0; }
.field-msg { color: var(--rot); font-size: .85rem; margin: .3rem 0 0; }
.field-error input { border-color: var(--rot); }

/* --- Layout --- */
.app-shell { min-height: 100vh; }
.app-main { max-width: 1120px; margin: 0 auto; padding: var(--gap); }
.page { padding: .5rem 0 3rem; }
.card { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1rem; margin-bottom: var(--gap); }
.boot-splash { min-height: 100vh; display: grid; place-items: center; }

/* --- Probefahrt (Kap. 11): dauerhaftes Banner, ruhige Sperr-Karten --- */
.demo-banner { display: flex; align-items: center; justify-content: center; gap: 1rem; flex-wrap: wrap;
	background: var(--primary-weak); border-bottom: 1px solid var(--primary); color: var(--text);
	padding: .55rem var(--gap); position: relative; z-index: 6; }
.demo-banner-text { font-weight: 600; }
.demo-lock { border-left: 4px solid var(--primary); }

/* --- Topbar --- */
.topbar { display: flex; align-items: center; gap: var(--gap); padding: .6rem var(--gap);
	background: var(--surface); border-bottom: 1px solid var(--border); position: sticky; top: 0; z-index: 5; }
.topbar-slim { justify-content: space-between; }
.topbar-brand { font-weight: 700; letter-spacing: .02em; color: var(--primary); }
.topbar-nav { display: flex; gap: .25rem; flex: 1; flex-wrap: wrap; }
.topbar-right { display: flex; align-items: center; gap: .6rem; }
.site-name { max-width: 220px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.nav-link { font: inherit; background: transparent; border: 0; color: var(--text); padding: .45rem .7rem; border-radius: var(--radius-sm); cursor: pointer; }
.nav-link:hover { background: var(--surface-2); }
.nav-link.is-active { background: var(--primary-weak); color: var(--primary); font-weight: 600; }

/* Verbindungs-Indikator */
.conn-dot { width: 11px; height: 11px; border-radius: 50%; display: inline-block; }
.conn-ok { background: var(--gruen); }
.conn-bad { background: var(--rot); animation: pulse 1.4s ease-in-out infinite; }
@keyframes pulse { 0%,100% { opacity: 1; } 50% { opacity: .35; } }

/* --- Login --- */
.login-screen { min-height: 100vh; display: grid; place-items: center; padding: var(--gap); }
.login-card { width: 100%; max-width: 380px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1.6rem; }
.login-motif { color: var(--primary); display: grid; place-items: center; margin-bottom: .5rem; }
.login-title { text-align: center; margin-bottom: 1.1rem; }
/* Nur die Einladung hat einen erklaerenden Satz unter dem Titel. */
.login-lead { text-align: center; color: var(--muted); font-size: .92rem; margin: -.6rem 0 1.1rem; }

/* --- Onboarding --- */
.onboard-screen { min-height: calc(100vh - 52px); display: grid; place-items: center; padding: var(--gap); }
.onboard-card { width: 100%; max-width: 460px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1.6rem; }
.onboard-step { color: var(--muted); font-size: .8rem; text-transform: uppercase; letter-spacing: .06em; }
.onboard-card.success { text-align: center; }
.success-mark { font-size: 2.6rem; }
.pairing-block { margin-top: 1rem; }
.pairing-code { font-family: ui-monospace, monospace; font-size: 1.5rem; letter-spacing: .12em; text-align: center;
	background: var(--surface-2); border: 1px dashed var(--border); border-radius: var(--radius-sm); padding: .8rem; }
.pairing-hint { text-align: center; color: var(--muted); font-size: .85rem; }
.pairing-steps { padding-left: 1.2rem; }
.pairing-wait { display: flex; align-items: center; gap: .6rem; color: var(--muted); margin-top: .6rem; }

/* --- Bridge --- */
.bridge-head { display: flex; justify-content: space-between; align-items: flex-start; gap: var(--gap); flex-wrap: wrap; margin-bottom: 1rem; }
.greeting { font-size: 1.7rem; }
.briefing { color: var(--muted); }
.columns { display: grid; grid-template-columns: repeat(3, 1fr); gap: var(--gap); }
.column { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1rem; }
.column-soon { opacity: .85; }
.soon-card { background: var(--surface-2); border-radius: var(--radius-sm); padding: 1rem; color: var(--muted); }
.task-list, .mini-list, .sub-list, .task-checks, .agent-list { list-style: none; margin: 0 0 .8rem; padding: 0; }
.task-row { display: flex; align-items: center; gap: .5rem; padding: .4rem 0; border-bottom: 1px solid var(--border); }
.task-open, .mini-row { text-align: left; background: transparent; border: 0; color: var(--text); cursor: pointer; width: 100%; padding: .2rem 0; display: block; }
.task-title { display: block; font-weight: 600; }
.task-meta { display: block; color: var(--muted); font-size: .82rem; }
.mini-row span { display: block; }
.mini-list li { border-bottom: 1px solid var(--border); }

/* Segelwetter-Badge (doppelt kodiert) */
.weather { display: inline-flex; align-items: center; gap: .4rem; padding: .4rem .75rem; border-radius: 999px; border: 1px solid var(--border); cursor: pointer; font-weight: 600; }
.weather-symbol { font-size: 1.05rem; }
.weather-gruen { background: var(--gruen-bg); color: var(--gruen); border-color: var(--gruen); }
.weather-gelb { background: var(--gelb-bg); color: var(--gelb); border-color: var(--gelb); }
.weather-rot { background: var(--rot-bg); color: var(--rot); border-color: var(--rot); }

.badge { font-size: .72rem; padding: .12rem .45rem; border-radius: 999px; border: 1px solid; font-weight: 600; }
.badge-rot { color: var(--rot); background: var(--rot-bg); border-color: var(--rot); }

/* --- Empty / Lighthouse --- */
.empty { text-align: center; color: var(--muted); padding: 1rem .5rem; }
.empty-scene, .lighthouse-art { color: var(--primary); display: grid; place-items: center; }
.empty-title { color: var(--text); font-weight: 600; margin-top: .5rem; }
.lighthouse { max-width: 460px; margin: 4rem auto; text-align: center; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 2rem; }
.lighthouse h2 { font-size: 1.25rem; }
.lighthouse-diag { color: var(--muted); font-size: .9rem; }

/* --- Board --- */
.board-head { display: flex; justify-content: space-between; align-items: baseline; gap: var(--gap); }
/*
 * Das Board ist Arbeitsflaeche, keine Lesespalte. Die 1120px Lesebreite von
 * .app-main sind fuer Text richtig und fuers Board falsch: auf einem
 * 1280er Laptop lagen dadurch 432px hinter dem Rand - zwei ganze Stufen,
 * darunter "Gewonnen". Die Seite mit dem Board darf die Lesebreite verlassen.
 */
.app-main:has( .board-page ) { max-width: none; }

.board { display: grid; grid-auto-flow: column; grid-auto-columns: minmax(220px, 1fr); gap: var(--gap); overflow-x: auto; padding-bottom: 1rem; }

/*
 * Scroll-Schatten: Ab etwa sechs Stufen passt das Board auf keinen Laptop mehr
 * (das ist bei Kanban normal), aber nichts zeigte an, dass rechts noch etwas
 * kommt - das Board sah einfach abgeschnitten aus. Die vier Verlaeufe machen es
 * sichtbar, ohne JavaScript: die beiden Abdeckungen in Hintergrundfarbe scrollen
 * mit dem Inhalt (`local`), die beiden Schatten stehen fest (`scroll`). Wo eine
 * Abdeckung weggescrollt ist, kommt der Schatten zum Vorschein - er erscheint
 * also nur an der Seite, an der wirklich noch Inhalt liegt.
 */
@media (min-width: 861px) {
	.board {
		background:
			linear-gradient(to right, var(--bg) 30%, transparent) left center,
			linear-gradient(to left, var(--bg) 30%, transparent) right center,
			radial-gradient(farthest-side at 0 50%, rgba(0, 0, 0, .28), transparent) left center,
			radial-gradient(farthest-side at 100% 50%, rgba(0, 0, 0, .28), transparent) right center;
		background-repeat: no-repeat;
		background-size: 44px 100%, 44px 100%, 15px 100%, 15px 100%;
		background-attachment: local, local, scroll, scroll;
	}
}
.board-col { background: var(--surface-2); border: 1px solid var(--border); border-radius: var(--radius); padding: .6rem; min-height: 120px; }
.col-won { border-color: var(--gruen); }
.col-lost { border-color: var(--border); opacity: .9; }
.board-col-head { display: flex; justify-content: space-between; align-items: center; margin-bottom: .5rem; }
.col-label { font-weight: 700; }
.col-count { font-variant-numeric: tabular-nums; background: var(--surface); border: 1px solid var(--border); border-radius: 999px; padding: 0 .5rem; font-size: .82rem; }
.card-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: .5rem; }
.card { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius-sm); padding: .55rem; cursor: grab; transition: transform 150ms ease-out, box-shadow var(--motion); }
.card.is-dragging { transform: rotate(2.5deg); box-shadow: 0 8px 20px rgba(0,0,0,.18); }
.card-open { text-align: left; background: transparent; border: 0; color: var(--text); cursor: pointer; font-weight: 600; width: 100%; }
.card-move { display: block; margin-top: .4rem; }
.card-move select { font-size: .82rem; padding: .3rem .4rem; }
.card-empty { padding: .4rem; font-size: .85rem; }
.rollback-banner { display: flex; justify-content: space-between; align-items: center; gap: .8rem; background: var(--rot-bg); color: var(--rot); border: 1px solid var(--rot); border-radius: var(--radius-sm); padding: .6rem .8rem; margin-bottom: .8rem; }

/* Won-Zelebration */
.celebration { position: fixed; left: 0; right: 0; bottom: 24px; pointer-events: none; z-index: 20; }
.ship { font-size: 2.4rem; animation: sail 1.5s ease-in-out forwards; }
@keyframes sail { from { transform: translateX(-12vw); } to { transform: translateX(96vw); } }
@media (prefers-reduced-motion: reduce) {
	.ship { animation: none; }
	.card.is-dragging { transform: none; }
	.conn-bad { animation: none; }
}

/* --- Contact profile --- */
.back-link { background: transparent; border: 0; color: var(--primary); cursor: pointer; padding: 0; margin-bottom: .5rem; }
.contact-head { margin-bottom: 1rem; }
.stepper { display: flex; flex-wrap: wrap; gap: .4rem; margin-top: .7rem; }
.step { font: inherit; padding: .35rem .7rem; border: 1px solid var(--border); background: var(--surface); border-radius: 999px; cursor: pointer; font-size: .85rem; }
.step.is-active { background: var(--primary); color: var(--primary-ink); border-color: var(--primary); }
.step[disabled] { cursor: default; }
.contact-grid { display: grid; grid-template-columns: 1fr 1fr; gap: var(--gap); }
.timeline { list-style: none; margin: 0; padding: 0; }
.timeline li { display: flex; gap: .6rem; padding: .4rem 0; border-bottom: 1px solid var(--border); }
.timeline-dot { width: 9px; height: 9px; border-radius: 50%; background: var(--primary); margin-top: .4rem; flex: none; }
.timeline p { margin: 0; }
/* Notiz in der Historie (CP5): mehrzeilig, mit ruhiger Abgrenzung. */
.timeline-note { white-space: pre-wrap; border-left: 3px solid var(--border); padding-left: .6rem; }
.task-checks li { display: flex; justify-content: space-between; align-items: center; gap: .5rem; padding: .3rem 0; }
.task-checks .is-done span { text-decoration: line-through; color: var(--muted); }
.task-checks label { display: flex; gap: .5rem; align-items: center; }
.task-add { display: flex; gap: .4rem; flex-wrap: wrap; margin-top: .6rem; }
.task-add input[type='text'] { flex: 1; min-width: 140px; }
.inline-row { display: flex; align-items: center; gap: .5rem; }
.saved-check { color: var(--gruen); font-size: .82rem; white-space: nowrap; }

/* --- Contacts table --- */
.filters { display: flex; gap: .5rem; flex-wrap: wrap; margin-bottom: 1rem; }
.filters input[type='search'] { flex: 1; min-width: 180px; }
.filters select { width: auto; }
/* Eigene Regel statt .card: .card ist weiter unten fuer die Board-Karten neu
   definiert (cursor: grab), das Formular haette den Greifzeiger geerbt. */
.contact-new { background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1rem; margin-bottom: var(--gap);
	display: grid; grid-template-columns: repeat(auto-fit, minmax(13rem, 1fr)); gap: 0 .8rem; align-items: end; }
.contact-new .btn { margin-bottom: .9rem; }
.table-wrap { overflow-x: auto; }
.contact-table { width: 100%; border-collapse: collapse; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; }
.contact-table th, .contact-table td { text-align: left; padding: .6rem .7rem; border-bottom: 1px solid var(--border); }
.contact-table th { background: var(--surface-2); font-size: .82rem; text-transform: uppercase; letter-spacing: .04em; color: var(--muted); }
.row-click { cursor: pointer; }
.row-click:hover td { background: var(--surface-2); }

/* --- Team --- */
.agent-row { display: flex; justify-content: space-between; gap: .8rem; padding: .6rem 0; border-bottom: 1px solid var(--border); flex-wrap: wrap; }
.invite-link { margin-top: .3rem; font-size: .82rem; }
.buy-moment { margin-top: 1rem; background: var(--primary-weak); border: 1px solid var(--primary); border-radius: var(--radius); padding: 1rem; }
.radio-set { border: 0; padding: 0; margin: 0; display: flex; flex-direction: column; gap: .4rem; }
.radio, .switch { display: flex; align-items: center; gap: .5rem; cursor: pointer; }

/* --- Toasts --- */
.toasts { position: fixed; right: var(--gap); bottom: var(--gap); display: flex; flex-direction: column; gap: .5rem; z-index: 30; max-width: 90vw; }
.toast { display: flex; align-items: center; gap: .6rem; background: var(--surface); border: 1px solid var(--border); border-left-width: 4px; border-radius: var(--radius-sm); padding: .6rem .8rem; box-shadow: 0 6px 18px rgba(0,0,0,.14); }
.toast-success { border-left-color: var(--gruen); }
.toast-error { border-left-color: var(--rot); }
.toast-info { border-left-color: var(--primary); }
.toast-x { background: transparent; border: 0; font-size: 1.1rem; cursor: pointer; color: var(--muted); }

/* --- Command palette --- */
.palette-overlay { position: fixed; inset: 0; background: rgba(6,14,20,.45); display: grid; place-items: start center; padding-top: 12vh; z-index: 40; }
.palette { width: 100%; max-width: 520px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); overflow: hidden; box-shadow: 0 20px 50px rgba(0,0,0,.3); }
.palette-input { border: 0; border-bottom: 1px solid var(--border); border-radius: 0; padding: .9rem 1rem; font-size: 1rem; }
.palette-list { list-style: none; margin: 0; padding: .3rem; max-height: 50vh; overflow-y: auto; }
.palette-item { display: flex; justify-content: space-between; gap: 1rem; padding: .6rem .7rem; border-radius: var(--radius-sm); cursor: pointer; }
.palette-item.is-active { background: var(--primary-weak); }
.palette-hint { color: var(--muted); font-size: .82rem; }
.palette-empty { padding: .7rem; color: var(--muted); }
.palette-fab { position: fixed; right: var(--gap); bottom: var(--gap); background: var(--surface); border: 1px solid var(--border); border-radius: 999px; padding: .5rem .8rem; cursor: pointer; box-shadow: 0 6px 16px rgba(0,0,0,.14); font-weight: 600; }

/* --- Modal --- */
.modal { width: 100%; max-width: 420px; background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius); padding: 1.4rem; }
.modal-actions { display: flex; justify-content: flex-end; gap: .6rem; margin-top: 1rem; }

/* --- Spinner --- */
.spinner { display: grid; place-items: center; padding: 2rem; }
.spinner-ring { width: 26px; height: 26px; border: 3px solid var(--border); border-top-color: var(--primary); border-radius: 50%; animation: spin 800ms linear infinite; }
@keyframes spin { to { transform: rotate(360deg); } }
@media (prefers-reduced-motion: reduce) { .spinner-ring { animation-duration: 2s; } }

/* --- Hans-Karte (Kap. 5): eine je Screen, immer schliessbar --- */
.hans-card { background: var(--surface-2); border: 1px solid var(--border); border-left: 4px solid var(--primary); border-radius: var(--radius-sm); padding: .8rem; }
.hans-title { font-weight: 600; margin: 0 0 .3rem; }
.hans-body { margin: 0 0 .7rem; }
.hans-actions { display: flex; flex-wrap: wrap; gap: .5rem; }
.hans-draft textarea { width: 100%; font: inherit; margin-bottom: .5rem; }
.hans-quota { margin: .6rem 0 0; }

/* --- Termine (lesend) --- */
.booking-list { list-style: none; margin: 0; padding: 0; }
.booking-row { display: flex; align-items: baseline; gap: .8rem; padding: .5rem 0; border-bottom: 1px solid var(--border); flex-wrap: wrap; }
.booking-row:last-child { border-bottom: 0; }
.booking-time { font-variant-numeric: tabular-nums; font-weight: 600; min-width: 4.5rem; }
.booking-main { flex: 1 1 14rem; }

/* --- Statistik + Pro-Flaeche "beschlagenes Glas" (Kap. 6) --- */
.stats-head { display: flex; align-items: center; justify-content: space-between; gap: 1rem; flex-wrap: wrap; }
.kpi-row { list-style: none; display: flex; flex-wrap: wrap; gap: 1.4rem; margin: 0; padding: 0; }
.kpi-row li { display: flex; flex-direction: column; }
.kpi-value { font-size: 1.6rem; font-weight: 700; font-variant-numeric: tabular-nums; }
.kpi-label { color: var(--muted); font-size: .85rem; }
.campaign-list { list-style: none; margin: 0; padding: 0; }
.campaign-list li { padding: .5rem 0; border-bottom: 1px solid var(--border); }
.campaign-list li:last-child { border-bottom: 0; }
.contact-table td.num { text-align: right; font-variant-numeric: tabular-nums; }
.demo-badge { background: var(--gelb-bg); color: var(--gelb); border: 1px solid currentColor; border-radius: 999px; padding: .2rem .7rem; font-size: .82rem; font-weight: 600; }

.glass-wrap { position: relative; }
/* Milchglas: Weichzeichner + Aufhellung. Kein Modal, kein Overlay ueber der
   ganzen App - die Flaeche bleibt an ihrem Ort. */
.glass-content { filter: blur(5px) saturate(.7); opacity: .55; pointer-events: none; user-select: none; }
.glass-card { position: absolute; left: 50%; top: 2.5rem; transform: translateX(-50%); width: min(30rem, 92%);
	background: var(--surface); border: 1px solid var(--primary); border-radius: var(--radius); padding: 1.2rem;
	box-shadow: 0 14px 40px rgba(0,0,0,.22); }
.glass-card h2 { margin-top: 0; }
.glass-card .price { font-weight: 600; }
.glass-actions { display: flex; flex-wrap: wrap; gap: .6rem; margin-top: .8rem; }

/* --- Responsiv: Board wird zur Stufen-Liste (kein Touch-Drag-Zwang) --- */
@media (max-width: 860px) {
	.columns { grid-template-columns: 1fr; }
	.contact-grid { grid-template-columns: 1fr; }
	.board { grid-auto-flow: row; grid-auto-columns: auto; }
	.card { cursor: default; }
	.glass-card { position: static; transform: none; width: auto; margin-bottom: var(--gap); }
	.glass-content { filter: blur(4px); }
}

/* ============================================================
   Living Mesh (CP4b) - der Hintergrund traegt das Segelwetter.
   Vorbild: vorstellig.de. Reines CSS: keine Zeichenflaeche, kein
   Animations-Loop, nur wandernde Verlaufspositionen. Die Farbe
   steht nie allein - das Segelwetter nennt Wort und Symbol.
   ============================================================ */

.k-mesh {
	position: fixed;
	inset: 0;
	z-index: 0;
	overflow: hidden;
	pointer-events: none;
	background: var(--bg);
	animation: k-atmen 16s ease-in-out infinite alternate;
}

.k-mesh__lage {
	position: absolute;
	/* Ueberstand, damit beim Wandern nie eine Kante sichtbar wird. */
	inset: -18%;
	display: block;
	background-size: 150% 150%;
	background-repeat: no-repeat;
	filter: blur(16px) saturate(1.12);
	opacity: 0;
	/* Sanftes Ueberblenden beim Wetterwechsel statt hartem Umschalten. */
	transition: opacity 1900ms ease-in-out;
	transform: translate3d( 0, var(--k-mesh-shift, 0px), 0 );
	animation: k-mesh-wandern 32s ease-in-out infinite alternate;
	will-change: background-position, opacity;
}

.k-mesh__lage[data-aktiv='ja'] {
	opacity: var(--k-mesh-int, 1);
}

/* Klare Sicht: ruhiges Hafenwasser bei gutem Wetter. */
.k-mesh__lage--klar {
	background-image:
		radial-gradient( 34% 44% at 18% 26%, rgba( 88, 168, 190, .55 ), transparent 62% ),
		radial-gradient( 32% 42% at 82% 22%, rgba( 120, 190, 200, .42 ), transparent 62% ),
		radial-gradient( 26% 32% at 70% 70%, rgba( 210, 232, 236, .55 ), transparent 60% ),
		radial-gradient( 40% 50% at 34% 84%, rgba( 15, 110, 140, .28 ), transparent 66% ),
		linear-gradient( 120deg, #eef4f7 0%, #e6f0f4 100% );
}

/* Frische Brise: mehr Bewegung, waermeres Licht am Horizont. */
.k-mesh__lage--brise {
	background-image:
		radial-gradient( 36% 46% at 22% 20%, rgba( 76, 150, 180, .58 ), transparent 62% ),
		radial-gradient( 30% 40% at 78% 26%, rgba( 226, 178, 84, .34 ), transparent 62% ),
		radial-gradient( 28% 34% at 60% 74%, rgba( 150, 190, 205, .48 ), transparent 60% ),
		radial-gradient( 42% 52% at 30% 88%, rgba( 20, 90, 120, .30 ), transparent 66% ),
		linear-gradient( 125deg, #eef3f6 0%, #f2efe8 100% );
}

/* Sturmwarnung: tiefer, dichter, ernster - aber nie alarmrot. */
.k-mesh__lage--sturm {
	background-image:
		radial-gradient( 38% 48% at 20% 24%, rgba( 32, 62, 92, .62 ), transparent 62% ),
		radial-gradient( 34% 44% at 80% 18%, rgba( 60, 88, 118, .52 ), transparent 62% ),
		radial-gradient( 26% 30% at 68% 72%, rgba( 179, 38, 30, .16 ), transparent 60% ),
		radial-gradient( 44% 54% at 32% 86%, rgba( 18, 40, 64, .42 ), transparent 66% ),
		linear-gradient( 130deg, #e7ecf1 0%, #dde4ec 100% );
}

@keyframes k-mesh-wandern {
	0%   { background-position:  0% 18%; }
	50%  { background-position: 100% 82%; }
	100% { background-position: 22% 0%; }
}

@keyframes k-atmen {
	0%   { filter: saturate( 1 ); }
	100% { filter: saturate( 1.08 ); }
}

/* Ruhig-Modus: Verlauf bleibt, Bewegung nicht. Gilt sowohl bei
   Systemwunsch als auch, wenn die App ihn selbst setzt. */
.k-mesh--ruhig,
.k-mesh--ruhig .k-mesh__lage {
	animation: none;
}

@media ( prefers-reduced-motion: reduce ) {
	.k-mesh,
	.k-mesh__lage {
		animation: none;
	}
	.k-mesh__lage {
		transition: none;
	}
}

/* Der Inhalt liegt ueber dem Mesh. */
.app-shell,
.boot-splash {
	position: relative;
	z-index: 1;
}

/* Dunkelmodus: tiefere Toene, deutlich zurueckhaltender. */
@media ( prefers-color-scheme: dark ) {
	.k-mesh__lage {
		filter: blur( 20px ) saturate( 1.05 );
	}
	.k-mesh__lage--klar {
		background-image:
			radial-gradient( 34% 44% at 18% 26%, rgba( 30, 92, 116, .50 ), transparent 62% ),
			radial-gradient( 32% 42% at 82% 22%, rgba( 24, 70, 92, .46 ), transparent 62% ),
			radial-gradient( 40% 50% at 34% 84%, rgba( 12, 40, 56, .55 ), transparent 66% ),
			linear-gradient( 120deg, #0d151b 0%, #101c25 100% );
	}
	.k-mesh__lage--brise {
		background-image:
			radial-gradient( 36% 46% at 22% 20%, rgba( 32, 96, 122, .52 ), transparent 62% ),
			radial-gradient( 30% 40% at 78% 26%, rgba( 120, 92, 40, .30 ), transparent 62% ),
			radial-gradient( 42% 52% at 30% 88%, rgba( 12, 44, 60, .55 ), transparent 66% ),
			linear-gradient( 125deg, #0d151b 0%, #141d22 100% );
	}
	.k-mesh__lage--sturm {
		background-image:
			radial-gradient( 38% 48% at 20% 24%, rgba( 20, 44, 68, .70 ), transparent 62% ),
			radial-gradient( 34% 44% at 80% 18%, rgba( 34, 56, 80, .60 ), transparent 62% ),
			radial-gradient( 26% 30% at 68% 72%, rgba( 179, 38, 30, .12 ), transparent 60% ),
			linear-gradient( 130deg, #0b1218 0%, #0e1620 100% );
	}
}

/* ---- Echo-Licht (CP4b) --------------------------------------------------
   Ein weicher Lichtfleck, der dem Zeiger traege folgt und dabei vom "Wind"
   umgetrieben wird (Berechnung in src/logic/echo.js). Er atmet auf, wenn
   getippt, geklickt, fokussiert oder eine Karte gezogen wird. Position kommt
   ueber CSS-Variablen, damit die App dafuer nicht neu zeichnet.
   -------------------------------------------------------------------------- */

.k-mesh__echo {
	position: absolute;
	inset: 0;
	display: block;
	pointer-events: none;
	filter: blur( 28px );
	opacity: .5;
	transition: opacity 1800ms ease;
	background: radial-gradient(
		24% 28% at var( --k-echo-x, 62% ) var( --k-echo-y, 38% ),
		rgba( 90, 190, 205, .30 ),
		transparent 70%
	);
}

/* Aufatmen bei Eingabe: schneller Anstieg, langsames Abklingen. */
.k-echo-wach .k-mesh__echo {
	opacity: .85;
	transition-duration: 420ms;
}

/* Bei Sturm bleibt auch das Echo kuehler und zurueckhaltender. */
.k-mesh__lage--sturm[data-aktiv='ja'] ~ .k-mesh__echo {
	background: radial-gradient(
		24% 28% at var( --k-echo-x, 62% ) var( --k-echo-y, 38% ),
		rgba( 150, 180, 210, .22 ),
		transparent 70%
	);
}

@media ( prefers-color-scheme: dark ) {
	.k-mesh__echo {
		opacity: .38;
		background: radial-gradient(
			24% 28% at var( --k-echo-x, 62% ) var( --k-echo-y, 38% ),
			rgba( 70, 160, 185, .26 ),
			transparent 70%
		);
	}
}

@media ( prefers-reduced-motion: reduce ) {
	.k-mesh__echo {
		display: none;
	}
}

/* ---- Seegang: Duenung unten, Wind oben (CP4b-4) -------------------------
   Inhaber-Wunsch: der Hintergrund darf staerker sein und maritim gedacht -
   unten Wellen, oben ziehender Wind. Regel dabei: es soll Freude machen
   zuzuschauen, ohne die Arbeit zu stoeren. Deshalb lange Perioden (26 bis
   46 s), weiche Kanten und Bewegungen, die nie in dieselbe Phase fallen.
   -------------------------------------------------------------------------- */

/* Zwei Duenungs-Baender mit verschiedener Geschwindigkeit: das langsamere
   liegt tiefer und wirkt weiter entfernt (Parallaxe). */
.k-mesh__see {
	position: absolute;
	left: -12%;
	right: -12%;
	bottom: -10%;
	height: 58%;
	display: block;
	filter: blur( 22px );
	opacity: calc( var( --k-mesh-int, 1 ) * .9 );
	background-repeat: no-repeat;
	will-change: transform;
}

.k-mesh__see--fern {
	background-image:
		radial-gradient( 65% 120% at 18% 100%, rgba( 42, 122, 150, .46 ), transparent 72% ),
		radial-gradient( 55% 105% at 58% 100%, rgba( 70, 158, 178, .40 ), transparent 70% ),
		radial-gradient( 60% 115% at 92% 100%, rgba( 34, 104, 132, .38 ), transparent 72% );
	animation: k-duenung-fern 46s ease-in-out infinite alternate;
}

.k-mesh__see--nah {
	height: 42%;
	filter: blur( 16px );
	background-image:
		radial-gradient( 58% 130% at 34% 100%, rgba( 16, 92, 122, .52 ), transparent 70% ),
		radial-gradient( 50% 120% at 74% 100%, rgba( 24, 116, 142, .44 ), transparent 70% );
	animation: k-duenung-nah 29s ease-in-out infinite alternate;
}

/* Wind oben: langgezogene Schlieren, die quer ueber den Himmel ziehen. */
.k-mesh__wind {
	position: absolute;
	top: -12%;
	left: -20%;
	right: -20%;
	height: 62%;
	display: block;
	filter: blur( 26px );
	opacity: calc( var( --k-mesh-int, 1 ) * .75 );
	background-size: 60% 100%;
	background-image:
		radial-gradient( 42% 22% at 20% 32%, rgba( 214, 234, 240, .62 ), transparent 72% ),
		radial-gradient( 36% 16% at 62% 20%, rgba( 236, 244, 248, .50 ), transparent 70% ),
		radial-gradient( 30% 14% at 86% 44%, rgba( 190, 216, 228, .44 ), transparent 70% );
	animation: k-wind-ziehen 38s linear infinite;
	will-change: background-position;
}

@keyframes k-duenung-fern {
	0%   { transform: translate3d( -2.5%, 2%, 0 ) scaleY( 1 ); }
	100% { transform: translate3d(  2.5%, -1.5%, 0 ) scaleY( 1.07 ); }
}

@keyframes k-duenung-nah {
	0%   { transform: translate3d(  2%, 1.5%, 0 ) scaleY( 1.05 ); }
	100% { transform: translate3d( -2%, -2.5%, 0 ) scaleY( 1 ); }
}

@keyframes k-wind-ziehen {
	0%   { background-position: -30% 40%, 10% 20%, 50% 60%; }
	100% { background-position: 130% 46%, 170% 14%, 210% 66%; }
}

/* Sturm: die See wird dunkler und hoeher, der Wind schneller und dichter. */
.k-mesh[data-lage='sturm'] .k-mesh__see--fern {
	background-image:
		radial-gradient( 68% 130% at 16% 100%, rgba( 20, 48, 76, .62 ), transparent 72% ),
		radial-gradient( 58% 115% at 56% 100%, rgba( 30, 66, 96, .56 ), transparent 70% ),
		radial-gradient( 62% 125% at 94% 100%, rgba( 16, 40, 66, .58 ), transparent 72% );
	animation-duration: 34s;
}
.k-mesh[data-lage='sturm'] .k-mesh__see--nah {
	background-image:
		radial-gradient( 60% 140% at 32% 100%, rgba( 12, 36, 60, .68 ), transparent 70% ),
		radial-gradient( 52% 130% at 76% 100%, rgba( 22, 54, 82, .60 ), transparent 70% );
	animation-duration: 21s;
}
.k-mesh[data-lage='sturm'] .k-mesh__wind {
	opacity: calc( var( --k-mesh-int, 1 ) * .85 );
	animation-duration: 24s;
	background-image:
		radial-gradient( 46% 24% at 20% 30%, rgba( 176, 196, 214, .58 ), transparent 72% ),
		radial-gradient( 38% 18% at 60% 18%, rgba( 150, 174, 198, .52 ), transparent 70% ),
		radial-gradient( 32% 15% at 88% 46%, rgba( 130, 158, 186, .48 ), transparent 70% );
}

/* Frische Brise: etwas flotter als bei klarer Sicht, waermeres Licht. */
.k-mesh[data-lage='brise'] .k-mesh__see--nah { animation-duration: 24s; }
.k-mesh[data-lage='brise'] .k-mesh__wind {
	animation-duration: 30s;
	background-image:
		radial-gradient( 42% 22% at 20% 32%, rgba( 246, 236, 214, .58 ), transparent 72% ),
		radial-gradient( 36% 16% at 62% 20%, rgba( 236, 244, 248, .52 ), transparent 70% ),
		radial-gradient( 30% 14% at 86% 44%, rgba( 214, 226, 236, .46 ), transparent 70% );
}

@media ( prefers-color-scheme: dark ) {
	.k-mesh__see--fern {
		background-image:
			radial-gradient( 65% 120% at 18% 100%, rgba( 14, 58, 78, .58 ), transparent 72% ),
			radial-gradient( 55% 105% at 58% 100%, rgba( 20, 78, 96, .50 ), transparent 70% ),
			radial-gradient( 60% 115% at 92% 100%, rgba( 10, 44, 64, .52 ), transparent 72% );
	}
	.k-mesh__see--nah {
		background-image:
			radial-gradient( 58% 130% at 34% 100%, rgba( 8, 40, 60, .62 ), transparent 70% ),
			radial-gradient( 50% 120% at 74% 100%, rgba( 12, 56, 76, .54 ), transparent 70% );
	}
	.k-mesh__wind {
		opacity: calc( var( --k-mesh-int, 1 ) * .42 );
		background-image:
			radial-gradient( 42% 22% at 20% 32%, rgba( 120, 156, 178, .40 ), transparent 72% ),
			radial-gradient( 36% 16% at 62% 20%, rgba( 140, 172, 190, .34 ), transparent 70% ),
			radial-gradient( 30% 14% at 86% 44%, rgba( 100, 134, 160, .30 ), transparent 70% );
	}
}

@media ( prefers-reduced-motion: reduce ) {
	.k-mesh__see,
	.k-mesh__wind {
		animation: none;
	}
}

/* Der Mesh liegt hinter allem; Login und Onboarding brauchen deshalb einen
   eigenen Stapelkontext, sonst verschwinden sie dahinter (CP4b-5). */
.login-screen,
.topbar-slim {
	position: relative;
	z-index: 1;
}

/* Der Inhalt MUSS ueber dem Mesh liegen. Ohne eigenen Stapelkontext malt der
   Browser den fixierten Mesh (z-index 0, positioniert) ueber die nicht
   positionierten Inhaltsbloecke - die Seite wirkt dann leer (CP4b-5).
   Kopf und Banner hatten bereits eigene z-index-Werte, deshalb war nur der
   Hauptbereich betroffen. */
.app-main,
.page,
.demo-banner {
	position: relative;
	z-index: 1;
}

/* ============================================================
   Seekarte (CP6) - die Funnel-Ansicht mit drei Zoom-Stufen.
   Die Zahlen tragen die Aussage; Balkenbreite und Boote sind
   Darstellung. Alles bleibt lesbar, wenn die Bewegung fehlt.
   ============================================================ */

.seekarte-head { display: flex; align-items: center; justify-content: space-between; gap: 1rem; flex-wrap: wrap; }
.seekarte-frage { margin: 0 0 var(--gap); font-size: 1rem; }

.zoom-switch { display: inline-flex; border: 1px solid var(--border); border-radius: 999px; background: var(--surface); overflow: hidden; }
.zoom-btn { font: inherit; font-size: .88rem; padding: .4rem .9rem; border: 0; background: transparent; color: var(--text); cursor: pointer; }
.zoom-btn + .zoom-btn { border-left: 1px solid var(--border); }
.zoom-btn.is-active { background: var(--primary); color: var(--primary-ink); font-weight: 600; }

/* --- Filter: auf allen drei Zoom-Stufen dieselben --- */
.filterleiste { margin-bottom: var(--gap); }
.filter-feld { display: flex; flex-direction: column; gap: .2rem; }
.filter-label { font-size: .78rem; text-transform: uppercase; letter-spacing: .04em; color: var(--muted); }
.filterleiste .filters { align-items: flex-end; margin-bottom: .6rem; }
.filterleiste .filters select, .filterleiste .filters input[type='text'] { width: auto; min-width: 9rem; }
.schnellfilter { display: flex; flex-wrap: wrap; gap: 1rem; margin-bottom: .6rem; }
.filter-state { display: flex; align-items: center; justify-content: space-between; gap: .8rem; flex-wrap: wrap; border-top: 1px solid var(--border); padding-top: .6rem; }
.filter-state p { margin: 0; }

/* --- Zoom 1: die Haefen. Breite nach Menge, Zahl immer daneben. --- */
.haefen { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: .35rem; }
.hafen-knopf { display: grid; grid-template-columns: 4.5rem 1fr; align-items: center; gap: .8rem; width: 100%;
	font: inherit; color: var(--text); text-align: left; background: var(--surface-2); border: 1px solid var(--border);
	border-radius: var(--radius-sm); padding: .55rem .7rem; cursor: pointer; position: relative; overflow: hidden; }
.hafen-knopf:hover { border-color: var(--primary); }
/* Zahl und Label liegen ueber dem Balken - der Balken ist nur Darstellung und
   darf nie ein Grid-Element werden (sonst frisst ihn die Spaltenbreite). */
.hafen-zahl { font-size: 1.3rem; font-weight: 700; font-variant-numeric: tabular-nums; position: relative; z-index: 1; }
.hafen-label { font-weight: 600; position: relative; z-index: 1; }
.hafen-balken { position: absolute; inset: 0 auto 0 0; width: calc( var(--anteil, 0) * 100% ); background: var(--primary-weak); z-index: 0; }
.hafen-fluss { margin: .15rem 0 .35rem 5.3rem; color: var(--muted); font-size: .85rem; }

/* --- Zoom 2: Reede --- */
.reede { display: grid; grid-template-columns: repeat( auto-fill, minmax( 260px, 1fr ) ); gap: var(--gap); }
.reede-kopf { display: flex; align-items: center; justify-content: space-between; gap: .6rem; margin-bottom: .5rem; }
.reede-kopf h2 { margin: 0; }
.reede-karte { cursor: default; }
.reede-grund { margin: .2rem 0 0; color: var(--muted); font-size: .85rem; }
.reede-rest { margin-top: .6rem; display: flex; gap: .4rem; flex-wrap: wrap; align-items: baseline; }
.link-btn { background: transparent; border: 0; color: var(--primary); cursor: pointer; padding: 0; font: inherit; text-decoration: underline; }

/* --- Zoom 3: Hafenliste. Der Browser malt nur, was jemand sieht. --- */
.sort-btn { background: transparent; border: 0; color: inherit; font: inherit; cursor: pointer; padding: 0; text-transform: inherit; letter-spacing: inherit; }
.hafen-row { content-visibility: auto; contain-intrinsic-size: auto 2.6rem; }
.seiten { display: flex; align-items: center; justify-content: center; gap: 1rem; margin-top: .8rem; flex-wrap: wrap; }

/* --- Die oberste Schicht: Segel. Abschaltbar, nie die Grundlage. --- */
.segel-zeile { margin-bottom: .8rem; }
.segel { position: relative; height: 30px; overflow: hidden; border-radius: var(--radius-sm); }
.segel-welle { position: absolute; inset: auto 0 0 0; height: 12px; opacity: .5;
	background: repeating-linear-gradient( 90deg, var(--primary-weak) 0 14px, transparent 14px 28px );
	animation: segel-duenung 15s linear infinite; }
.segel-boot { position: absolute; bottom: 6px; left: -6%; font-size: 1rem; line-height: 1;
	/* Inhaber-Feedback 29.07.2026: 11s wirkten hektisch ("etwa 300% zu
	 * schnell"). Faktor 3 auf Fahrt, Duenung UND --verzug (seekarte.js),
	 * damit der Abstand der Boote zueinander gleich aussieht. */
	animation: segel-fahrt 33s linear infinite; animation-delay: var(--verzug, 0s); }
@keyframes segel-fahrt { from { transform: translateX(0); } to { transform: translateX(112vw); } }
@keyframes segel-duenung { from { background-position-x: 0; } to { background-position-x: 28px; } }
.segel-text { margin: .2rem 0 0; font-variant-numeric: tabular-nums; }

/* Angehalten statt entfernt: im Hintergrund-Tab und bei Systemwunsch. */
.segel--ruhig .segel-boot,
.segel--ruhig .segel-welle { animation-play-state: paused; }
@media ( prefers-reduced-motion: reduce ) {
	.segel-boot, .segel-welle { animation: none; }
	.segel-boot { position: static; display: inline-block; margin-right: .2rem; }
	.segel { height: auto; }
}

@media ( max-width: 860px ) {
	.reede { grid-template-columns: 1fr; }
	.hafen-fluss { margin-left: 0; }
}

/* --- Bootfahrt: der Kontakt segelt zum naechsten Hafen (Board) ------------
 *
 * Ein Boetchen begleitet jeden Stufenwechsel - per Auswahlmenue wie per Maus.
 * Es haengt an body und ist fixiert, damit die Koordinaten aus
 * getBoundingClientRect() unveraendert passen.
 *
 * Ausschliesslich Zierde: Die Karte steht im Ziel, bevor das Boot ankommt.
 * Abschaltbar ueber denselben Segel-Schalter wie die Seekarte (Profil) - eine
 * zweite Mechanik fuer dieselbe Entscheidung waere Ballast -, und automatisch
 * aus bei prefers-reduced-motion. `pointer-events: none` ist Pflicht, sonst
 * faengt das Boot Klicks auf dem Weg ab.
 *
 * WARUM `zug-boot` und nicht `segel-boot`: Die Seekarte oben in dieser Datei
 * belegt `.segel-boot` bereits fuer ihre endlos fahrenden Boote
 * (`animation: segel-fahrt 11s linear infinite`). Der erste Entwurf hier hiess
 * genauso - und die Board-Boote erbten am 28.07.2026 prompt beide Animationen:
 * meine 900-ms-Fahrt UND die 11-Sekunden-Endlosschleife quer ueber den Schirm.
 * Zwei Effekte, ein Klassenname, ein Element.
 */
.zug-boot {
	position: fixed;
	z-index: 60;
	pointer-events: none;
	font-size: 1.6rem;
	line-height: 1;
	will-change: transform, opacity;
	filter: drop-shadow( 0 2px 4px rgba( 0, 0, 0, .35 ) );
}

.zug-boot::before {
	content: "\26F5"; /* Boot mit Segel */
}

@media (prefers-reduced-motion: reduce) {
	/* Doppelter Boden: fahrtPlan() gibt hier ohnehin schon null zurueck. */
	.zug-boot { display: none; }
}
