创建定义
创建
在packge.json添加项目依赖 vue-router,再重启项目
{
...
"dependencies": {
"core-js": "^3.6.5",
"vue": "^3.0.0-0",
// 为了跟课程一直,使用了相同的版本号
"vue-router":"^4.0.0-0"
},
...
}
在 ./app目录下创建路由文件 app.router.ts
//app.router.ts
import { createRouter, createWebHistory, RouteRecordRaw } from 'vue-router';
/**
* 定义路由
*/
const routes: Array<RouteRecordRaw> = [
// 路由内容在这里
];
/**
* 创建路由
*/
const router = createRouter({
history: createWebHistory(),
routes,
});
export default router;
在 main.ts 根中使用 创建好的路由
// main.ts
import { createApp } from 'vue';
import App from './app/app.vue';
import appRouter from './app/app.router';
const app = createApp(App);
//应用路由
app.use(appRouter);
app.mount('#app');
定义
定义路由就是组件对应的地址,每一条路由记录是一个对象,放在路由数组中。
const routes: Array<RouteRecordRaw> = [
{
path: '/',
component: Index,
},
{
path: '/about',
component: About,
},
];
定义好路由以后,在app.vue 中用 <router-view> 定义路由显示区域
<template>
...
<div class="page-body">
<router-view></router-view>
</div>
</template>
路由名称
定义路由时,可以为路由起名,使用路由时,直接使用名称
const routes: Array<RouteRecordRaw> = [
...
{
path: '/about',
component: About,
name:'about'
},
];
当为路由使用了自定义名称时,:to="{name:'xxx'}" 需要绑定一个对象
路由模块
可以在不同的地方定义路由模块,再去到根路由中导入路由模块
//路由模块 post.route.ts
import { RouteRecordRaw } from 'vue-router';
import PostIndex from './index/post-index.vue';
const routes: Array<RouteRecordRaw> = [
{
path: '/post',
component: PostIndex,
},
...
];
export default routes;
// 根路由 app.routes.ts
...
import postRoutes from './post/post.route';
const routes: Array<RouteRecordRaw> = [
...
// ...postRoutes是展开操作符
...postRoutes,
];
...
export default router;
应用路由模块时,可直接使用路由地址或路由名称,无需考虑相对位置
嵌套路由
可以为路由创建子路由,子路由创建在路由的children属性中,children是一个路由数组,里面取相对位置
//路由模块 post.route.ts
import { RouteRecordRaw } from 'vue-router';
import PostShow from './show/post-show.vue';
import Meta from './components/meta.vue';
const routes: Array<RouteRecordRaw> = [
...
{
path: '/post/:postId',
name: 'postShow',
component: PostShow,
children: [
{
path: 'meta',
component: Meta,
},
],
},
];
export default routes;
定义好路由地址后,需要在路由组件中设置新的<router-view> 确定显示区域
//post-show.vue
<template>
<div>
this is post Show
{{ postId }}
</div>
<router-view></router-view>
</template>
访问的链接将会是: /post/:postId/meta ,Meta组件的内容显示在postShow组件里面
链接
router-link
通过点击页面上的元素进行路由跳转可以用 <router-link> 包装链接
<router-link> 中,具有 to="" 属性,需要填写要去的路由地址
当为路由使用了自定义名称时,:to="{name:'xxx'}" 需要绑定一个对象
<template>
<div class="pages">
...
<div class="menu">
<router-link class="menu-item" to="/">首页</router-link>
<router-link class="menu-item" :to="{ name: 'about' }"
>关于</router-link
>
<router-link class="menu-item" :to="{ name: 'postIndex' }"
>内容</router-link
>
</div>
</div>
</template>
用代码切换
除了在template中使用<router-link>,还可以直接在 script中用代码进行切换。
例如需要在一个点击事件中使用时:
<template>
<p>欢迎加入网站</p>
<p @click="onTapLink">我们是谁</p>
</template>
<script>
export default {
methods: {
onTapLink() {
// this.$router.push('/about');
this.$router.replace({ name: 'about' });
},
},
};
</script>
$router.push
会保存一条浏览器历史记录,可以用浏览器返回
$router.replace
不保存浏览器历史记录,无法用浏览器返回
重定向
可以使用重定向让用户访问指定位置。
重定向需要先决定重定向那个路由,所以他也是一条路由记录需要放在routes数组中。
const routes: Array<RouteRecordRaw> = [
{
path: '/about-us',
// redirect: '/about',
// redirect: { name: 'about' },
redirect(to) {
console.log(to);
return '/about';
},
},
...postRoutes,
];
有三种方式可以定义重定向到哪里去:
-
redirect: '/about'直接输入路由地址 -
redirect: { name: 'about' }使用路由名称 -
redirect(to) {... ;return '/about';}使用一个方法 ,-
to表示用户要访问的路由 -
需要返回一个路由
-
参数传递
动态路由
定义路由地址时,可以使用动态路由设置参数。
访问时 '/post/:postId' 中的 :postId 就是要传的参数
//路由模块 post.route.ts
import { RouteRecordRaw } from 'vue-router';
import PostShow from './show/post-show.vue';
const routes: Array<RouteRecordRaw> = [
{
path: '/post/:postId',
component: PostShow,
},
...
];
export default routes;
在访问对应链接时,可以在 <template> 和 <script> 上的 $route.params.postId 中找到参数的值
// post-show.vue
<template>
<div>
this is post Show
{{ $route.params.postId }}
</div>
</template>
<script>
export default {
created() {
console.log(this.$route.params.postId);
},
};
</script>
传递属性
除了使用$route.params.postId获取参数,还可以使用props直接获取参数。
如果是动态路由数据,需要在路由设置中打开props的属性
如果是静态数据,可以直接在props属性中定义
//路由模块 post.route.ts
import { RouteRecordRaw } from 'vue-router';
import PostShow from './show/post-show.vue';
const routes: Array<RouteRecordRaw> = [
{
path: '/post/:postId',
component: PostShow,
// 动态数据打开props选项
props: true,
},
{
path: '/post',
component: PostIndex,
// 定义静态数据直接使用
props: {
sute: 'cute',
},
},
];
export default routes;
在对应组件中,需要设置props属性,数据名称需要跟路由中定义的名称保持一致
//post-show.vue
// 动态路由数据
<template>
<div>
this is post Show
{{ postId }}
</div>
</template>
<script>
export default {
props: {
postId: String,
},
};
</script>
//post-index.vue
// 定义静态数据直接使用
<template>
<p>this is a post</p>
{{ sute }}
</template>
<script>
export default {
props: {
sute: String,
},
};
</script>
守卫判断
路由守卫
路由守卫可以为每一次访问进行拦截、处理、放行。使用router对象的beforeEach方法。beforeEach方法接受三个参数(to, from, next)
to:要去的路由from:来自那个路由next(): 后路由才会继续,否则会被拦截
//app.router.ts
import { createRouter, createWebHistory, RouteRecordRaw } from 'vue-router';
const routes: Array<RouteRecordRaw> = [
...
];
const router = createRouter({
...
});
router.beforeEach((to, from, next) => {
console.log('导航守卫开始工作');
//判断条件只包括当前路由,他的子路由仍然可以正常访问
if (to.name === 'postIndex') {
next('/');
} else {
next();
}
});
export default router;
路由元数据
可以为路由设置一些元数据,再根据元数据进行一些操作。
元数据可以在路由记录上使用 meta 的对象。
在守卫中使用 to.matched.some(record => record.meta.requiresAuth); 来判断是否存在对应meta值的路由。
//app.router.ts
import { createRouter, createWebHistory, RouteRecordRaw } from 'vue-router';
const routes: Array<RouteRecordRaw> = [
{
path: '/',
component: Index,
meta: {
requiresAuth: true,
},
},
...
];
const router = createRouter({
...
});
router.beforeEach((to, from, next) => {
const requiresAuth = to.matched.some(record => record.meta.requiresAuth);
if (requiresAuth) {
console.log('导航守卫开始工作');
}
next();
});
export default router;