Vuex核心概念

Vuex几个核心概念

  • State (单一状态树)
  • Getters (和计算属性差不多)
  • Mutations (同步方法)
  • Actions (异步方法)
  • Modules (模块)

state

修改state里面的属性的话必须要通过mutations来修改
state≈data
用来存放数据的

mutations

官方解释:更改 Vuex 的 store 中的状态的唯一方法是提交 mutation。Vuex 中的 mutation 非常类似于事件:每个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数:

// index.js
const store = new Vuex.Store({
  state: {
    counter: 100
  },
  mutations: {
    increment(state) {
      state.counter++
    },
    decrement(state) {
      state.counter--
    }
  }
})

这样就能直接拿到increment属性并且执行它

// .vue
methods: {
  jia() {
	// 通过this.$store.commit()发送mutations里面的属性
    this.$store.commit('increment') 
  },
  jian() {
    this.$store.commit('decrement')
  }
}
  • 将store对象放在new Vue对象中,用来保存多个组件共享的状态

  • 在其他的组件中使用store对象中保存的状态

    • 使用this.$store.state属性的方式来进行访问
    • 使用this.$store.commit(‘mutations里面的方法’)来进行修改

  • 这里通过的是提交mutations的方式,而不是直接改变store.state.count

  • 使用$store.commit(’’)是因为Vuex可以追踪到stat状态的变化,所以最好不要直接就使用store.state.count来进行改变count的值,这种直接修改的值Vuex是追踪不到的

mutations传参用法(两种方法)

// index.js
import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const store = new Vuex.Store({
  state: {
    list: [
      {
        name: 'aaa',
        age: 12,
        sex: true
      },
      {
        name: 'bbb',
        age: 18,
        sex: false
      },
      {
        name: 'ccc',
        age: 13,
        sex: true
      },
      {
        name: 'ddd',
        age: 16,
        sex: false
      }
    ]
  },
  mutations: {
  	// 第一个参数state就是store里面的state
    // 第二个参数all是用来接受this.$store.commit('addList', obj)发送过来的信息的
    // 普通方式接受参数
    // addList(state, all) {
    //  state.list.push(all)
    // }
	
	// 用payload接受传过来的对象
	addList(state, payload) {
      state.list.push(payload.obj)
    }
  }
})
export default store
<template>
  <div>
    <button @click="addL">点击添加信息</button>
    <div> {{ $store.state.list }} </div>
    <hr>
  </div>
</template>

<script>
  export default {
    name: 'counter',
    methods: {
      addL() {
        const obj = {id: 1, name: '测111', age: 999}
        // this.$store.commit('addList', obj)   普通传参方式
        // 把obj发送给index.js中mutations里面定义的addList方法
		// 用对象方式传参
		// 你可以向 store.commit 传入额外的参数,即 mutation 的 载荷(payload)
		this.$store.commit({
          type: 'addList',
          obj: obj
        })
      }
    }
  }
</script>

<style>

</style>

当点击添加信息的时候就会添加一个对象到数组里面
在这里插入图片描述

getters

官方解释:Vuex 允许我们在 store 中定义“getter”(可以认为是 store 的计算属性)。就像计算属性一样,getter 的返回值会根据它的依赖被缓存起来,且只有当它的依赖值发生了改变才会被重新计算。

getters和computed计算属性差不多

// index.js

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const store = new Vuex.Store({
  state: {
    list: [
      {
        name: 'aaa',
        age: 12,
        sex: true
      },
      {
        name: 'bbb',
        age: 18,
        sex: false
      },
      {
        name: 'ccc',
        age: 13,
        sex: true
      },
      {
        name: 'ddd',
        age: 16,
        sex: false
      }
    ]
  },
  getters: {
  	// 第一个参数state就是store 里面的state 
    abc(state) {
      return state.list.filter(a => a.sex)		// filter参数a就是list里面的对象,这里是只要sex是真就返回
    },
    // 第二个参数就是它本身
    def(state, geeters) {
      return geeters.abc.length
    },
    // 传参的方式
    ret(state) {
      return (userage) => {
        return state.list.filter(a => a.age > userage)
      }
    }
  }
})

export default store

Getter 会暴露为 store.getters 对象,你可以以属性的形式访问这些值:

<!--counter.vue-->

