React Router Dom路由切换时滚动至顶部的实现问题
问题描述
我使用的是react-router-dom@6.16.0,路由功能正常,但在页面中部点击导航链接跳转时,新页面会从中间位置加载而非顶部。查资料得知react-router-dom提供了ScrollRestoration组件替代传统的useEffect滚动方案,但不清楚如何在createBrowserRouter中使用该组件。
以下是我的App.js代码:
import { RouterProvider, createBrowserRouter } from 'react-router-dom' import { Courses, Error, Home, HomeLayout, Login, Register, Testing, Course, Contact, About, FAQ, Events, EventDetails, Library, Admin, } from '@/pages' const router = createBrowserRouter([ { path: '/', element: <HomeLayout />, errorElement: <Error />, children: [ { index: true, element: <Home />, }, { path: 'courses', element: <Courses />, }, { path: 'single-course', element: <Course />, }, { path: 'testing', element: <Testing />, }, { path: 'contact', element: <Contact />, }, { path: 'about-us', element: <About />, }, { path: 'faq', element: <FAQ />, }, { path: 'events', element: <Events />, }, { path: 'event-details', element: <EventDetails />, }, { path: 'library', element: <Library />, }, ], }, { path: '/login', element: <Login />, }, { path: '/register', element: <Register />, }, { path: '/admin', element: <Admin />, }, ]) const App = () => { return <RouterProvider router={router} /> } export default App
解决方案
ScrollRestoration得放在路由层级里才能监听路由变化,处理滚动恢复。按下面步骤来就行:
1. 先导入组件
在要用的文件里先把ScrollRestoration引进来:
import { ScrollRestoration } from 'react-router-dom'
2. 把组件加到布局或路由元素里
给根布局的子路由加
你的HomeLayout是根路由的容器,所有子页面都嵌套在它里面,直接在HomeLayout里加ScrollRestoration就行,这样所有子页面跳转都会自动滚到顶部:
// HomeLayout.jsx import { ScrollRestoration, Outlet } from 'react-router-dom' const HomeLayout = () => { return ( <div> {/* 这里放你的导航栏、页头这些内容 */} <Outlet /> {/* 加这行就行 */} <ScrollRestoration /> </div> ) }
给独立路由(Login、Register、Admin)加
这些页面没嵌套在HomeLayout里,有两种处理方式:
第一种:整个通用布局
先整个简单的通用布局组件:
// CommonLayout.jsx import { ScrollRestoration, Outlet } from 'react-router-dom' const CommonLayout = () => { return ( <div> <Outlet /> <ScrollRestoration /> </div> ) }
然后改路由配置,把这些独立路由套进这个布局:
const router = createBrowserRouter([ // 根路由原样保留 { path: '/', element: <HomeLayout />, errorElement: <Error />, children: [...], }, { path: '/login', element: <CommonLayout />, children: [{ index: true, element: <Login /> }] }, { path: '/register', element: <CommonLayout />, children: [{ index: true, element: <Register /> }] }, { path: '/admin', element: <CommonLayout />, children: [{ index: true, element: <Admin /> }] }, ])
第二种:直接在组件里加
比如在Login.jsx里直接加:
import { ScrollRestoration } from 'react-router-dom' const Login = () => { return ( <div> {/* 登录页面的内容 */} <ScrollRestoration /> </div> ) }
提醒一下
ScrollRestoration默认会处理跳转新页面到顶部,返回时回到之前的滚动位置,和浏览器原生行为一致,不用额外写逻辑。- 每个路由层级里只加一次,别重复加,不然会有重复监听的问题。
内容的提问来源于stack exchange,提问作者saimarshadd
相关产品推荐
相关产品推荐

