Next.js:如何禁用历史按钮触发的自动滚动到顶部?
Great question! I’ve dealt with this exact issue when building single-page apps, and there’s a straightforward browser-native solution that works across most modern frameworks (like React, Vue, etc.).
The Core Solution: history.scrollRestoration
Browsers have a built-in property called history.scrollRestoration that controls exactly this behavior. Here’s how it works:
- By default, it’s set to
'auto', which means the browser will automatically scroll to the top (or restore the previous scroll position) when navigating via the back/forward buttons. - Setting it to
'manual'disables this automatic scrolling entirely, putting you in control of the scroll behavior.
Implementation Example
Add this code early in your app’s initialization (like your entry point file, or a root component’s useEffect if using React):
// Check if the browser supports the property first if ('scrollRestoration' in history) { history.scrollRestoration = 'manual'; }
Compatibility
This works in all modern browsers: Chrome, Firefox, Edge, and Safari 11.1+. For older browsers, it’ll just be ignored (they’ll keep the default behavior), so no need for complex fallbacks unless you need to support legacy users.
Bonus: Custom Scroll Behavior (If Needed)
If you want to manually handle scroll position restoration instead of just disabling auto-scroll, you can pair this with popstate event listeners to save and restore scroll positions:
// Save scroll position before navigation/unload window.addEventListener('beforeunload', () => { sessionStorage.setItem('savedScroll', JSON.stringify({ x: window.scrollX, y: window.scrollY })); }); // Restore scroll position when navigating back/forward window.addEventListener('popstate', () => { const savedScroll = JSON.parse(sessionStorage.getItem('savedScroll')); if (savedScroll) { window.scrollTo(savedScroll.x, savedScroll.y); } });
But if your only goal is to prevent the automatic scroll-to-top on history navigation, just setting history.scrollRestoration = 'manual' is all you need.
内容的提问来源于stack exchange,提问作者LucasBertrand