<template>
  <div>
    <h2>对象:-------{{ $store.getters.abc }}</h2>
    <h2>长度:{{ $store.getters.def }}</h2>
    <h2>传参:{{ $store.getters.ret(17) }}</h2>
  </div>
</template>

<script>
  export default {
    name: 'counter'
  }
</script>

<style>

</style>

在这里插入图片描述


actions

异步操作处理在action里面做,action类似于mutation,但action是来代替mutation进行异步操作的

官方解释: Action 函数接受一个与 store 实例具有相同方法和属性的 context 对象,因此你可以调用 context.commit 提交一个 mutation,或者通过 context.state 和 context.getters 来获取 state 和 getters。

actions里面定义方法的参数不是state,而是context(上下文)
可以把context理解成state

// index.js

  state: {
    info: {
      name: 'qqq'
    }
  },
  mutations: {
    abc(state) {
      state.info.name = 'ccc'
    }
  },
  actions: {
    aAbc(context, payload) {
      return new Promise((resolve, reject) => {
        setTimeout(() => {
          context.commit('abc')     // 把mutations里面的abc发射出去
          console.log(payload)      // 这里打印的是App.vue里面传过来的第二个参数
          resolve('我已经完成了操作') // 完成之后调用resolve
        }, 1000)
      })
    }
  },
<!--App.vue-->

<template>
  <div id="app">
    <button @click="btnCli">dsad</button>
    <h2>{{ $store.state.info }}</h2>
  </div>
</template>

<script>


export default {
  name: 'App',
  methods: {
    btnCli() {
      // 通过同步修改修用commit
      // this.$store.commit('abc')   


      // 通过异步修改用dispatch 
      this.$store
      .dispatch('aAbc', '我是payload传参')
      .then(res => {
        console.log('我已经完成了提交')
        console.log(res)    // resolve()在这里打印
      }) 
    }
  }
}
</script>

<style>

</style>

return new Promise(){} 整体返回给aAbc,.dispatch(‘aAbc’, ‘我是payload传参’)调用了aAbc,那么他就是Promise,所以在这里就可以直接调用.then方法

在这里插入图片描述
在这里插入图片描述


modules

官方解释:由于使用单一状态树,应用的所有状态会集中到一个比较大的对象。当应用变得非常复杂时,store 对象就有可能变得相当臃肿。
为了解决以上问题,Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter、甚至是嵌套子模块——从上至下进行同样方式的分割:

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const moduleA = {
  state: {
    demo: '测试1'
  },
  mutations: {},
  getters: {},
  actions: {}
}

const store = new Vuex.Store({
  state: {},
  mutations: {},
  getters: {},
  actions: {},
  modules: {
    a: moduleA
  }
})

export default store

上面的moduleA对象 给了store里面modules里面的a,那么这个a就会到store里面的state里面,所以想要拿到moduleA 里面的demo属性,就直接 $store.state.a

在里面使用mutations也和之前一样

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const moduleA = {
  state: {
    demo: '测试1'
  },
  mutations: {
    edit(state, payload) {
      state.demo = payload
    }
  }
}

const store = new Vuex.Store({
  modules: {
    a: moduleA
  }
})

export default store
<template>
  <div id="app">
    <button @click="btnCli">点击修改</button>
    <h2>{{ $store.state.a }}</h2>
  </div>
</template>

<script>
export default {
  name: 'App',
  methods: {
    btnCli() {
      this.$store.commit('edit', '测试2')
    }
  }
}
</script>

<style>

</style>

modules里面的getters有第三个参数,第三个参数可以获取到(rootState)根

import Vue from 'vue'
import Vuex from 'vuex'

Vue.use(Vuex)

const moduleA = {
  state: {
    demo: '测试1'
  },
  getters: {
    name1(state) {
      return state.demo + '111'
    },
    name2(state, getters) {
      return getters.name1 + '222'
    },
    // 第三个参数就是最下面的state
    name3(state, getters, rootState) {
      return getters.name2 + rootState.count
    }
  }
}

const store = new Vuex.Store({
  state: {
    count: 666
  },
  modules: {
    a: moduleA
  }
})

export default store
	<h2>{{ $store.getters.name1 }}</h2> <!--测试1111-->
    <h2>{{ $store.getters.name2 }}</h2> <!--测试1111222-->
    <h2>{{ $store.getters.name3 }}</h2> <!--测试1111222666-->
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值