一、概述
路由,其实就是指向的意思,当我点击页面上的home按钮时,页面中就要显示home的内容,如果点击页面上的about 按钮,页面中就要显示about 的内容。Home按钮 => home 内容, about按钮 => about 内容,也可以说是一种映射。 所以在页面上有两个部分,一个是点击部分,一个是点击之后,显示内容的部分。
点击之后,怎么做到正确的对应,比如,我点击home 按钮,页面中怎么就正好能显示home的内容。这就要在js 文件中配置路由。
路由中有三个基本的概念 route, routes, router。
- route,它是一条路由,由这个英文单词也可以看出来,它是单数, Home按钮 => home内容, 这是一条route, about按钮 => about 内容, 这是另一条路由。
- routes,是一组路由,把上面的每一条路由组合起来,形成一个数组。[{home 按钮 =>home内容 }, { about按钮 => about内容}]
- router 是一个机制,相当于一个管理者,它来管理路由。因为routes只是定义了一组路由,它放在哪里是静止的,当真正来了请求,怎么办? 就是当用户点击home 按钮的时候,怎么办?这时router 就起作用了,它到routes 中去查找,去找到对应的 home 内容,所以页面中就显示了 home 内容。
二、vue-router中的路由的实现
在vue中实现路由还是相对简单的。因为我们页面中所有内容都是组件化的,我们只要把路径和组件对应起来就可以了,然后在页面中把组件渲染出来。
1, 页面实现(html模版中)
在vue-router中, 我们看到它定义了两个标签<router-link>
和<router-view>
来对应点击和显示部分。<router-link>
就是定义页面中点击的部分,<router-view>
定义显示部分,就是点击后,区配的内容显示在什么地方。所以 <router-link>
还有一个非常重要的属性 to,定义点击之后,要到哪里去。
如:<router-link to="/home">Home</router-link>
2, js 中配置路由
首先要定义route, 一条路由的实现。它是一个对象,由三个部分组成: path、component和name, path 指路径,此路径在浏览器地址栏中输入,component 指的是路由地址对应的组件,name对应组件里的to后的内容例如::to=“{name:‘xxx’}”。如:{path:’/home’, component: home,name:“home”}
我们这里有两条路由,组成一个routes:
const routes = [
{ path: '/home', component: Home,name:"Home" },
{ path: '/about', component: About,name:"About" }
]
最后创建router 对路由进行管理,它是由构造函数 new vueRouter() 创建,接受routes 参数。
const router = new VueRouter({
routes // routes: routes 的简写
})
配置完成后,把router 实例注入到 vue 根实例中,就可以使用路由了
const app = new Vue({
router
}).$mount('#app')
三、vue-router中路由的嵌套
实际生活中的我们经常会遇到 多层嵌套的组件组合而成, URL 中各段动态路径也按某种结构对应嵌套的各层组件。
嵌套路由只需要加上一个 children 就好, children 里面的写法和外面的一样
例如:
路由配置:
const router = new VueRouter({
routes: [{
path: '/h',
name:‘Home’,
component: Home,
children: [{
path: '/user',
component: UC,
name: 'UC'
}]
}]
})
组件写法:
<template>
<div class="home">
<h1>Home</h1>
<router-link :to="{ name: 'UC' }">【个人中心】</router-link>
<div class="child-router">
<router-view></router-view>
</div>
</div>
</template>
注意: children里的path若加了“/”,name整个地址都会被替换(被当做根路径),若不加“/”,则在父路由path的后面拼接当前地址。
四、路由组件之间传参
vue-router页面传递参数有两种常见方式
1、使用params传参
需要在路由表中做配置,如果不在路由中进行配置也可以进行传递, 在router-link中设置需要传递的参数
如果使用to+path进行跳转,需要传递的参数是必须在路由表中进行配置
例如:
<router-link :to="{path:‘MovieDetail‘,params: {movie.id}}"/>
路由配置:
{ path: '/l/:id', // 路由传参 :id 表示路由中传递的参数的名字
component: Detail,
name: 'MovieDetail'
}
params中的参数id就是要传的参数,在组件中获取的方法为:
created: function() {
var id = this.$route.params.id;
},
如果使用to+name进行跳转,需要传递的参数是可以不用在路由表中进行配置
例如:
params中的参数id,name就是要传的参数,在组件中获取的方法为:
created: function() {
this.id = this.$route.params.id
this.name= this.$route.params.name
},
2、使用query传参
同parmas,只是获取参数的方式不同
使用parmas传参:在获取参数的时候使用this.$route.params
进行获取
使用query传参:在获取参数的时候使用this.$route.query
进行获取,url中传递的参数以?形式分割的
五、路由钩子函数
路由的切换过程,本质上是执行一系列路由钩子函数,钩子函数总体上分为两大类:
- 全局的钩子函数
- 组件的钩子函数
1、全局钩子函数
全局钩子函数有2个分别是beforeEach和afterEach:
beforeEach:在路由切换开始时调用,有三个参数:
- to:router即将进入的路由对象
- from:当前导航即将离开的路由
- next:Function,进行管道中的一个钩子,如果执行完了,则导航的状态就是 confirmed
(确认的);否则为false,终止导航。
afterEach:在每次路由切换成功进入激活阶段时被调用,不用传next()函数
全局钩子函数主要作用于全局,一般用来判断权限,以及以及页面丢失时候需要执行的操作,例如:
router.beforeEach(function(to, from, next) {
// 在next方法中传递一个路由对象当做参数执行跳转
if (to.meta.needLogin) { //判断此页面是否需要登录才能访问
if (isLogined()) { // 判断是否已经登录
next()
} else {
next({
name: 'Login' //跳到登录页
});
}
} else {
next();
}
})
2、组件的钩子函数
vue2.X的组件内钩子函数:
主要用于写某个指定路由跳转时需要执行的逻辑
beforeRouteEnter 和 beforeRouteLeave再加一个 watch函数
-
使用组件自身的生命周期钩子函数来替代 activate 和 deactivate
-
在 $router 上使用 watcher来响应路由改变
-
canActivate 可以被 router 的配置中的 beforeEnter 中实现
-
canDeactivate已经被 beforeRouteLeave 取代, 后者在一个组件的根级定义中指定。这个钩子函数在调用时是将组件的实例作为其上下文的。
-
canReuse 已经被移除,因其容易混淆且很少被用到。
-
用ajax获取数据的data(to, from, next) 钩子用组件内beforeRouteEnter (to, from, next)来替代
{ path: '/dashboard', component: resolve => require(['../components/page/Dashboard.vue'], resolve), meta: { title: '系统首页' }, beforeEnter: (to, from, next) => { }, beforeLeave: (to, from, next) => { } },
vue1.X中的组件内钩子函数:
组件的钩子函数一共6个:
- data:可以设置组件的data
- activate:激活组件
- deactivate:禁用组件
- canActivate:组件是否可以被激活
- canDeactivate:组件是否可以被禁用
- canReuse:组件是否可以被重用
vue-router1.X中 每个切换钩子函数都会接受一个 transition 对象作为参数,参数下有5个属性/方法 to from next() abort([reason]) redirect(path)
vue-router2.X中 其中后三个都归到next()函数里了 , 所以next()函数改为3个直接的参数 ( to from next() )
六、页面跳转
1、通过a标签
2、通过<router-link>
标签
3、使用 this.$router.push进行页面跳转
例如:
export default {
methods: {
loginHandle() {
loginIn()
// this.$router表示路由对象,可以在其上执行路由跳转方法
// 编程方式实现跳转,通过.push一个路由对象实现
// 当登录成功之后跳回个人中心
this.$router.push({
name: 'UserCenter'
})
}
}
}