Tuesday, June 15, 2021

How to Implement Smooth Scrolling With CSS & JavaScript

How to Implement Smooth Scrolling With CSS & JavaScript

In this new tutorial, we’ll learn how to implement smooth scrolling in our web pages. We’ll start with a pure CSS solution and then move on to a common jQuery approach for creating this functionality. Next, we’ll get rid of jQuery and discuss two pure JavaScript solutions.

Just to give you an idea of what we’ll discuss during this tutorial, check out one of the demos we’ll be building:

Let’s get started!

1. Begin With the HTML Markup

For demonstration purposes, we’ll define a header wrapped within a container and four sections. Inside it, we’ll specify a navigation menu and an introductory text. 

Each section will have an id whose value will match the href value of a menu link. This association (what we refer to as a fragment identifier) will allow us to jump to specific parts of our page.

Here’s the HTML:

2. Define the Styles

The CSS part will be pretty straightforward, nothing extraordinary.

First, we’ll use CSS Grid to layout the page header. The menu will cover one-fourth of the available width, while the text the remaining three-fourths (the responsive stuff isn’t really important here):

Coming up next, we’ll apply some styles to the sections. Most importantly, we’ll ensure that they will be tall enough, so there’s adequate scrolling inside the page for the effect:

That’s all we need so far! If we now click on a specific link, we’ll immediately jump to the relevant page section. 

Check out our initial demo:

Basic HTML stuff, right? Let’s now take it a step further and learn how to navigate to the sections smoothly.

3. Smooth Scrolling With CSS

The easiest and quickest approach for applying smooth scrolling inside a page is via the following rule:

Let's explain.

There's a relatively new CSS property called scroll-behavior. This property accepts two values: auto (default) and smooth. As soon as we give scroll-behavior: smooth to the html element, the magic will happen, and we’ll be able to navigate to the target section smoothly.

Note: if you set scroll-behavior: smooth to the body element, smooth scrolling won't work.

As an additional note, keep in mind that at the time of this writing, there isn’t any speed option defined in the specification for manipulating the animation speed.

Here's the associated demo:

Solution Review

Although it's a great and promising CSS feature, it still lacks wide support. For example, at the time of this writing, no Safari version supports it. 

4. Smooth Scrolling With jQuery

We'll continue with the traditional jQuery approach. That said, to create smooth scrolling with jQuery, we’ll take advantage of its animate() method. 

Each time we click on a navigation link, we’ll do the following things:

  1. Cancel its default behavior to jump to the corresponding section.
  2. Grab its href attribute value. 
  3. Smoothly navigate to the associated section by animating the scrollTop property. Note that the animate() method allows us to adjust the animation speed. In our case, the animation will last 800ms.

Here’s the jQuery code:

And the related demo:

Solution Review

The major downside of this method is that you have to load an extra JavaScript library. On the contrary, it's a reliable solution that will work well on different screens/devices and you can customize the scrolling speed. My recommendation is to use it only if your project already uses or needs jQuery.

5. Smooth Scrolling With Vanilla JavaScript

At this point, we’ll throw away jQuery and concentrate on two pure JavaScript solutions. Happily enough, it’s much simpler than you might expect. 

Using the scroll() Method

First, we’ll use the scroll() method. The logic for this approach is similar to the previous jQuery implementation. 

Inside this method, we’ll determine the scrolling behavior via the behavior configuration property. This property is the JavaScript representation of the scroll-behavior CSS property and can receive the auto (default) and smooth values. Again here, all we have to do is to set the value of the behavior property to smooth.

Here’s the required code:

Tip: instead of the scroll() method, we could equally have used the scrollTo() and scrollBy() methods. The effect should look the same.

Here’s the associated demo:

Using the scrollIntoView() Method

Beyond the aforementioned scroll methods which are attached to the window object (i.e. window.scroll()), there’s also the scrollIntoView() method which applies to DOM elements. This can accept as well the familiar behavior property with the value set to smooth.

Here’s the code needed for this implementation:

The related demo:

Solutions Review

The native JavaScript version of smooth scrolling requires more code compared to the native CSS property. Like the CSS solution, it still lacks extended support, and there's no easy way to control the scrolling speed unless we write our code.

6. Polyfills Please?

As already discussed, native smooth scrolling with CSS or JavaScript is still somehow limited.

However, there are polyfills out there in case you need them. For instance, there's the Smooth Scroll polyfill with over 3.4k GitHub stars developed by Dustan Kasten.

To include it in your projects, grab it from a CDN, then insert it as a script tag before your JavaScript code.

In our case, as soon as we load it in one of our JavaScript demos, the scrolling animation will work in browsers like Safari and devices like iPad Mini 4. But, if we add it in our CSS demo, the scrolling animation won't work on unsupported browsers/devices.

Here’s one of our aforementioned JavaScript demos with the polyfill embedded:

Conclusion

That’s it, folks! Today we covered some options for achieving smooth scrolling with CSS and JavaScript (including jQuery).

I hope you found this exercise useful and have enhanced your front-end knowledge a little bit. If you have ever built something similar in the past, please share it with us via social media.

Challenge: before closing, I have a small challenge for you! Your job is to extend one of our JavaScript demos by including a “back to top” button. The final functionality should work like this demo. Do you accept the challenge? If so, I’d be glad to see your solution!

As always, thanks a lot for reading!


No comments:

Post a Comment