Vuex起步

[TOC]

Vuex起步

每一个 Vuex 应用的核心就是 store(仓库)。
"store" 基本上就是一个容器,它包含着你的应用中大部分的状态(state)。
Vuex 和单纯的全局对象有以下两点不同:

  • Vuex 的状态存储是响应式的。
    当 Vue 组件从 store 中读取状态的时候,若 store 中的状态发生变化,那么相应的组件也会相应地得到高效更新。
  • 你不能直接改变 store 中的状态。
    改变 store 中的状态的唯一途径就是显式地提交(commit) mutations。
    这样使得我们可以方便地跟踪每一个状态的变化,从而让我们能够实现一些工具帮助我们更好地了解我们的应用。

最简单的 Store

假设一个微小的应用,有一个标签显示数字,两个按钮分别做数字的加一和减一的操作。用户界面看起来是这样的:

使用vue的话,就是这样:

<script src="https://unpkg.com/vue/dist/vue.js"></script>
		<div id="app">
		  <p>{{count}}
		    <button @click="inc">+</button>
		    <button @click="dec">-</button>
		  </p>
		</div>
		<script>
		new Vue({
		  el:"#app",
		  data () {
		    return {
		      count: 0
		    }
		  },
		  methods: {
		    inc () {
		      this.count++
		    },
		    dec () {
		      this.count--
		    }
		  }
		})
</script>

预览:

整个代码结构非常清晰,代码是代码,数据是数据。代码就是放在methods数组内的两个函数inc、dec,被指令@click关联到button上。而data内返回一个属性count,此属性通过{{count}}绑定到标签p内。

现在来看看,同样的demo app,使用vuex完成的代码的样子
安装 Vuex 之后,让我们来创建一个 store。创建过程直截了当——仅需要提供一个初始 state 对象和一些 mutations:

<script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://unpkg.com/vuex@2.0.0"></script>
		<div id="app">
		  <p>{{count}}
		    <button @click="inc">+</button>
		    <button @click="dec">-</button>
		  </p>
		</div>
        
  <script>
  // 如果在模块化构建系统中,请确保在开头调用了 Vue.use(Vuex)
		const store = new Vuex.Store({
		  state: {
		    count: 0
		  },
		  mutations: {
		    inc: state => state.count++,
		    dec: state => state.count--
		  }
		})
		
		const app = new Vue({
		  el: "#app",
		  computed: {
		    count () {
		        return store.state.count
		    }
		  },
		  methods: {
		    inc () {
		        store.commit("inc")
		    },
		    dec () {
		        store.commit("dec")
		    }
		  }
		})
</script>

预览:

我们先看到有哪些重要的变化:

  • 新的代码添加了对vuex脚本的依赖。这是当然的,因为你需要使用vuex的技术,当然需要引用它
  • methods数组还是这两个方法,这和demo1是一样的;但是方法内的计算逻辑,不再是在函数内进行,而是提交给store对象!这是一个新的对象!
  • count数据也不再是一个data函数返回的对象的属性;而是通过计算字段来返回,并且在计算字段内的代码也不是自己算的,而是转发给store对象。再一次store对象!

就是说,之前在vue实例内做的操作和数据的计算现在都不再自己做了,而是交由对象store来做了。

store对象是Vuex.Store的实例。
在store内有分为state对象和mutations对象,其中的state放置状态,mutations则是一个会引发状态改变的所有方法。
正如我们看到的,目前的state对象,其中的状态就只有一个count。
而mutations有两个成员,它们参数为state,在函数体内对state内的count成员做加1和减1的操作。

再次强调,我们通过提交 mutation 的方式,而非直接改变 store.state.count,是因为我们想要更明确地追踪到状态的变化。这个简单的约定能够让你的意图更加明显,这样你在阅读代码的时候能更容易地解读应用内部的状态改变。此外,这样也让我们有机会去实现一些能记录每次状态改变,保存状态快照的调试工具。有了它,我们甚至可以实现如时间穿梭般的调试体验。

由于 store 中的状态是响应式的,在组件中调用 store 中的状态简单到仅需要在计算属性中返回即可。触发变化也仅仅是在组件的 methods 中提交 mutations。

文章导航