Vue前端之路(四)---Vue Router

本文详细介绍了Vue Router的使用,包括安装、基础路由配置、动态路由、重定向、嵌套路由、命名路由、导航守卫、路由元信息、过渡动效等关键概念。通过实例展示了如何实现一级路由、动态传参、404路由、嵌套视图和编程式导航。同时,还探讨了如何利用导航守卫进行权限控制,以及如何添加过渡效果提升用户体验。
摘要由CSDN通过智能技术生成

目录

1.Vue Router概述

2.安装和引用

3.基础路由使用

3.1.一级路由

3.2.动态路由传参(基础写法)

3.3.重定向路由和404路由

3.4.嵌套路由

3.5.声明式导航和编程式导航

4.命名路由和命名视图

4.1.命名路由

4.2.命名视图

5.动态路由传参(改进写法)

6.导航守卫

6.1.全局前置守卫

6.2.全局后置钩子

6.3.路由独享的守卫

7.路由元信息

8.过渡动效


1.Vue Router概述

Vue Router是vue官方的路由管理器,与vue核心深度集成,让构建页面应用变得易如反掌

2.安装和引用

npm install vue-router

使用vue-cli搭建vue项目,在main.js中配置

import router from "./router";

// 创建和挂载根实例。
// 记得要通过 router 配置参数注入路由,
// 从而让整个应用都有路由功能
new Vue({
  router,
  render: h => h(App)
}).$mount("#app");

在router.js中配置

import Vue from "vue";
import VueRouter from "vue-router";

Vue.use(VueRouter);
//定义路由
// 每个路由应该映射一个组件。 其中"component" 可以是
// 通过 Vue.extend() 创建的组件构造器,
// 或者,只是一个组件配置对象。
// 我们晚点再讨论嵌套路由。
export const routes = [];

// 创建 router 实例,然后传 `routes` 配置
// 你还可以传别的配置参数, 不过先这么简单着吧。
const router = new VueRouter({
  routes
});
export default router;

3.基础路由使用

3.1.一级路由

在App.vue中配置

<!-- 路由出口 -->
<!-- 路由匹配到的组件将渲染在这里 -->
<template>
  <div id="app">
    <router-view />
  </div>
</template>

在router.js中配置

export const routes = [
  {
    path: "/login",
    name: "Login",
    component: () => import("./views/login")
  },
]

3.2.动态路由传参(基础写法)

场景:经常需要把某种模式匹配到的所有路由,全都映射到同个组件,那么,我们可以在 vue-router 的路由路径中使用“动态路径参数”(dynamic segment) 来达到这个效果。

export const routes = [
  // 动态路径参数 以冒号开头
  { 
    path: '/user/:id', 
    component: () => import("./views/user")
  }
]

可以通过{{ $route.params.id }}获取参数值

当使用路由参数时,例如从 /user/foo 导航到 /user/bar原来的组件实例会被复用。因为两个路由都渲染同个组件,比起销毁再创建,复用则显得更加高效。不过,这也意味着组件的生命周期钩子不会再被调用

想对路由参数的变化作出响应的话,你可以简单地 watch (监测变化) $route 对象

watch: {
   $route(to, from) {
     // 对路由变化作出响应...
   }
}

3.3.重定向路由和404路由

路由定义得越早,优先级就越高。

export const routes = [
  { path: "", redirect: "/dashboard", hidden: true },
  { path: "/", redirect: "/dashboard", hidden: true },
  { path: "*", redirect: "/404", hidden: true }
]

重定向的目标也可以是一个命名的路由:

{ path: '/a', redirect: { name: 'foo' }}

甚至是一个方法,动态返回重定向目标:

{ 
    path: '/a', 
    redirect: to => {
      // 方法接收 目标路由 作为参数
      // return 重定向的 字符串路径/路径对象
    }
}

3.4.嵌套路由

场景:实际的应用界面,通常由多层嵌套的组件组合而成。同样地,URL 中各段动态路径也按某种结构对应嵌套的各层组件,例如:横向主菜单和左侧主菜单下的子菜单

export const routes = [
  {
    path: "/dashboard",
    name: "Dashboard",
    redirect: "/dashboard/devops",
    component: () => import("./views/dashboard"),
    children: [
      {
        path: "devops",
        name: "Devops",
        component: () => import("./views/dashboard/devops"),
      },
      {
        path: "system",
        name: "System",
        component: () => import("./views/dashboard/system"),
      },
    ],
  }
]

别忘了创建路由出口的渲染位置

<div id="app">
  <router-view></router-view>
</div>

3.5.声明式导航和编程式导航

在 Vue 实例内部,你可以通过 $router 访问路由实例。因此你可以调用 this.$router.push

声明式

<router-link 
  :to="{path:item.url}"
  v-for="(item, index) in navsList" :key="index" class="menu"
