vuex使用详解

Vuex的作用

  1. 组件通信(兄弟组件)

  2. 跨页面通信

Vuex使用

创建vuex实例

vuex项目初始化后,src目录会多一个store/index.js,里面会进行vuex的初始化

import Vue from 'vue'
import Vuex from 'vuex';

Vue.use(Vuex)

export default new Vuex.store({
 
 // 所有状态
 state: {
  count: 0
},
 
 
 // 计算属性
 getters: {
         filterCount(state) {
            return state.count + 10;
        }
},
 
 
 // 修改state
 mutations: {
         add (state, payload) { // payload是接收的参数
           // 只能使用同步操作
           state.count += payload;

           // 不能使用异步操作
           // setTimeout(()=>{
           //   state.count += payload;
           // }, 10000)
        },
         updateCount(state, payload){
            state.count = payload
        }
},
 
 
 // 异步操作
 actions: {
         getCount({commit}, payload){
           console.log(payload); // 接收dispatch传来的参数

           setTimeout(() => {
             const count = Math.ceil(Math.random()*10);

             // 修改state数据还是得触发mutations
             commit('updateCount', count)
          }, 3000)
        }
}
})

在main.js中导入store

import store from '@/store/index.js';

new Vue({
 store
})

访问state中的数据

// store/index.js
state: {
   count: 0
},
// xxxx.vue
created(){
 console.log(this.$store) // 就是store实例对象
 console.log(this.$store.state.count) // 访问state中的count
}

修改state中的数据 - mutations

通过commit触发mutations中的方法

// xxxx.vue
methods: {
 handle(){
   
   // this.$store.state.count++; //这句话也能实现,但是不推荐这样使用
   
   // 通过commit触发mutations中的方法修改state
   this.$store.commit('add', 2)
}
}
// store/index.js
mutations: {
   add (state, payload) { // payload是接收的参数
     // 只能使用同步操作
     state.count += payload;
     
     // 不能使用异步操作
     // setTimeout(()=>{
     //   state.count += payload;
     // }, 10000)
  },
},

 

mutations使用注意

  • 不能直接修改state的数据:

    this.$store.state.count++; // 不能这样使用
  • 必须使用mutations修改state中的数据:

    • 通过mutations修改state的数据可以监测到state数据的变化

  • mutations中不能写异步方法修改state:

    • 为了防止state中的数据混乱(不可以监测到state数据的变化)

异步操作state中的数据 - actions

通过dispatch触发actions中的方法

// xxxx.vue
created(){
 this.$store.dispatch('getCount', 123)
}
// store/index.js
 actions: {
   getCount({commit}, payload){
     console.log(payload); // 接收dispatch传来的参数
     
     setTimeout(() => {
       const count = Math.ceil(Math.random()*10);
       
       // 修改state数据还是得触发mutations
       commit('updateCount', count)
    }, 3000)
  }
}

注意:在actions中要修改state还是要触发mutations中的方法进行修改

getters计算属性

// store/index.js
getters: {
   filterCount(state) {
      return state.count + 10;
  }
},

访问计算属性

// xxxx.vue
created(){
 console.log(this.$store.getters.filterCount) // 访问getters中的count
}

上午总结

new Vuex.store({
 // 存储的是所有的状态
 state: {
   count: 0
},
 // 计算属性
 getters: {
   filterCount(state) {
     return state.count + 10
  }
},
 // 所有的修改state的方法
 mutations: {
   add(state, payload) {
     // payload是commit传过来的第二个参数
     state.count++;
  },
   updateCount(state, payload) {
     // payload是commit传过来的第二个参数
     state.count = payload;
  }
},
 // 异步操作的方法
 actions: {
   getCount(context, payload) {
     // payload是dispatch传过来的第二个参数
     const count = ajax('xxx');
     
     // 在actions中要修改state,还是要调用mutations中的方法
     context.commit('updateCount', count)
  }
}
})
// xxx.vue

// 访问state
this.$store.state.count // 0
// 触发mutations中的方法
this.$store.commit('add', 2)
// 访问计算属性
this.$store.getters.filterCount // 10
// 调用actions方法
this.$store.dispatch('getCount', "abcd")

操作vuex的第二种方法

mapState, mapMutations, mapGetters, mapActions

作用:在.vue组件中直接获取vuex的状态和方法

  • 通过this.xxx获取state和getters

  • 通过this.xxx()调用mutations和actions

注意

  1. mapState和mapGetters用法一样

  2. mapMutations和mapActions用法一样

今日总结

1. state中存放什么数据?

// 存放所有的状态
state: {
 a: 1,
 b:2
}

2. 读取state中的数据

<div>{{{$store.state.a}}</div>

3. 修改state中的数据 - mutations

<button @click="add">+1</button>
methods: {
 add(){
   this.$store.commit('add', 2)
}
}
// store
mutations: {
 add(state, payload) {
   // payload是commit传的第二个参数
   state.a++;
}
}

4. this.$store.state.a++?

可以达到效果,但是不建议使用,这种方法不能监听到state的变化。

推荐还是使用mutations修改state

5. mutations的方法中可以进行异步操作吗?

不可以。mutations异步操作不能监听state的变化,会导致数据的混乱。

所以说mutations只能进行同步操作。

6. getters计算属性

getters: {
 c(state, getters){
   return state.a + state.b
}
}

7. 读取getters计算属性?

 // 跟读取state格式一样 
{{$store.getters.c}}

8. 在vuex中如何进行异步操作?

mutations: {
 updateA(state, payload) {
   state.a = payload
}
},
actions: {
 getList(context, payload) {
   setTimeout(() => {
     // 在actios中修改state的数据,还是要触发mutations
     context.commit('updateA', 2)
  }, 3000)
}
}

9. 如何调用actions中的方法

// xxx.vue
created(){
 this.$store.dispatch('getList', 123)
}

注意

  • dispatch是触发actions的

  • commit是触发mutations的

操作vuex的第二种方法

第一种方法

// xxx.vue

// 访问state
this.$store.state.count // 0
// 触发mutations中的方法
this.$store.commit('add', 2)
// 访问计算属性
this.$store.getters.filterCount // 10
// 调用actions方法
this.$store.dispatch('getCount', "abcd")

第二种方法

mapState,mapMutations,mapGetters,mapActions

// xxx.vue中
import {mapState,mapMutations,mapGetters,mapActions} from 'vuex';

// 改写this.$store.state.count
computed: {
 ...mapState(['count']) // 相当于当前组件中有个count计算属性,可以通过this.count访问
}

// 改写this.$store.getters.filterCount
computed: {
 ...mapGetters(['filterCount']) // 相当于当前组件中有个filterCount计算属性,可以通过this.filterCount访问
}

// 改写this.$store.commit('add', 2)
methods: {
 ...mapMutations(['add']) // 就可以这样调用了:this.add(2)
}

// 改写this.$store.dispatch('getCount', "abcd")
methods: {
 ...mapActions(['getCount']) // 就可以这样调用了:this.getCount("abcd")
}

mapState和mapGetters用法一致,都是放在computed里面

mapMutations和mapActions用法一致,都是放在methods里面

 

 

如果使用模块化modules,使用方法为:

vuex使用详解

"m_cart ''为注册在vuex实例中的模块名

 

 

注:本文为转载,非本人所写

上一篇:Vue-actions 跨域


下一篇:Vuex核心概念-04-Mutation传参两种方式