next-scroll-restorer handles scroll restoration for Next.js apps built with app directory. Fixed bugs related to forward/backward browser navigation that Next.js team ignored. Important! This component works only for application written with Next.js 'app' directory.
npm install next-scroll-restorerfor NPMpnpm add next-scroll-restorerfor pnpmyarn add next-scroll-restorerfor Yarn
- 100% of codebase written in Typescript
- Can be used at any nesting
layout.tsxfile. Root layout isn't required. - Fixed bug where built-in Next.js scroll restoration is not immediate
- Fixed annoying bug where scroll position forgotten by Next.js built-in scroll restoration.
- Extensive testing in different browsers with Playwright testing library.
Before you start, keep in mind following rules.
- Keep disabled native
scrollRestorationoption in Next.js config to avoid conflicts. - Skip this rule for Next.js 14.1.0 and higher. In case your Next.js version is less than 14.1.0 then you should enable
windowHistorySupportin your Next.js config underexpermimentalproperty. Since Next.js 14.1.0 browser history support is enabled by default.
/** @type {import('next').NextConfig} */
const nextConfig = {
experimental:{
//Only For Next.js versions prior to 14.1.0 because it is enabled by default since version 14.1.0
windowHistorySupport:true
},
}
module.exports = nextConfigCreate component named ClientSideScrollRestorer in your src directory with useScrollRestorer hook and "use client" directive to prevent server errors.
src/ClientSideScrollRestorer.tsx
"use client"
import {useScrollRestorer} from 'next-scroll-restorer';
const ClientSideScrollRestorer = () => {
useScrollRestorer()
return <></>
}
export default ClientSideScrollRestorerImport component created in a previous step to your root layout file (layout.tsx).
Wrap it wih React <Suspense/> to avoid possible client-side deopting for entire page.
app/layout.tsx
import ClientSideScrollRestorer from '../src/ClientSideScrollRestorer'
import {ReactNode, Suspense} from "react";
type Props = {
children: ReactNode
}
const RootLayout = ({children}) => {
return (
<html lang="uk">
<body>{children}</body>
<Suspense>
<ClientSideScrollRestorer/>
</Suspense>
</html>
)
}
export default RootLayoutIt can be any nesting layout shared by group of routes in case you do not want to enable scroll restoration for the whole application.
Made by Revotale ❤️.