></router-link>
<!-- 联动的css样式 .router-link-active {} -->

编程式:其中path和query匹配,name和params匹配,不能交叉使用,否则不生效

//带查询参数,等价于 /register?plan=private
router.push({ path: 'register', query: { plan: 'private' }})
//或者 命名路由,请看下一章节
router.push({ name: 'user', params: { userId: '123' }})

4.命名路由和命名视图

4.1.命名路由

通过一个名称来标识一个路由显得更方便一些,特别是在链接一个路由,或者是执行一些跳转的时候

export const routes = [
  {
    path: "/login/:userId",
    name: "Login",
    component: () => import("./views/login")
  },
]

要链接到一个命名路由,可以给 router-link 的 to 属性传一个对象

<router-link :to="{ name: 'Login', params: { userId: 123 }}">
    User
</router-link>

等价于

router.push({ name: 'Login', params: { userId: 123 } })

等价于

/login/123

4.2.命名视图

有时候想同时 (同级) 展示多个视图,而不是嵌套展示,例如创建一个布局,有 sidebar (侧导航) 和 main (主内容) 两个视图,这个时候命名视图就派上用场了。你可以在界面中拥有多个单独命名的视图,而不是只有一个单独的出口。如果 router-view 没有设置名字,那么默认为 default

<router-view></router-view>
<router-view name="a"></router-view>
<router-view name="b"></router-view>

那么

export const routes = [
  {
    path: '/',
    components: {
      default: Foo,
      a: Bar,
      b: Baz
    }
  },
]

5.动态路由传参(改进写法)

在组件中使用 $route 会使之与其对应路由形成高度耦合,从而使组件只能在某些特定的 URL 上使用,限制了其灵活性

const User = {
  template: '<div>User {{ $route.params.id }}</div>'
}
const router = new VueRouter({
  routes: [{ path: '/user/:id', component: User }]
})

进阶的写法,通过 props 解耦

const User = {
  props: ['id'],
  template: '<div>User {{ id }}</div>'
}
const router = new VueRouter({
  routes: [
    { path: '/user/:id', component: User, props: true },

    // 对于包含命名视图的路由,你必须分别为每个命名视图添加 `props` 选项:
    {
      path: '/user/:id',
      components: { default: User, sidebar: Sidebar },
      props: { default: true, sidebar: false }
    }
  ]
})

6.导航守卫

6.1.全局前置守卫

// to 将要访问的路径
// from 代表从哪个路径跳转而来
// next 是一个函数,表示放行 
// next() 放行 
// next(/login) 强制跳转
// next(false) 中断了这次导航
// next(new Error()) 导航守卫抛出了一个错误
const router = new VueRouter({ ... })
router.beforeEach((to, from, next) => {
  // ...
})

6.2.全局后置钩子

你也可以注册全局后置钩子,然而和守卫不同的是,这些钩子不会接受 next 函数也不会改变导航本身

router.afterEach((to, from) => {
  // ...
})

6.3.路由独享的守卫

你可以在路由配置上直接定义 beforeEnter 守卫:

export const routes = [
  {
	path: '/foo',
	component: Foo,
	beforeEnter: (to, from, next) => {
	// ...
	}
  }
]

7.路由元信息

定义路由的时候可以配置 meta 字段:

export const routes = [
	{
	  path: '/foo',
	  component: Foo,
	  children: [
		{
		  path: 'bar',
		  component: Bar,
		  meta: { requiresAuth: true }
		}
	  ]
	}
]

一个路由匹配到的所有路由记录会暴露为 $route 对象 (还有在导航守卫中的路由对象) 的 $route.matched 数组。因此,我们需要遍历 $route.matched 来检查路由记录中的 meta 字段。

router.beforeEach((to, from, next) => {
  if (to.matched.some(record => record.meta.requiresAuth)) {
    // this route requires auth, check if logged in
    // if not, redirect to login page.
   ...
  } else {
    next() // 确保一定要调用 next()
  }
})

8.过渡动效

<router-view> 是基本的动态组件,所以我们可以用 <transition> 组件给它添加一些过渡效果

例如:

<transition name="slide-left" mode="out-in">
  <router-view />
</transition>

过渡模式mode:

            1.in-out:新元素先进入过渡,完成之后当前元素过渡离开。

            2.out-in:当前元素先进行过渡离开,离开完成后新元素过渡进入。

/*过渡效果*/
.slide-left-enter {
    opacity: 0;
    -webkit-transform: translate(30px, 0);
    transform: translate(30px, 0);
}
.slide-left-enter-active{
    transition: all .5s ease;
}
.slide-left-leave-to{
    opacity: 0;
    -webkit-transform: translate(-30px, 0);
    transform: translate(-30px, 0);
}
.slide-left-leave-active {
    transition: all .5s ease;
}

常用的大概就这些

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

彼岸花@开

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值