安装
直接下载 / CDN
https://unpkg.com/vue-router/dist/vue-router.js
Unpkg.com 提供了基于 NPM 的 CDN 链接。上面的链接会一直指向在 NPM 发布的最新版本。你也可以像https://unpkg.com/[email protected]/dist/vue-router.js
这样指定 版本号 或者 Tag。
NPM
npm install vue-router
如果在一个模块化工程中使用它,必须要通过 Vue.use() 明确地安装路由功能:
import Vue from 'vue'
import VueRouter from 'vue-router'
Vue.use(VueRouter)
如果使用全局的 script 标签,则无须如此 (手动安装)。
起步
<body>
<div id="app">
<h1>Hello App!</h1>
<p>
<!-- 使用 router-link 组件来导航. -->
<!-- 通过传入 `to` 属性指定链接. -->
<!-- <router-link> 默认会被渲染成一个 `<a>` 标签 -->
<router-link to="/one">Go to one</router-link>
<router-link to="/two">Go to two</router-link>
</p>
<!-- 路由出口 -->
<!-- 路由匹配到的组件将渲染在这里 -->
<router-view></router-view>
</div>
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue-router.js"></script>
<script>
let one = {
template: "<h1>Hello One</h1>"}
let two = {
template: `<h1>Hello Two</h1>`}
const router = new VueRouter({
routes: [
{
path: "/one", component: one},
{
path: "/two", component: two}
]
})
new Vue({
el: '#app',
router // (缩写) 相当于 router: router
})
</script>
</body>
上面的案例中使用 router-link
组件来导航, 默认会被渲染成一个 <a>
标签,当然也可以通过tag属性指明想要渲染的元素比如渲染成按钮样式:<router-link tag="button">
。通过传入 to
属性指定链接,这个属性可以和v-on
联合使用进行声明式导航。路由匹配到的组件将渲染在<router-view>
。通过注入路由器,我们可以在任何组件内通过 this.$router
访问路由器,也可以通过 this.$route
访问当前路由。
传参
query传递参数
查询参数其实就是在路由地址后面带上参数和传统的url参数一致的,传递参数使用query而且必须配合path来传递参数而不能用name,目标页面接收传递的参数使用query。
<router-link to="/one?name=zs&age=18">Go to one</router-link>
我们可以在html中使用插值表达式体现出参数的具体值:<h2>{
{this.$route.query}}</h2>
params传递参数
一个“路径参数”使用冒号 :
标记。当匹配到一个路由时,参数值会被设置到this.$route.params
,可以在每个组件内使用:
模式 | 匹配路径 | $route.params |
---|---|---|
/user/:username | /user/evan | { username: 'evan' } |
/user/:username/post/:post_id | /user/evan/post/123 | { username: 'evan', post_id: '123' } |
<router-link to="/two/zhagnsa/20">Go to Two</router-link>
{path:"/two/:name/:age", name:"two", component:two}
除了上面那种还有声明式的导航,这里对上面两种的参数传递进行简单演示:
<!-- query传参 -->
<router-link :to="{path:'/one',query:{name:'zs',age:18}}" tag="button">Go to One</router-link>
注意这里的的:to
<!-- params传参 -->
<router-link :to="{name:'two',params:{name:'wangwu',age:20}}" tag="button">Go to Two</router-link>
路径传参中的name对应query的path,parmsd对应其query。
到此总结一下
- 命名路由搭配params,刷新页面参数会丢失
- 查询参数搭配query,刷新页面数据不会丢失
- 接受参数使用
this.$route.query/params
就能获取到参数的值
路由组件传参
在组件中使用 $route 会使之与其对应路由形成高度耦合,从而使组件只能在某些特定的 URL 上使用,限制了其灵活性。使用 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 }
}
]
})
对于包含命名视图的路由,必须分别为每个命名视图添加 props
选项。
除了布尔类型,对象类型,还有函数类型:
const two = {
props:['name','age'],
template:`<h1>Hello {
{name}} {
{age}}</h1>`
}
{
path:"/two/:name/:age",name:"two",component:two, props: (route) => ({
age: route.params.age })}
注意这里的name,在下面的方法中没有返回,所以这里是无效的,没有结果!
嵌套路由
URL 中各段动态路径也可以按某种结构对应嵌套的各层组件,例如:
/user/foo/profile /user/foo/posts
+------------------+ +-----------------+
| User | | User |
| +--------------+ | | +-------------+ |
| | Profile | | +------------> | | Posts | |
| | | | | | | |
| +--------------+ | | +-------------+ |
+------------------+ +-----------------+
借助 vue-router,使用嵌套路由配置,就可以很简单地表达这种关系。上面有个实例:
{
path: "/one", component: one},
那么/one/sub
路由可以这么来写:
{
path:"/one",
component:one,
children:[
{
path:"sub", // path 不要写成“/sub”
name:"sub",
component:sub
}
]
},
path 不要写成"/sub",因为Vue会自动拼接路径,这样写反而会识别不出来。子路由进行参数传递和上面一样,大家可以试一试。
命名视图
有时候想同时 (同级) 展示多个视图,而不是嵌套展示,例如创建一个布局,有 sidebar (侧导航) 和 main (主内容) 两个视图,这个时候命名视图就派上用场了。你可以在界面中拥有多个单独命名的视图,而不是只有一个单独的出口。如果 router-view 没有设置名字,那么默认为 default。
<!-- 视图,和插槽类似 -->
<router-view></router-view>
<router-view name="one"></router-view>
<router-view name="two"></router-view>
</div>
一个视图使用一个组件渲染,因此对于同个路由,多个视图就需要多个组件。确保正确使用 components
配置 (带上 s):
new VueRouter({
routes:[
{
path:'/',
components:{
default: {
template:`<h1>Default!</h1>`}
one:{
template:`<h1>One!</h1>`},
two:{
template:`<h1>Two!</h1>`}
}
}
]
})
重定向和别名
重定向
重定向也是通过 routes 配置来完成,下面例子是从 /a 重定向到 /b:
const router = new VueRouter({
routes: [
{
path: '/a', redirect: '/b' }
]
})
重定向的目标也可以是一个命名的路由:
const router = new VueRouter({
routes: [
{
path: '/a', redirect: {
name: 'foo' }}
]
})
甚至是一个方法,动态返回重定向目标:
const router = new VueRouter({
routes: [
{
path: '/a', redirect: to => {
// to : 对象类型
// return 重定向的 字符串路径/路径对象
return "/b"
}}
]
})
这里的to是本身路由作为参数,类型是Object类型:
{
"meta": {
},
"path": "/",
"hash": "",
"query": {
},
"params": {
},
"fullPath": "/",
"matched": [
{
"path": "",
"regex": {
"keys": []
},
"components": {
},
"instances": {
},
"enteredCbs": {
},
"meta": {
},
"props": {
}
}
]
}
别名
“重定向”的意思是,当用户访问 /a时,URL 将会被替换成 /b,然后匹配路由为 /b,那么“别名”又是什么呢?
/a
的别名是 /b,意味着,当用户访问 /b
时,URL 会保持为 /b
,但是路由匹配则为 /
a,即 /a = /b
:
const router = new VueRouter({
routes: [
{
path: '/a', component: A, alias: '/b' }
]
})
“别名”的功能让你可以自由地将 UI 结构映射到任意的 URL,而不是受限于配置的嵌套路由结构。