vue-router中的参数传递

Posted 赵云澜

tags:

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

文章目录


前言

希望我能从事web前端开发工作,文章写得啰嗦无厘头还请见谅,个人学习拙见,学得好的朋友能快速找到关键代码,和我一下还在学习阶段的朋友可以慢慢看步骤操作。


一、本文章中练习需要的准备工作

本文章就简单练习在路由中参数传递,样式简单点就好了。

  1. 暴力引入bootstrap
  2. 安装Vue Router

暴力引入bootstrap

  1. 在项目文件中的public文件夹中新建css文件夹。
  2. 把bootstrap.css文件放入新建的css文件夹。
  3. 在public文件夹下的index.html 在head标签内引入下方代码 👇 然后保存。
<link rel="stylesheet" href="<%= BASE_URL %>./css/bootstrap.css">

Bootstrap官方文档 👉Bootstrap v4 中文文档

示例代码:

安装Vue Router

大致了解一下在vue2项目中的vue-router版本版本是vue-router@3
vue3则是vue-router@4 官方文档👉 安装|Vue Router
本文章是在vue2项目中练习。

在npm下

npm install vue-router@3

在yarn下

yarn add vue-router@3

运行示例图:

二、项目基本架构

  1. 配置router文件导出并引用
  2. 路由组件分类

基本结构示例图:

1. 配置router文件

1-1 在src文件下新建router文件夹,在router文件夹下创建index.js文件,基本配置代码如下:

// 引入Vue 和 VueRouter
import Vue from 'vue'
import VueRouter from 'vue-router'
// 引入需要匹配路由规则的一级子组件
import Vparams from '@/view/Vparams'
import Vprops from '@/view/Vprops'
import Vquery from '@/view/Vquery'

// 把router挂载到vue实例对象上
Vue.use(VueRouter)

// 开始匹配路由规则啦
// 记得导出(暴露)去main.js 引用!
export default new VueRouter (
  routes: [
    // 重定向也是通过 routes 配置来完成,下面例子是从 /vparams 重定向到 / 
    // 重定向可以实现我们已进入时就显示首要展示的页面
     path: '/', redirect: '/vparams' ,
     path: '/vparams', component: Vparams,,
     path: '/vprops', component: Vprops ,
     path: '/vquery', component: Vquery 
  ]
)

1-2 在main.js中引入router文件,基本配置代码如下:

import Vue from 'vue'
import App from './App.vue'
// 1. 引入router文件,这里可以省略index.js 默认找文件夹下的index文件
// 完整写法 import router from '@/router/index.js'
import router from '@/router'

Vue.config.productionTip = false

new Vue(
  render: h => h(App),
  // 2. 挂载
  // 键值对一样可省略,完整写法: router: router 
  router
).$mount('#app')

2. 写入路由组件 一级路由

2-1 本文章想练习query、params、props传参,所以路由组件按它们三命名。
这里就只展示一个算了。
Vquery.vue 代码示例:

<template>
  <div>
    <h2 style="color:orange">我是Vquery组件</h2>
    <hr/>
    <ol>
      <li v-for="(q, id) in queList" :key="id">q.msg</li>
    </ol>
  </div>
</template>

<script>
export default 
  name: 'Vquery',
  data() 
    return 
      queList: [
         id: 1, msg: '跳转路由并携带query参数 to的字符串写法' ,
         id: 2, msg: '跳转路由并携带query参数 to的对象写法' ,
      ]
    
  

</script>

2-2 在App.vue组件中引入
注意:router-link 组件支持用户在具有路由功能的应用中 (点击) 导航。 通过 to 属性指定目标地址,默认渲染成带有正确链接的 a 标签,可以通过配置 tag 属性生成别的标签.。

通过 router-link 进行跳转不会跳转到新的页面,也不会重新渲染,它会选择路由所指的组件进行渲染,避免了重复渲染的“无用功”。

router-view 渲染路径匹配到的视图组件,也可粗略的理解为插槽路由目的地址将在此标签内渲染。

<template>
  <div>
    <!-- 无需路由的组件称为一般组件 -->
    <Jumbotron/>
    <nav class="nav nav-pills flex-column flex-sm-row">
      <router-link class="flex-sm-fill text-sm-center nav-link" active-class="active" to="/vparams">vparams</router-link>
      <router-link class="flex-sm-fill text-sm-center nav-link" active-class="active" to="/vprops">vprops</router-link>
      <router-link class="flex-sm-fill text-sm-center nav-link" active-class="active" to="/vquery">vquery</router-link>
    </nav>
    <!-- 路由占位符 我们点击的组件内容将在这展示 -->
    <router-view></router-view>
  </div>
