How to Use IntersectionObserver to Mark Current Scroll Progress

Follow me!

If you like this article, go ahead and follow me on Twitter:

Follow @getButterfly

Intersection

Let’s say you have a list of anchors, or a table of contents, and this list is fixed on screen. Let’s say you want thislist to be fixed on screen and you want the titles to get highlighted as you scroll through the document.

You need a tiny bit of CSS:

<style>
html {
    scroll-behavior: smooth;
}

/* Basic, opinionated style */
.section-nav li.active > a {
    color: #000000;
    font-weight: 700;
}
</style>

You also need a tiny bit of JavaScript, no dependencies:

<script>
window.addEventListener('DOMContentLoaded', () => {
    const observer = new IntersectionObserver(entries => {
        entries.forEach(entry => {
            const id = entry.target.getAttribute('id');
            if (entry.intersectionRatio > 0) {
                document.querySelector(`nav li a[href="#${id}"]`).parentElement.classList.add('active');
            } else {
                document.querySelector(`nav li a[href="#${id}"]`).parentElement.classList.remove('active');
            }
        });
    });

    // Track all sections that have an `id` applied
    document.querySelectorAll('section[id]').forEach((section) => {
        observer.observe(section);
    });
});
</script>

And then you need the HTML structure. Below is a placeholder structure:


<nav class="section-nav">
    <ol>
        <li><a href="#introduction">Introduction</a></li>
        <li><a href="#installation">Installation</a></li>

        <li><a href="#components">Components</a>
            <ul>
                <li><a href="#components--buttons">Buttons</a></li>
                <li><a href="#components--boxes">Boxes</a></li>
                <li><a href="#components--pills">Pills</a></li>
            </ul>
        </li>
    </ol>
</nav>

<section id="introduction">
    Introduction here
</section>
<section id="installation">
    Installation steps here
</section>
<section id="components--buttons">
    Button component here
</section>

Note how all the anchors match the section IDs. That’s it. Simple, fast and modern (using the IntersectionObserver API).

Use this for your documentation projects, how-to’s, frequently asked questions, tables of contents and more.

Photo by Deb Dowd on Unsplash.

Added by Ciprian on Monday, September 28, 2020 in Blog

Contribute!

Contribute to this article by sharing your opinion on Twitter:

Unlimited Automated Page Speed Monitoring & Tracking.
Use SpeedFactor to track your website. It’s simple and reliable.
See how real people experience the speed of your website. Then find (and fix) your web performance problems.
Get Started
Privacy Policy