React/Next项目跳转页面不保留滚动位置的问题如何解决
解决方案
核心原因是你当前的代码执行时机太晚,是在新页面渲染完成后才触发滚动,所以会先出现偏移状态再回顶,根据你使用的Next版本选择对应方案即可:
如果你使用Next.js 13+ App Router
Next.js 已经原生支持跳转重置滚动,不需要手动写scrollTo逻辑:
- 使用
<Link>组件跳转时,确保没有添加scroll={false}属性,默认就会在跳转后自动滚动到顶部 - 编程式跳转(调用useRouter的push/replace方法)时,添加
scroll: true配置即可:
router.push('/target-path', { scroll: true })
如果你使用Next.js 12及更早的Pages Router
在根_app.js/_app.tsx文件中添加路由变化监听,在路由开始切换时就执行滚动重置,避免渲染后再修改滚动位置:
import { useEffect } from 'react' import { useRouter } from 'next/router' export default function App({ Component, pageProps }) { const router = useRouter() useEffect(() => { // 路由开始切换时就滚动到顶部,早于新页面渲染流程 const resetScroll = () => window.scrollTo(0, 0) router.events.on('routeChangeStart', resetScroll) return () => router.events.off('routeChangeStart', resetScroll) }, [router.events]) return <Component {...pageProps} /> }
如果有部分页面不需要跳转后回顶部,只需要在重置滚动的逻辑里加路径判断即可,过滤掉需要保留滚动位置的路径。
临时单页面解决方案
如果你只需要个别页面实现回顶,不想全局配置,可以把页面内的滚动逻辑从useEffect替换为useLayoutEffect,它的执行时机早于浏览器绘制,不会出现视觉延迟:
import { useLayoutEffect } from 'react' // 目标页面组件内代码 useLayoutEffect(() => { window.scrollTo(0, 0) }, [])
内容的提问来源于stack exchange,提问作者ZeFifi
相关产品推荐
相关产品推荐

