SkillAgentSearch skills...

BasicScroll

Standalone parallax scrolling for mobile and desktop with CSS variables.

Install / Use

/learn @electerious/BasicScroll
About this skill

Quality Score

0/100

Supported Platforms

Universal

README

basicScroll

Donate via PayPal

Standalone parallax scrolling for mobile and desktop with CSS variables.

basicScroll allows you to change CSS variables depending on the scroll position. Use the variables directly in your CSS to animate whatever you want. Highly inspired by skrollr and Reactive Animations with CSS Variables.

Contents

Demos

| Name | Description | Link | Author | |:-----------|:------------|:------------|:------------| | Default | Includes most features | Try it on CodePen | | Callback | Animate properties in JS via callbacks | Try it on CodePen | | Parallax scene | A composition of multiple, moving layers | Try it on CodePen | @electerious | | Rolling eyes | Custom element to track scrolling | Try it on CodePen | @electerious | | Headline explosion | Animated letters | Try it on CodePen | @electerious | | Scroll and morph | Morph text using CSS clip-path | Try it on CodePen | @mikaelainalem | | Parallax with JS | Several examples and a debug mode | Try it on CodePen | AnimatiCSS |

Tutorials

| Name | Link | |:-----------|:------------| | 📃 Parallax scrolling with JS controlled CSS variables | Read it on Medium | | 🎬 Apple-like scroll animations | Watch it on YouTube | | 🎬 Parallax effect tutorial (🇪🇸) | Watch it on YouTube |

Features

  • Framework independent
  • Insane performance
  • Support for mobile and desktop
  • CommonJS and AMD support
  • Simple JS API

Requirements

basicScroll depends on the following browser features and APIs:

Some of these APIs are capable of being polyfilled in older browsers. Check the linked resources above to determine if you must polyfill to achieve your desired level of browser support.

Setup

We recommend installing basicScroll using npm or yarn.

npm install basicscroll
yarn add basicscroll

Include the JS file at the end of your body tag…

<script src="dist/basicScroll.min.js"></script>

…or skip the JS file and use basicScroll as a module:

const basicScroll = require('basicscroll')
import * as basicScroll from 'basicscroll'

Usage

This demo shows how to to change the opacity of an element when the user scrolls. The element starts to fade as soon as the top of the element reaches the bottom of the viewport. A opacity of .99 is reached when the middle of the element is in the middle of the viewport.

Tip: Animating from .01 to .99 avoids the repaints that normally occur when the element changes from fully transparent to translucent and from translucent to fully visible.

const instance = basicScroll.create({
	elem: document.querySelector('.element'),
	from: 'top-bottom',
	to: 'middle-middle',
	props: {
		'--opacity': {
			from: .01,
			to: .99
		}
	}
})

instance.start()
.element {
	/*
	 * Use the same CSS variable as specified in our instance.
	 */
	opacity: var(--opacity);
	/*
	 * The will-change CSS property provides a way for authors to hint browsers about the kind of changes
	 * to be expected on an element, so that the browser can setup appropriate optimizations ahead of time
	 * before the element is actually changed.
	 */
	will-change: opacity;
}

API

.create(html, opts)

Creates a new basicScroll instance.

Be sure to assign your instance to a variable. Using your instance, you can…

  • …start and stop the animation.
  • …check if the instance is active.
  • …get the current props.
  • …recalculate the props when the window size changes.

Examples:

const instance = basicScroll.create({
	from: '0',
	to: '100px',
	props: {
		'--opacity': {
			from: 0,
			to: 1
		}
	}
})
const instance = basicScroll.create({
	elem: document.querySelector('.element'),
	from: 'top-bottom',
	to: 'bottom-top',
	props: {
		'--translateY': {
			from: '0',
			to: '100%',
			timing: 'elasticOut'
		}
	}
})
const instance = basicScroll.create({
	elem: document.querySelector('.element'),
	from: 'top-middle',
	to: 'bottom-middle',
	inside: (instance, percentage, props) => {
		console.log('viewport is inside from and to')
	},
	outside: (instance, percentage, props) => {
		console.log('viewport is outside from and to')
	}
})

Parameters:

  • data {Object} An object of data.

Returns:

  • {Object} The created instance.

Instance API

Each basicScroll instance has a handful of handy functions. Below are all of them along with a short description.

.start()

Starts to animate the instance. basicScroll will track the scroll position and adjust the props of the instance accordingly. An update will be performed only when the scroll position has changed.

Example:

instance.start()

.stop()

Stops to animate the instance. All props of the instance will keep their last value.

Example:

instance.stop()

.destroy()

Destroys the instance. Should be called when the instance is no longer needed. All props of the instance will keep their last value.

Example:

instance.destroy()

.update()

Triggers an update of an instance, even when the instance is currently stopped.

Example:

const props = instance.update()

Returns:

  • {Object} Applied props.

.calculate()

Converts the start and stop position of the instance to absolute values. basicScroll relies on those values to start and stop the animation at the right position. It runs the calculation once during the instance creation. .calculate() should be called when elements have altered their position or when the size of the site/viewport has changed.

Example:

instance.calculate()

.isActive()

Returns true when the instance is started and false when the instance is stopped.

Example:

instance.isActive()

Returns:

  • {Boolean}

.getData()

Returns calculated data. More or less a parsed version of the data used for the instance creation. The data might change when calling the calculate function.

Example:

instance.getData()

Returns:

  • {Object} Parsed data.

Data

The data object can include the following properties:

{
	/*
	 * DOM element/node.
	 */
	elem: null,
	/*
	 * Start and stop position.
	 */
	from: null,
 	to: null,
	/*
	 * Direct mode.
	 */
	direct: false,
	/*
	 * Track window size changes.
	 */
	track: true,
	/*
	 * Callback functions.
	 */
	inside: (instance, percentage, props) => {},
	outside: (instance, percentage, props) => {},
	/*
	 * Props.
	 */
	props: {
		/*
		 * Property name / CSS Custom Properties.
		 */
		'--name': {
			/*
			 * Start and end values.
			 */
			from: null,
			to: null,
			/*
			 * Animation timing.
			 */
			timing: 'ease'
		}
	}
}

DOM element/node

Type: Node Default: null Optional: true

A DOM element/node.

The position and size of the element will be used to convert the start and stop position to absolute values. How else is basicScroll supposed to know when to start and stop an animation with relative values?

You can skip the property when using absolute values.

Example:

{
	elem: document.querySelector('.element')
	/* ... */
}

Start and stop position

Type: Integer|String Default: null Optional: false

basicScroll starts to animate the props when the scroll position is above from and below to. Absolute and relative values are allowed.

Relative values require a DOM element/node. The first part of the value describes the element position, the last part describes the viewport position: <element>-<viewport>. middle-bottom in from specifies that the animation starts when the middle of the element reaches the bottom of the viewport.

Known relative values: top-top, top-middle, top-bottom, middle-top, middle-middle, middle-bottom, bottom-top, bottom-middle, bottom-bottom

It's possible to track a custom anchor when you want to animate for a specific viewport height or when you need to start and end with an offset.

Examples:

{
	/* ... */
	from: '0px',
	to: '100px',
	/* ... */
}
{
	/* ... */
	from: 0,
	to: 360,
	/* ... */
}
{
	/* ... */
	from: 'top-middle',
	to: 'bottom-middle',
	/* ... */
}

Direct mode

Type: Boolean|Node Default: false Opti

Related Skills

View on GitHub
GitHub Stars3.6k
CategoryDevelopment
Updated3d ago
Forks150

Languages

JavaScript

Security Score

95/100

Audited on Mar 20, 2026

No findings