Add ToDo-Karten product page, fluid design tokens, and Navbar/Hero fixes
New /todo-cards page (Hero, How-it-works, Focus, Testimonials, Pricing) built with the fluid clamp() token system (app/lib/fluid.ts) and scroll-reveal animations (app/components/Reveal.tsx), matching styling consistency with /challenge's testimonial section. Navbar: page-aware active state and anchor-link navigation from any route (not just "/"), fixed logo click to actually navigate instead of silently rewriting the URL, fluid nav text size, custom hash-scroll handling for cross-page anchor links. Hero: responsive breakpoint fix for the text/image split at Tablet widths, entrance animation for the brand's orange dot, removed a red dot artifact from hero.png. Also includes prior uncommitted work on About/Blog/Newsletter/Footer and the cart lib (app/lib/cart.ts). Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
+61
-50
@@ -1,57 +1,68 @@
|
||||
export function Divider() {
|
||||
import { Reveal } from "./Reveal";
|
||||
|
||||
function Word({ children }: { children: string }) {
|
||||
return (
|
||||
<div className="flex items-center justify-center pb-[1.25rem] pt-[3rem] w-full bg-[#f5f0e8]">
|
||||
<div className="flex gap-[2rem] items-center overflow-clip shrink-0">
|
||||
<p
|
||||
className="font-bold leading-normal text-text-primary text-h2 whitespace-nowrap"
|
||||
style={{ fontFamily: "var(--font-caveat)" }}
|
||||
>
|
||||
{children}
|
||||
</p>
|
||||
);
|
||||
}
|
||||
|
||||
<p
|
||||
className="font-bold leading-normal text-[#222221] text-[2rem] whitespace-nowrap"
|
||||
style={{ fontFamily: "var(--font-caveat)" }}
|
||||
>
|
||||
Klarheit
|
||||
</p>
|
||||
|
||||
{/* Arrow separator (flipped) */}
|
||||
<div className="flex items-center justify-center">
|
||||
<div className="-scale-y-100 rotate-180">
|
||||
<div className="h-[0.75rem] relative w-[2.625rem]">
|
||||
<img alt="" src="/icon-separator.svg" className="absolute inset-0 w-full h-full" />
|
||||
</div>
|
||||
</div>
|
||||
function Arrow() {
|
||||
return (
|
||||
<div className="flex items-center justify-center shrink-0">
|
||||
<div className="-scale-y-100 rotate-180">
|
||||
<div className="relative" style={{ height: "var(--divider-arrow-h)", width: "var(--divider-arrow-w)" }}>
|
||||
<img alt="" src="/icon-separator.svg" className="absolute inset-0 w-full h-full" />
|
||||
</div>
|
||||
|
||||
<p
|
||||
className="font-bold leading-normal text-[#222221] text-[2rem] whitespace-nowrap"
|
||||
style={{ fontFamily: "var(--font-caveat)" }}
|
||||
>
|
||||
Fokus
|
||||
</p>
|
||||
|
||||
{/* Arrow separator (flipped) */}
|
||||
<div className="flex items-center justify-center">
|
||||
<div className="-scale-y-100 rotate-180">
|
||||
<div className="h-[0.75rem] relative w-[2.625rem]">
|
||||
<img alt="" src="/icon-separator.svg" className="absolute inset-0 w-full h-full" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p
|
||||
className="font-bold leading-normal text-[#222221] text-[2rem] whitespace-nowrap"
|
||||
style={{ fontFamily: "var(--font-caveat)" }}
|
||||
>
|
||||
Entlastung
|
||||
</p>
|
||||
|
||||
{/* Sparkle icon */}
|
||||
<div className="flex items-center justify-center h-[2.506rem] w-[1.919rem]">
|
||||
<div style={{ rotate: "4.6deg" }}>
|
||||
<div className="h-[2.375rem] relative w-[1.734rem]">
|
||||
<img alt="" src="/icon-separator-right.svg" className="absolute inset-0 w-full h-full" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export function Divider() {
|
||||
return (
|
||||
<Reveal className="flex items-center justify-center flex-wrap gap-x-8 gap-y-3 pb-5 pt-12 px-[var(--layout-padding-x)] w-full bg-bg-base text-center">
|
||||
|
||||
{/* Word + its trailing icon are grouped into one shrink-0 flex unit
|
||||
so flex-wrap only ever breaks BETWEEN pairs, never leaving an
|
||||
arrow stranded alone on its own line — the arrows are always
|
||||
visible now (previously hidden below md: entirely to sidestep
|
||||
that exact problem), this fixes the root cause instead. */}
|
||||
<div className="flex items-center gap-8 shrink-0">
|
||||
<Word>Klarheit</Word>
|
||||
<Arrow />
|
||||
</div>
|
||||
|
||||
<div className="flex items-center gap-8 shrink-0">
|
||||
<Word>Fokus</Word>
|
||||
<Arrow />
|
||||
</div>
|
||||
|
||||
<div className="flex items-center gap-8 shrink-0">
|
||||
<Word>Entlastung</Word>
|
||||
|
||||
{/* Sparkle icon — sizes now fluid (--divider-sparkle-*) to match
|
||||
the text-h2 words next to it, previously hard rem values that
|
||||
stayed visually static while the words scaled. */}
|
||||
<div
|
||||
className="flex items-center justify-center"
|
||||
style={{ height: "var(--divider-sparkle-h)", width: "var(--divider-sparkle-w)" }}
|
||||
>
|
||||
<div style={{ rotate: "4.6deg" }}>
|
||||
<div
|
||||
className="relative"
|
||||
style={{ height: "var(--divider-sparkle-inner-h)", width: "var(--divider-sparkle-inner-w)" }}
|
||||
>
|
||||
<img alt="" src="/icon-separator-right.svg" className="absolute inset-0 w-full h-full" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</Reveal>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user