Scroll Progress Number
Displays the current scroll progress as a zero-padded percentage number, updated in real time via a GSAP ScrollTrigger scrub on the full document body.
gsapscrolltriggerscrollprogresscounter
Setup — External Scripts
Setup: External Scripts
html
<script src="https://cdn.jsdelivr.net/npm/gsap@3.12.5/dist/gsap.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/gsap@3.12.5/dist/ScrollTrigger.min.js"></script>Code
index.html
html
<p data-progress-nr="" class="progress-nr">00</p>styles.css
css
.progress-nr {
margin: 0px;
font-size: 5em;
font-weight: 500;
line-height: 1;
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}script.js
javascript
gsap.registerPlugin(ScrollTrigger);
function initScrollProgressNumber() {
const progressCounter = document.querySelector('[data-progress-nr]');
ScrollTrigger.create({
trigger: document.body,
start: 'top top',
end: 'bottom bottom',
scrub: 0.5,
onUpdate: (self) => {
const progress = Math.round(self.progress * 100); // Calculate progress as a percentage
progressCounter.textContent = progress.toString().padStart(2, '0'); // Update counter
},
});
}
// Initialize Scroll Progress Number
document.addEventListener('DOMContentLoaded', () => {
initScrollProgressNumber();
});Guide
Overview
A ScrollTrigger instance spans the entire document body and fires onUpdate on every scroll tick. The progress value (0–1) is multiplied by 100, rounded, and written as a zero-padded two-digit string into the counter element.
Attribute
Add data-progress-nr to any element you want to use as the counter. The script targets it with querySelector, so only one element per page is supported.
Scrub
scrub: 0.5 adds a small lag so the number smoothly catches up to the scroll position rather than jumping. Set to true for instant updates or a higher number for more lag.