Vuex-基础使用

本文详细介绍了Vuex的状态管理模式,包括如何安装、使用state、mutations、actions和getters。Vuex帮助解决Vue组件间的复杂数据传递问题,通过commit同步更新state,dispatch异步操作,以及getters的计算属性功能,实现高效的数据管理和通信。同时强调了mutations中必须使用同步操作,而actions可用于处理异步任务。
摘要由CSDN通过智能技术生成

        Vuex,一个专为 Vue.js 应用程序开发的状态管理模式,用来处理在 vue 各个组件之间传值的痛苦。比如:在父子、兄弟组件,传值可能会很方便,但是如果是没有关联的组件之间要使用同一组数据,就显得及其蛋疼。而 vuex 就很好的解决了这种问题。

目录

安装好后,会在目录下生成一个store文件夹

Mutation 更改state状态的唯一方法

1.声明mutations方法

2.在页面中通过commit来调用mutations方法 

3.mapMutations 辅助函数

第一步:在要使用mutations里的方法的页面引入 mapMutations

第二步:在页面中通过【this.方法名】来调用Mutations里的方法

注意点:

Action 异步操作Mutations方法

1.定义好actions对象中的方法

2.页面中通过dispatch调用action方法

3.mapActions 辅助函数 

第一步:在要使用Actions里的方法的页面引入 mapActions 

第二步:在页面中通过【this.方法名】来调用Actions里的方法

 注意:

Getter 类似于计算属性

同样,getters也有自己的辅助函数mapGetters 辅助函数


        关于如何安装vuex,这里不做赘述,请参考官方文档

State | Vuex (vuejs.org)https://vuex.vuejs.org/zh/guide/state.html

安装好后,会在目录下生成一个store文件夹

index.js文件中的内容,就是基础的引用内容

import Vue from 'vue'
import Vuex from 'vuex'
// 注册vuex ==>将状态从根组件“注入”到每一个子组件中
Vue.use(Vuex)
// 初始化
export default new Vuex.Store({
  // 申明全局使用的数据  相当于vue实例选项中的data
  state: {
    userName: 'cj'
  },
  // 存放修改state数据的方法
  mutations: {},
  actions: {},
  modules: {}
})

         通过在根实例中注册 store 选项,该 store 实例会注入到根组件下的所有子组件中,且子组件能通过 this.$store 访问到了,此时,state中存了一个字段,那么在其他页面中,就可以通过:

this.$store.state.userName  来获取到这个值 ===> cj


Mutation 更改state状态的唯一方法

1.声明mutations方法

        在子页面中,想要修改vuex中的全局字段,就需要通过mutations对象,通过调用里面定义的方法,来修改state中的数据

  // mutations是更改store中state状态的唯一方法(通过store.commit调用)
  // 由mutations中的方法导致的状态变更都应该在此刻完成==>也就是里面的方法必须都是同步函数,不能有异步的函数。
  mutations: {
    changeName (state, newName) {
      // 修改state中数据
      state.userName = newName
    }
  },

2.在页面中通过commit来调用mutations方法 

        在mutations对象中定义了一个changeName的方法,通过传入的参数state、newName,来对state中的数据进行修改。

在子页面中,需要通过特定的方法来调用并触发mutations里的方法:

this.$store.commit('changeName','cj2')

这样,就将state中的userName变成了 cj2 

你可以向 store.commit 传入额外的参数,即 mutation 的 载荷(payload),这里就是newName

在大多数情况下,载荷应该是一个对象,这样可以包含多个字段并且记录的 mutation 会更易读,参考官网的写法格式:

如果载荷是个对象的情况下,你也可以用这种写法,来调用mutations方法

this.$store.commit({
  type: 'changeName',
  newName: 'cj2'
})

3.mapMutations 辅助函数

当我们在页面中要使用mutations里的方法时,你当然可以每次使用都乖乖地写好下面的格式来调用方法:

this.$store.commit('方法名','载荷')

但是这样太麻烦了,所以可以使用mapMutations辅助函数,来简化页面中调用mutations里的方法

第一步:在要使用mutations里的方法的页面引入 mapMutations

import { mapMutations } from 'vuex'

export default {
  // ...
  methods: {
    ...mapMutations([
  // 将 `this.changeName()` 映射为 `this.$store.commit('changeName')`
      'changeName', 
      'delName',
       ... 
    ]),
  }
}

如上,首先通过import引入这个辅助函数,然后,在页面的methods方法里通过扩展运算符,展开mapMutations辅助函数里的这个  字符串数组   里面的字符串就是mutations里的方法名。

第二步:在页面中通过【this.方法名】来调用Mutations里的方法

//通过辅助函数申明的方法,也是可以正常传入载荷(参数)的
this.changeName('cj2')

...
this.delName()

