Day 14: Scroll Interactions
Build scroll-based interactions that reveal a Back to Top button after the user scrolls down and hide or reveal the site header based on scroll direction.
JavaScript focus
- reading scroll position
- storing previous scroll position
- comparing values to determine direction
- toggling classes based on thresholds
- handling the scroll event cleanly
- keeping state simple and predictable
Nice extras
- use a small threshold before hiding the header
- add a transition so the header movement feels smooth
- add a class to the body or target elements instead of setting inline styles
- make the Back to Top button keyboard accessible
- make the button an anchor or button with clear text
- separate the logic for the header and the Back to Top button so each piece is easier to reason about
- only run the feature if the relevant elements exist
MDN prep
Scroll Interactions
- Scroll to top button appears on scroll.
- Hide header on scroll.
The HTML
<!-- this should be the last item in the DOM -->
<button type="button" class="button scroll_top" hidden>Scroll to Top
The JavaScript
function initScrollInteractions() {
const body = document.body;
const header = document.querySelector(".header");
const button = document.querySelector(".scroll_top");
if (!header || !button) return;
const logo = document.querySelector(".primary-logo a");
let shouldFocusLogo = false;
window.addEventListener("scroll", () => {
if (window.scrollY > 50) {
body.classList.add("scroll_active");
} else {
body.classList.remove("scroll_active");
}
if (window.scrollY > 100) {
button.removeAttribute("hidden", "");
} else {
button.setAttribute("hidden", "");
}
});
button.addEventListener("click", () => {
shouldFocusLogo = true;
window.scrollTo({
top: 0,
behavior: "smooth",
});
});
// wait for the scroll to finish
window.addEventListener("scrollend", () => {
if (!shouldFocusLogo) return;
logo.focus();
shouldFocusLogo = false;
});
}
initScrollInteractions();