JavaScript Element scrollend Event

Beginner
⏱️ 11 min read
📚 Updated: Jul 2026
🎯 5 Examples
🚀 5 Try-it labs
DOM event
Instance event

What You’ll Learn

The scrollend event fires when element scrolling has completed. Learn addEventListener vs onscrollend, how it pairs with scroll, when it does not fire, feature detection for older browsers, and five try-it labs.

01

Kind

Instance event

02

Type

Event

03

When

Scrolling finished

04

Handler

onscrollend

05

Bubbles?

No

06

Status

Baseline newly available

Introduction

scrollend answers: “Has scrolling on this element fully stopped?” Scrolling is complete when there are no more pending scroll position updates and the user has finished their gesture.

That includes wheel scrolling, keyboard scrolling, scroll-snap, and APIs that change scroll position. Touch panning and trackpad scrolling are not complete until pointers or keys are released. If the scroll position never changed, scrollend does not fire.

💡
Beginner tip

Use scroll for continuous updates (progress bars, live offsets). Use scrollend for one-shot work when motion stops—snap UI, save position, or run a final calculation.

Understanding scrollend

An instance event that answers: “Did scrolling finish on this element?”

  • Trigger — scroll completed (gesture done, no pending position updates).
  • Event type — generic Event; read final position from the element.
  • Does not bubble — attach to the scrolling element.
  • No fire if unchanged — if offset did not move, no scrollend.
  • Baseline Newly available on MDN (since December 2025).

📝 Syntax

Use the event name with addEventListener, or set the handler property:

JavaScript
addEventListener("scrollend", (event) => { });

onscrollend = (event) => { };

Event type

A generic Event.

Feature detection

JavaScript
if ("onscrollend" in window) {
  el.addEventListener("scrollend", onDone);
} else {
  // Fallback: debounce scroll with setTimeout
}

⚡ When scrollend Fires

  • After smooth or instant wheel / keyboard / snap / API scroll settles.
  • After touch or trackpad gestures release (pointers / keys up).
  • Not if the scroll position did not change.
  • Listen on the element that scrolls; for the page, see Document scrollend.

⚡ Quick Reference

GoalCode / note
Listenel.addEventListener("scrollend", fn)
Handler propertyel.onscrollend = fn
Final positionel.scrollTop, el.scrollLeft
While scrollingElement scroll
Detect support"onscrollend" in window
MDN statusBaseline Newly available (Dec 2025)

🔍 At a Glance

Four facts to remember about scrollend.

Event type
Event

Generic event

Means
scroll done

Gesture finished

Bubbles
false

Listen on target

Baseline
2025

Newly available

Examples Gallery

Examples follow MDN Element: scrollend event. Scroll inside the overflow boxes in each try-it lab, then stop to see scrollend.

📚 Getting Started

MDN listener patterns: wait during scroll, celebrate on scrollend.

Example 1 — Pair scroll + scrollend (MDN)

Show “waiting…” while scrolling, then “fired!” when scrolling ends.

JavaScript
const element = document.querySelector("div#scroll-box");
const output = document.querySelector("p#output");

element.addEventListener("scroll", (event) => {
  output.textContent = "scroll event fired, waiting for scrollend...";
});

element.addEventListener("scrollend", (event) => {
  output.textContent = "scrollend event fired!";
});
Try It Yourself

How It Works

scroll updates during motion; scrollend runs once when the gesture and position updates settle.

Example 2 — onscrollend Property (MDN)

Same idea using the handler property form.

JavaScript
const element = document.querySelector("div#scroll-box");
const output = document.querySelector("p#output");

element.onscroll = (event) => {
  output.textContent = "Element scroll event fired, waiting for scrollend...";
};

element.onscrollend = (event) => {
  output.textContent = "Element scrollend event fired!";
};
Try It Yourself

How It Works

Prefer addEventListener when you need multiple listeners or easy removal.

📈 Detect, Position & Count

Feature-detect, read the final offset, and compare fire rates.

Example 3 — Feature Detect + Fallback

Use native scrollend when available; otherwise debounce scroll.

JavaScript
const box = document.getElementById("scroll-box");
const out = document.getElementById("out");
let timer = null;

function onDone() {
  out.textContent = "done · top=" + Math.round(box.scrollTop);
}

if ("onscrollend" in window) {
  out.textContent = "native scrollend supported";
  box.addEventListener("scrollend", onDone);
} else {
  out.textContent = "fallback: debounce scroll";
  box.addEventListener("scroll", () => {
    clearTimeout(timer);
    timer = setTimeout(onDone, 150);
  });
}
Try It Yourself

How It Works

"onscrollend" in window is a simple support check. The timer fallback approximates completion on older browsers.

Example 4 — Final scrollTop / scrollLeft

Read the settled offsets only when scrolling ends.

JavaScript
const box = document.getElementById("scroll-box");
const out = document.getElementById("out");

box.addEventListener("scrollend", () => {
  out.textContent =
    "final top=" + Math.round(box.scrollTop) +
    " left=" + Math.round(box.scrollLeft);
});
Try It Yourself

