react-路由
单页面应用
-
SPA(single page application):
-
整个应用只有一个完整的页面
-
点击页面中的链接不会刷新页面,只会做页面的局部更新
-
数据需要通过ajax请求获取,并且在前端异步展示
-
路由的理解
什么是路由?
- 一个路由就是一个映射关系(key:value)
- key为路径,value可能是function或component
- function:后端路由
- component:前端路由
路由分类?
- 后端路由:
- 理解:value是function,用来处理客户端提交的请求
- 注册路由:router.get(path,function(req,res))
- 工作过程:当node接收到一个请求时,根据请求路径找到匹配的路由,调用路由中的函数来处理请求,返回响应数据
- 前端路由:
- 浏览器路由:value是component,用于展示页面内容
- 注册路由:
<Route path="/test" component={Test}>
- 工作过程:当浏览器的path变为/test时,当前路由组件就会变为Test
两种路由方式
-
路由有两种创建方式:history路由、hash路由
-
<script type="text/javascript" src="https://cdn.bootcss.com/history/4.7.2/history.js"></script> //引入第三方js
history路由
-
直接使用h5推出的historyAPI
-
let histo let history = History.createBrowserHistory() //方法一,直接使用H5推出的history身上的API function push (path) { history.push(path) return false } function replace (path) { history.replace(path) } function back() { history.goBack() } function forword() { history.goForward() } history.listen((location) => { console.log('请求路由路径变化了', location) })
-
hash路由
let history = History.createHashHistory() //方法二,hash值(锚点)
react-router-dom
- react-xxx一般都是react的插件库
- react的一个插件库
- 专门用来实现SPA应用
- 基于react的项目基本都会用到这个库
路由的使用
**第一步:**安装react-router-dom
-
npm i react-router-dom@5
**第二步:**在index.js中创建路由:BrowserRouter或HashRouter
-
import React from 'react'; import ReactDOM from 'react-dom'; import App from './App'; import { BrowserRouter } from 'react-router-dom' ReactDOM.render( <BrowserRouter> <App /> </BrowserRouter> , document.getElementById('root') );
**第三步:**在APP.jsx中设置路由链接和注册路由
-
import React, { Component } from 'react' import { Link, BrowserRouter, Route } from "react-router-dom" import About from "./components/About" import Home from "./components/Home" export default class App extends Component { render() { return ( <div> <div className="row"> <div className="col-xs-offset-2 colnpm r-xs-8"> <div className="page-header"><h2>React Router Demo</h2></div> </div> </div> <div className="row"> <div className="col-xs-2 col-xs-offset-2"> <div className="list-group"> {/* react-router靠路由链接实现切换组件 */} <Link className="list-group-item" to="/about" >About</Link> <Link className="list-group-item" to="/home" >home</Link> {/* 原生html中靠a标签跳转页面 */} {/* <a className="list-group-item active" href="./about.html">About</a> <a className="list-group-item" href="./home.html">Home</a> */} </div> </div> <div className="col-xs-6"> <div className="panel"> <div className="panel-body"> {/* 注册路由 */} <Route path="/about" component={About}/> <Route path="/home" component={Home}/> </div> </div> </div> </div> </div> ) } }
总结
- 明确好界面中的导航区和展示区
- 导航区的a标签改为Link标签
<Link to="/xxx"></Link>
- 展示区写Route标签进行路径的匹配
<Route path="/xxx" component={Demo}/>
<APP>
的最外侧包裹了一个<BrowserRouter>
或<HashRouter>
BrowerRouter与HashRouter展示的区别
- BrowserRouter或HashRouter最终都会被渲染为a标签,只是渲染的href内容有些不同:
BrowserRouter
:<a href="/about"/>
HashRouter
:<a href="#/about"/>
一般组件与路由组件
- 一般组件,没有通过router或route进行请求的组件
一般组件与路由组件的区别?
-
写法不同:
- 一般组件:
<Demo/>
- 路由组件:
Route path='/demo' component={Demo} /
- 一般组件:
-
存放位置不同:
- 一般组件:components
- 路由组件:pages
-
接收到的pops不同
-
一般组件的props只能接收到父组件明传给子组件的东西
-
路由组件不仅能够收到父组件传给子组件的东西,还能收到当前路由的详细信息
- history:
- location:
- match:
-
设置导航栏选中状态
-
导航栏的选中状态需要将Link改为NavLink,并用
activeClassName
绑定对应的类名 -
<NavLink activeClassName='active' className="list-group-item" to="/about" >About</NavLink> <NavLink activeClassName='active' className="list-group-item" to="/home" >home</NavLink>
封装NavLink
-
注意点:标签体内容也是一个当前标签的一个属性:children
-
//MyNavLink.jsx import React, { Component } from 'react' import { NavLink } from 'react-router-dom'; export default class MyNavLink extends Component { render() { return ( <div> <NavLink activeClassName='active' className="list-group-item" {...this.props}/> </div> ) } }
-
调用:
-
<MyNavLink to="/about" >About</MyNavLink> <MyNavLink to="/home" >Home</MyNavLink>
-