Vue2.0 Vuex集中式储存管理

引用官网的话:Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态

这里是它的官方文档:https://vuex.vuejs.org/zh-cn/

我们可以很直观的看到有五个方法:

  • State 可以简单的理解为组件的data,不过state是全局唯一的。
  • Getters 可以在模板中静态的显示数据。换句话说,getters 可以读取数据,但不能改变状态。
  • Mutations 允许更新状态,但永远是同步的。Mutations 是 store 中改变状态数据的唯一方式。
  • Actions 允许异步更新状态,但是需要使用一个已经存在的 mutation 。如果你需要以特定的顺序同时执行不同的 mutations 会非常有用。
  • Modules Vuex 允许我们将 store 分割到模块(module)。每个模块拥有自己的 state、mutation、action、getters、甚至是嵌套子模块——从上至下进行类似的分割

一、简单demo

搭建一个vue-cli,新建一个store.js

在main.js种先引入vuex

// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
import Vue from 'vue'
import App from './App'
import router from './router'

import {store} from './vuex/store'

Vue.config.productionTip = false

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  // 注意这里要注入到vue实例
  store,
  template: '<App/>',
  components: { App }
})

在store.js种引用vuex

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

Vue.use(Vuex);

export const store = new Vuex.Store({
    state: {
        counter: 8,
        weather: 'rainy',
        time: '20:40'
    },
    // 展示内容,无法改变状态
    getters: {
        counter: state => {
            return state.counter 
        },
        weather: state => {
            return state.weather
        },
        time: state => {
            return state.time
        }
    },
    //mutations 永远是同步的
    mutations: {
        // 显示传递的载荷 payload, 用 num 表示
        increment: (state, num) => {
            state.counter += num;
        },
        decrement: (state, num) => {
            state.counter = state.counter - num;
        }
    },
    // actions 可异步
    actions: {
        acDecremen:({commit}, asyncNum) => {
            setTimeout(() => {
                 // asyncNum 对象可以是静态值
                 commit('decrement', asyncNum.num);
                }, 1000);
        }
    },
});

在app.vue种拿到数据

<template>
  <div id="app">
    {{counter}} || {{weather}} || {{time}}
    <button @click='add'> +1 </button>
    <button @click='increment'> -1 </button>
  </div>
</template>

<script>
  export default {
    computed: {
      counter() {
        return this.$store.getters.counter
      },
      weather() {
        return this.$store.getters.weather
      },
      time() {
        return this.$store.getters.time
      }
    },
    methods: {
      add(){
        this.$store.commit('increment',1)
      },
      increment(){
        this.$store.dispatch('acDecremen',{num:1})
      }
    }
  }
</script>

<style>
  #app {
    font-family: 'Avenir', Helvetica, Arial, sans-serif;
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
    text-align: center;
    color: #2c3e50;
    margin-top: 60px;
  }
</style>

运行:一个按钮立即加一(mutations),一个一秒后减一(actions)

二、利用vuex实现子组件间的通讯

我们先注册几个子组件

/*App.vue*/

import music from './components/music'
import movie from './components/movie'
new Vue({
     //..........
    components:{
      music,
      movie
    }
})

/*music.vue*/

<template>
    <div class = 'music'>
        I'm music,my counter is {{counter}}
    </div>
</template>
<script>
    export default{
        computed:{
            counter() {
                return this.$store.getters.counter
            },
        }
    };
</script>
<style>
</style>

/*movie.vue*/

<template>
    <div class = 'movie'>
        I'm movie,my counter is {{counter}}
    </div>
</template>
<script>
    export default{
        computed:{
            counter() {
                return this.$store.getters.counter
            },
        }
    };
</script>
<style>
</style>

然后在app.vue种直接使用模板,就可以同步更新数据了

三、Module

感觉这个功能有点像命名空间的功能,其中的getters,mutations,actions现在仍然注册在全局命名空间——这样保证了多个模块能够响应同一 mutation 或 action。

即 getters,mutations,actions的名字不可以重复

修改store.js

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

Vue.use(Vuex);

const moduleA = {
    state: {
        name: 'moduleA'
    },
    getters: {
        aname: state => state.name
    },
    mutations: {
        setBName: state => state.name = 'new modulesA'
    },
    actions: {
        acSetAName: state => state.name = 'ac moudleA'
    }
}
const moduleB = {
    state: {
        name: 'moduleB'
    },
    getters: {
        bname: state => state.name
    },
    mutations: {
        setBName: state => state.name = 'new modulesB'
    },
    actions: {
        acSetBName: state => state.name = 'ac moudleB'
    }
}

export const store = new Vuex.Store({
    modules: {
        a: moduleA,
        b: moduleB
    }
})

想拿到moduleA的name的值可以不用getters,直接

this.$store.state.a.name

其他方法的调用都一样,因为都是不同的方法名

原文地址:https://www.cnblogs.com/lastnigtic/p/6799236.html