文章目录
React-Router
github
最新的路由的版本是5.2的版本。里面提供了一些包用于创建管理路由
所以在做web端开发的时候只需要安装react-router-dom就可以了,因为内部已经包含了最核心的内容了。
react-router | react-router-native | react-router-config
路由的简单使用
安装路由
yarn add react-router-dom
在最外层的节点上:
引入Router,使用Router标签包裹根节点
import {HashRouter as Router} from "react-router-dom"
ReactDOM.render(
<Router>
<App />
</Router>
,
document.getElementById('root')
);
HashRouter和BrowserRouter类似于vue-router的哈希模式和历史模式,表现为HashRouter的url中有#符号,核心区别是history模式刷新会报错,需要后端进行专门的配置
区别
路由的实现 Route | Switch | Redirect
import React,{useState} from 'react';
import {Route,Redirect,Switch} from "react-router-dom"
import Home from "./components/Home"
import Article from "./components/Article"
import NotFound from "./components/NotFound"
function App() {
let [count,setCount] = useState(12)
return (
<Switch>
<Route path="/home" component={Home} />
<Route path="/article" component={Article}/>
<Route path="/404" component={NotFound}/>
<Redirect to="/home" from="/" exact />
<Redirect to="/404" />
</Switch>
);
}
export default App;
使用Route实现路由
<Route path="/home" component={Home} />
- Route是一个路由对象,path指明url,component代表映射的路径组件
- 路径的匹配默认是不完全匹配,即/home也可以匹配到/homeless
exact属性添加后表示路径要完全匹配,必须一模一样
使用Redirect实现路由重定向
<Redirct to="/home" from="/">
Redirect实现路由重定向,to="“代表定向到的路径,from=”"代表原始路径
使用Switch
使用Switch包裹所有标签,然后只要匹配到了路径,就不会接着向下匹配了,以保证路由不会后边的覆盖前边的
<Switch>
<Route path="/home" component={Home} />
<Route path="/article" component={Article}/>
<Route path="/404" component={NotFound}/>
<Redirect to="/home" from="/" exact />
<Redirect to="/404" />
</Switch>
导航
声明式导航
声明式导航在vue中是通过router-link是实现的,在react中通过react-router-dom提供的Link或者NavLink实现
使用Link实现
import {Link} from "react-router-dom"
<Link to="/home">首页 </Link>
使用NavLink实现
使用NAVLink是实现可以给链接添加动态的样式,如通过activeStyle={{}}添加活跃状态的内联样式,或者通过activeClassName添加活跃状态的class属性,配合外部样式或者内部样式实现不同效果
import {NavLink as Link} from "react-router-dom"
<Link to="/home">首页 </Link>
编程式导航
动态路由
通过Route的component指明的组件,他的props上就会有路由相关的api了,动态路由的获取可以从props中获取
父组件
<Link to="/article/1">详情1<Link>
<Link to="/article/2">详情2<Link>
<Route path="/article/:id" component={ArticleDetail} />
子组件通过this.props获取属性
{this.props.match.params.id}
路由的常用api方法
render函数
render函数的返回值是原先要用component表明的组件
通过Route组件的component指明的组件就会带有路由相关的api,可以在组件中通过props使用这些api
如果想要给组件传入额外的属性,仅仅靠component是实现不了的。通过render能够给组件传入额外的属性
<Route path="/center" render={ (routeProps)=>{
return isLogin ? <Center {...routeProps} a={100}/> :null
}}/>
如果在Route上面写了render属性,内部返回组件。那么这个组件的props上面是没有路由相关的api属性的。
所以通过{…routeProps}方式才可以保证路由组件通过this.props获取路由相关的api属性。
render和component同时存在是component会覆盖render
link的参数传递
-
如上文,可以通过动态路由的方式进行参数传递
path="/detail/:id"组件内部可以通过this.props.match.params.id来获取到动态参数
-
可以通过query传递参数
path = “/detail?title=文章一”
detail内部通过this.props.loaction.search可以获取到“?title=文章一” -
可以通过state进行隐式传参
to={{
pathname:"/detail/1",
state:{title:“文章二”}
}}
detail组件中通过this.props.location.state.title可以获取到
withRouter
withRouter是一个高阶组件(HOC:已经学习了React.memo()、connect()、withRouter三个高阶组件),
我们可以通过引入withRouter来将普通组件包裹,那么这个普通组件就变成了伪路由组件,他本身不能实现跳转,但是可以通过属性去访问到相关api。
import React,{Component} from "react"
import {withRouter} from "react-router-dom"
class BackHome extends Components {
backBtn = ()=>{
this.props.history.push("/home")
}
render(){
return(
<button onClick={this.backBtn}>返回首页</button>
)
}
}
export default withRouter(BackHome)
在配置好相关配置的情况下,也可以使用装饰器写法 @withRouter
如果父组件中有需要的api,也可以直接展开父组件的this.props传递给子组件<BackBtn {…this.props}/>