feat(web): restore tall hero + carousel slide + viewport-fixed scroll cue
All checks were successful
Deploy to Production / deploy (push) Successful in 1m0s
All checks were successful
Deploy to Production / deploy (push) Successful in 1m0s
Three coordinated tweaks to the landing-page above-the-fold: 1. **Hero padding restored to py-14/sm:py-20/md:py-28** (was py-12/14/16). Compressing it for the scroll-cue position fight made the hero feel cramped and gave the ParticleHero background less room to breathe. With the cue moved out (see #3), there's no reason to shrink the hero. 2. **Step rotator switches to carousel-style horizontal slide.** The AnimatePresence transition was a fade+y-shift cross-fade — clean but sequential. Now the leaving card slides left out (x:-220) while the entering card slides right in (x:220→0), both coexisting in the same 3D-space and inheriting the same mouse-tilt. The container gets `min-h-[240px]` so the absolutely-positioned cards have layout to anchor to (claude_desktop_config.json is the tallest at 7 lines). Reduced-motion still gets the opacity-only cross-fade — sliding content sideways is exactly the kind of motion that preference is meant to suppress. 3. **`<ScrollCue>` extracted into its own client component**, fixed- positioned at viewport bottom (bottom-5) with a frosted pill style. Fades to opacity:0 once `window.scrollY > 80`, so it doesn't shadow the rest of the page. Lives next to `<section>` in page.tsx rather than inside the hero — that way it anchors to the loadscreen's natural bottom edge whether the hero is short or tall. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
43
apps/web/components/scroll-cue.tsx
Normal file
43
apps/web/components/scroll-cue.tsx
Normal file
@@ -0,0 +1,43 @@
|
||||
'use client';
|
||||
|
||||
import { ChevronDown } from 'lucide-react';
|
||||
import { useEffect, useState } from 'react';
|
||||
|
||||
/**
|
||||
* Scroll cue — a fixed pill anchored to the bottom of the viewport that
|
||||
* points the visitor down to the flow video below the hero. Fades out
|
||||
* once the user has scrolled past the loadscreen so it doesn't follow
|
||||
* them around the page.
|
||||
*
|
||||
* Lives at z-30 so it sits above the hero content but below modals.
|
||||
* The frosted pill (backdrop-blur + border) reads clearly against the
|
||||
* particle background without stealing focus from the H1.
|
||||
*/
|
||||
export function ScrollCue({ targetId }: { targetId: string }) {
|
||||
const [visible, setVisible] = useState(true);
|
||||
|
||||
useEffect(() => {
|
||||
function onScroll() {
|
||||
setVisible(window.scrollY < 80);
|
||||
}
|
||||
onScroll();
|
||||
window.addEventListener('scroll', onScroll, { passive: true });
|
||||
return () => window.removeEventListener('scroll', onScroll);
|
||||
}, []);
|
||||
|
||||
return (
|
||||
<a
|
||||
href={`#${targetId}`}
|
||||
aria-label="See the flow in action"
|
||||
className={`fixed inset-x-0 bottom-5 z-30 mx-auto flex w-fit items-center gap-1.5 rounded-full border border-[--color-border] px-3 py-1.5 text-[10.5px] uppercase tracking-[0.18em] text-[--color-fg-subtle] backdrop-blur transition-opacity duration-500 hover:text-[--color-fg] ${
|
||||
visible ? 'opacity-100' : 'pointer-events-none opacity-0'
|
||||
}`}
|
||||
style={{
|
||||
backgroundColor: 'color-mix(in oklab, var(--color-bg-elevated) 75%, transparent)',
|
||||
}}
|
||||
>
|
||||
<span>see it run</span>
|
||||
<ChevronDown size={12} className="animate-bounce" />
|
||||
</a>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user