路由守卫****
vue中路由守卫一共有三种,一个全局路由守卫,一个是组件内路由守卫,一个是router独享守卫
全局路由守卫
所谓全局路由守卫,就是小区大门,整个小区就这一个大门,你想要进入其中任何一个房子,都需要经过这个大门的检查
全局路由守卫有个两个:一个是全局前置守卫,一个是全局后置守卫
router.beforeEach((to, from, next) => {
console.log(to) => // 到哪个页面去?
console.log(from) => // 从哪个页面来?
next() => // 一个回调函数
}
后置
router.afterEach(to,from) = {}
next():回调函数参数配置
next(false): 中断当前的导航。如果浏览器的 URL 改变了 (可能是用户手动或者浏览器后退按钮),那么 URL 地址会重置到 from 路由对应的地址
next('/') 或者 next({ path: '/' }): 跳转到一个不同的地址。当前的导航被中断,然后进行一个新的导航。你可以向 next 传递任意位置对象,且允许设置诸如 replace: true、name: 'home' 之类的选项以及任何用在 router-link 的 to prop 或 router.push 中的选项
组件内的守卫****
beforeRouteEnter:在渲染该组件的对应路由被验证前调用
beforeRouteUpdate 在当前路由改变,但是该组件被复用时调用
beforeRouteLeave:在导航离开渲染该组件的对应路由时调用
路由独享的守卫****
1、beforeEnter:beforeEnter守卫 只在进入路由时触发,不会在 params、query 或 hash 改变时触发。例如,从 /users/2 进入到 /users/3 或者从 /users/2#info 进入到 /users/2#projects。它们只有在 从一个不同的 路由导航时,才会被触发。
Watch(监听器)****
什么是watch?
Watch就是我们的监听
为什么要学watch?
我们都知道vue是双向数据绑定的东西,数据改变页面也发生改变
但是如果说要在数据变化的时候我们要做一些操作该怎么办?
有同学说可以在methods里写方法啊
是没错可以,但是我们是不是要获取数据然后再判断是不是变化了是吧?
麻烦吧。
Watch就解决了这个问题
那么该怎样去用?
1. 普通数据类型
监听 当userName值发生变化时触发
方法1,
watch: {
userName (newName, oldName) {
console.log(newName)
}
}
方法2,
watch: {
userName: {
handler(newName, oldName) {
console.log(newName);
},
immediate: true,
},
},
缺点:
只有一个缺点 就是当值第一次绑定的时候 不会执行监听函数,只有当值改变的时候 才会执行
如果我们想在第一次绑定的时候执行此监听函数 则需要 设置 ** immediate为true**
** 2. 对象类型:**
当需要监听对象的改变时,此时就需要设置deep为true
第三种
data (){
return {
cityName: {name:'北京'}
}
},
watch: {
cityName: {
handler(newName, oldName) {
console.log(newName)
},
immediate: true,
deep: true
}
}
注意点:如果对象的属性较多,可以之监听某一个属性 'cityName.name':
** 3. 数组类型:**
数组的变化不需要深度监听
注意点:
在watch中不要使用箭头函数,因为箭头函数中的this是指向当前作用域
上面说到计算属性的时候 初始化的时候就可以被监听到并且计算 但是watch是发生改变的时候才会触发。
当你有一些数据需要随着其它数据变动而变动时,或者当需要在数据变化时执行异步或开销较大的操作时,你可以使用 watch。
侦听属性是侦听的值改变会重新执行函数,将一个值重新赋值作为最新结果,所以赋值的时候可以进行一些异步操作。
Computed (计算属性)
computed:计算属性是依赖的值改变会重新执行函数,计算属性是取返回值作为最新结果,所以里面不能异步的返回结果。不能写异步逻辑********
computed: {
getadd() {
var value=new Date()
return value.getFullYear()+'-'+value.getMonth()+'-'+value.getDate();
},
},
区别: 1.变量不在 data中定义,而是定义在computed中,写法跟写方法一样,有返回值,函数名直接在页面模板中渲染,不加小括号 。
2.根据传入的变量的变化 进行结果的更新。
3.计算属性基于响应式依赖进行缓存。如其中的任意一个值未发生变化,它调用的就是上一次 计算缓存的数据,因此提高了程序的性能。而methods中每调用一次就会重新计算 一次,为了进行不必要的资源消耗,选择用计算属性
********
Vuex(仓库)
vuex是使用vue中必不可少的一部分,基于父子、兄弟组件,我们传值可能会很方便,但是如果是没有关联的组件之间要使用同一组数据,就显得很无能为力,那么vuex就很好的解决了我们这种问题,它相当于一个公共仓库,保存着所有组件都能共用的数据。
一、Vuex的五个核心概念:state、getters、mutations、actions、modules
1、state: vuex的基本数据,用来存储变量;(数据存储)
2、getters: 从基本数据(state)派生的数据,相当于state的计算属性;
3、mutations: 提交更新数据的方法,必须是同步的(如果需要异步使用action)。每个mution 都有一个字符串的事件类型(type)和一个回调函数(handler)。
回调函数就是我们实际进行状态更改的地方,并且它会接受 state作为第一个参数,提交载荷作为第二个参数。(更改state中状态的逻辑 同步操作)
4、action: 和mutations的功能大致相同,不同之处在于 ①action提交的是mution,而不是直接变更状态,②action可以包含任意异步操作。(提交mutation 异步操作)
5、modules: 模块化vuex,可以让每一个模块拥有自己的 state、mutation、action、 getters,使得结构非常清晰,方便管理。( 模块化)
例子、
1、state使用
state:{
a:'true',
b:2,
c:false,
d:null
},
页面中使用:this.$store.state.a
3、 getter:从基本数据(state)派生的数据,相当于state的计算属性,具有返回值的方法
getter: {
b: function(state){
return state.b * 2
}
}
在页面使用
this.$store.getters.a
或
import { mapGetters } from 'vuex';
computed: {
...mapGetters(['a'])
}
页面使用 this.a
4.mutation:提交更新数据的方法,必须是同步的(如果需要异步使用action)。每个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler)。
mutations: {
a: (state, userId) => {
state.userId = userId
},
b: (state, token) => {
// console.log(token)
state.token = token
}
},
页面中使用 commit:同步操作,写法: this.$store.commit(‘mutations方法名’,值)
<button @click="$store.commit(mutation方法名,'李四')">调用
回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数,提交载荷作为第二个参数。
action:和mutation的功能大致相同,不同之处在于****
1) Action 提交的是 mutation,而不是直接变更状态。****
2) Action 可以包含任意异步操作。****
3)
actions: { // {} 是es6中解构,把对象解构成属性
a({ commit }, value) {
commit('SET_USER', value)
},
}
dispatch:异步操作,写法: this.$store.dispatch(‘actions方法名’,值)
<button @click="$store.dispatch('actions方法名','李四')">调用
modules使用 分模块可以建新页面例如print
/**
* 存放 ** 数据
* **/
// initial state
const state = {
all: {
ID:'',
BrandID:''
}
}
// getters
const getters = {}
// actions
const actions = {}
// mutations
const mutations = {
setPrint(state, all) { //设置参数
state.all = all;
}
}
export default {
//namespaced: true 的方式使其成为带命名空间的模块。保证在变量名一样的时候,添加一个父级名拼接。
namespaced: true,
state,
getters,
actions,
mutations
}
Index.Js需要引入
import print from './print';
modules: {
}
页面上引用
this.$store.commit("print/setPrint", {
//print 表示vuex的文件名
ID: "001",
BrandID: 402,