@zeitonline/scrolleo
v1.0.3
Published
Lightweight scrollytelling library using IntersectionObserver
Maintainers
Readme
Scrolleo
A modern & lightweight Vanilla JS library for scrollytelling experiences
No dependencies, no framework, pure ESM.
About
Scrolleo is a modernization of scrollama with:
- Performance improvements
- Improved TypeScript definitions
- A modern ESM-only build
Why?
Scrollytelling can be complicated to implement and difficult to make performant. The goal of this library is to provide a simple interface for creating scroll-driven interactives. Scrolleo is focused on performance by using IntersectionObserver to handle element position detection.
Examples
Check out the demo gallery to see Scrolleo in action:
- Basic - Basic step enter/exit functionality
- Progress - Track scroll progress through steps with visual feedback
- Sticky Side - Sticky graphic on the side with scrolling text
- Sticky Overlay - Sticky graphic overlay pattern
- Percentage Offset - Per-step offset customization using percentages
- Pixel Offset - Fixed pixel-based offsets for mobile-friendly experiences
- Multiple Instances - Multiple scrolleo instances on the same page
- Nested Scroll Container - Using a nested scroll container instead of window
- Performance Test - Performance monitoring with multiple instances
Installation
npm install @zeitonline/scrolleoAnd then import it:
import scrolleo from '@zeitonline/scrolleo';How to use
Basic
Create step elements in your HTML:
<section id="scrolly">
<article>
<div class="step">
<p>Step 1</p>
</div>
<div class="step">
<p>Step 2</p>
</div>
<div class="step">
<p>Step 3</p>
</div>
</article>
</section>Then initialize Scrolleo and set up your callbacks:
import scrolleo from '@zeitonline/scrolleo';
// Create a scrolleo instance
const scroller = scrolleo();
// Setup with options and attach callbacks
scroller
.setup({
step: '#scrolly article .step',
offset: 0.5, // Trigger when step is 50% from top of viewport
debug: false, // Set to true to see visual debugging
})
.onStepEnter((response) => {
// Called when a step enters the offset threshold
const { element, index, direction } = response;
element.classList.add('is-active');
console.log(`Step ${index} entered from ${direction}`);
})
.onStepExit((response) => {
// Called when a step exits the offset threshold
const { element, index, direction } = response;
element.classList.remove('is-active');
console.log(`Step ${index} exited to ${direction}`);
});The response object contains:
element: The DOM element that triggered the callbackindex: The zero-based index of the stepdirection: Either'up'or'down'indicating scroll direction
API
scrolleo.setup([options])
options:
| Option | Type | Description | Default |
| --------- | ----------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | --------- |
| step | string or HTMLElement[] | required Selector (or array of elements) for the step elements that will trigger changes. | |
| offset | number (0 - 1, or string with "px") | How far from the top of the viewport to trigger a step. | 0.5 |
| progress | boolean | Whether to fire incremental step progress updates or not. | false |
| threshold | number (1 or higher) | The granularity of the progress interval in pixels (smaller = more granular). | 4 |
| once | boolean | Only trigger the step to enter once then remove listener. | false |
| debug | boolean | Whether to show visual debugging tools or not. | false |
| parent | HTMLElement[] | Parent element for step selector (use if you steps are in shadow DOM). | undefined |
| container | HTMLElement | Parent element for the scroll story (use if scrollama is nested in a HTML element with overflow set to scroll or auto) | undefined |
| root | HTMLElement | The element that is used as the viewport for checking visibility of the target. Must be the ancestor of the target. Defaults to the browser viewport if not specified or if null. See more details about usage of root on MDN. | undefined |
scrolleo.onStepEnter(callback)
Callback that fires when the top or bottom edge of a step element enters the offset threshold.
The argument of the callback is an object: { element: DOMElement, index: number, direction: string }
element: The step element that triggered
index: The index of the step of all steps
direction: 'up' or 'down'
scrolleo.onStepExit(callback)
Callback that fires when the top or bottom edge of a step element exits the offset threshold.
The argument of the callback is an object: { element: DOMElement, index: number, direction: string }
element: The step element that triggered
index: The index of the step of all steps
direction: 'up' or 'down'
scrolleo.onStepProgress(callback)
Callback that fires the progress (0 - 1) a step has made through the threshold.
The argument of the callback is an object: { element: DOMElement, index: number, progress: number }
element: The step element that triggered
index: The index of the step of all steps
progress: The percent of completion of the step (0 - 1)
direction: 'up' or 'down'
scrolleo.offset([number or string])
Get or set the offset percentage. Value must be between 0-1 (where 0 = top of viewport, 1 = bottom), or a string that includes "px" (e.g., "200px"). If set, returns the scrolleo instance.
scrolleo.resize()
This is no longer necessary with the addition of a built-in resize observer. Tell scrolleo to get latest dimensions the browser/DOM. It is best practice to throttle resize in your code, update the DOM elements, then call this function at the end.
scrolleo.enable()
Tell scrolleo to resume observing for trigger changes. Only necessary to call if you have previously disabled.
scrolleo.disable()
Tell scrolleo to stop observing for trigger changes.
scrolleo.destroy()
Removes all observers and callback functions.
custom offset
To override the offset passed in the options, set a custom offset for an individual element using data attributes. For example: <div class="step" data-offset="0.25"> or data-offset="100px".
Alternatives
- scrollama (the original library)
- Scroll Trigger
- Waypoints
- ScrollMagic
- graph-scroll.js
- ScrollStory
- enter-view
Credits
This project is a modernization and rebrand of scrollama by Russell Samora.
Original scrollama is licensed under the MIT License. This version maintains the same license and includes the original copyright notice. Scrolleo is maintained by DIE ZEIT / ZeitOnline.
License
MIT License - see LICENSE file for details.
