5.0 路由组件的使用

一、概述

路由器:路由器管理路由;

路由:路由是一种映射关系,一个key对应一个value,key是path,对于后台路由,

      value是处理请求的回调函数,对于前台路由value是组件。

说明:
1) 官方提供的用来实现 SPA(单个页面) 的 vue 插件
2) github: https://github.com/vuejs/vue-router
3) 中文文档: http://router.vuejs.org/zh-cn/
4) 下载: npm install vue-router --save

1. 路由的使用

(1) VueRouter(): 用于创建路由器的构建函数
  new VueRouter({  // 创建路由器实例
    // 多个配置项(配置对象)
  })


(2)路由配置
  routes: [
    { // 一般路由
      path: '/about',  
      component: About
    },
    { // 自动跳转路由
      path: '/',
      redirect: '/about'
    }
  ]


(3)注册路由器
  import router from './router'
  new Vue({
    router
  })


(4)使用路由组件标签
   <router-link>: 用来生成路由链接(当点击路由连接的时候需要在界面上显示当前路由组件)
   eg: <router-link to="/home">Go to home</router-link>

      <router-link to="/about">Go to about</router-link>


   <router-view>: 用来显示当前路由组件界面
   eg: <div> 

      <router-view></router-view>  //表示如果点击了路由链接(/about),则该路由链接的界面显示在这里,即显示在这个div里面.

    </div>

2. 缓存路由组件对象

正常情况下,一个路由组件被切换的时候,这个路由组件就会死亡,在切换回来时,又重先创建。

路由组件的缓存就是,在切换的时候将路由组件进行缓存,不要让它死亡。实现:

<keep-alive>
  <router-view></router-view>   // 缓存路由组件对象,只是平时我们会说缓存路由组件  (这里为保持About和Home活着)
</keep-alive>

现象:在如下图About组件的输入框输入abc后,切换到Home组件,然后在切回About组件,此时输入框还显示abc。

3. 向路由组件传递参数

方式一:  路由路径携带参数(param/query)

这里的参数有两种类型,param参数和query参数(这两种参数的传递等效),以下实例为param参数的传递,如果要使用query参数类型

传递参数,则不需要写下面的:id占位符,<router-link>路由链接中,路径的拼接方式和以前一样如: xxxx?id=1
1) 配置路由
children: [
  {
    path: 'mdetail/:id',  //占位符
    component: MessageDetail
  }
]
2) 路由路径
  <router-link :to="'/home/message/mdetail/'+m.id">{{m.title}}</router-link>
3) 路由组件中读取请求参数
  this.$route.params.id

方式二:<router-view>属性携带数据

<router-view :msg="msg"></router-view>

以下实例中App.vue通过msg属性将数据传递至About组件中。

4. 编程式路由导航

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

二、使用(基本路由/嵌套路由)

先下载vue-router包:npm install vue-router --save

非路由组件一般放在components文件夹下,路由组件一般放在views|pages文件夹下; 

1. 路由的使用步骤:

步骤一: 定义路由组件

index.html:

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width,initial-scale=1.0">
  <link rel="stylesheet" href="/static/css/bootstrap.css">
  <title>vue_demo</title>

  <style> /*设置选择路由时的样式,!important表示 提高指定样式规则的应用优先权*/
    .router-link-active {
      color: red !important;
    }
  </style>
</head>
<body>
<div id="app"></div>
<!-- built files will be auto injected -->
</body>
</html>
View Code

App.vue:

<template>
  <div>
    <div class="row">
      <div class="col-xs-offset-2 col-xs-8">
        <div class="page-header"><h2>Router Test</h2></div>
      </div>
    </div>

    <div class="row">
      <!--左边部分-->
      <div class="col-xs-2 col-xs-offset-2">
        <div class="list-group">
          <!--5.使用路由标签-->
          <!-- 生成路由链接 -->
          <router-link to="/about" class="list-group-item">About</router-link>
          <router-link to="/home" class="list-group-item">Home</router-link>
        </div>
      </div>

      <!--右边部分-->
      <div class="col-xs-6">
        <div class="panel">
          <div class="panel-body">
            <!-- 显示当前组件 -->
            <keep-alive>
              <!--传递一个属性,值为abc,如果写成:msg="abc", 则abc为变量-->
              <router-view msg="abc"></router-view>
            </keep-alive>
          </div>
        </div>
      </div>

    </div>
  </div>
</template>

<!--根组件-->
<script>
  export default {}
</script>

<style>

</style>
View Code

 About.vue/Home.vue:用户演示基本路由

<template>
  <div>
    <h2>About</h2>
    <p>{{msg}}</p>
    <input type="text">
  </div>
</template>

<!--About组件-->
<script>
  export default {
    // 接收一个属性,这个属性是由App组件路由传递过来的
    props: {
      msg: String
    }
  }
</script>

<style>

</style>
View Code
<template>
  <div>
    <h2>Home</h2>
    <div>
      <ul class="nav nav-tabs">
        <!--使用路由:路由链接-->
        <li><router-link to="/home/news">News</router-link></li>
        <li><router-link to="/home/message">Message</router-link></li>
      </ul>

      <!--使用路由:当前路由-->
      <router-view></router-view>
    </div>
  </div>
</template>

<!--Home组件-->
<script>
  export default {}
</script>

<style>

</style>
View Code

News.vue/Message.vue:Home下的子路由,用户演示嵌套路由

<template>
  <ul>
    <li v-for="(news, index) in newsArr" :key="index">{{news}}</li>
  </ul>
</template>

