前言
一、vue router 路由
1、基础使用方式
1) 在vue 下面引入 vue router
<script src="https://cdn.bootcss.com/vue-router/3.1.3/vue-router.js"></script>
2) 将之前的样式 style拷贝过来
3)将之前的组件模版 template 拷贝过来
4) 在 vue 实例化前面定义一下
const writeback = {
template: '#writeback'
}
const aite = {
template: '#aite'
}
const zan = {
template: '#zan'
}
- 主容器 #app 里面写一个结构的架子
<div id="app">
<div class="bili-content">
<div class="bili-leftnav">
<ul>
<li></li>
<li></li>
<li></li>
</ul>
</div>
<div class="bili-rightcontent">
</div>
</div>
</div>
- 在
vue 实例化中 进行router 实例化
// vue实例化
var vm = new Vue({
el: '#app',
data() {
return {}
},
// 实例化 router
router: new VueRouter({
// 地址配置
routes: [
{},
{},
{},
]
})
})
7)这里我们实例化vue的时候,属性里面的 router传入一个 VueRouter 的实例,这个数组routes就是详细的路径和对应的组件信息,比如我们浏览器访问 www.lookroot.cn/writeback的时… writeback组件
8)实例化部分 这样写
// vue实例化
var vm = new Vue({
el: '#app',
data() {
return {}
},
// 实例化 router
router: new VueRouter({
// 地址配置
routes: [{
path: '/writeback',
component: writeback,
},
{
path: '/aite',
component: aite
},
{
path: '/zan',
component: zan
},
]
})
})
9)在主容器 这样使用
<div id="app">
<div class="bili-content">
<div class="bili-leftnav">
<ul>
<li>
// 这个地方用到 router-link 的方式
<router-link to="/writeback">回复我的</router-link>
</li>
<li>
<router-link to='/aite'>@我的</router-link>
</li>
<li>
<router-link to='/zan'>赞我的</router-link>
</li>
</ul>
</div>
<div class="bili-rightcontent">
<router-view></router-view>
</div>
</div>
</div>
10) 这样大致展示了效果 原本的导航也要进行修改 这个 router-link就会在页面中渲染成a标签,作为导航
11)需要
区别一下 我当前选中的颜色 区别一下 加一个不同颜色就可
在 style 里面添加
/* 显示当前显示路由的颜色 */
li .router-link-active {
color: skyblue;
}
12) 加一点动画 将之前的动画效果拿过来
<div class="bili-rightcontent">
<transition enter-active-class="animated fadeInDown" leave-active-class="animated fadeInUp"
mode="out-in" :duration="200">
// 这个地方需要注意 是这个
<router-view></router-view>
</transition>
</div>
13)引入动画库 <link href="https://cdn.jsdelivr.net/npm/animate.css@3.5.1" rel="stylesheet" type="text/css">
14)基本的效果达到了 动画效果加上了
15)现在 有个小问题需要处理一下 我想 它初始状态就在writeback 界面怎么实现?
需要用到 router 重定向 加一点东西就可以
// router 重定向
{
// 因为网页打开初始状态后面就会加一个斜杠
path: '/',
// 跳转到那? 到 writeback 组件
redirect: '/writeback'
},
2、命名视图和命名路由
一点补充的内容 需要知道一下
1、 router 实例里面有个模式选择
// 实例化 router
router: new VueRouter({
// 模式选择
mode: 'history',
// 地址配置
routes: [],
好处是 地址拦地址变得简洁 http://127.0.0.1:5500/writeback
坏处是 复制地址到其他地方无法打开
默认是 mode:'hash'
就是这个长串的东西 http://127.0.0.1:5500/4%E3%80%81%20router/routerfirst.html#/writeback
2-1命名视图
为啥需要取名字 ?因为需要展示多个视图 也就是需要展示多个 router-view
1)
2)
<!-- vuefooter 组件模版 -->
<template id="vuefooter">
<div>
<h2>footer</h2>
</div>
</template>
3) vue实例化 之前 定义 这样不用注册
const vuefooter = {
template: '#vuefooter'
}
4) 在 router实例化的 routes: [ ] 里面更改一下 wirteback的内容
{
path: '/writeback',
// component: writeback,
// 因为这个地方需要展示两个 组件
components: {
// 这个展示的是默认没有名字的 router-view
default: writeback,
// 下面这个展示有名字 name='common'的组件
common: vuefooter
}
},
5) 展示效果
2-2 命名路由
1)我们给路由也起名字,这样方便使用,这里还是以 writeback为例
{
path: '/writeback',//点击的路径
// 命名视图
components: {
default: writeback,
common: vuefooter
},
// 命名路由
name: 'writeback',
},
2) 修改它的导航链接,这样就完成了
<router-link :to="{name:'writeback'}">回复我的</router-link>
3、嵌套路由 路由传参
2)
定义上图的 2 这部分 子组件
<!-- 这个是上图 2 部分 -->
<!-- 这是子组件 -->
<template id="mymsg">
<div>
<div>{{username}}的消息</div>
<ul>
<ol v-for="index in 10">
<!-- 这里的index 作为id 传递 -->
<router-link :to="'/mymsg/msgcontent/'+ index">用户{{index}}</router-link>
</ol>
</ul>
</div>
</template>
3)定义上图的 3 这部分 子组件的子组件
<!-- 这个是上图 3 部分 -->
<!-- 这是子组件的子组件 -->
<template id="msgcontent">
<div>
<!-- 路由传参 -->
这是和用户{{index}}具体的聊天界面
</div>
</template>
4)在vue 实例化前定义一下
const mymsg = {
template: '#mymsg'
}
const msgcontent = {
template: '#msgcontent'
}
- router 实例化的routes中 写出来
{
path:'/mymsg',
component:mymsg
}
6)页面使用一下 在上面的 <div class="bili-leftnav">增加一组li显示
<li>
<router-link to='/mymsg'>我的消息</router-link>
</li>
7)当前的关系和情况
8) 增加一点内容 mymsg
const mymsg = {
template: '#mymsg',
data() {
return {
username: ''
}
},
created() {
// 父组件将信息传递给子组件 username从哪里来
// 这是第一种传值方式 配合9)
this.username = this.$route.query.username;
}
}
9)如果我先在这个 li 里面写一个 fhj
<li>
<router-link to="/mymsg?username='fhj'">我的消息</router-link>
</li>
页面就会显示
10) 下一步需要做的事情是
点击用户1-10 后面的具体消息展示出来 也就是说 msgcontent 展示出来
11) 在下面的routes里面补充
{
path: '/mymsg',
component: mymsg,
// 嵌套在里面的路由
children: [
// 第二中路由传值 方式
{
path: 'msgcontent/:index',
component: msgcontent,
// 改成false 无法切换
props: true,
}
]
}
12) 需要在上面的 msgcontent 定义 index
const msgcontent = {
template: '#msgcontent',
// props 父组件向子组件传值
props: ['index']
}
4、路由的扩展部分 路由模式
1)定义两个组件模板
<template id="page1">
<div>
page1
</div>
</template>
<template id="page2">
<div>
page2
</div>
</template>
- 定义这两个组件
const page1 = {
template: '#page1',
}
const page2 = {
template: '#page2',
}
3)实例化一个router,
const router = new VueRouter({
mode: 'hash',
routes: [
{
// 重定向 到 page1
path: '/',
redirect: '/page1',
},
// page1 的名字是page1
{
path: '/page1',
component: page1,
name: 'page1',
},
// page2的名字是page2
{
path: '/page2',
component: page2,
name: 'page2',
},
],
});
- 接下来是
在#app 容器中使用它
这次不使用<router-link></router-link>我们使用 另外一种路由跳转的方式编程式的导航
<div id="app">
<button @click="gotoPage('./page1')"></button>
<button @click="gotoPage('./page2')"></button>
<router-view></router-view>
</div>
- vue 实例中
写到methods里面
methods: {
gotoPage(path) {
// 编程式的导航
this.$router.push(path)
}
},
- 暂且看一下实现的效果
点击page1 时 出现page1 点击page2时 出现 page2
5、路由守卫
1)守卫嘛,就是拦截放行的效果
首先我们在vue的原型指向上挂载一个属性,用来记录用户是否登录
// 初始定义为 false 表示未登录的状态
Vue.prototype.isLogn = false;
2)然后编写,第三个组件 login,并添加一个login点击事件
<template id="login">
<div>
<button @click="login">login</button>
</div>
</template>
3)然后定义这个组件,并编写点击事件,点击就修改isLogin的值为 true,并使用this.$router.back返回上一个页面
// 定义login
const login = {
tempalte: '#login',
methods: {
login() {
Vue.prototype.isLogin = true,
// 使用 下面这个返回
this.$router.back()
}
}
}
- 然后
配置路由信息
{
path: '/login',
component: login,
name: 'login'
},
- app 容器中使用
<div id="app">
<button @click="gotoPage('/page1')">page1</button>
<button @click="gotoPage('/page2')">page2</button>
<button @click="gotoPage('/login')">login</button>
<router-view></router-view>
</div>
- 实现效果
7)
router 实例化完成后 设置 全局守卫
// 设置守卫
router.beforeEach((to,from,next)=>{
})
- 设置 守卫
更新 一下 变成这样
// 设置守卫
// to 要去的页面
router.beforeEach((to, from, next) => {
// 目的为了去meta 里面到isLogin 看是不是true
if (to.matched.some(item => item.meta.isLogin)) {
if (!Vue.prototype.isLogin) {
next({
name: 'login'
})
} else {
next();
}
// 如果里面没有这个isLogin 直接跳转
} else {
next();
}
})
9) 实现的效果是 未登录 不能查看页面 点击login 之后才能看
看到这个 给自己点个赞 买个肥宅水快乐一下吧