How It Works

Perfect for saving position or snapping UI after motion stops—no work on every intermediate scroll.

Example 5 — Count scroll vs scrollend

See how many continuous scroll events happen before one completion.

JavaScript
const box = document.getElementById("scroll-box");
const out = document.getElementById("out");
let scrolls = 0;
let ends = 0;

box.addEventListener("scroll", () => {
  scrolls += 1;
  out.textContent = "scroll=" + scrolls + " · scrollend=" + ends;
});

box.addEventListener("scrollend", () => {
  ends += 1;
  out.textContent = "scroll=" + scrolls + " · scrollend=" + ends;
});
Try It Yourself

How It Works

One gesture can produce many scroll events and typically one scrollend—why completion handlers belong on scrollend.

🚀 Common Use Cases

  • Run cleanup or analytics only when the user stops scrolling.
  • Save the final scrollTop / scrollLeft for restore later.
  • Snap custom UI or lazy-load after motion settles.
  • Replace brittle “debounce scroll” hacks when native support exists.
  • Pair continuous scroll feedback with a final scrollend action.

🔧 How It Works

1

Scrolling starts

User or script changes scroll offset; scroll may fire repeatedly.

Motion
2

Updates finish

No pending position updates; gesture pointers / keys released.

Settle
3

scrollend fires

Generic Event on that element; does not bubble; skipped if offset never changed.

Event
4

Do final work

Read settled offsets, snap UI, save state, or run one-shot logic.

📝 Notes

  • MDN: Baseline Newly available (since December 2025) — no Deprecated / Experimental / Non-standard banner.
  • Does not bubble—listen on the scrolling element.
  • Does not fire if scroll position did not change.
  • Touch / trackpad: wait until pointers or keys are released.
  • Related learning: scroll, scrollTop, scrollTo(), addEventListener(), JavaScript hub.

Browser Support

scrollend is marked Baseline Newly available on MDN (since December 2025). Logos use the shared browser-image-sprite.png sprite from this project. Feature-detect and keep a debounced scroll fallback for older browsers.

Baseline · Newly available

Element scrollend

Fires when scrolling has completed; Chrome 114+, Firefox 109+, Safari 26.2+, Edge 114+, Opera 100+.

New Newly available
Google Chrome 114+
Supported
Mozilla Firefox 109+
Supported
Apple Safari 26.2+
Supported
Microsoft Edge 114+
Supported
Opera 100+
Supported
Internet Explorer Not supported
Unavailable
scrollend Baseline 2025

Bottom line: Listen on the scrolling element, pair with scroll for live updates, and feature-detect for older Safari / Chromium builds.

Conclusion

scrollend is the standard signal that an element’s scrolling has finished. Attach it to the scrolling target, read the final offsets, and feature-detect when you still support older browsers.

Continue with scrollsnapchange, scroll, addEventListener(), or the JavaScript hub.

💡 Best Practices

✅ Do

  • Listen on the element that actually scrolls
  • Use scroll for live updates and scrollend for stop work
  • Feature-detect with "onscrollend" in window
  • Read final scrollTop / scrollLeft in the handler
  • Prefer addEventListener for multiple handlers

❌ Don’t

  • Expect scrollend if the offset never changed
  • Expect the event to bubble from a child scroller
  • Put heavy continuous UI work only on scrollend (use scroll)
  • Skip a fallback on older browsers still in your audience
  • Overwrite onscrollend if you need multiple listeners

Key Takeaways

Knowledge Unlocked

Five things to remember about scrollend

Scrolling finished—listen on the scroller, then do one-shot work.

5
Core concepts
📄02

Event

read final offset

API
03

vs scroll

many vs one

Compare
🔎04

Detect

onscrollend in window

Compat
🎯05

Baseline

newly available 2025

Status

❓ Frequently Asked Questions

It fires when element scrolling has completed—no more pending scroll position updates and the user’s gesture is finished. Use it when you need a stop signal, not continuous scroll updates.
No. MDN marks Element scrollend as Baseline Newly available (since December 2025). It is not Deprecated, Experimental, or Non-standard.
A generic Event (not a specialized ScrollEvent). Read the final scroll position from the element via scrollTop, scrollLeft, and related properties.
No. If the scroll position did not change, scrollend does not fire.
MDN notes that touch panning and trackpad scrolling are not complete until pointers or keys have been released.
scroll fires whenever the offset changes (often many times). scrollend fires once scrolling has finished. Pair them: scroll for live feedback, scrollend for final work.
Did you know?

Before scrollend was widely available, developers often debounced scroll with setTimeout to guess when scrolling stopped. Native scrollend is the reliable replacement when supported.

Next: scrollsnapchange

React when a new CSS scroll snap target is selected.

scrollsnapchange →

About the author

Mari Selvan M P
Mari Selvan M P 🔗

Developer, cloud engineer, and technical writer

  • Experience 12 years building web and cloud systems
  • Focus Full Stack Development, AWS, and Developer Education

I write practical tutorials so students and working developers can learn by doing—from databases and APIs to deployment on AWS.

5 people found this page helpful