Vuex是什么 && 核心概念之State

47 阅读2分钟

Vuex 是什么?

Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式 + 库。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。

store 是个大容器,包含所有核心概念

核心概念之state

Vuex 使用单一状态树——是的,用一个对象就包含了全部的应用层级状态。state可以用来读取状态

在组件中如何获取Vuex的状态呢?
由于 Vuex 的状态存储是响应式的,从 store 实例中读取状态最简单的方法就是在计算属性中返回某个状态:

// 通常都会建立一个store的文件夹
// store/index.js
import Vue from 'vue'
import Vuex from 'vuex'
// 使用Vuex插件
Vue.use(Vuex)
// state,用于存储数据
const state = {
  count: 0,
}
// 创建store并暴露store
export const store = new Vuex.Store({
  state: state
})

// Count组件
<template>
  <div>{{count}}<div>
</template>

<script>
import {store} from '../store'
export default {
  name: 'Count',
  computed: {
    count(){
      return store.state.count
    }
  }
}
</script>

每当 store.state.count 变化的时候, 都会重新求取计算属性,并且触发更新相关联的 DOM。 然而这种模式是导致组件依赖全局状态的单例

Vuex还可以通过Vue的插件系统将store实例从组件中“注入”到所有的子组件里。并且子组件可以通过this.$store访问到,接下来我们继续改造一下Count组件

// store/index.js
import Vue from 'vue'
import Vuex from 'vuex'
// 使用Vuex插件
Vue.use(Vuex)
// state,用于存储数据
const state = {
  count: 0,
}
// 创建store并暴露store
export const store = new Vuex.Store({
  state: state
})

// main.js 中引入Vuex并且进行注入
//引入Vue
import Vue from 'vue'
//引入App
import App from './App.vue'
// 引入store
import store from './store'
//关闭Vue的生产提示
Vue.config.productionTip = false

//创建vm
new Vue({
  el:'#app',
  render: h => h(App),
  store: store,
})

// Count组件
<template>
  <div>{{count}}<div>
</template>

<script>
export default {
  name: 'Count',
  computed: {
    count(){
      return this.$store.state.count
    }
  }
}

state还带有一个 mapState的辅助函数

当一个组件需要获取多个状态的时候,将这些状态都声明为计算属性会有些重复和冗余。为了解决这个问题,我们可以使用 mapState 辅助函数帮助我们生成计算属性,让你少按几次键

// Count.vue
<div>{{count}}</div>

import { mapState } from 'vuex'
export default {
  computed: mapState({
    // 箭头函数可使代码更简练
    count: state => state.count,

    // 传字符串参数 'count' 等同于 `state => state.count`
    countAlias: 'count',
  })
}

当映射的计算属性的名称与 state 的子节点名称相同时,我们也可以给 mapState 传一个字符串数组。

computed: mapState([
  // 映射 this.count 为 store.state.count
  'count'
])

对象展开运算符

mapState 函数返回的是一个对象。我们如何将它与局部计算属性混合使用呢?

computed: {
  ...mapState(['count'])   // 映射成 this.$store.state.count
}