Vue —— 精讲 VueX (2)
五、mutation的提交风格
这个是commit的另一种写法,高档货
两种写法是有区别的,就是传递的参数不一样的表现
this.$sorte.commit('incrementCour',palyload)
拿到的是一个原模原样的palyload
this.$store.commit({
type:'incrementCour',
palyload:palyload
})
和这个时候你拿到的就是一个对象,
六,mutation响应规则
这里写的都是,有关Vue的数据管理,响应式系统的知识点,set方法非常的重要,更改数据,delete是不行的,vue.delete就可以了
这里的知识点,在vue中有很多地方都是这个东西,实际上,vue的响应式原理就是这样的
- 首先我们看看如果我修改state里的数据,会发生响应式吗?
我们的state有些情况下是响应式的,有些情况下不是的,什么情况下不是响应式呢?
这里我就直接说明了,
- 提前在store中初始化所需要的属性,这样才能响应,后添加的属性不会做到数据响应式
如何解决 数据无法深度检测的问题呢? set就能解决
1. 修改
Vue.set( originDate, modifyData ,newValue )
参数说明:originDate ----> 原数据
modifyData ----> 要更改的数据 Strng:key || number ,如果是修改对象就是 key 数组就是number下标
newVlaue ----> 新的值
2. 删除
Vue.delete(object,key)
- 以上就是我们的整个的vue的核心响应式原理,其它的部分与vueX里面的响应式原理是差不多类似的东西
七,mutation类型常量
这个东西,跟我们的angular里面的定义类型文件有点相像
核心思想就是定义类型常量
我们目前发现现在这样的一个问题,也就是我们的
- 先来看看我们的需求,
我们需求就是,把commit里的字符串提取出啦
我希望我这样用
additon() {
this.$store.commit(INCREMENT)
},
就能出发修改,而不需要
additon() {
this.$store.commit('increment')
},
- 那么我们改如何做呢?
- 第一步,找到我们的store的文件夹,定义一个类型文件mutation-types.js
export const INCREMENT = 'increment'
- 第二步,把store里的定义换了,注意啊要把这个类型文件先引入
import { INCREMENT } from './mutations-types'
// 安装
Vue.use(Vuex)
// 使用
const store = new Vuex.Store({
state: {
contuned: 1000,
students: [
{ id: 110, name: 'why', age: 18 },
{ id: 111, name: 'haha', age: 25 },
{ id: 112, name: 'laoli', age: 45 }
],
info: {
name: 'laoli',
age: 18,
number: 666
}
},
mutations: {
[INCREMENT](state) {
state.contuned++
},
- 第三步 在用的地方搞掉就好了
/app.vue
<template>
<div id="app">
<p>{{ $store.state.contuned }}</p>
<button @click="additon" >+</button>
<button @click="subraction" >-</button>
<h1>------bmlaoli的界面--------</h1>
<bmlao></bmlao>
<p>{{$store.state.info}}</p>
<button @click="uplateInfo">修改信息</button>
<h1>-------我是测试响应式的数据-------</h1>
<div>
<p>{{$store.state.info}}</p>
</div>
</div>
</template>
<script>
import bmlao from '@/components/Bmlaoli';
import { INCREMENT } from './store/mutations-types'
export default {
name: 'App',
components: {
bmlao,
},
data() {
return {
// contuned: 100
}
},
methods: {
additon() {
this.$store.commit(INCREMENT)
},
subraction() {
this.$store.commit('decrement')
},
uplateInfo(){
this.$store.commit('uplateInfo')
}
},
}
</script>
<style>
</style>
八,actions里面的异步操作
1. 简单的异步处理
目前,我们的需求是:我们的修改muatrion里面的存在着异步的操作,那么我如何解决呢?
解决方案就是使用action对mutaion替代
- 定义action
/store/index.js
actions: {
// context = store对象 上下文对象
aupdataeInfo(context) {
// 这样就是一个异步的操作了
setTimeout(() => {
context.commit('uplateInfo')
}, 1000)
}
},
- 触发action
/app.vue
this.$store.dispatch( 'aupdataeInfo')
2. 传递参数
实际上这个action和mutacion是差不多一样的写法 palyad负载
/store/index.js
// context = store对象 上下文对象
aupdataeInfo(context) {
// 这样就是一个异步的操作了
setTimeout(() => {
context.commit('uplateInfo', payload)
console.log(payload);//这就是你丢过来的参数
}, 1000)
}
APP.vue
this.$store.dispatch( 'aupdataeInfo','我是携带的讯息')
3. 通知(回调)
- 大对象的方式
我们传递的是这样的东西就可以了,在异步的里面进行回调就好了
app.vue
this.$store.dispatch( 'aupdataeInfo',{
message:{
name:'我是携带的讯息'
},
success:() => {
conslog.log('我是回调')
}
})
/stoe/
// context = store对象 上下文对象
aupdataeInfo(context) {
// 这样就是一个异步的操作了
setTimeout(() => {
context.commit('uplateInfo', payload)
console.log(payload.message);//这就是你丢过来的参数
payload.sucees()//我是回调
}, 1000)
}
问题,不够高端,B格不够
2. promise的方式
/store/index.js
aupdataeInfo(context,payload) {
// 这样就是一个异步的操作了
setTimeout(() => {
retrun new Promies( (resolve,rejcet)=>{
context.commit('uplateInfo')
consloe.log(payload)
// resolve()//回调出去就好了。如果有讯息就可以外卖拿
resolve('message is susecce')
} )
}, 1000)
}
*问题严重了,我们去哪儿点then呢?答案很简单,我们去被用到的地方*,这个设计就非常的好,谁用了,就在谁哪里调
app.vue
this.$store.dispatch()
.then( (res)=>{
console.log('回调完成了任务')
console.log(res)
} )
以上就是我们的action的相关讲解
九、mouldes分模块出去
简单的抽离
我们现在有这样的有这样的需求,我现在发现我们的store对象里面的state有点多,有没有办法把这个东西抽离出去呢?答案是有的,这就是我们的模块核心modules
- 抽离
这里我干的事情就是把我的林一个状态,以模块的形式抽离出去
/store/index.js
modules: {
// 假设我们这里有abc三个模块,注意 每一个模块实际上就是一个子的store对象
a:{
state:{},
getters:{},
mutations:{},
actions:{}
},
c:{
state:{},
getters:{},
mutations:{},
actions:{}
},
}
// 实际上我应该这样的抽离出去
// 模块
const moduleA = {
state: {
state:{
name:'厉害着'
}
},
mutations: {},
actions:{},
getters:{
}
}
++++
modules: {
a : moduleA,
b : moduleB
}
- 使用
使用起来也是相对的比较简单
/App.vue
<h1>------module的界面--------</h1>
<p>{{$store.state.a.name}}</p>
<!-- 注意啊 有点奇怪。确确实实你需啊哟state.a才能拿到模块 -->
mutation怎么搞?
如果我要在模块里面使用mutataion那么我该如何做呢?实际上也非常的简单
store/index.js
const moduleA = {
state: {
state:{
name:'厉害着'
}
},
mutations: {
// 注意啊,这里的名字不能喝下面的重复
upadtaeName(state,payload){
state.name = payload
}
},
actions:{},
getters:{
}
}
- 使用的时候也是一样
/App.vue
upadtae(){
this.$store.dispatch( 'upadtaeName','我是模块修改的内容')
}
getter如何搞?
getter也是一样的,和我们的平常的使用是一样的
/store/index.js
getters:{
fullName(state){
return state.name + '111'
},
// 如果我想要要自己毁掉呢?
fullName2(state,getters){
return getters.fullName + '222'// 这里的fullNamez这里的getter指代的就是这个模块的getter
},
//如果我想用下面的大的对象的 爸爸的数据呢?
fullName3(state,getters,rootState){
return getters.fullName + '222'// 这里的fullNamez这里的getter指代的就是这个模块的getter
// rootState 就是我们的大的store的state
},
}
使用
/App.vue
<P>{{ $store.getter.fullName }} </p>
action异步的操作是怎么样的?
异步操作也是非常的简单的 ,定义操作模式
/store/index.js
// 注意啊,这里的上下文和以前的是不一样的
actions:{
aupdateName( context ){
setTimeout(() => {
// 拿到这个操作对象 你就能干很多的东西了
console.log(context);
}, 1000);
}
},
基础的使用也是非常的简单的
asnycUpdateName(){
this.$store.dispatch('aupdateName')
}
十、文件抽离组织
十、文件抽离组织
高度解耦,来来来,我们看看管方给的定义
我们现在要做一件这样的事情,把我们的一些代码抽离到一些文件中去,这样我们就能非常的方便灵活的管理我们的vuex的一些状态了
├── index.html
├── main.js
├── api
│ └── ... # 抽取出API请求
├── components
│ ├── App.vue
│ └── ...
└── store
├── index.js # 我们组装模块并导出 store 的地方
├── actions.js # 根级别的 action
├── mutations.js # 根级别的 mutation
└── modules
├── cart.js # 购物车模块
└── products.js # 产品模块
我们现在就分别抽离出去就好了
--- 抽离出去之后我们的vuex的代码就简洁多得多了
/sotre/index.js
import Vue from 'vue'
import Vuex from 'vuex'
import mutations from './mutation'
import actions from './actions'
import getters from './getters'
// 模块
import moduleA from './modules/modules'
// 安装
Vue.use(Vuex)
// 使用
const store = new Vuex.Store({
state: {
contuned: 1000,
students: [
{ id: 110, name: 'why', age: 18 },
{ id: 111, name: 'haha', age: 25 },
{ id: 112, name: 'laoli', age: 45 }
],
info: {
name: 'laoli',
age: 18,
number: 666
}
},
mutations,
actions,
getters,
modules: {
a : moduleA,
}
})
// 倒出
export default store