/* ==========================================================================
   VISARO — Startseite: Hero
   --------------------------------------------------------------------------
   Links die Textführung, rechts das Shirt (Plugin „VISARO Shirt Hero",
   Shortcode [visaro_shirt], E259). Bis 2026-10-07 stand dort der
   „Werkstattstapel" aus fünf Musterplatten (E32).

   Das Shirt rendert selbst: WebGL auf transparentem Grund, Ersatzbild bis
   das Modell steht, Pause außerhalb des Bildes, im inaktiven Tab und bei
   reduzierter Bewegung. Dieses Stylesheet gibt ihm nur den Platz — und den
   fest, damit beim Laden nichts springt.

   Alle Werte aus tokens.css.
   ========================================================================== */

/* ══════════════════════════════════════════════════════════════════════════
   BÜHNE
   ══════════════════════════════════════════════════════════════════════════ */

.vis-hero {
	position: relative;
	overflow: hidden;
	isolation: isolate;

	background: var(--vis-grad-navy);
	color: var(--vis-white);

	--vis-text: var(--vis-white);
	--vis-text-2: var(--vis-ink-300);
	--vis-text-3: var(--vis-ink-400);
	--vis-border: var(--vis-ink-800);
	--vis-border-strong: var(--vis-ink-700);
	--vis-accent-text: var(--vis-purple-400);

	/* Der Hero trägt den transparenten Header. Der Kopfbereich muss also
	   so viel Luft haben, dass die Navigation nicht auf dem Kicker sitzt. */
	padding-block-start: calc(var(--vis-header-height) + var(--vis-section-s));

	/* Unten steht nicht einfach ein Abstand, sondern die Kante des nächsten
	   Abschnitts.

	   Der Einstieg zieht sich um die Höhe der 60°-Schräge nach oben
	   (`--vis-cut-lg / --vis-tan60`, rund 69 px) und schneidet seine linke
	   obere Ecke weg. Links beginnt das Weiß damit 69 px über der
	   Hero-Unterkante — bei festen 64 px Abstand lief es der Spec-Zeile
	   also buchstäblich in den Rücken: „01 START" stand 5 px *unter* der
	   Kante statt darüber. Rechts fiel es nicht auf, weil die Schräge dort
	   auf der Unterkante endet.

	   Deshalb ist der Abstand jetzt **abgeleitet** statt geraten: die
	   Kantenhöhe plus ein echter Abstand. Ändert sich `--vis-cut-lg`,
	   rechnet sich die Zeile mit — und sie kann nie wieder verschluckt
	   werden. Auf dem Telefon greift dieselbe Rechnung, obwohl die
	   Hero-Schräge dort bewusst gleich groß bleibt. */
	padding-block-end: calc(var(--vis-cut-lg) / var(--vis-tan60) + var(--vis-space-8));
}


/* ── Licht ───────────────────────────────────────────────────────────────
   Ein lila Lichtpunkt auf dem Navy-Verlauf. Er folgt dem Zeiger (hero.js
   schreibt --vis-hero-lx/-ly) und atmet sonst langsam — kein Glanz auf
   Elementen, nur Licht im Raum. Auf Touch und bei reduzierter Bewegung
   steht er still an seiner Ruhelage. */

.vis-hero::before {
	content: "";
	position: absolute;
	z-index: 0;
	inset-inline-start: var(--vis-hero-lx, 72%);
	inset-block-start: var(--vis-hero-ly, 38%);
	inline-size: min(90vmax, 1100px);
	aspect-ratio: 1;
	translate: -50% -50%;
	background: var(--vis-light-lilac);
	opacity: 0.85;
	pointer-events: none;
	transition: inset-inline-start var(--vis-duration-cinematic) var(--vis-ease-out), inset-block-start var(--vis-duration-cinematic) var(--vis-ease-out);
	animation: vis-hero-breathe var(--vis-duration-ambient) var(--vis-ease-inout) infinite alternate;
}

