zchfeng / Front-End-note

1 stars 0 forks source link

Vuex #4

Open zchfeng opened 2 years ago

zchfeng commented 2 years ago

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

State

使用

// 创建一个 Counter 组件
const Counter = {
  template: `<div>{{ count }}</div>`,
  computed: {
    count () {
      return store.state.count
    }
  }
}
const Counter = {
  template: `<div>{{ count }}</div>`,
  computed: {
    count () {
      return this.$store.state.count
    }
  }
}

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

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

// 为了能够使用 `this` 获取局部状态,必须使用常规函数
countPlusLocalState (state) {
  return state.count + this.localCount
}

}) }

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


## Getter
Vuex 允许我们在 store 中定义“getter”(可以认为是 store 的计算属性)。

Getter 接受 state 作为其第一个参数: const store = createStore({ state: { todos: [ { id: 1, text: '...', done: true }, { id: 2, text: '...', done: false } ] }, getters: { doneTodos: (state) => { return state.todos.filter(todo => todo.done) } } })

访问

store.getters.doneTodosCount

- mapGetters 辅助函数

import { mapGetters } from 'vuex'

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

...mapGetters({ // 把 this.doneCount 映射为 this.$store.getters.doneTodosCount doneCount: 'doneTodosCount' })

zchfeng commented 2 years ago

Mutation

使用

const store = createStore({
  state: {
    count: 1
  },
  mutations: {
    increment (state) {
      // 变更状态
      state.count++
    }
  }
})

触发mutations

store.commit('increment')
// store.commit('increment', 10)
//  store.commit({
  type: 'increment',
  amount: 10
})

export default { // ... methods: { ...mapMutations([ 'increment', // 将 this.increment() 映射为 this.$store.commit('increment')

  // `mapMutations` 也支持载荷:
  'incrementBy' // 将 `this.incrementBy(amount)` 映射为 `this.$store.commit('incrementBy', amount)`
]),
...mapMutations({
  add: 'increment' // 将 `this.add()` 映射为 `this.$store.commit('increment')`
})

} }



### Mutation 必须是同步函数:现在想象,我们正在 debug 一个 app 并且观察 devtool 中的 mutation 日志。每一条 mutation 被记录,devtools 都需要捕捉到前一状态和后一状态的快照。然而,在上面的例子中 mutation 中的异步函数中的回调让这不可能完成:因为当 mutation 触发的时候,回调函数还没有被调用,devtools 不知道什么时候回调函数实际上被调用——实质上任何在回调函数中进行的状态的改变都是不可追踪的。
zchfeng commented 2 years ago

Action

Action 类似于 mutation,不同在于:

zchfeng commented 2 years ago

module

为了解决以上问题,Vuex 允许我们将 store 分割成模块(module)。每个模块拥有自己的 state、mutation、action、getter、甚至是嵌套子模块——从上至下进行同样方式的分割:

const moduleA = {
  state: () => ({ ... }),
  mutations: { ... },
  actions: { ... },
  getters: { ... }
}

const moduleB = {
  state: () => ({ ... }),
  mutations: { ... },
  actions: { ... }
}

const store = createStore({
  modules: {
    a: moduleA,
    b: moduleB
  }
})

store.state.a // -> moduleA 的状态
store.state.b // -> moduleB 的状态
zchfeng commented 2 years ago

Vuex