核心概念
- state
- mutations
- actions
- modules
手動引入vuex
如果在vue腳手架中沒有引入vuex需要進行手動配置。
在main.js中添加如下代碼:
import store from 'vuex'
// 在建立vue執行個體時,将store挂載進去
new Vue({
render: h => h(App),
store
}).$mount('#app')
state
state中設定資料源,頁面中所有在vuex中存放的資料都要放到store的state中進行存儲。
export default new Vuex.Store({
state: {
number: 0
}
})
通路state中資料的兩種方法
- 通過vue對象進行通路:
this.$store.state.number
- 第二種方式:
- 在元件中導入mapState函數
- 元件中可以使用mapState函數将需要的資料映射為計算屬性
- 示例:
// 在需要使用資料的元件中導入該函數
import { mapState } from 'vuex'
export default {
data () {
return {}
},
components: {
'my-add': add,
'my-sub': sub
},
// 設定為計算屬性
computed: {
...mapState(['number'])
}~~
~~}
這樣可以直接通過插值表達式通路number屬性
mutations
mutations用于對store中的資料進行變更。
需要注意的是,隻能通過mutations中的函數來變更資料,不能在元件中直接對資料進行更改。
在mutations中定義函數:
mutations: {
add (state) {
state.number++
},
sub (state) {
state.number--
}
},
在元件中調用函數需要通過
this.$store.commit
方法:
methods: {
addOne () {
this.$store.commit('add')
console.log('目前值為' + this.$store.state.number)
}
}
調用時傳遞參數
mutations對象中的函數是可以傳遞參數的,如果要傳遞參數至少需要2個形參,第一個位置的形參必須為state,從第二個形參開始才是要接受的參數。
在使用commit調用mutations裡的函數時。第一個實參為要觸發的函數(String類型),第二個實參才是要傳遞的參數。
如下代碼所示:
在vuex中定義:
export default new Vuex.Store({
state: {
number: 0
},
mutations: {
add (state) {
state.number++
},
sub (state) {
state.number--
},
// 第一個參數傳遞state
addN (state, num) {
state.number += num
}
}
})
在元件中調用:
methods: {
addN () {
this.$store.commit('addN', parseInt(this.addNumber))
console.log('目前值為' + this.$store.state.number)
}
}
this.addNumber為雙向資料綁定的input值
觸發函數的另一種方式
在元件中導入mapMutations函數:
import { mapMutations } from 'vuex'
将需要的函數映射為目前元件中的methods:
methods: {
...mapMutations(['addN'])
}
這樣可以通過this來調用導入的addN,使用這種方式導入的函數無需傳遞第一個參數如下代碼所示:
<template>
<div>
<input type="text" v-model="addNumber">
<button @click='addMore'>加N</button>
</div>
</template>
<script>
import { mapMutations } from 'vuex'
export default {
data () {
return {
addNumber: 0
}
},
methods: {
addMore () {
// 如果不涉及類型轉換可以直接在@click=調用
this.addN(parseInt(this.addNumber))
},
// 導入addN
...mapMutations(['addN'])
}
}
</script>
<style ></style>
不可以在mutations中處理異步代碼
actions
在mutations中不要執行異步操作,應該通過Action來處理異步操作。
在vue的開發工具中:如果是同步代碼,開發工具可以捕獲到值的變換;但是如果是異步代碼,頁面中的值雖然變化了,但是開發工具不能夠捕捉。如下圖所示:
在actions中定義異步代碼
異步代碼在actions中執行,但是仍然需要使用commit去調用mutations的函數将資料進行更改。如下代碼所示:
actions: {
// actions中的異步代碼必須聲明一個context參數,用來調用mutations中的函數
asyncAddOne (context) {
setTimeout(() => {
// 實質上還是通過調用add方法進行+1
context.commit('add')
}, 1000)
}
}
這樣在vuex中異步+1的函數寫好了,如果要觸發actions中的函數需要下面操作。
觸發actions中的異步函數
觸發actions中的異步函數有兩種方法。
通過vue對象觸發
通過dispatch調用actions中的異步代碼,如下代碼所示:
<template>
<div>
<button @click='asyncAddOne'>延遲一秒+1</button>
</div>
</template>
<script>
export default {
methods: {
asyncAddOne () {
this.$store.dispatch('asyncAddOne')
}
}
}
</script>
千萬不可以使用actions中的函數直接改變值,隻能調用mutations中的函數,使mutations中的函數協助操作值
通過mapActions導入函數
與mapMutations的使用是一樣的
getters
getters用來對state中擷取的資料進行加工,但是不會更改state中的資料。
使用方法:
export default new Vuex.Store({
state: {},
mutations: {},
actions: {},
// 與state等同級
getters: {}
})
在getters中聲明一個函數,函數中包含要擷取的值和對值進行的加工。如下代碼所示:
getters: {
showNumber(state) {
return `目前number值為:${state.number}`
}
}
調用getters中定義的函數,見下文
調用getters中的函數
仍然是兩種方式:vue對象、挂載到計算屬性
vue對象方式
this.$store.getters.showNumber
mapGetters方式
- 導入mapGetters函數
import { mapGetters } from 'vuex'
- 挂載到計算屬性
computed: {
...mapGetters(['showNumber'])
}