.vis-hero::after {
	content: "";
	position: absolute;
	z-index: 0;
	inset: auto -10% -30% -10%;
	block-size: 60%;
	background: radial-gradient(60% 60% at 30% 100%, color-mix(in srgb, var(--vis-violet-deep) 90%, transparent), transparent 70%);
	pointer-events: none;
}

@keyframes vis-hero-breathe {
	from { scale: 0.92; opacity: 0.7; }
	to   { scale: 1.06; opacity: 0.95; }
}

@media (prefers-reduced-motion: reduce) {
	.vis-hero::before { animation: none; transition: none; }
}
/* ── Werkstattraster ─────────────────────────────────────────────────────
   Fünf senkrechte Haarlinien auf dem Spaltenraster. Sie liegen hinter
   allem und geben der Fläche Maßstab — dieselbe Idee wie die Risslinien
   auf einem Werkstattplan. Auf schmalen Geräten entfallen sie: Dort ist
   die Fläche zu klein, das Raster würde nur unruhig. */

.vis-hero__grid {
	position: absolute;
	inset: 0;
	z-index: 0;
	display: none;

	max-width: var(--vis-container-wide);
	margin-inline: auto;
	padding-inline: var(--vis-gutter);

	pointer-events: none;
}

.vis-hero__grid span {
	position: absolute;
	inset-block: 0;
	inline-size: var(--vis-border-width);
	background: linear-gradient(
		to bottom,
		transparent,
		var(--vis-ink-800) 12%,
		var(--vis-ink-800) 80%,
		transparent
	);
}

.vis-hero__grid span:nth-child(1) { inset-inline-start: 0; }
.vis-hero__grid span:nth-child(2) { inset-inline-start: 25%; }
.vis-hero__grid span:nth-child(3) { inset-inline-start: 50%; }
.vis-hero__grid span:nth-child(4) { inset-inline-start: 75%; }
.vis-hero__grid span:nth-child(5) { inset-inline-end: 0; }

@media (min-width: 1024px) {
	.vis-hero__grid { display: block; }
}

.vis-hero__inner {
	position: relative;
	z-index: 1;

	max-width: var(--vis-container-wide);
	margin-inline: auto;
	padding-inline: var(--vis-gutter);

	display: grid;
	gap: var(--vis-space-12);
}

/* Zwei Spalten erst ab 1280, nicht schon ab 1024.

   Bei 1024 bliebe für den Text eine Spalte von rund 475 px — die
   Überschrift zerfiele dort in fünf schmale Zeilen, während sie daneben in
   dreien steht. Auf einem Tablet in Querlage ist das Bild unter dem Text
   die bessere Komposition als ein gequetschter Satz neben ihm.

   Das Verhältnis 1.45 zu 1 gibt dem Text so viel Raum, dass die
   Überschrift auch bei 1280 in drei bis vier Zeilen steht. */
@media (min-width: 1280px) {
	.vis-hero__inner {
		grid-template-columns: minmax(0, 1.45fr) minmax(0, 1fr);
		gap: var(--vis-space-10);
		align-items: center;
		min-block-size: min(76vh, var(--vis-stage-height-max));
	}
}

/* ══════════════════════════════════════════════════════════════════════════
   TEXTFÜHRUNG
   ══════════════════════════════════════════════════════════════════════════ */

.vis-hero__text {
	position: relative;
	z-index: 2;
	min-inline-size: 0;
}

.vis-hero__kicker {
	display: flex;
	align-items: center;
	gap: var(--vis-space-3);
	margin: 0 0 var(--vis-space-6);

	color: var(--vis-text-2);
	font-family: var(--vis-font-mono);
	font-size: var(--vis-fs-label);
	font-weight: var(--vis-fw-medium);
	letter-spacing: var(--vis-ls-label);
	text-transform: uppercase;
}

.vis-hero__kicker .vis-marker { flex: none; }

