zyz
Vuex状态管理
04/06
一、什么是Vuex
Vuex 是一个专为 Vue.js 应用程序开发的状态管理模式。它采用集中式存储管理应用的所有组件的状态,并以相应的规则保证状态以一种可预测的方式发生变化。
二、为什么要使用Vuex
1.场景一:对于页面中,多层级嵌套组件是非常常见的,例如A组件嵌套B组件,B组件嵌套C组件,想要从C组件传递参数到A组件怎么办?
1、C组件先通过自定义事件方式,将数据传到B组件【子组件传递参数到父组件】
2、接着在B组件中通过自定义事件方式,将数据传递到A组件【子组件传递参数到父组件】
2.场景二:兄弟组件中,例如A组件中,包含了B组件和C组件。此时需要的是B组件和C组件需要相互传递参数,怎么办?
1、A组件作为中转站一样
2、B组件先将参数传递给A组件【子组件传递参数到父组件】,A组件再将参数传递给C组件【父组件传递参数到组件】
3、C组件先将参数传递给A组件【子组件传递参数到父组件】,A组件再讲参数传递给B组件【父组件传递参数到组件】
3.说明:上面列举的场景都是非常常见的,实际操作组件甚至更多的时,代码会变的非常脆弱,通常会导致无法维护的代码。因此,我们为什么不把组件的共享状态抽取出来,以一个全局单例模式管理呢?在这种模式下,我们的组件树构成了一个巨大的“视图”,不管在树的哪个位置,任何组件都能获取状态或者触发行为!这个就是我们的Vuex
状态管理。
三、什么情况下应该使用 Vuex
Vuex 是专门为 Vue.js 设计的状态管理库,以利用 Vue.js 的细粒度数据响应机制来进行高效的状态更新。Vuex可以帮助我们管理共享状态,但也带了更多的概念和框架,这需要对短期和长期效益进行权衡。
- 简单页面开发
如果您不打算开发大型单页应用,使用 Vuex 可能是繁琐冗余的。如果应用够简单,建议最好不要使用 Vuex。这提供了有 [store 模式]。 - 中大型项目
如果需要构建一个中大型单页应用,很可能就会考虑如何更好地在组件外部管理状态,Vuex将会成为自然而然的选择。
四、Vuex基本概念
- store仓库
每一个Vuex
应用的核心就是 store(仓库)。store
基本上就是一个容器,它包含着应用中大部分的状态state
【不管什么数据,都可以看作为一个状态】。
- Vuex 的状态存储是响应式的
当Vue
组件从store
中读取状态的时候,若store
中的状态发生变化,那么相应的组件也会相应地得到高效更新。
- commit提交
当改变store
中的状态,是不被允许的。改变 store 中的状态的唯一途径就是显式地提交 (commit) ,这样是Vuex
为了更方便地跟踪每一个状态的变化。
五、本项目中的场景
在GoodsItemView
是商品的显示组件,这里包含有商品ID
以及点击事件的绑定。
在商品点击后,需要将商品详情显示状态
传递到 HomeView
组件中。
六、Vuex使用
安装
npm install vuex --save
配置
# main.js中 // 导入Vuex import Vuex from 'vuex' Vue.use(Vuex) // 定义状态管理器 var store = new Vuex.Store({ state:{ // 定义状态 goodsDetailShow: false, // 控制商品详情的显示隐藏状态 }, mutations:{ // 定义方法 changeGoodsDetailShow(state){ // 触发方法用于改变状态 state.goodsDetailShow = !state.goodsDetailShow }, } }) new Vue({ ... store // 状态管理器 }).$mount('#app')
HomeView组件
<template> ... <!-- 商品详情 --> <GoodsDetailView v-if='goodsDetailShow'></GoodsDetailView> </template> <script> export default{ ... computed:{ // 添加计算属性 goodsDetailShow(){ // 获取对应的状态 return this.$store.state.goodsDetailShow } }, } </script>
GoodsItemView组件 【触发事件,显示商品详情】
<script> export default{ ... methods:{ goodsItemClick: function(){ / 改变goodsDetailShow状态 this.$store.commit('changeGoodsDetailShow') } } } </script>
GoodsDetailView组件 【触发事件,隐藏商品详情】
<script> export default { ... methods: { onBack: function() { // 改变goodsDetailShow状态 this.$store.commit('changeGoodsDetailShow') } }, } </script>