I want to do smooth scroll with router hash but next js don't understand it. I use this function
export const scrollTo = (id: string) => {
const element = document.getElementById(id);
if (element) {
window.scrollTo({
top: element.getBoundingClientRect().top + window.scrollY,
left: 0,
behavior: 'smooth',
});
}
};
But when I use it I need to disable router push,
import Link from 'next/link';
import React from 'react';
import _ from 'lodash';
import useAppRouter from '../../../hooks/useAppRouter';
interface INavigation {
links: string[];
}
const Navigation: React.FC<INavigation> = ({ links }) => {
const router = useAppRouter();
const handleCLick = (e,link) =>{
e.preventDefault();
scrollTo(link)
}
return (
<section className="stories-navigation">
<ul>
{links.map((link: string) => (
<Link href={`#${link}`} key={link}>
<li>
<a onClick={e => handleCLick(e, link)} className={router.hash === link ? 'active-link' : ''}>
{_.capitalize(link)}
</a>
</li>
</Link>
))}
</ul>
</section>
);
};
export default Navigation;
But I also need to show this #hashlink, but when I use and next js don't understand scrollTo function and scroll imadiatly without smooth
Here helper callback functions for next/router events. It works globally for next js.
export const smoothScroll = () => {
const html = document.querySelector('html');
if (html) {
html.style.scrollBehavior = 'smooth';
}
};
export const removeSmoothScroll = () => {
const html = document.querySelector('html');
if (html) {
setTimeout(() => {
html.style.scrollBehavior = 'unset';
}, 0);
}
};
And use this events above App component
Router.events.on('hashChangeStart', smoothScroll);
Router.events.on('hashChangeComplete', removeSmoothScroll);