Smooth Scrolling
Relevant source files
The following files were used as context for generating this wiki page:
Smooth scrolling in the Wasalny landing page is a core UX feature implemented to provide a fluid, momentum-based scrolling experience. It integrates the Lenis library with GSAP (GreenSock Animation Platform) to ensure that scroll-based animations, such as parallax effects and scroll triggers, remain synchronized with the user's viewport movement.
This system is encapsulated within a React context provider, allowing components throughout the application to programmatically control the scroll position, stop or start scrolling, and interact with the scroll instance.
Sources: src/providers/SmoothScrollProvider.tsx:1-5, AGENTS.md:15-18
System Architecture
The smooth scrolling implementation relies on a provider-consumer pattern. The SmoothScrollProvider initializes the Lenis engine and exposes its API through a React Context.
Core Components
- Lenis Engine: Handles the high-performance momentum scrolling logic.
- GSAP Ticker: Synchronizes the Lenis frame updates with GSAP's internal animation loop.
- ScrollTrigger Sync: Updates GSAP's
ScrollTriggerplugin on every Lenis scroll event to ensure layout-dependent animations are accurate.
The following diagram illustrates the initialization and synchronization flow of the smooth scroll system:
A flowchart showing the initialization of the Lenis engine and its integration with GSAP for global synchronization.
Sources: src/providers/SmoothScrollProvider.tsx:28-56, src/App.tsx:25-45
Provider Implementation
The SmoothScrollProvider uses useLayoutEffect to initialize the Lenis instance before the browser paints, preventing jumps in scroll position during the initial load.
Initialization Parameters
The system is configured with specific physics and behavior settings to achieve a premium feel:
| Parameter | Value | Description |
|---|---|---|
duration | 1.2 | The duration of the scroll animation in seconds. |
easing | expo.out | Exponential easing function for natural deceleration. |
orientation | 'vertical' | Primary scroll axis. |
smoothWheel | true | Enables smooth interpolation for mouse wheel input. |
wheelMultiplier | 1 | Sensitivity multiplier for the mouse wheel. |
touchMultiplier | 2 | Sensitivity multiplier for touch devices. |
Sources: src/providers/SmoothScrollProvider.tsx:30-40
Integration with GSAP Ticker
To ensure consistent frame rates and avoid "jitter" between scroll-based animations and the scroll itself, the Lenis .raf() method is hooked into the gsap.ticker. Additionally, lagSmoothing is disabled in GSAP to maintain synchronization.
// Add Lenis to GSAP Ticker
const rafCallback = (time: number) => {
lenisInstance.raf(time * 1000);
};
gsap.ticker.add(rafCallback);
// Disable lag smoothing in GSAP to prevent jumpiness with Lenis
gsap.ticker.lagSmoothing(0);
Sources: src/providers/SmoothScrollProvider.tsx:47-53
Interaction API
The system provides a custom hook useLenis to allow functional components to interact with the scroll engine.
Context Methods
| Method | Description |
|---|---|
scrollTo(target, options) | Smoothly scrolls to a specific selector, HTMLElement, or pixel value. |
stop() | Pauses the scroll engine (often used for modals or loading screens). |
start() | Resumes the scroll engine. |
lenis | Direct access to the Lenis instance for advanced event listening. |
Sources: src/providers/SmoothScrollProvider.tsx:10-18, src/providers/SmoothScrollProvider.tsx:64-74
Styling and CSS Integration
For Lenis to function correctly, the project includes specific CSS configurations in src/index.css. This includes managing the html height and handling overscroll behavior for elements that should ignore the global smooth scroll.
/* Lenis smooth scroll */
html.lenis, html.lenis body {
height: auto;
}
.lenis.lenis-smooth {
scroll-behavior: auto !important;
}
.lenis.lenis-smooth [data-lenis-prevent] {
overscroll-behavior: contain;
}
.lenis.lenis-stopped {
overflow: hidden;
}
Sources: src/index.css:216-232
Dependency Flow
Smooth scrolling is the foundation for several other animation systems within the project, specifically those provided by useAnimations.ts.
A sequence diagram showing how user input flows through Lenis to GSAP and finally to custom animation hooks.
Sources: src/hooks/useAnimations.ts:75-90, src/lib/gsap.ts:65-72
Summary
The Smooth Scrolling system is a robust integration of Lenis and GSAP, managed via the SmoothScrollProvider. By centralizing the scroll engine in a React Provider, the project ensures that all scroll-based interactions—from simple momentum scrolling to complex parallax effects—are synchronized and performant. This architecture also facilitates global control over scrolling, such as disabling input during the PageLoader phase or while modals are active.
Sources: src/App.tsx:25-30, src/providers/SmoothScrollProvider.tsx:75-80