Files
einfach-produktiv/app/not-found.tsx
T
Marco 3cf45cfb16 Use real Figma assets for 404 page, subtle icon zoom instead of color
- Replace both placeholder images with the actual exports pulled from
  the built Figma page-404 (node 4692:341, file jCCZyh1DGwdjpv1wGge9To):
  testimonial-photo (4699:372) at full 810x306 resolution, and the
  sticky-note-404 (4693:382) — a real photographed/rendered note, not the
  hand-coded CSS+Caveat approximation this had before.
- Help-link icon hover: subtle scale-110 zoom (matching Testimonials.tsx's
  avatar hover) instead of a color inversion.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-07-19 20:24:39 +00:00

201 lines
8.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import type { Metadata } from "next";
import Link from "next/link";
import { Reveal, RevealGroup, RevealItem } from "./components/Reveal";
import { Footer } from "./components/Footer";
import { TrustRow } from "./components/TrustRow";
export const metadata: Metadata = {
title: "Seite nicht gefunden",
description: "Diese Seite ist gerade nicht dort, wo sie sein sollte.",
robots: { index: false, follow: true },
};
const helpLinks = [
{
href: "/",
title: "Startseite",
desc: "Zurück zu den wichtigsten Inhalten und Angeboten.",
cta: "Zur Startseite",
icon: (
<svg viewBox="0 0 24 24" className="size-6" fill="none" aria-hidden="true">
<path
d="M4 11.5 12 4l8 7.5M6 9.5V20h5v-5.5h2V20h5V9.5"
stroke="currentColor"
strokeWidth="1.6"
strokeLinecap="round"
strokeLinejoin="round"
/>
</svg>
),
},
{
href: "/blog",
title: "Im Blog stöbern",
desc: "Lass dich von Impulsen, Methoden und Gedanken inspirieren.",
cta: "Zum Blog",
icon: (
<svg viewBox="0 0 24 24" className="size-6" fill="none" aria-hidden="true">
<path
d="M6 3.5h9.5L20 8v12.5a1 1 0 0 1-1 1H6a1 1 0 0 1-1-1v-16a1 1 0 0 1 1-1Z"
stroke="currentColor"
strokeWidth="1.6"
strokeLinejoin="round"
/>
<path d="M8.5 9.5h7M8.5 13h7M8.5 16.5h4.5" stroke="currentColor" strokeWidth="1.6" strokeLinecap="round" />
</svg>
),
},
{
href: "/#werkzeuge",
title: "Werkzeuge entdecken",
desc: "Praktische Tools für mehr Fokus, Struktur und Klarheit.",
cta: "Zu den Werkzeugen",
icon: (
<svg viewBox="0 0 24 24" className="size-6" fill="none" aria-hidden="true">
<path
d="M4 9.5h16a1 1 0 0 1 1 1V19a1 1 0 0 1-1 1H4a1 1 0 0 1-1-1v-8.5a1 1 0 0 1 1-1Z"
stroke="currentColor"
strokeWidth="1.6"
strokeLinejoin="round"
/>
<path
d="M8.5 9.5V7a2 2 0 0 1 2-2h3a2 2 0 0 1 2 2v2.5"
stroke="currentColor"
strokeWidth="1.6"
strokeLinejoin="round"
/>
</svg>
),
},
];
export default function NotFound() {
return (
<>
<main className="flex flex-col flex-1 bg-bg-base">
{/* Hero — eyebrow / Ups. / subheading / copy / CTA, sticky note beside it */}
<div className="flex flex-col lg:flex-row gap-12 lg:gap-16 items-center pt-16 pb-20 px-[var(--layout-padding-x)] w-full">
<Reveal className="flex flex-col gap-4 items-start w-full lg:flex-1 max-w-[32rem]">
<p className="font-semibold text-body-sm text-brand tracking-wide">404 Seite nicht gefunden</p>
<p
className="font-semibold text-[3.5rem] leading-[1.05] text-text-primary"
style={{ fontFamily: "var(--font-lora)" }}
>
Ups.
</p>
<p
className="font-semibold text-h-feature text-text-primary"
style={{ fontFamily: "var(--font-lora)" }}
>
Diese Seite ist gerade nicht dort, wo sie sein sollte.
</p>
<div className="h-[0.125rem] w-8 bg-brand" />
<p className="text-body text-text-muted">
Vielleicht wurde sie verschoben, umbenannt oder es hat sich ein kleiner Tippfehler eingeschlichen.
</p>
<p className="text-body text-text-muted">Aber kein Problem wir bringen dich gerne zurück auf Kurs.</p>
<Link
href="/"
className="group flex items-center gap-2 mt-2 px-7 py-4 rounded-sm bg-brand text-h4 font-bold text-text-primary hover:bg-brand-hover active:scale-[0.97] transition-all"
>
Zur Startseite
<svg
viewBox="0 0 20 20"
className="size-4 transition-transform duration-200 group-hover:translate-x-1"
fill="none"
aria-hidden="true"
>
<path d="M4 10h12m0 0-5-5m5 5-5 5" stroke="currentColor" strokeWidth="1.75" strokeLinecap="round" strokeLinejoin="round" />
</svg>
</Link>
</Reveal>
{/* Sticky note — real asset exported straight from the built
Figma page (page-404, node 4693:382), not a hand-coded
approximation — matches project convention of using the
actual photographed/rendered note rather than recreating its
handwriting in CSS. */}
<Reveal delay={0.15} className="w-full lg:flex-1 flex items-center justify-center">
<img
alt="Sticky Note: 404. Nicht hier. Aber dein Ziel ist sicher nicht weit."
src="/404-sticky-note.png"
className="w-full max-w-[22rem] rotate-2 hover:rotate-0 transition-transform duration-300"
/>
</Reveal>
</div>
{/* Help links */}
<div className="flex flex-col gap-10 items-center pb-16 px-[var(--layout-padding-x)] w-full">
<Reveal className="flex flex-col items-center gap-2">
<p
className="font-semibold text-h-small text-text-primary"
style={{ fontFamily: "var(--font-lora)" }}
>
Vielleicht hilft dir das weiter:
</p>
<div className="h-[0.125rem] w-8 bg-brand" />
</Reveal>
<RevealGroup className="grid grid-cols-1 md:grid-cols-3 gap-10 md:gap-8 w-full max-w-[64rem] divide-y md:divide-y-0 md:divide-x divide-border">
{helpLinks.map((link) => (
<RevealItem
key={link.href}
className="group flex flex-col items-center text-center gap-3 pt-10 md:pt-0 first:pt-0 px-4 transition-transform duration-200 hover:-translate-y-1"
>
<div className="flex size-14 items-center justify-center rounded-full bg-bg-muted text-brand transition-transform duration-300 group-hover:scale-110">
{link.icon}
</div>
<p className="font-semibold text-body text-text-primary">{link.title}</p>
<p className="text-body-sm text-text-muted">{link.desc}</p>
<Link href={link.href} className="flex items-center gap-1.5 text-body-sm font-semibold text-text-primary hover:underline">
{link.cta}
<svg
viewBox="0 0 20 20"
className="size-3.5 transition-transform duration-200 group-hover:translate-x-1"
fill="none"
aria-hidden="true"
>
<path d="M4 10h12m0 0-5-5m5 5-5 5" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round" />
</svg>
</Link>
</RevealItem>
))}
</RevealGroup>
</div>
{/* Testimonial band — photo bleeds to the viewport edge, gradient
fade into bg-base on its trailing edge instead of a hard cut,
same idea as page-bestellbestaetigung's photo+quote pattern.
404-testimonial-photo.jpg is cropped directly from the actual
mockup pixels (mockups/einfach-produktiv_mockup_404.png) rather
than reusing an unrelated existing asset — same real-photo
extraction convention the Figma rebuild used, just done on the
flat mockup image instead of in Figma. */}
<Reveal className="relative w-full flex items-stretch min-h-[16rem] bg-bg-muted overflow-hidden">
<div className="relative w-full md:w-[45%] shrink-0">
<img
alt=""
src="/404-testimonial-photo.jpg"
className="absolute inset-0 w-full h-full object-cover"
/>
<div className="hidden md:block absolute inset-y-0 right-0 w-40 bg-gradient-to-l from-bg-muted to-transparent" />
</div>
<div className="flex-1 flex flex-col justify-center gap-3 px-8 md:px-16 py-12">
<p
className="font-semibold text-h-section text-text-primary leading-[1.3] max-w-[28rem]"
style={{ fontFamily: "var(--font-lora)" }}
>
Manchmal führt der falsche Weg zu neuen klaren Gedanken.
</p>
<div className="h-[0.125rem] w-8 bg-brand" />
<p className="text-body text-text-muted">Björn</p>
</div>
</Reveal>
<TrustRow />
</main>
<Footer />
</>
);
}