</template>

<script>
import Jumbotron from '@/components/Jumbotron'
export default 
  name: 'App',
  components:  Jumbotron 

</script>

2-3 运行效果 一级路由

3. 二级路由 实现传参

3.1 使用params 传参

params参数:属性 路径的一部分,需要注意在配置路由的时候需要占位
若指定params参数可传可不传,在配置路由的时候在占位的后面加上一个问号即可:
path: ‘detail/:id/:msg?’
但是这样如果传递是个空串,url会出错,解决方案:
params: msg: ‘’ || undefind ,需要传递一个undefind

3.1.1 在router文件下配置二级路由

在原router文件下新增以下代码

// 引入需要匹配路由规则的二级子组件
import Detail from '@/view/Detail'

   path: '/vparams', 
   component: Vparams,
   children: [
    // params 传参 在path内带上参数项
    // name 命名路由 为简写路径
     name: 'Detail', path: 'detail/:id/:msg', component: Detail 
      ]
    ,

3.1.2 在view文件下新建二级路由组件

在组件内用钩子函数mounted()
作用:在组件被挂载之后调用
打开控制台找到$route 和 $router 。

$route是“路由信息对象”,包括path,params,hash,query,fullPath,matched,name等路由信息参数。

而$router是“路由实例”对象包括了路由的跳转方法,钩子函数等。

二级路由 Detail.vue 代码:
通过$route.params传参

<template>
  <div class="card" style="width: 18rem;">
    <ul class="list-group list-group-flush">
      <li class="list-group-item">id:$route.params.id</li>
      <li class="list-group-item">msg:$route.params.msg</li>
    </ul>
  </div>
</template>

<script>
export default 
  name: 'Detail',
  mounted() 
  // 观察$router和$route内的参数
    console.log(this)
  

</script>

3.1.3 在上一级路由组件配置router-link

Vparams组件 – to的字符串写法

<template>
  <div>
    <h2 style="color: red">我是Vparams组件</h2>
    <hr/>
    <ul>
      <li v-for="(m,id) in parList" :key="id">
      <!-- 开始二级路由 并传参 params传参用法 -->
      <!-- 给to动态绑定属性,在字符串模板内$会解析成属性 -->
       <router-link :to="`/vparams/detail/$m.id/$m.msg`">
          m.msg
        </router-link>
      </li>
    </ul>
    <hr>
    <!-- 二级路由展示区 -->
    <router-view></router-view>
  </div>
</template>

Vparams组件 – to的对象写法 不能用path必须用name

<router-link :to="
  name: 'Detail',
  params: 
     id: m.id,
     msg: m.msg
  
">
  m.msg
</router-link>

3.1.4 运行结果 - params

3.2 使用query传参

query参数:不属于路径的一部分,类似ajax中的queryString /home?k=val&k=val 不需要占位

3.2.1 在router文件下配置二级路由

在原来的router文件中新增:


  path: '/vquery', component: Vquery,
  children: [
  // name 不要与上一name重名
    name: 'Detailquery', path: 'detail', component: Detail
 ]

3.2.2 在一级路由组件配置router-link

Vquery组件 – to的字符串写法

参数会以 url string 的形式进行传递,即?后的字符串则为其请求参数,并以&作为分隔符。常用在 GET 请求方式时使用。 其他请求方式也可以使用,拼接在接口地址 url? 后面

形式 : /路由路径/…/路由路径/?key=value&key=value

<template>
  <div>
    <h2 style="color:orange">我是Vquery组件</h2>
    <hr/>
    <ol>
      <li v-for="(m, id) in queList" :key="id">
        <!-- 配置路由导航地址 -->
        <!-- 跳转路由并携带query参数 to的字符串写法 --> 
        <router-link :to="`/vquery/detail?id=$m.id&msg=$m.msg`">
          m.msg
        </router-link>
      </li>
    </ol>
    <!-- 路由占位符 -->
    <router-view></router-view>
  </div>
</template>

<script>
export default 
  name: 'Vquery',
  data() 
    return 
      queList: [
         id: 1, msg: '跳转路由并携带query参数 to的字符串写法' ,
         id: 2, msg: '跳转路由并携带query参数 to的对象写法' ,
      ]
    
  

</script>

<style lang="less" scoped>

</style>

Vquery组件 – to的对象写法