<script>
  export default {
    data () {
      return {
        newsArr: ['News001', 'News002', 'News003']
      }
    }
  }
</script>

<style>

</style>
View Code
<template>
  <!--根标签div:只能有一个-->
  <div>
    <ul>
      <!-- :key一般写index,如果这个对象里面有标识属性,则最好写标识属性-->
      <li v-for="m in messages" :key="m.id">
        <!--要拼接字符串得是js语法,不能是html的语法,所以,这里是:to="" , 如果用es5的语法则为 :to="''", 如果用es6的语法则为:to="``"-->
        <router-link :to="`/home/message/detail/${m.id}`">{{m.title}}</router-link>
        <button @click="pushShow(m.id)">push查看</button>
        <button @click="replaceShow(m.id)">replace查看</button>
      </li>
    </ul>
    <button @click="$router.back()">回退</button>
    <hr>
    <router-view></router-view>
  </div>
</template>

<script>
  export default {
    data () {
      return {
        messages: [
          /* {id: 1, title: 'Message001'},
           {id: 3, title: 'Message003'},
           {id: 5, title: 'Message005'}*/
        ]
      }
    },

    mounted () { // 用于异步操作
      // 模拟ajax请求从后台获取数据,注意:回调函数要用箭头函数
      setTimeout(() => {
        const messages = [
          {id: 1, title: 'Message001'},
          {id: 3, title: 'Message003'},
          {id: 5, title: 'Message005'}
        ]
        this.messages = messages
      }, 1000)
    },

    methods: {
      pushShow (id) {
        this.$router.push(`/home/message/detail/${id}`)
      },

      replaceShow (id) {
        this.$router.replace(`/home/message/detail/${id}`)
      }
    }
  }
</script>

<style>

</style>
View Code

MessageDetail.vue: Message下的子路由

<template>
  <ul>
    <!--$route表示当前路由-->
    <li>id: {{$route.params.id}}</li>
    <li>title: {{detail.title}}</li>
    <li>content: {{detail.content}}</li>
  </ul>
</template>

<script>
  /*这里面就没有做异步了,真实的情况应该是详情页面根据传递过来的id去后台查询*/
  const messageDetails = [
    {id: 1, title: 'Message001', content: 'message content00111....'},
    {id: 3, title: 'Message003', content: 'message content00222....'},
    {id: 5, title: 'Message005', content: 'message content00333....'}
  ]
  export default {
    data() {
      return {
        detail: {}  // 里面的属性不用列举
      }
    },
    mounted () {// 改变当前路由组件参数数据时, 不会重新创建组件对象, mounted不会重新执行,所以这里需要用watch去监视
      // 模拟异步到后台查询数据
      setTimeout(() => {
        const id = this.$route.params.id // 这是传递过来的id,有可能传递过来后就变成文本了,乘以1后就变成数字了
        this.detail = messageDetails.find(detail => detail.id===id*1)
      }, 1000)
    },

    watch: {
      // 方法一
      // $route: function () { // 改变当前路由组件参数数据时自动调用(组件对象有$route这个属性)
      //   console.log('$route()')
      //   const id = this.$route.params.id
      //   this.detail = messageDetails.find(detail => detail.id===id*1)
      // }
      $route: function (value) { // 方式二
        console.log(value);
        const id = value.params.id
        console.log(id);
        this.detail = messageDetails.find(detail => detail.id===id*1)
      }
    }
  }
</script>

<style>

</style>
View Code

步骤二:注册路由组件(将路由组件映射成路由)

router/ index.js:

/*
路由器对象模块
 */
import Vue from 'vue' //引入vue
import VueRouter from 'vue-router' //1. 引入vue的路由器组件

import About from '../pages/About.vue' //引入路由组件
import Home from '../pages/Home.vue'
import News from '../pages/News.vue'
import Message from '../pages/Message.vue'
import MessageDetail from '../pages/MessageDetail.vue'

Vue.use(VueRouter) // 2.声明使用vue-router插件

// 3.对外暴露路由器对象(这里为默认暴露,默认暴露,引入时可以使用任何名字)
export default new VueRouter({
  routes: [   // 注册应用中所有的路由
    {
      path: '/about',
      component: About
    },
    {
      path: '/home',
      component: Home,
      children: [  // 配置子路由组件
        {
          path: '/home/news', // path最左侧的/永远代表根路由
          component: News
        },
        {
          path: 'message', // 这是简化写法
          component: Message,
          children: [
            {
              path: 'detail/:id',  // :id表示占位符
              component: MessageDetail
            }
          ]
        },
        {
          path: '', // 设置子路由的默认显示,代表当前,这里为/home,因为这是/home下的自路由
          redirect: '/home/news'
        }
      ]
    },
    {
      path: '/',  // 设置默认请求about,即当请求根路径的时候
      redirect: '/about' // 重定向请求/about
    }
  ]
})

main.js:注册路由器

/*
入口JS
 */
import Vue from 'vue'
import App from './App.vue'
import router from './router' //引入路由器(因为是index.js,所以这里直接写到./router就可以了)


new Vue({//配置对象的属性名都是一些确定的属性名,不能随便修改
  el: '#app',
  components: {App}, // 映射组件标签
  template: '<App/>', // 指定需要渲染到页面的模板
  router  // 4.注册路由器  等价于 router: router
})
View Code

步骤三:使用路由(标签)

关于路由的使用主要是使用路由标签-路由链接 <router-link> 、当前路由<router-view>,在以上实例中主要存在App.vue、

News.vue、Messages中。

效果图:

|

        图1                           图2

猜你喜欢

转载自www.cnblogs.com/shiyun32/p/10909141.html