前言
本篇介绍React的React—v5,(旧版路由)React的路由概念,路由的安装使用、包括路由标签等等
一、Router5的路由概念
一个路由是一种映射关系
key为路径,value可能是function或组件
前端路由:
- value是组件
- 注册路由==> <Route path="/test" component={Test} >
- 工作过程==> 浏览器路径变为/test,展示出Test组件
后端路由:
- value是function,用于处理客户端的请求
- 注册路由==> router.get(path, function(req,res))
- 工作过程==> Node接收到请求,根据路径匹配路由,调用对应函数处理请求,返回响应数据
二、路由(React5)的安装和使用
安装react-router-dom
// 安装 5.X 版本路由
npm install react-router-dom@5.2.0 -S// 最新已经 6.X 版本,用法和 5.X 有所不同
npm install react-router-dom -S
导航区域使用<Link />,展示区域使用<Route />
// App.jsx
import React, { Component } from 'react'
import { Link, Route } from 'react-router-dom'
import Home from './components/Home'
import About from './components/About'export default class App extends Component {render() {return (<div><div className="list-group"><Link className="list-group-item" to="/about">About</Link><Link className="list-group-item" to="/home">Home</Link></div><div className="panel-body"><Route path="/about" component={About} /><Route path="/home" component={Home} /></div></div>)}
}
在App组件最外层包裹<BrowserRouter>和<HashRouter>
// index.js
import React from 'react'
import ReactDOM from 'react-dom'
import { BrowserRouter } from 'react-router-dom'
import App from './App'ReactDOM.render(<BrowserRouter><App /></BrowserRouter>,document.getElementById('root')
)
三、NavLink组件的使用
NavLink 可以实现路由链接的高亮,通过 activeClassName 指定样式名,默认追加类名为 active
封装 NavLink 组件:由于 NavLink 组件中重复的代码太多,因此进行二次封装。
细节点:组件标签的内容会传递到 this.props.children 属性中,反过来通过指定标签的 children 属性可以修改组件标签内容
// MyNavLink 组件
import React, { Component } from 'react'
import { NavLink } from 'react-router-dom'export default class MyNavLink extends Component {render() {// this.props.children 可以取到标签内容,如 About, Home// 反过来通过指定标签的 children 属性可以修改标签内容return <NavLink activeClassName="demo" className="list-group-item" {...this.props} />}
}
四、Switch组件的使用
Switch组件可以提高路由匹配效率,如果匹配成功,则不再匹配后面的路由,即单一匹配
<!-- 只会展示 Home 组件 -->
<Switch><Route path="/about" component="{About}" /><Route path="/home" component="{Home}" /><Route path="/home" component="{Test}" />
</Switch>
五、严格匹配和模糊匹配
- 默认使用模糊匹配,输入的路径必须包含要匹配的路径并且顺序一致
- 开启严格匹配:<Route exact path="/about" component={About} />
- 严格匹配模式在需要时在开启,开启之后可能会导致无法继续匹配二级路由
六、路由重定向
<Switch><Route path="/about" component="{About}" /><Route path="/home" component="{Home}" /><Redirect to="/about" /> // 重定向
</Switch>
七、路由传参
路由传参有三种方式:params,search,state参数
三种方式对比:
- state方式当前页面刷新可保留参数,但在新页面打开不能保留。前两种方式由于参数存在URL地址上,因此都能保留参数
- params和search参数都会变成字符串
<!-- 路由链接 -->
<Link to='/home/message/detail/Bruce/21'>params</Link>
<Link to={`/home/message/detail/${item.name}/${item.age}`}>{item.name}</Link><Link to='/home/message/detail/?name=Bruce&age=21'>search</Link>
<Link to={`/home/message/detail/?id=${item.name}&title=${item.age}`}>{item.name}</Link><Link to={{pathname: '/home/message/detail', state: {name: 'Bruce', age: 21}}}>state</Link><!-- 注册路由 -->
<Route path='/home/message/detail/:name/:age' component={Detail} />
<!-- search 和 state 按正常注册即可 -->
<Route path='/home/message/detail' component={Detail} />
//接收参数
const { name, age } = this.props.match.paramsimport qs from 'querystring'
const { search } = this.props.location
const { name, age } = qs.parse(search.slice(1))const { name, age } = this.props.location.state
八、withRouter的作用和编程式导航
编程式导航就是使用路由组件this.props.history提供的API进行路由跳转
this.props.history.push(path, state)
this.props.history.replace(path, state)
this.props.history.goForward()
this.props.history.goBack()
this.props.history.go(n)// 编程式导航传参
this.props.history.push(`/home/message/detail/${id}/${title}`)
this.props.history.push(`/home/message/detail?id=${id}&title=${title}`)
this.props.history.push(`/home/message/detail`, { id: id, title: title })
WithRouter的作用:加工一般组件,让其拥有路由组件的API
九、BrowserRouter和HashRouter
底层原理不一样:
- BrowserRouter 使用的是 H5 的 history API,不兼容 IE9 及以下版本。
- HashRouter 使用的是 URL 的哈希值。
路径表现形式不一样:
- BrowserRouter 的路径中没有 # ,如:localhost:3000/demo/test
- HashRouter 的路径包含#,如:localhost:3000/#/demo/test
刷新后对路由 state 参数的影响:
- BrowserRouter 没有影响,因为 state 保存在 history 对象中。
- HashRouter 刷新后会导致路由 state 参数的丢失!
备注:HashRouter 可以用于解决一些路径错误相关的问题
有不明白的或者有其他问题的可以评论区留言噢
今天的知识分享就到这里啦~希望大家在这能学到知识一起分享一起进步,成为更好的自己!