to和query中可以用path,name和path二选一就好了,路由组件少地址短用path更合适点,路由组件多且长命名路由(name)更好点。

<template>
  <div>
    <h2 style="color:orange">我是Vquery组件</h2>
    <hr/>
    <ol>
      <li v-for="(m, id) in queList" :key="id">
        <router-link :to="
        // name 和 path 指定路由二选一 
          // name: 'Detailquery',
          path: '/vquery/detail',
          query: 
            id: m.id,
            msg: m.msg
          
        ">
          m.msg
        </router-link>
      </li>
    </ol>
    <!-- 路由占位符 -->
    <router-view></router-view>
  </div>
</template>

3.2.3 在目的路由组件内 – Detail.vue

本文是使用了一个目标路由组件,所以若你想同时看三种方式的写法,建议给每个一级路由组件写对应的目的路由组件。

<template>
  <div class="card" style="width: 18rem;">
    <ul class="list-group list-group-flush">
    <!-- $route.query下 -->
      <li class="list-group-item">id:$route.query.id</li>
      <li class="list-group-item">msg:$route.query.msg</li>
    </ul>
  </div>
</template>

3.2.4 运行效果 – query

3.2 使用props传参

3.1.1 props 键值对形式 key-value (不推荐使用)

此方法传递的是假数据,了解即可。再此也简单描述。

3.1.1.1 修改router/index.js

  path: '/vprops', component: Vprops,
  children: [
     
       name: 'Detailprops', path: 'detail', component: Detail, 
       // props 值为对象 该对象中所有key-value都会以props形式传给Detail组件
       props: id:666, msg: 'abc'
     
  ]
,
3.1.1.2 目的路由组件引入

和父传子中的props使用方法一样。
Detail.vue:

<template>
  <div class="card" style="width: 18rem;">
    <ul class="list-group list-group-flush">
      <li class="list-group-item">id:--id</li>
      <li class="list-group-item">msg:--msg</li>
    </ul>
  </div>
</template>

<script>
export default 
  name: 'Detail',
  props: ['id', 'msg']

</script>

3.1.1.3 实现效果

3.1.2 props 值为布尔值(推荐)

props 值为布尔值, 若布尔值为真,则会把改路由组件收到的所有params值 都会以props形式传给目的路由组件。
注意:此方法只能通过params方式上行得通。

3.1.2.1 修改router/index.js

 path: '/vprops', component: Vprops,
 children: [
    name: 'Detailprops', path: 'detail/:id/:msg', component: Detail, props: true 
   ]
,
3.1.2.2 在Vprops组件中
<router-link :to="
// params中to对象形式只能用name 命名路由 不能用path
  name: 'Detailprops',
  params: 
     id: p.id,
     msg: p.msg   
">
    p.msg
</router-link>
3.1.2.3 在Detail组件中
<template>
  <div class="card" style="width: 18rem;">
    <ul class="list-group list-group-flush">
   <!-- 与params不同,此处引用不需要加 $route.params -->
      <li class="list-group-item">id:--id</li>
      <li class="list-group-item">msg:--msg</li>
    </ul>
  </div>
</template
        
                

目录

传递参数的方式

params和query
①params
在前面讲动态路由的时候用到过

1.配置路由映射的path: /router/:id
2.指定<router-link> 中的to属性:/router/123(也就是传递之后形成的路径)
3.这样通过$route.params.id就可以拿到123

②query
1.配置路由映射的path: /router
src/router/index.js

2.指定<router-link> 中的to属性,to后面是一个对象,对象里面有个query选项,这里可以传参数

<router-link :to="{path: '/profile', query: {name: 'fyx', age: 20, height:175}}">档案</router-link>

最后形成的路径:http://localhost:8080/profile?name=fyx&age=20&height=175
在路径中,问号后面的东西就是query
(URL组成:scheme://host:port/path?query#fragment)

如何获取参数并显示?
profile.vue

<template>
<div>
  <h2>我是profile组件</h2>
  <h2>{{$route.query}}</h2>
  <h2>{{$route.query.name}}</h2>
  <h2>{{$route.query.age}}</h2>
  <h2>{{$route.query.height}}</h2>
</div>
</template>

<script>
export default {
  name: "profile"
}
</script>

<style scoped>
</style>

效果:

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

Vue.js 中的动态路由

vue-router路由的使用

关于vue-router接收参数?

Vue之 vue-router

vue.js的路由地址会以#号分隔,有啥办法可以去掉这个#号吗

vue routes url不存在怎么跳指定的页面