/* Die Überschrift ist das größte Element der Seite — aber sie ist ein
   Satz, kein Plakat.

   display-l statt display-xl: Bei 96 px zerfiel der Satz in fünf schmale
   Zeilen und wurde zur Wortliste. Bei 72 px und 19 Zeichen Maß steht er in
   drei Zeilen, und der Umbruch fällt an den richtigen Stellen —
   „Wir machen Werbung, / die zu deinem / Unternehmen passt."

   `text-wrap: balance` verteilt die Zeilen gleichmäßig, wenn die Spalte
   schmaler wird; auf dem Telefon bricht der Satz dadurch natürlich um,
   ohne dass eine Zeile mit einem einzelnen Wort endet. */
.vis-hero__headline {
	margin: 0;
	max-inline-size: 19ch;

	font-size: var(--vis-fs-display-l);
	font-weight: var(--vis-fw-bold);
	line-height: var(--vis-lh-display);
	letter-spacing: var(--vis-ls-display);
	text-wrap: balance;
}

/* Ab der zweispaltigen Stufe begrenzt die Spalte, nicht das Zeichenmaß —
   sonst wirken beide Grenzen gegeneinander und der Satz bricht enger als
   nötig. */
@media (min-width: 1280px) {
	.vis-hero__headline { max-inline-size: none; }
}

.vis-hero__lead {
	margin: var(--vis-space-6) 0 0;
	max-inline-size: 46ch;

	color: var(--vis-text-2);
	font-size: var(--vis-fs-body-l);
}

/* ── Die kurze Zeile ─────────────────────────────────────────────────────
   Sie ersetzt die frühere Leistungsaufzählung. Weiß und in Medium statt
   grau: Es ist eine Aussage, keine Fußnote. Der Marker davor bindet sie
   an den Kicker oben — beide gehören zur Marke, der Text dazwischen zum
   Angebot. */

.vis-hero__claim {
	display: flex;
	align-items: center;
	gap: var(--vis-space-3);
	margin: var(--vis-space-6) 0 0;

	color: var(--vis-white);
	font-size: var(--vis-fs-body-l);
	font-weight: var(--vis-fw-medium);
	letter-spacing: var(--vis-ls-heading);
}

.vis-hero__claim::before {
	content: "";
	flex: none;

	inline-size: var(--vis-space-2);
	block-size: calc(var(--vis-space-2) / var(--vis-tan60) * 2);

	background: var(--vis-purple-500);
	clip-path: polygon(0 0, 100% 50%, 0 100%);
}

.vis-hero__actions {
	display: flex;
	flex-wrap: wrap;
	gap: var(--vis-space-4);
	margin-block-start: var(--vis-space-10);
}

/* ── Faktenzeile ─────────────────────────────────────────────────────────
   Nur belegte Angaben. Keine erfundenen Zahlen (Non-Negotiable 10). */

.vis-hero__facts {
	display: flex;
	flex-wrap: wrap;
	gap: var(--vis-space-8);
	margin: var(--vis-space-12) 0 0;
	padding-block-start: var(--vis-space-6);
	border-block-start: var(--vis-border-width) solid var(--vis-border);
}

.vis-hero__fact dt {
	margin-block-end: var(--vis-space-2);
	color: var(--vis-text-3);
	font-family: var(--vis-font-mono);
	font-size: var(--vis-fs-label);
	letter-spacing: var(--vis-ls-label);
	text-transform: uppercase;
}

.vis-hero__fact dd {
	margin: 0;
	font-size: var(--vis-fs-body);
	font-weight: var(--vis-fw-medium);
}

/* ══════════════════════════════════════════════════════════════════════════
   DAS SHIRT

   Die Höhe kommt aus --vis-hero-shirt-height und steht fest, bevor Skript
   oder Modell da sind: Ersatzbild und Canvas liegen absolut darin, das
   Layout kennt die Fläche also vom ersten Byte an (kein Layoutsprung).
   Die Regel ist bewusst eine Klasse stärker als die des Plugins, damit
   seine Vorgabehöhe (clamp mit 48vw) hier nicht greift.
   ══════════════════════════════════════════════════════════════════════════ */

