diff --git a/website/app.js b/website/app.js index ce98527..cd974df 100644 --- a/website/app.js +++ b/website/app.js @@ -379,19 +379,19 @@ document.addEventListener('DOMContentLoaded', () => { } }; + // Listen for `click`, not `pointerdown`: a click never fires while the + // page is being scrolled, so touch users no longer trigger a shower of + // leaves every time they swipe. Leaves are also only shed by actual + // interactive controls (links/buttons and the demo widgets), so a stray + // tap on plain text or an illustration stays quiet. let lastBurst = 0; - document.addEventListener('pointerdown', (e) => { - if (e.button !== 0 || !e.isPrimary) return; + document.addEventListener('click', (e) => { + const control = e.target.closest('a, button, [role="button"], .btn, .mock-tab, select, .demo-progress'); + if (!control) return; const now = Date.now(); if (now - lastBurst < 180) return; lastBurst = now; - const control = e.target.closest('button, [role="button"], .btn, .mock-tab, select, .demo-progress'); - if (control) { - burstFromElement(control); - } else { - const count = 4 + Math.floor(Math.random() * 3); - for (let i = 0; i < count; i++) spawnLeaf(e.clientX, e.clientY); - } + burstFromElement(control); }, { passive: true }); } diff --git a/website/styles/demo.css b/website/styles/demo.css index 890a53c..b30f1c4 100644 --- a/website/styles/demo.css +++ b/website/styles/demo.css @@ -1147,12 +1147,8 @@ html.theme-light .hero-demo-scene .demo-video::after { font-size: 1.1rem; pointer-events: none; z-index: 10; - animation: pointer-click 1.6s infinite ease-in-out; -} - -@keyframes pointer-click { - 0%, 100% { transform: translate(0, 0) scale(1); } - 50% { transform: translate(-3px, -3px) scale(0.9); } + /* Static hand — the looping tap bob was the busiest part of step 2 and + distracted from the copy (step 3 keeps its lively animation). */ } /* Step 3 forest movie continuous animation bindings */ diff --git a/website/styles/foundation.css b/website/styles/foundation.css index bc502aa..b9a3714 100644 --- a/website/styles/foundation.css +++ b/website/styles/foundation.css @@ -119,8 +119,11 @@ body { /* --- Animated Bamboo Forest Background (v3 Greens Update) --- */ .bg-nature { - --sway: 1.2deg; - --leaf-drift: 26px; + /* Motion dialled back so the scene reads as a calm backdrop rather than + competing with the text that scrolls over it (sway/drift roughly + halved from the original 1.2deg / 26px). */ + --sway: 0.6deg; + --leaf-drift: 13px; } .bg-nature { @@ -354,11 +357,20 @@ body { @keyframes leafFall { 0% { transform: translateY(-40px) rotate(0); opacity: 0; } - 8% { opacity: 0.65; } - 92% { opacity: 0.5; } + 8% { opacity: 0.3; } + 92% { opacity: 0.24; } 100% { transform: translateY(110vh) translateX(120px) rotate(280deg); opacity: 0; } } +/* Thin the drifting leaves down to four so fewer of them cross the reading + column at once (the even ones stay hidden, keeping an even spread). */ +.fall-leaf-2, +.fall-leaf-4, +.fall-leaf-6, +.fall-leaf-8 { + display: none; +} + @keyframes leafSway { 0%, 100% { margin-left: 0; } 50% { margin-left: var(--leaf-drift, 26px); } @@ -413,8 +425,8 @@ body { .godray-3 { left: 56%; width: 140px; animation-duration: 13s; animation-delay: -6s; background: linear-gradient(180deg, oklch(0.85 0.05 110 / 0.08), transparent 75%); } @keyframes rayShimmer { - 0% { opacity: 0.45; } - 100% { opacity: 1; } + 0% { opacity: 0.35; } + 100% { opacity: 0.6; } } /* (e) Canopy: dark vignette at the top plus hanging leaf arcs */ @@ -579,8 +591,8 @@ body { } @keyframes fireflyPulse { - 0%, 100% { opacity: 0.2; transform: scale(1); } - 50% { opacity: 0.9; transform: scale(1.35); } + 0%, 100% { opacity: 0.15; transform: scale(1); } + 50% { opacity: 0.55; transform: scale(1.2); } } @keyframes fireflyWander { @@ -675,8 +687,8 @@ html.theme-light .bg-horizon { left: -30%; width: 160%; height: 160%; - background: linear-gradient(115deg, transparent 42%, oklch(0.68 0.13 150 / 0.05) 50%, transparent 58%); - animation: lightSweep 26s ease-in-out infinite alternate; + background: linear-gradient(115deg, transparent 42%, oklch(0.68 0.13 150 / 0.03) 50%, transparent 58%); + animation: lightSweep 38s ease-in-out infinite alternate; will-change: transform; } @@ -1061,12 +1073,15 @@ html.theme-light :is(.use-case-card, .feature-card, .faq-item, .comparison-table padding: 0 2rem; } +/* Unified vertical rhythm: every content section shares one padding scale so + the page reads as an even cadence instead of a series of tall, half-empty + panels. Tightened from the old fixed 6rem. */ section { - padding: 6rem 0; + padding: clamp(3.5rem, 6.5vh, 5rem) 0; } #how-it-works { - padding: 4.5rem 0; + padding: clamp(3.5rem, 6.5vh, 5rem) 0; } /* Content-visibility for offscreen sections to improve INP */ diff --git a/website/styles/hero.css b/website/styles/hero.css index 8afdb89..8baa836 100644 --- a/website/styles/hero.css +++ b/website/styles/hero.css @@ -1,10 +1,13 @@ /* --- Hero Section --- */ .hero { - min-height: 100vh; + min-height: 100svh; display: flex; - align-items: flex-start; - padding-top: clamp(8rem, 12vh, 10rem); - padding-bottom: clamp(2rem, 5vh, 4rem); + /* Centre the hero content vertically so the empty space is balanced above + and below instead of pooling under the CTAs. Padding-top only needs to + clear the fixed nav. */ + align-items: center; + padding-top: clamp(6rem, 9vh, 8rem); + padding-bottom: clamp(3rem, 6vh, 5rem); } .hero-grid { @@ -20,7 +23,6 @@ gap: 3rem; text-align: left; width: 100%; - min-height: calc(100svh - 12.5rem); } @media (min-width: 1024px) { @@ -333,6 +335,25 @@ html.theme-light .koala-speech-bubble::after { .btn-install.is-detected .btn-label-short { display: none; } .btn-install.is-detected .btn-label-full { display: inline; } +/* GitHub is the tertiary hero action. Strip the button chrome so it reads as a + quiet link beside the two install CTAs, keeping a clear primary → secondary → + tertiary hierarchy (Chrome filled → Firefox outline → GitHub text). The + theme-light selector matches the specificity of the light-theme .btn-secondary + override in foundation.css so the transparent treatment wins in both themes. */ +.hero-github-cta.btn-secondary, +html.theme-light .hero-github-cta.btn-secondary { + background: transparent; + border-color: transparent; + color: var(--text-muted); +} + +.hero-github-cta.btn-secondary:hover, +html.theme-light .hero-github-cta.btn-secondary:hover { + background: transparent; + color: var(--text); + transform: none; +} + .version-badge { display: inline-block; background: oklch(0.68 0.13 150 / 0.1); diff --git a/website/styles/join.css b/website/styles/join.css index e9b2ff8..8521c3e 100644 --- a/website/styles/join.css +++ b/website/styles/join.css @@ -54,15 +54,10 @@ .selfhost-mascot { display: block; - width: 300px; + width: 220px; height: auto; margin: 0 auto; - filter: drop-shadow(0 4px 12px rgba(0,0,0,0.15)); - transition: transform 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275); -} - -.selfhost-mascot:hover { - transform: scale(1.05) translateY(-4px) rotate(-1deg); + filter: drop-shadow(0 6px 14px oklch(0.15 0.02 145 / 0.22)); } .status-ring { diff --git a/website/styles/landing-controls.css b/website/styles/landing-controls.css index 13f5ef7..35544eb 100644 --- a/website/styles/landing-controls.css +++ b/website/styles/landing-controls.css @@ -167,11 +167,6 @@ html.theme-light .lang-dropdown option { max-width: 270px; width: 100%; height: auto; - transition: transform 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275); -} - -.compat-mascot:hover { - transform: scale(1.05) translateY(-5px) rotate(1deg); } .compat-heading { diff --git a/website/styles/landing-primary.css b/website/styles/landing-primary.css index 692d25c..b436f08 100644 --- a/website/styles/landing-primary.css +++ b/website/styles/landing-primary.css @@ -51,15 +51,8 @@ pointer-events: none; } -.feature-card:hover { - transform: translateY(-5px); - box-shadow: 0 15px 30px oklch(0.68 0.13 150 / 0.2); - border-color: oklch(0.68 0.13 150 / 0.3); -} - -.feature-card:hover::before { - background: linear-gradient(to bottom right, oklch(0.68 0.13 150 / 0.3), transparent); -} +/* Feature cards are static content, not links — no hover lift/glow, so they + don't read as clickable. */ /* Feature Icon with Inline SVG Wrapper */ .feature-icon-svg { @@ -73,14 +66,6 @@ color: var(--accent); border-radius: 12px; margin-right: 14px; - transition: background 0.3s ease, color 0.3s ease, box-shadow 0.3s ease, transform 0.3s ease; -} - -.feature-card:hover .feature-icon-svg { - background: var(--accent); - color: var(--text-on-green); - box-shadow: 0 0 15px var(--accent-glow); - transform: scale(1.05); } .bento-icon { @@ -152,11 +137,6 @@ right: 2.5rem; height: 2px; background: linear-gradient(90deg, transparent, oklch(0.68 0.13 150 / 0.4), transparent); - opacity: 0; - transition: opacity 0.3s ease; -} - -.feature-card.bento-large:hover::after { opacity: 1; } @@ -237,7 +217,7 @@ .steps { display: flex; flex-direction: column; - gap: 4rem; + gap: 2.75rem; } .step { @@ -331,11 +311,7 @@ html.theme-light .step-num { } } -.step-illustration-1:hover, .step-illustration-2:hover, .step-illustration-3:hover { - transform: translateY(-6px) scale(1.02); - border-color: oklch(0.68 0.13 150 / 0.25); - box-shadow: 0 25px 50px oklch(0.68 0.13 150 / 0.15), inset 0 1px 0 rgba(255, 255, 255, 0.1); -} +/* Step illustrations are screenshots, not controls — no hover lift/scale. */ /* ========================================================================== Step 1 Illustration: Browser & Installed Success Popup @@ -704,28 +680,14 @@ html.theme-light .step-num { position: relative; overflow: hidden; cursor: default; - animation: create-btn-pulse 2s infinite alternate; -} - -@keyframes create-btn-pulse { - 0% { transform: scale(1); box-shadow: 0 4px 12px oklch(0.68 0.13 150 / 0.3); } - 100% { transform: scale(1.03); box-shadow: 0 6px 16px oklch(0.68 0.13 150 / 0.5); } + /* Static: the constant scale/shadow pulse pulled the eye away from the + copy while reading the steps (step 3 keeps the lively animation). */ } +/* Shine sweep removed — kept the element off-canvas so the button reads as a + calm static control rather than a repeatedly glinting one. */ .illus-btn-shine { - position: absolute; - top: 0; - left: -100%; - width: 50%; - height: 100%; - background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.25), transparent); - transform: skewX(-20deg); - animation: shimmer-sweep 3s infinite ease-in-out; -} - -@keyframes shimmer-sweep { - 0% { left: -100%; } - 50%, 100% { left: 150%; } + display: none; } .illus-collapsed-details { @@ -764,16 +726,12 @@ html.theme-light .step-num { align-items: center; gap: 4px; box-shadow: 0 6px 14px rgba(0, 0, 0, 0.45), 0 0 12px oklch(0.68 0.13 150 / 0.18); - animation: floating-success-fade 5s infinite; + /* Shown statically instead of fading in and out on a loop — the toast now + reads as part of the popup state rather than a flashing notification. */ white-space: nowrap; z-index: 10; } -@keyframes floating-success-fade { - 0%, 100%, 75% { opacity: 0; transform: translate(-50%, 5px) scale(0.9); } - 15%, 60% { opacity: 1; transform: translate(-50%, 0) scale(1); } -} - .illus-floating-success .success-icon { font-size: 0.65rem; } @@ -1022,16 +980,6 @@ html.theme-light .step-illustration-3 { inset 0 1px 0 rgba(255, 255, 255, 0.9); } -html.theme-light .step-illustration-1:hover, -html.theme-light .step-illustration-2:hover, -html.theme-light .step-illustration-3:hover { - border-color: oklch(0.56 0.13 150 / 0.28); - box-shadow: - 0 22px 44px oklch(0.20 0.025 140 / 0.15), - 0 0 22px oklch(0.56 0.13 150 / 0.10), - inset 0 1px 0 #ffffff; -} - html.theme-light .step-illustration-1 .illus-popup-card, html.theme-light .step-illustration-2 .illus-popup-card, html.theme-light .step-illustration-3 .illus-player-card { diff --git a/website/styles/landing-sections.css b/website/styles/landing-sections.css index 96bf997..11be630 100644 --- a/website/styles/landing-sections.css +++ b/website/styles/landing-sections.css @@ -1,6 +1,6 @@ /* --- Use Cases / Anwendungsszenarien Section --- */ .use-cases-section { - padding: 6rem 0; + padding: clamp(3.5rem, 6.5vh, 5rem) 0; position: relative; border-bottom: 0; } @@ -12,6 +12,18 @@ margin-top: 1rem; } +/* Sub-heading that separates the use-case scenarios from the feature tiles so + the two card types read as intentional groups (and gives the "Features" nav + link a real target). */ +.section-subheading { + text-align: center; + font-size: 1.55rem; + font-weight: 800; + letter-spacing: -0.03em; + margin: 3.25rem 0 1.5rem; + scroll-margin-top: 96px; +} + .use-cases-feature-grid { grid-template-columns: repeat(3, minmax(0, 1fr)); } @@ -63,13 +75,9 @@ .use-case-card:nth-child(3) { --card-accent-border: oklch(0.75 0.10 150); } -.use-case-card:hover { - transform: translateY(-5px); - box-shadow: 0 12px 30px rgba(0, 0, 0, 0.35); - border-color: rgba(255, 255, 255, 0.15); -} - -.use-case-card:hover::before { +/* Use-case cards are static content, not links — no hover lift so they don't + read as clickable. The top accent bar (::before) stays visible instead. */ +.use-case-card::before { opacity: 1; } @@ -91,30 +99,30 @@ margin: 1.5rem auto; } +/* Shared framing so the section mascots read as one set even though the + underlying illustrations differ slightly in style (a consistent, soft ground + shadow — true art-direction alignment needs the assets themselves redrawn). */ +.compat-mascot, +.features-questions-mascot, +.comparison-mascot, +.selfhost-mascot { + filter: drop-shadow(0 6px 14px oklch(0.15 0.02 145 / 0.22)); +} + .features-questions-mascot { display: block; width: 100%; - max-width: 250px; + max-width: 185px; height: auto; - margin: -1.5rem auto 0.2rem auto; - transition: transform 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275); -} - -.features-questions-mascot:hover { - transform: scale(1.05) translateY(-4px) rotate(-1.5deg); + margin: -1rem auto 0.4rem auto; } .comparison-mascot { display: block; width: 100%; - max-width: 260px; + max-width: 195px; height: auto; - margin: -2.2rem auto 0.2rem auto; - transition: transform 0.3s cubic-bezier(0.175, 0.885, 0.32, 1.275); -} - -.comparison-mascot:hover { - transform: scale(1.05) translateY(-4px) rotate(1deg); + margin: -1.4rem auto 0.4rem auto; } .use-case-icon { @@ -141,7 +149,7 @@ /* --- Comparison Section --- */ .comparison-section { - padding: 6rem 0; + padding: clamp(3.5rem, 6.5vh, 5rem) 0; background: transparent; border-bottom: 0; } diff --git a/website/styles/legal.css b/website/styles/legal.css index 26a78ce..d9d856c 100644 --- a/website/styles/legal.css +++ b/website/styles/legal.css @@ -101,6 +101,16 @@ .nav-links.open { display: flex; } + /* The dropdown panel is dark-green by default; in the light theme that + hard-coded colour clashed with the pale navbar and washed out the link + text. Match the panel and its links to the active theme instead. */ + .nav-links a { + color: var(--text); + } + html.theme-light .nav-links { + background: oklch(0.95 0.01 100 / 0.97); + border-bottom-color: oklch(0.20 0.025 140 / 0.10); + } .nav-right { margin-left: auto; } @@ -144,12 +154,8 @@ @media (min-width: 769px) and (max-height: 920px) { .hero { - padding-top: clamp(7.5rem, 10vh, 9rem); - padding-bottom: clamp(1.5rem, 3vh, 2.75rem); - } - - .hero-grid { - min-height: calc(100svh - 9.5rem); + padding-top: clamp(6.5rem, 9vh, 8rem); + padding-bottom: clamp(2rem, 4vh, 3.5rem); } } diff --git a/website/template.html b/website/template.html index 621547f..29b6e07 100644 --- a/website/template.html +++ b/website/template.html @@ -960,8 +960,13 @@

{{USE_CASE_3_DESC}}

+ +

+ {{NAV_FEATURES}} +

+
-
+

@@ -1166,11 +1171,6 @@ {{STEP_2_ILLUS_MANUAL}}

- -
- - {{STEP_2_ILLUS_COPIED}} -
@@ -1510,7 +1510,7 @@ -
+

{{BOTTOM_TITLE}}