vue-router
- 官方提供的用來實現(xiàn) SPA 的 vue 插件
- github: https://github.com/vuejs/vue-router
- 中文文檔: http://router.vuejs.org/zh-cn/
- 下載: npm install vue-router --save
相關(guān) API 說明
-
VueRouter(): 用于創(chuàng)建路由器的構(gòu)建函數(shù)
new VueRouter({
// 多個配置項
})
- 路由配置
routes: [
{ // 一般路由
path: '/about',
component: About
},
{ // 自動跳轉(zhuǎn)路由
path: '/',
redirect: '/about'
}
]
- 注冊路由器
import router from './router'
new Vue({
router
})
- 使用路由組件標(biāo)簽
<router-link>: 用來生成路由鏈接
<router-link to="/xxx">Go to XXX</router-link>
<router-view>: 用來顯示當(dāng)前路由組件界面
<router-view></router-view>
路由組件
- Home.vue
- About.vue
應(yīng)用組件: App.vue
<div>
<!--路由鏈接-->
<router-link to="/about">About</router-link>
<router-link to="/home">Home</router-link>
<!--用于渲染當(dāng)前路由組件-->
<router-view></router-view>
</div>
路由器模塊: src/router/index.js
export default new VueRouter({
routes: [
{
path: '/',
redirect: '/about'
},
{
path: '/about',
component: About
},
{
path: '/home',
component: Home
}
]
})
注冊路由器: main.js
import Vue from 'vue'
import router from './router'
// 創(chuàng)建 vue 配置路由器
new Vue({
el: '#app',
router,
render: h => h(app)
})
優(yōu)化路由器配置
linkActiveClass: 'active', // 指定選中的路由鏈接的 class
總結(jié): 編寫使用路由的 3 步
- 定義路由組件
- 注冊路由
- 使用路由
<router-link>
<router-view>
嵌套路由
子路由組件
- News.vue
- Message.vue
配置嵌套路由: router.js
path: '/home',
component: home,
children: [
{
path: 'news',
component: News
},
{
path: 'message',
component: Message
}
]
路由鏈接: Home.vue
<router-link to="/home/news">News</router-link>
<router-link to="/home/message">Message</router-link>
<router-view></route-view>
向路由組件傳遞數(shù)據(jù)
- 方式 1: 路由路徑攜帶參數(shù)(param/query)
配置路由
children: [
{
path: 'mdetail/:id',
component: MessageDetail
}
]
路由路徑
<router-link :to="'/home/message/mdetail/'+m.id">{{m.title}}</router-link>
路由組件中讀取請求參數(shù)
this.$route.params.id
- 方式 2: <router-view>屬性攜帶數(shù)據(jù)
<router-view :msg="msg"></router-view>
緩存路由組件對象
- 默認(rèn)情況下, 被切換的路由組件對象會死亡釋放, 再次回來時是重新創(chuàng)建的
- 如果可以緩存路由組件對象, 可以提高用戶體驗
編碼
<keep-alive>
<router-view></router-view>
</keep-alive>
編程式路由導(dǎo)航
- this.$router.push(path): 相當(dāng)于點擊路由鏈接(可以返回到當(dāng)前路由界面)
- this.$router.replace(path): 用新路由替換當(dāng)前路由(不可以返回到當(dāng)前路由界面)
- this.$router.back(): 請求(返回)上一個記錄路由
- this.$router.go(-1): 請求(返回)上一個記錄路由
- this.$router.go(1): 請求下一個記錄路由
完整示例代碼
/*index.js*/
/*
路由器對象模塊
*/
import Vue from 'vue'
import VueRouter from 'vue-router'
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-router插件
/*
內(nèi)部定義并注冊了2個組件標(biāo)簽(router-link/router-view),
給組件對象添加了2個屬性:
1. $router: 路由器
2. $route: 當(dāng)前路由
*/
Vue.use(VueRouter)
export default new VueRouter ({
// 注冊應(yīng)用中所有的路由
routes: [
{
path: '/about',
component: About
},
{
path: '/home',
component: Home,
children: [
{
path: '/home/news',
component: News
},
{
path: 'message',
component: Message,
children: [
{
path:'detail/:id',
component: MessageDetail
}
]
},
{
path: '',
redirect: '/home/news'
}
]
},
{
path: '/',
redirect: '/about'
}
]
})
/*main.js*/
/*
入口JS
*/
import Vue from 'vue'
import App from './App.vue'
import router from './router'
/* eslint-disable no-new */
new Vue({
el: '#app',
components: {App}, // 映射組件標(biāo)簽
template: '<App/>', // 指定需要渲染到頁面的模板
router // 注冊路由器
})
/* 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">
<!--生成路由鏈接-->
<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">
<!--顯示當(dāng)前組件-->
<keep-alive>
<router-view msg="abc"></router-view>
</keep-alive>
</div>
</div>
</div>
</div>
</div>
</template>
<script>
export default {}
</script>
<style>
</style>
/*About.vue*/
<template>
<div>
<h2>About</h2>
<p>{{msg}}</p>
<input type="text">
</div>
</template>
<script>
export default {
props: {
msg: String
}
}
</script>
<style>
</style>
/*home.vue*/
<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>
<script>
export default {}
</script>
<style>
</style>
/*Message.vue*/
<template>
<div>
<ul>
<li v-for="m in messages" :key="m.id">
<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 () {
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>
/*MessageDetail.vue*/
<template>
<ul>
<li>id: {{$route.params.id}}</li>
<li>title: {{detail.title}}</li>
<li>content: {{detail.content}}</li>
</ul>
</template>
<script>
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 () {// 改變當(dāng)前路由組件參數(shù)數(shù)據(jù)時, 不會重新創(chuàng)建組件對象, mounted不會重新執(zhí)行
const id = this.$route.params.id
this.detail = messageDetails.find(detail => detail.id===id*1)
},
watch: {
$route: function () { // 改變當(dāng)前路由組件參數(shù)數(shù)據(jù)時自動調(diào)用
console.log('$route()')
const id = this.$route.params.id
this.detail = messageDetails.find(detail => detail.id===id*1)
}
}
}
</script>
<style>
</style>
/*News.vue*/
<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>