Vue之 vue-router

Posted smyz

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Vue之 vue-router相关的知识,希望对你有一定的参考价值。

简介

vue-router是Vue.js官方的路由插件,它和vue.js是深度集成的,适合用于构建单页面应用。
vue-router是基于路由和组件的,路由用户设定访问路径的,将路径和组件映射起来。在vue-router的单页面应用中,页面的路径的改变就是组件的切换。
官网地址:https://router.vuejs.org/zh/

安装vue-router

# 可以在创建项目时就直接安装好vue-router
# 也可以单独安装,使用下面的命令
npm install vue-router

# 第二步:在main.js中引入
import router from \'./router\'
new Vue(
  router,    # 添加这一行
  store,
  render: h => h(App)
).$mount(\'#app\')

使用vue-router

配置路由的跳转,只需要在src/router/index.js目录下导入组件之后,再

import IndexView from "@/views/IndexView";   // 创建好组件之后,导入组件
const routes = [
    
        path: \'/index/\',       // 浏览器的路由
        name: \'index\',         // 别名
        component: IndexView   // 对应的是哪个组件
    ,
]

router的方法

this.$router.push(path)    // 相当于点击路由链接(可以返回到当前路由界面)
this.$router.replace(path) // 用新路由替换当前路由(不可以返回到当前路由界面)
this.$router.back()        // 请求(返回)上一个记录路由
this.$router.go(-1)        // 请求(返回)上一个记录路由
this.$router.go(1)         // 请求下一个记录路由
this.$router.forward()     // 前进

路由跳转

方法一 使用js控制

  • 使用给按钮绑定事件的方式进行跳转
<button @click="goToLogin">点我</button>
<script>
export default 
  name: \'HomeView\',
  methods:
    goToLogin()
      this.$router.push(\'/Index\')   // 这样点击上面的按钮后就会跳转到index页面了
    
  

</script>

方法二 使用标签控制

  • 使用标签的方法进行跳转
<!--写法-->
<router-link to="路由"> xxx </router-link>
<!--示例-->
<router-link to="/index"><button>点我</button></router-link>

路由跳转携带参数

方法一 使用问号携带

<router-link to="/index/?pk=1"><button>点我</button></router-link>
或
<router-link to="/index/?pk="+xxx><button>点我</button></router-link>
  • 通过打印console.log(this.$route)发现,数据在query中
  • 所以如果要取数据,可以直接使用query对象取
<script>
export default 
  name: "IndexView",
  created() 
    console.log(\'route:\', this.$route.query.pk)
  

</script>

方法二 使用斜杠分隔符携带

  • 第一步 配置router目录下index.js

    path: \'/index/:pk\',    // 这里配置什么参数,前台传入的值对应的Key就是什么
    name: \'index\',
    component: IndexView
,
  • 第二步 配置跳转功能
<router-link to="/index/1/"><button>点我</button></router-link>
  • 第三步取值
    根据console.log(this.$route)可以看到,值在params中
console.log(this.$route.params.pk)   // 这样就可以取到值了

方法三 使用对象的方式跳转

  • 可以直接在push方法中携带参数
<template>
  <div class="home">
    <button @click="clickFunc">点我</button>
  </div>
</template>

<script>
export default 
  name: \'HomeView\',
  methods:
    clickFunc()
      this.$router.push(
        name: \'index\',        // 这里的name就是router/index.js中路由配置的name别名,这个路由不需要作变化
        query:               // 可以将内容放到query中
          name: \'jack\',
          age: \'18\'
        ,
        params:              // 可以将内容放到params中,这样路由中需要配置为path: \'/index/:pk\'
          pk: \'16\',
        
      )
    
  

</script>
  • 可以看到,使用问题携带参数的截图

  • 可以看到,使用斜杠分隔携带参数的截图

方法四 标签方式跳转携带参数


path: \'/index/:pk\',    // 这里配置了:pk
    name: \'index\',
        component: IndexView
,
<template>
  <div class="home">
    <!--可以定义好对象,将内容写到对象中,并在这里引用-->
    <router-link :to="obj">
      <button>点我</button>
    </router-link>
    <!--可以将跳转对象写到标签中-->
    <!--如果路由配置了:pk这种分隔的方式,可以写query和params两个-->
    <router-link :to="name:\'index\', query:id:99, params:pk:100">
      <button>点我2</button>
    </router-link>
  </div>
</template>

<script>
export default 
  name: \'HomeView\',
  data() 
    return 
      obj: 
        name: \'index\',
        query: id: \'99\',
        params: pk: \'100\'
      
    
  

</script>
  • 返回结果如下显示

router与route的区别

route     # 当前页面的对象,也可以说是当前路由对象
router    # new VueRouter对象,也是就是vue-router的实例
  • 我们可以使用console.log查看一下这两个对象分别是什么
  • 可以看到route对应的就是当前页面的一些信息
  • router中对应的就是vue-router实例

多级路由

routes:[
    
        path: \'/about\',
        component: About,
    ,
    
        path: \'/home\',
        component: Home,
        children: [ //通过children配置子级路由
            
                path: \'news\', //此处一定不要写:/news 注意这个斜杠
                component: News
            ,
            
                path: \'message\',//此处一定不要写:/message 注意这个斜杠
                component: Message
            
        ]
    
]

// 跳转
< router - link
to = "/home/news" > News < /router-link>
    
        path: \'/demo\',
        component: Demo,
        children: [
            
                path: \'test\',
                component: Test,
                children: [
                    
                        name: \'hello\'     // 给路由定义别名
                        path: \'welcome\',
                        component: Hello,
                    
                ]
            
        ]
    
<!--简化前,需要写完整的路径 -->
<router-link to="/demo/test/welcome">跳转</router-link>

<!--简化后,直接通过别名跳转 -->
<router-link :to="name:\'hello\'">跳转</router-link>

<!--简化写法配合传递参数 -->
<router-link :to="name:\'hello\',query:id:666,itle:\'你好\'">跳转</router-link>

路由守卫

对路由进行权限控制,按分类分为:全局守卫(最常用),独享守卫,组件内守卫

全局路由守卫

  • 前置路由守卫:在进路由前,执行代码。
  • 后置路由守卫:路由跳转走,执行代码。

前置路由守卫配置

  • 只需要在router/index.js文件中新增一个函数即可
router.beforeEach(
    (to, from, next) => 
        console.log(to, from, next)
        // to 代表要去的路由
        // from 代表从哪个路由跳转过来
        // next 是一个函数,需要加括号执行,没有next则不会跳转到要去的路由

        // 下面写一个简单的路由守卫功能
        if (to.name == \'index\')
            console.log(\'成功访问index界面\')
            next()  // 这里不加next()是不会跳转的
        else
            alert(\'您不允许访问这个页面\')
        
    
)
  • 访问index页面可以访问

  • 访问home页面无法访问,先是弹窗,之后因为没有next()所以也不会跳转到home路由中

后置路由守卫配置

  • 与前置不同的只是函数名不同,用得很少
router.afterEach((to, from)=> 
函数内容
)

独享守卫

// 该文件专门用于创建整个应用的路由器
import VueRouter from \'vue-router\'
//引入组件
import About from \'../pages/About\'
import Home from \'../pages/Home\'
import News from \'../pages/News\'
import Message from \'../pages/Message\'
import Detail from \'../pages/Detail\'

//创建并暴露一个路由器
const router =  new VueRouter(
    routes:[
        
            name:\'guanyu\',
            path:\'/about\',
            component:About,
            meta:title:\'关于\'
        ,
        
            name:\'zhuye\',
            path:\'/home\',
            component:Home,
            meta:title:\'主页\',
            children:[
                
                    name:\'xinwen\',
                    path:\'news\',
                    component:News,
                    meta:isAuth:true,title:\'新闻\',
                    beforeEnter: (to, from, next) => 
                        console.log(\'独享路由守卫\',to,from)
                        if(to.meta.isAuth) //判断是否需要鉴权
                            if(localStorage.getItem(\'name\')===\'lqz\')
                                next()
                            else
                                alert(\'名不对,无权限查看!\')
                            
                        else
                            next()
                        
                    
                ,
                
                    name:\'xiaoxi\',
                    path:\'message\',
                    component:Message,
                    meta:isAuth:true,title:\'消息\',
                    children:[
                        
                            name:\'xiangqing\',
                            path:\'detail\',
                            component:Detail,
                            meta:isAuth:true,title:\'详情\',
                        
                    ]
                
            ]
        
    ]
)

export default router

组件内守卫

//进入守卫:通过路由规则,进入该组件时被调用
beforeRouteEnter (to, from, next) 
,
//离开守卫:通过路由规则,离开该组件时被调用
beforeRouteLeave (to, from, next) 


//通过路由规则,进入该组件时被调用
    beforeRouteEnter (to, from, next) 
        console.log(\'About--beforeRouteEnter\',to,from)
        if(to.meta.isAuth) //判断是否需要鉴权
            if(localStorage.getItem(\'school\')===\'atguigu\')
                next()
            else
                alert(\'学校名不对,无权限查看!\')
            
        else
            next()
        
    ,

    //通过路由规则,离开该组件时被调用
    beforeRouteLeave (to, from, next) 
        console.log(\'About--beforeRouteLeave\',to,from)
        next()
    

Vue.js 生态之vue-router

vue-router是什么~~

vue-router是Vue的路由系统,定位资源的,我们可以不进行整页刷新去切换页面内容。

vue-router的安装和基本配置

vue-router.js 可以下载 也可以用cdn,基本配置信息看如下代码~~~

技术分享图片
// html 代码
<div id="app">
    <div>
        <router-link to="/">首页</router-link>
        <router-link to="/about">关于我们</router-link>
    </div>
    <div>
        <router-view></router-view>
    </div>

</div>

<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://unpkg.com/vue-router/dist/vue-router.js"></script>
<script src="../js/router_demo.js"></script>
// js 代码
var routes = [
    {
        path: "/",
        component: {
            template: `<div><h1>首页</h1></div>`
        }
    },
    {
        path: "/about",
        component: {
            template: `<div><h1>关于我们</h1></div>`
        }
    }
]

var router = new VueRouter({
    routes: routes,
    // 路由去掉#
    // mode: ‘history‘,
});

var app = new Vue({
    el: ‘#app‘,
    router: router,
});
vue-router demo

路由的一些方法

路由传参以及获取参数~~

技术分享图片
// html 代码
<div id="app">
    <div>
        <router-link to="/">首页</router-link>
        <router-link to="/about">关于我们</router-link>
        <router-link to="/user/琴女?age=20">琴女</router-link>
        <router-link to="/user/提莫">提莫</router-link>
    </div>
    <div>
        <router-view></router-view>
    </div>
</div>
// js 代码
var routes = [
    {
        path: "/",
        component: {
            template: `<div><h1>首页</h1></div>`
        }
    },
    {
        path: "/about",
        component: {
            template: `<div><h1>关于我们</h1></div>`
        }
    },
    {
        path: "/user/:name",
        component: {
            template: `<div>
                      <h1>我是:{{$route.params.name}}</h1>
                      <h1>我年龄是:{{$route.query.age}}</h1>
                    </div>`,
        }
    }
]

var router = new VueRouter({
    routes: routes,
});

var app = new Vue({
    el: ‘#app‘,
    router: router,
});
传参以及获取参数

命名路由~  注意router-link里to一定要v-bind~~

技术分享图片
// html代码
<div id="app">
    <div>
        <router-link to="/">首页</router-link>
        <router-link :to="{name: ‘about‘}">关于我们</router-link>
        <router-link to="/user/gaoxin?age=19">gaoxin</router-link>
    </div>
    <div>
        <router-view></router-view>
    </div>
</div>
// js代码
let routes = [
        {
            path: ‘/‘,
            component: {
                template: `<h1>这是主页</h1>`
            }
        },
        {
            path: "/about",
            name: "about",
            component: {
                template: `<h1>关于我们</h1>`
            }
        },
        {
            path: "/user/:name",
            component: {
                template: `<div>
                            <h1>我是{{$route.params.name}}</h1>
                           <h2>我的年龄是{{$route.query.age}}</h2>
                            </div>
                          `
            }
        }
    ];

    let router = new VueRouter({
        routes: routes,
        mode: "history"
    });

    const app = new Vue({
        el: "#app",
        router: router,
        mounted(){
            console.log(this.$route)
            console.log(this.$router)
        }
    })
命名路由

子路由~~ 以展示详细为例~~

技术分享图片
// 添加子路由变化的只有父级路由 
// 基于上面的例子增加
// js 代码
{
        path: "/user/:name",
        component: {
            template: `<div>
                      <h1>我是:{{$route.params.name}}</h1>
                      <h1>我年龄是:{{$route.query.age}}</h1>
                      <router-link to="more" append>更多信息</router-link>
                      <router-view></router-view>
                    </div>`,
        },
        children: [
            {
            path: "more",
            component: {
                template: `<div>
                      {{$route.params.name}}的详细信息
                </div>`,
            }
        }
        ]

    },
子路由

 手动访问路由,以及传参~~

技术分享图片
// 基于上面例子追加
// html 代码
<div id="app">
    <div>
        <router-link to="/">首页</router-link>
        <router-link to="/about">关于我们</router-link>
        <router-link to="/user/琴女?age=20">琴女</router-link>
        <router-link to="/user/提莫">提莫</router-link>
        // 添加一个button按钮
        <button @click="on_click">旅游</button>
    </div>
    <div>
        <router-view></router-view>
    </div>
</div>    
// js 代码
// 注意路由name的使用 这是在原例子追加
var app = new Vue({
    el: ‘#app‘,
    router: router,
    methods: {
        on_click: function () {
            setTimeout(function () {
                this.$router.push(‘/about‘)
                setTimeout(function () {
                    this.$router.push({name: "user", params:{name: "琴女"},query:{age: 20}})
                }, 2000)
            }, 2000)
        }
    }
});
手动路由~以及传参

命名路由视图 router-view

当我们只有一个<router-view></router-view>的时候~所有内容都展示在这一个面板里面~

如果是content 和 footer 就需要同时显示并且不同区域~这就需要对视图进行命名~

技术分享图片
// html 代码
<div id="app">
    <div>
        <router-link to="/">首页</router-link>
        
    </div>
    <div>
        <router-view name="content" class="content-view"></router-view>
        <router-view name="footer" class="footer-view"></router-view>
    </div>

</div>
// js 中的主要代码
var routes = [
    {
        path: "/",
        components: {
            content: {
                template: `<div><h1>首页</h1></div>`,
            },
            footer: {
                template: `<div><h1>关于我们</h1></div>`,
            }
        }
    },
]
命名路由视图

错误路由的重定向~~

技术分享图片
let routes = [
     {
            path: "**",
            redirect: "/"
        }   
]
redirect

$route以及$router的区别~~

  -- $route为当前router调转对象,里面可以获取name, path, query, params等~

  -- $router为VueRouter实例,有$router.push方法等~~

路由的钩子

路由的生命周期就是从一个路由跳转到另一路由整个过程,下面介绍两个钩子~

router.beforeEach()   router.afterEach()  详情请看代码~~

技术分享图片
// html 代码
<div id="app">
    <router-link to="/">首页</router-link>
    <router-link to="/login">登录</router-link>
    <router-link to="/user">用户管理</router-link>
    <div>
        <router-view></router-view>
    </div>
</div>
//  js 代码
var routes = [
    {
        path: "/",
        component: {
            template: "<h1>首页</h1>"
        }
    },
    {
        path: "/login",
        component: {
            template: "<h1>登录</h1>"
        }
    },
    {
        path: "/user",
        component: {
            template: "<h1>用户管理</h1>"
        }
    }
];
var router = new VueRouter({
    routes: routes
});

router.beforeEach(function (to,from,next) {
    // console.log(to)
    // console.log(from)
    // console.log(next)
    // next(false)
    if(to.path=="/user"){
        next("/login")
    }
    else {
        next();
    }
});
router.afterEach(function (to, from) {
    console.log(to)
    console.log(from)
});

var app = new Vue({
    el: ‘#app‘,
    router: router
});
路由钩子
技术分享图片
next:function  一定要调用这个方法来resolve这个钩子函数。
        执行效果依赖next方法的调用参数
        next() 什么都不做继续执行到调转的路由
        next(false) 中断当前导航 没有跳转 也没有反应
        next("/")  参数是路径 调转到该路径
        next(error)  如果next参数是一个Error实例 导航终止该错误
                    会传递给router.onError()注册过的回调中
next 参数详解
    router.beforeEach(function (to,from,next) {
        console.log(to);
        console.log(from);
        console.log(next);
        next()
    });

后面加   next()

 

上面的例子~~如果/user下面还有子路由的情况下会怎么样呢~????

技术分享图片
// 匹配子路由 改一下匹配方法就可以~
// js 改动代码
router.beforeEach(function (to,from,next) {
    // console.log(to)
    // console.log(from)
    // console.log(next)
    // next(false)
    if(to.matched.some(function (item) {
            return item.path == "/post"
        })){
        next("/login")
    }
    else {
        next();
    }
});
// 元数据配置 改动代码
// html 部分
 {
        path: "/user",
        meta: {
            required_login: true,
        },
        component: {
            template: `
                <div>
                <h1>用户管理</h1>
                <router-link to="vip" append>vip</router-link>
                <router-view></router-view>
                </div>
                `
        },
        children: [{
            path: "vip",
            meta: {
              required_login: true,
            },
            component: {
                template: ‘<h1>VIP</h1>‘
            }
        }]
    }
// js 部分
router.beforeEach(function (to,from,next) {
    // console.log(to)
    // console.log(from)
    // console.log(next)
    // next(false)
    if(to.meta.required_login){
        next("/login")
    }
    else {
        next();
    }
});
匹配子路由以及元数据配置

 

以上是关于Vue之 vue-router的主要内容,如果未能解决你的问题,请参考以下文章

Vue.js 生态之vue-router

Vue.js生态之vue-router

Vue.js 生态之Vue-router 基础三

Vue之 vue-router

vue之vue-router的使用

vue-router原理剖析之自行实现router