first commit
Docker-Images bauen und veroeffentlichen / build-and-push (push) Failing after 1m32s

This commit is contained in:
Nick Szaunig committed 2026-09-27 06:06:56 +02:00
commit 59bb5a38a3
132 files changed
+19435

No files matched your search

+88
View File
@@ -0,0 +1,88 @@
import { site } from "@/content/site";
import type { PublicCampFacts } from "@/lib/camp";
import { formatEuroShort } from "@/lib/money";
import type { PublicPricing } from "@/lib/public-page";
import { formatIsoDateLong } from "@/lib/time";
import { MediaFrame } from "./MediaFrame";
import { BookButton } from "./booking/BookingProvider";
export function dateLine(facts: PublicCampFacts): string {
if (!facts.startDate) return "Termin wird bekanntgegeben";
if (!facts.endDate) return `ab ${formatIsoDateLong(facts.startDate)}`;
return `${formatIsoDateLong(facts.startDate)} bis ${formatIsoDateLong(facts.endDate)}`;
}
export function priceLine(pricing: PublicPricing): string {
if (pricing.phase === "EARLY_BIRD" && pricing.currentCents !== null) {
return `${formatEuroShort(pricing.currentCents)} Early Bird statt ${formatEuroShort(pricing.regularCents)}`;
}
if (pricing.phase === "REGULAR" && pricing.currentCents !== null) return `${formatEuroShort(pricing.currentCents)} pro Person`;
return `Early Bird ab 1. November 2026: ${formatEuroShort(pricing.earlyBirdCents)}`;
}
/**
* Hero als Magazin-Cover: der Masthead "ARTISTA" ueberlappt das Leitbild,
* Termin, Ort und Preis stehen als Cover-Lines daneben.
*/
export function Hero({ facts, pricing, showDrafts }: { facts: PublicCampFacts; pricing: PublicPricing; showDrafts: boolean }) {
const place = facts.location ? `${facts.location}${facts.region ? `, ${facts.region}` : ""}` : "Italien";
return (
<section id="top" aria-labelledby="hero-title" className="relative pb-16 pt-4 md:pb-24">
<div className="container-edge">
<p className="hero-fade flex items-baseline justify-between border-b border-ink pb-2 text-sm">
<span>Modelcamp 2027</span>
<span>{place}</span>
</p>
<h1 id="hero-title" className="relative z-10 mt-3">
<span className="masthead hero-rise block" aria-hidden>
ARTISTA
</span>
<span className="sr-only">ARTISTA Modelcamp 2027 – {site.hero.headline}</span>
</h1>
<div className="mt-[-3.2vw] grid gap-8 md:grid-cols-12 md:gap-10">
<div className="hero-image md:col-span-7 lg:col-span-8">
<MediaFrame
media={site.hero.media}
aspect="aspect-[4/5] md:aspect-[5/4] lg:aspect-[16/11]"
sizes="(min-width: 1024px) 66vw, (min-width: 768px) 58vw, 100vw"
showLabel={showDrafts}
priority
/>
</div>
<div className="hero-fade flex flex-col justify-end md:col-span-5 lg:col-span-4">
<p className="display text-[2.25rem] leading-[1.05] md:text-[2.75rem]">{site.hero.headline}</p>
<p className="mt-5 max-w-md text-lg text-ink/85">{site.hero.subline}</p>
<dl className="mt-8 divide-y divide-line border-y border-line text-[0.9375rem]">
<div className="flex justify-between gap-4 py-3">
<dt className="text-stone">Termin</dt>
<dd className="text-right">{dateLine(facts)}</dd>
</div>
<div className="flex justify-between gap-4 py-3">
<dt className="text-stone">Ort</dt>
<dd className="text-right">{facts.location ?? "Italien, genauer Ort folgt"}</dd>
</div>
<div className="flex justify-between gap-4 py-3">
<dt className="text-stone">Preis</dt>
<dd className="text-right">{priceLine(pricing)}</dd>
</div>
</dl>
<div className="mt-8 flex flex-wrap gap-3">
{pricing.checkoutOpen ? (
<BookButton className="btn btn-primary">Platz buchen</BookButton>
) : (
<a href="#preis" className="btn btn-primary">
Preis und Buchungsstart
</a>
)}
<a href="#camp" className="btn btn-quiet">
Mehr über das Camp
</a>
</div>
</div>
</div>
</div>
</section>
);
}