一、基础api
1. Route:是用于声明路由映射到应用程序的组件层,主要参数有用于react-router匹配使用的path,匹配后对应渲染到页面上的component
2. 路由模式选择:hash模式:HashRouter,history模式:BrowserRouter
import { BrowserRouter as Router } from 'react-router-dom'
3. switch:只匹配第一个的Route并返回到页面上,如下面的例子,在本地打开项目,假设启动后的路径为localhost:3000,如果不用switch把Route包裹起来的话,path="/"和path="/login"对应的组件都会渲染到页面上
import {
BrowserRouter as Router,
Route,
Switch
} from 'react-router-dom'
function HomePage() {
return <h1>首页</h1>
}
function app() {
return <Router>
<Switch>
<Route path="/" exact component={HomePage} />
<Route path="/login" render={() => <h1>登录页面</h1>}/>
<Route path="/list" render={() => <h1>列表页面</h1>}/>
</Switch>
</Router>
}
export default app;
4. exact:完全匹配,如上例中path="/"的Route,如果我们访问localhost:3000/login的地址,理论上应该显示“登录页面”的内容,实际上显示的是Homepage组件里的内容,因为不加exact时“/”也会被“/login”匹配。?
5. Redirect:重定向,比如我们想输入localhost:3000时就重定向到localhost:3000/home,可以做如下改造:
import {
BrowserRouter as Router,
Route,
Switch,
Redirect
} from 'react-router-dom'
function HomePage() {
return <h1>首页</h1>
}
function app() {
return <Router>
<Switch>
<Route exact path="/">
<Redirect to="home"/>
<Route>
<Route path="/home" component={HomePage} />
<Route path="/login" render={() => <h1>登录页面</h1>}/>
<Route path="/list" render={() => <h1>列表页面</h1>}/>
</Switch>
</Router>
}
export default app;
6. 404页面
只需要在Router中最后的一个路由加上一个Route就可以了,原理是当所有Route的path都不匹配时,命中最后一个默认的404路由
import {
BrowserRouter as Router,
Route,
Switch,
Redirect
} from 'react-router-dom'
function HomePage() {
return <h1>首页</h1>
}
function app() {
return <Router>
<Switch>
<Route exact path="/">
<Redirect to="home"/>
<Route>
<Route path="/home" component={HomePage} />
<Route path="/login" render={() => <h1>登录页面</h1>}/>
<Route path="/list" render={() => <h1>列表页面</h1>}/>
<Route render={() =><h1>404 not found</h1>}/>
</Switch>
</Router>
}
export default app;
至此,一个简单的路由就搭建好了
二、获取history对象和location对象
????????获取路由对象有两种方式?
import {
BrowserRouter,
Route,
Switch,
useLocation,
useHistory,
Redirect
} from 'react-router-dom'
function HomePage(props) {
const history = useHistory()
const loaction = useLocation()
console.log('props.history',props.history)
console.log('history',history)
console.log('props.location',props.location)
console.log('loaction',loaction)
return <h1>首页</h1>
}
function App() {
return <BrowserRouter>
<Switch>
<Route exact path="/">
<Redirect to="home"/>
</Route>
<Route path="/home" component={HomePage} />
<Route path="/login" render={() => <h1>登录页面</h1>}/>
<Route path="/list" render={() => <h1>列表页面</h1>}/>
</Switch>
</BrowserRouter>
}
export default App;
打印结果如下:?
?可以看出props.history和useHistory的返回值,props.location和useLocation的返回值是一样的
三、路由跳转
????????有两种方式可以进行路由跳转,一种是通过history对象中的push或go功能,一种是通过react-router-dom中的Link组件。我们将/login对应的组件改写后,在HomePage组件中使用history跳转,LoginPage组件中使用Link跳转,则代码如下:
import {
BrowserRouter,
Route,
Switch,
useHistory,
Redirect,
Link
} from 'react-router-dom'
function HomePage() {
const history = useHistory()
const goLogin = () => {
history.push('/login')
}
return <h1 onClick={goLogin}>首页</h1>
}
function LoginPage() {
return <h1>
<Link to="/list">登录页面</Link>
</h1>
}
function App() {
return <BrowserRouter>
<Switch>
<Route exact path="/">
<Redirect to="home"/>
</Route>
<Route path="/home" component={HomePage} />
<Route path="/login" component={LoginPage}/>
<Route path="/list" render={() => <h1>列表页面</h1>}/>
</Switch>
</BrowserRouter>
}
export default App;
四、路由参数传递
? ? ? ? 一种是通过params方式传递,这种更符合restful API规范,通过location的match方法可以获取到对应参数;另一种是通过search(query)方式传递,具体代码如下:
import {
BrowserRouter,
Route,
Switch,
useHistory,
useLocation,
Redirect,
useRouteMatch,
useParams,
Link
} from 'react-router-dom'
const useQuery = () => {
return new URLSearchParams(useLocation().search);
}
function ListPage() {
const history = useHistory()
const goDetail2 = (id) => {
history.push({
pathname: '/detail2',
search: `?id=${id}`
})
}
return <>
<h1>
<Link to="/detail1/111">跳转到detail1页面</Link>
</h1>
<h1 onClick={() => goDetail2(222)}>
跳转到detail2页面
</h1>
</>
}
const Detail1Page = (props) => {
let match = useRouteMatch()
let params = useParams()
const id = match.params.id // 和下面注释掉的两种方法返回的参数一样
// const id = params.id
// const id = props.match.params.id
return <h1>
detail1页面{id}
</h1>
}
const Detail2Page = () => {
let query = useQuery()
const id = query.get('id')
return <h1>
detail2页面{id}
</h1>
}
function App() {
return <BrowserRouter>
<Switch>
<Route exact path="/">
<Redirect to="list"/>
</Route>
<Route path="/list" component={ListPage}/>
<Route path="/detail1/:id" component={Detail1Page}/>
<Route path="/detail2" component={Detail2Page}/>
</Switch>
</BrowserRouter>
}
export default App;
至此,最基本的react-router路由的使用就完成了,计划下篇博客将谈一谈从react-router v5迁移到v6。
|