我正在使用 React 重建我的个人网站,并决定使用最新版本的 React-router-dom,我正在构建我的
App
组件来包含导航栏,然后在我想要显示的内容下方,例如 Home
或Projects
。这在我的 /projects
路线上效果很好,但我似乎无法弄清楚如何在索引路线上渲染 App
和 Home
。有办法吗?这是我到目前为止所拥有的:
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import reportWebVitals from './reportWebVitals';
import { BrowserRouter, Link, Route, Routes } from 'react-router-dom';
// N.B. Routes replaces Switch as of V6
ReactDOM.render(
<React.StrictMode>
<BrowserRouter>
<Routes>
// Using <App/> here keeps the navbar but doesn't display the homepage content
<Route path="/" element={<App/>}>
// But using <Home/> loses the navbar
// Should I have my Navbar component in here somewhere or within the App?
<Route path="projects" element={<Projects/>}/>
</Route>
</Routes>
</BrowserRouter>
</React.StrictMode>,
document.getElementById('root')
);
function App() {
// Help?
}
function Navbar() {
return (
<header> // Very crude example as I'm self-answering, in production I'll rename the component to Header
<nav>
<ul>
<li>
<Link to="/">Home</Link>
</li>
<li>
<Link to="/projects">Projects</Link>
</li>
</ul>
</nav>
</header>
}
function Home() {
return <h1>Home</h1>
}
function Projects() {
return <h1>Projects</h1>
}
如果您按照React-Router 6的教程使用了
createBrowserRouter
功能,并且不想更改为使用<BrowserRouter>
,您可以进行以下转换:
const router = createBrowserRouter([
{
path: "/",
element: <Root/>
},
{
path: "/somePath",
element: <SomePath/>
}
])
root.render(
<div>
<NavBar/>
<RouterProvider router={router}/>
</div>
)
导航栏显示错误
useHref() may be used only in the context of a <Router> component
重构您的
createBrowserRouter
对象,以便您拥有带有导航栏组件的路径“/”和 <Outlet/>
。
import {Outlet} from "react-router-dom";
const router = createBrowserRouter([
{
path: "/",
element: <NavbarWrapper/>
children:[
{
path: "/", // yes, again
element: <Root/>
},
{
path: "/somePath",
element: <SomePath/>
},
]
}
])
function NavbarWrapper(){
return (
<div>
<Navbar/>
<Outlet/>
</div>
)
};
应用程序可以无条件渲染
Navbar
,并将Routes
组件和路由移动到App
。索引文件将 App
渲染到 BrowserRouter
。
应用程序
function App() {
return (
<>
<Navbar />
<Routes>
<Route path="/" element={<Home/>}>
<Route path="projects" element={<Projects/>}/>
</Routes>
</>
);
}
index.js
ReactDOM.render(
<React.StrictMode>
<BrowserRouter>
<App />
</BrowserRouter>
</React.StrictMode>,
document.getElementById('root')
);
首先,您的
App
组件如下所示:
function App() {
return (
<div className="App">
<Navbar/>
<main> // You don't *have* to wrap the Outlet in a main tag, but I am doing, to save having to remember to do it in each component
<Outlet/>
</main>
</div>
)
}
因此,现在您的
App
始终显示 Navbar
,并且插座将显示路线告诉它的任何页面。
好吧,这很好,但是当我想要渲染
App
并仍然保留导航栏时,它仍然意味着渲染 Home
,这真的能解决这个问题吗?
嗯,不是单独的。首先将该 Outlet 组件添加到从
react-router-dom
的导入中,否则我们将一事无成!
现在像这样调整你的路由:
import { BrowserRouter, Link, Outlet, Route, Routes } from 'react-router-dom';
ReactDOM.render(
<React.StrictMode>
<BrowserRouter>
<Routes>
<Route path="/" element={<App/>}>
<Route index element={<Home/>}/>
<Route path="projects" element={<Projects/>}/>
</Route>
</Routes>
</BrowserRouter>
</React.StrictMode>,
document.getElementById('root')
);
看到带有
Route
组件的 Home
标签上如何有 index
标签吗?就是这样,这就是解决方案!现在,您的应用程序按应有的方式呈现,包括导航栏,并且其 Outlet
呈现索引路线上的 Home
元素。