.vis-hero__shirt {
	position: relative;
	min-inline-size: 0;
	/* Rein gezeichnet: Der Zeiger im Shirt ist Teil der Animation, die echte
	   Maus wird über das Fenster gelesen. Klicks gehen durch. */
	pointer-events: none;
}

/* Am Desktop darf die Bühne bis an den Seitenrand reichen: Die Breite der
   Spalte begrenzt sonst die Größe des Shirts, nicht seine Höhe. */
@media (min-width: 1280px) {
	.vis-hero__shirt { margin-inline-end: calc(-1 * var(--vis-gutter)); }
}

.vis-hero__shirt .visaro-shirt-hero {
	block-size: var(--vis-hero-shirt-height);
}

/* ══════════════════════════════════════════════════════════════════════════
   SPEC-ZEILE
   Das Werkstattdetail am Fuß. Sie markiert zugleich die Kante zum
   nächsten Abschnitt.
   ══════════════════════════════════════════════════════════════════════════ */

.vis-hero__spec {
	position: relative;
	z-index: 1;

	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: var(--vis-space-6);

	max-width: var(--vis-container-wide);
	margin: var(--vis-space-16) auto 0;
	padding-inline: var(--vis-gutter);
	padding-block-start: var(--vis-space-5);

	color: var(--vis-text-3);
	font-family: var(--vis-font-mono);
	font-size: var(--vis-fs-label);
	letter-spacing: var(--vis-ls-label);
	text-transform: uppercase;
}

.vis-hero__spec::before {
	content: "";
	position: absolute;
	inset-block-start: 0;
	inset-inline: var(--vis-gutter);
	block-size: var(--vis-border-width);
	background: var(--vis-ink-800);
}

.vis-hero__spec-item {
	display: inline-flex;
	align-items: center;
	gap: var(--vis-space-3);
}

.vis-hero__spec .vis-index { color: var(--vis-purple-400); }

.vis-hero__scroll {
	display: inline-flex;
	align-items: center;
	gap: var(--vis-space-3);
}

/* Ein kurzer Strich statt eines hüpfenden Pfeils. Er läuft nicht dauerhaft,
   sondern ist eine ruhige Kante — Bewegung erklärt, sie dekoriert nicht.

   Deshalb genau ein Durchgang beim Laden, danach steht die Kante still.
   Eine Endlosschleife wäre eine Daueranimation (motion.css schließt sie
   aus) und nach WCAG 2.2.2 ohne Pause-Schalter nicht zulässig. */
.vis-hero__scroll-rail {
	display: block;
	inline-size: var(--vis-space-10);
	block-size: var(--vis-border-width);
	background: var(--vis-ink-700);
	position: relative;
	overflow: hidden;
}

.vis-hero__scroll-rail::after {
	content: "";
	position: absolute;
	inset-block: 0;
	inset-inline-start: 0;
	inline-size: 40%;
	background: var(--vis-purple-500);
	transform: translateX(-100%);
	animation: vis-hero-rail 2.8s var(--vis-ease-inout) 1;
}

@keyframes vis-hero-rail {
	0%   { transform: translateX(-100%); }
	55%  { transform: translateX(250%); }
	100% { transform: translateX(250%); }
}

/* ══════════════════════════════════════════════════════════════════════════
   RESPONSIVE

   Unterhalb von 1280 px steht das Shirt unter dem Text.
   ══════════════════════════════════════════════════════════════════════════ */

@media (max-width: 1023.98px) {
	.vis-hero {
		padding-block-start: calc(var(--vis-header-height-mobile) + var(--vis-space-12));
	}
}

@media (max-width: 767.98px) {
	.vis-hero__facts { gap: var(--vis-space-6); }
	.vis-hero__spec { margin-block-start: var(--vis-space-12); }
}

/* ══════════════════════════════════════════════════════════════════════════
   REDUZIERTE BEWEGUNG

   Kein laufender Strich. Das Shirt hält selbst an (Vorderansicht).
   ══════════════════════════════════════════════════════════════════════════ */

@media (prefers-reduced-motion: reduce) {
	.vis-hero__scroll-rail::after { animation: none; transform: none; inline-size: 100%; }
}
