vue.js路由vue-router(二)——路由进阶
导航钩子
导航钩子类似于生命周期钩子,包含路由进入前,进入后,更新时,退出前等几个周期,主要用于控制导航的前进后退或跳转等。
在开始之前,我们先来写两个路由
新建html,引入vue.js及vue-router.js
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>路由</title> <script src="js/vue.js"></script> <script src="js/vue-router.js"></script> </head> <body> <div id="app"> <div> <button><router-link to='/route1'>路由一</router-link></button> <button><router-link to='/route2'>路由二</router-link></button> </div> <router-view></router-view> </div> <script src="js/router.js"></script> </body> </html>
在router.js中定义路由及vue实例
//构建组件 var route1 = Vue.extend({ template: '<div>路由一内容</div>' }); var route2 = Vue.extend({ template: '<div>路由二内容</div>' }); //定义路由 var router = new VueRouter({ routes: [ { path: '/route1', name: 'route1', component: route1 }, { path: '/route2', name: 'route2', component: route2 } ] }); //定义vue实例 var app = new Vue({ el: '#app', router })
打开浏览器,查看效果
1.全局钩子
定义路由之后,接着就可以使用router.beforeEach
定义全局钩子
在router.js中定义路由后面加上如下代码
router.beforeEach((to,from,next) => { console.log(to) console.log(from) })
全局钩子作用于所有路由,里面的参数to
表示即将要进入的路由对象,from
表示即将要离开的路由对象,next
是继续跳转或中断的方法。
我们来看一下打印出的对象
我们的操作是点击路由一按钮,即将由'/'跳转至'/route1',可以看到打印出的第一个对象to
的path为'/route1',第二个对象from
的path为'/'。
有一个问题,点击按钮之后路由并没有进行跳转,这是因为我们没有写next方法。next方法有以下3种:
1.
next()
默认跳转
2.next(false)
保持当前路由不进行跳转
3.next('路由路径')
指定路由跳转
(1)默认跳转
我们先来试第一种
router.beforeEach((to,from,next) => { console.log(to) console.log(from) next() })
打开浏览器,可以看到路由跳转正常,并且以默认的路由进行跳转
(2)保持当前路由不进行跳转
如果不写next方法就不会进行跳转,那么与next(false)的区别就在于,后者是不管url怎么改变,也会重置到from对应的路由。
router.beforeEach((to,from,next) => { console.log(to) console.log(from) next(false) })
可以看到点击按钮并无反应,在地址栏输入其他路由也跳转回当前路由
(3)指定路由跳转
这个方法最好不要写在全局钩子中,不然会陷入无限循环,跳转到指定路由又触发该导航钩子又进行跳转
2.路由内钩子
导航钩子也可以通过beforeEnter
写在某个路由内部
var router = new VueRouter({ routes: [ { path: '/route1', name: 'route1', component: route1, meta:{title: '路由一'} beforeEnter: function(to,from,next){ console.log(to) console.log(from) next() } }, { path: '/route2', name: 'route2', component: route2, meta:{title: '路由二'} } ] });
这样只在路由'/route1'下才会触发该钩子
3.组件内钩子
组件内钩子有三种
var route1 = Vue.extend({ template: '<div>路由一内容</div>', //对应该组件的路由被确认之前,此时还未创建组件实例 beforeRouteEnter:function(to,from,next){ }, //对应该组件的路由被重复调用之时,如嵌套路由,此时组件实例已被创建 beforeRouteUpdate:function(to,from,next){ }, //即将离开对应该组件的路由时 beforeRouteLeave:function(to,from,next){ } });
路由元信息
定义路由的时候可以设置meta
字段
var router = new VueRouter({ routes: [ { path: '/route1', name: 'route1', component: route1, meta:{title: '路由一'}, }, { path: '/route2', name: 'route2', component: route2, meta:{title: '路由二'} } ] });
通过这个我们可以在全局钩子中设置页面的标题之类的,例如
router.beforeEach(function(to,from,next){ console.log(to) console.log(from) if(to.meta.title){ document.title = to.meta.title }else{ document.title = '路由' } next() })
查看效果
过渡动效
在路由中可以给路由视图<router-view>
用<transition>
标签设置总的过渡类名
<transition name="fade" v-on:before-enter="enter"> <router-view></router-view> </transition>
其中before-enter
为钩子函数,钩子函数有以下几种,本例中只写了第一种“进入之前”
<transition v-on:before-enter="beforeEnter" v-on:enter="enter" v-on:after-enter="afterEnter" v-on:enter-cancelled="enterCancelled" v-on:before-leave="beforeLeave" v-on:leave="leave" v-on:after-leave="afterLeave" v-on:leave-cancelled="leaveCancelled" > <!-- ... --> </transition>
接着给fade
类写过渡样式
.fade-enter-active, .fade-leave-active{transition: all 0.5s ease;} .fade-enter, .fade-leave-active{opacity:0;}
查看效果