这样,就完成了对store中的state里的字段的修改了。

注意点:

        由mutations中的方法导致的状态变更都应该在此刻完成  ==> 也就是里面的方法必须都是同步函数,不能有异步的函数 【例如:不能通过请求、settimeout延时后,再进行修改state】


Action 异步操作Mutations方法

        action是用来异步操作mutations方法的,它提交的是mutations方法,而不是直接修改state中的数据,所以能够进行异步操作。

        所谓能进行异步操作,就是调用action方法的时候,可以再里面使用异步请求,获取到数据后,在进行state的修改或其他操作,不用像mutations方法一样,一调用直接同步修改state中的内容。

1.定义好actions对象中的方法

方法可以跟mutations中的同名,也可以在末尾加上个Async表示异步

  // mutations是更改store中state状态的唯一方法【通过this.$store.commit('方法名')调用】
  // mutations中的方法,导致的状态变更都应该在此刻完成==>也就是里面的方法必须都是同步函数,不能有异步的函数。
  mutations: {
    changeName= (state, newName) => {
      // 修改state中数据
      state.userName = newName
    }
  },  
...
/**
   * actions可以异步操作Mutation方法。
   * action 提交的是 mutation方法,而不是直接变更状态
   * 【通过this.$store.dispatch('方法名','载荷')】
   */
  actions: {
    // 你也可以命名成 changeNameAsync,直观看出是异步的方法
    changeName = ({ commit })=> {
   // 异步方法返回的数据(能异步获取到数据,再去进行修改),作为载荷传给mutations方法
      this.$axios.get('url', { key: 'xxx' }).then(res => {
        //! 触发对应的Mutation方法,而不是直接修改state里的变量
        commit('changeName', res)
      })
      
     ...
     
      setTimeout(() => {
        //! 触发对应的Mutation方法,而不是直接修改state里的变量
        commit('delName')
      }, 1000)
    }
  },

2.页面中通过dispatch调用action方法

此时,在其他页面,就可以通过下方的代码(dispatch),来调用action里的异步方法了

this.$store.dispatch('changeName', 'cj2')

3.mapActions 辅助函数 

同上,在页面中频繁的使用this.$store.dispatch,不美观也不方便,所以可以通过辅助函数,来批量地引入并映射方法名称,这样就能在页面里通过 【this.方法名】 来使用方法了

第一步:在要使用Actions里的方法的页面引入 mapActions 

import { mapActions } from 'vuex'

export default {
  // ...
  methods: {
    ...mapActions([
   // 将 `this.changeName()` 映射为 `this.$store.dispatch('changeName')`
      'changeName', 
      'delName',
       ... 
    ]),
  }
}
...mapActions({
      add: 'increment' // 将 `this.add()` 映射为 `this.$store.dispatch('increment')`
    })

 为引用的方法设置别名也是可以的

第二步:在页面中通过【this.方法名】来调用Actions里的方法

//通过辅助函数申明的方法,也是可以正常传入载荷(参数)的
this.changeName('cj2')

...
this.delName()

这样,就完成了对store中的state里的字段的修改了


 注意:

store.dispatch 可以处理被触发的 action 的处理函数返回的 Promise,并且 store.dispatch 仍旧返回 Promise

 上面这段话什么意思呢,就是说,actions里的方法,返回的是promise类型的结果,所以,在调用actions的方法的时候,可以直接跟上.then(res=>{}),来解决回调地狱的问题

this.changeName('cj2').then(res=>{
    this.delName()
})

Getter 类似于计算属性

 getter 的返回值会根据它的依赖被缓存起来,且只有当它的依赖值发生了改变才会被重新计算

以官网的例子做演示:

const store = new Vuex.Store({
  state: {
    todos: [
      { id: 1, text: '...', done: true },
      { id: 2, text: '...', done: false }
    ]
  },
  getters: {
    doneTodos: (state) => {
      return state.todos.filter(todo => todo.done)
    }
  }
})

 

 所以你能在页面中通过使用下方的形式,来调用这个方法

this.$store.getters.doneTodos

就能拿到过滤后的数据:  [{ id: 1, text: '...', done: true }]


同样,getters也有自己的辅助函数mapGetters 辅助函数

import { mapGetters } from 'vuex'

export default {
  // ...
  computed: {
  // 使用对象展开运算符将 getter 混入 computed 对象中
    ...mapGetters([
      'doneTodosCount',
      'anotherGetter',
      // ...
    ])
  }
}

特别地:mapGetters辅助函数,需要在computerd 计算属性 中展开,

而其他几个辅助函数,则是需要在methods中展开

【因为getters是当作计算属性来用,而mutations、actions是当作methods来用】

这样,就能在页面中,像使用普通计算属性一样,来使用引入的方法了

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

DTcode7

客官,赏个铜板吧

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值