官方文档说道:Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的全部组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化javascript
当咱们的应用遇到多个组件共享状态时,单向数据流的简洁性很容易被破坏,这时候咱们就须要一个全局的状态管理来让咱们的代码结构化html
const store = new Vuex.Store({ state: { count: 0 }, mutations: { increment (state) { state.count++ } } })
store.commit('increment') console.log(store.state.count) // -> 1
因为 store 中的状态是响应式的,在组件中调用 store 中的状态简单到仅须要在计算属性中返回便可。触发变化也仅仅是在组件的 methods 中提交 mutation。vue
// 建立一个 Counter 组件 const Counter = { template: `<div>{{ count }}</div>`, computed: { count () { return store.state.count //this.$store.state.count } } }}
从 store 实例中读取状态最简单的方法就是在计算属性中返回某个状态java
咱们仍可使用mapState函数帮咱们生成计算属性 mapState
函数返回的是一个对象vuex
import { mapState } from 'vuex' export default { // ... computed: mapState({ // 箭头函数可以使代码更简练 count: state => state.count, // 传字符串参数 'count' 等同于 `state => state.count` countAlias: 'count', // 为了可以使用 `this` 获取局部状态,必须使用常规函数 countPlusLocalState (state) { return state.count + this.localCount } }) }
import Vue from 'vue' import Vuex from 'vuex' Vue.use(Vuex) let state = { count: 0 } let getters = { total: state => { return '$' + state.count; } } let mutations = { increment(_state, n){ _state.count += n || 1; }, decrement(){ state.count -= 1; } } const store = new Vuex.Store({ state, getters, mutations }) export default store
<h3>count-{{$store.getters.total}}</h3>
若是上面的方法想改变货币符号,那就要经过传参方式来解决异步
let getters = { total: (state) => (symbol) => { return (symbol || '$') + state.count; } } <h3>count-{{$store.getters.total('¥')}}</h3>
<template> <div> <h3>count-{{total('¥')}}</h3> </div> </template> <script> import common from '../../common/common.js' import {mapState, mapMutations, mapGetters} from 'vuex'; export default { computed: { ...mapGetters([ 'total' ]) } } </script>
<template> <div> <h3>count-{{amount('¥')}}</h3> </div> </template> <script> import common from '../../common/common.js' import {mapState, mapMutations, mapGetters} from 'vuex'; export default { computed: { ...mapGetters({ amount: 'total' }) } } </script>
更改 Vuex 的 store 中的状态的惟一方法是提交 mutation。Vuex 中的 mutation 很是相似于事件,每一个 mutation 的方法都会有一个 state 的参数在 commit 的时候当回调形参传过来,该形参就是 store.stateide
let mutations = { increment(_state){ _state.count += 1; }, }
能够向 store.commit 传入额外的参数,即 mutation 的 载荷(payload):函数
let mutations = { increment(_state){ _state.count += 1; }, } this.$store.commit('increment', 10);
大多数状况下要传多个参数,可是 mutation 的方法最多只有两个参数,一个是 state,另外一个是 payload,因此参数能够用对象的方式去传。ui
<input type="button" value="increment" @click="increment(10)"/> <script type="text/javascript"> import {mapMutations} from 'vuex'; methods: mapMutations(['increment']) </script>
<input type="button" value="increment" @click="add(10)"/> <script type="text/javascript"> import {mapMutations} from 'vuex'; methods: mapMutations({ add: 'increment' }) </script>
<input type="button" value="increment" @click="increment(10)"/> <script type="text/javascript"> import {mapMutations} from 'vuex'; methods: { ...mapMutations(['increment']), } </script>
<input type="button" value="increment" @click="add(10)"/> <script type="text/javascript"> import {mapMutations} from 'vuex'; methods: { ...mapMutations({ add: 'increment' }), } </script>
先引用官方文档的说法this
Action 相似于 mutation,不一样在于:
实现上是没问题,action 调用 mutation,但关于异步要放到 action 的说法,我的观点是没有这个必要,在 mutation 的小结中有说到过,mutation 只作同步也不是制性的
在使用 Action 前先与 Mutation 作个小结
在 action
import Vue from 'vue' import Vuex from 'vuex' Vue.use(Vuex) let state = { count: 0 } let getters = { total: (state) => (symbol) => { return (symbol || '$') + state.count; } } let mutations = { increment(_state, n){ console.log(arguments) _state.count += n || 1; }, decrement(){ state.count -= 1; } } let actions = { increment(context, n){ context.commit('increment', n) } } const store = new Vuex.Store({ state, getters, mutations, actions }) export default store
<input type="button" value="increment" @click="$store.dispatch('increment', 5)"/>
和 mutation 的使用方法基本同样
methods: { ...mapActions(['increment']), ...mapActions({add: 'increment'}) }
const moduleA = { state: { ... }, mutations: { ... }, actions: { ... }, getters: { ... } } const moduleB = { state: { ... }, mutations: { ... }, actions: { ... } } const store = new Vuex.Store({ modules: { a: moduleA, b: moduleB } }) store.state.a // -> moduleA 的状态 store.state.b // -> moduleB 的状态