做者:小土豆biubiubiujavascript
博客園:www.cnblogs.com/HouJiao/css
掘金:juejin.im/user/58c61b…html
簡書:www.jianshu.com/u/cb1c3884e…前端
微信公衆號:土豆媽的碎碎念(掃碼關注,一塊兒吸貓,一塊兒聽故事,一塊兒學習前端技術)vue
碼字不易,點贊鼓勵喲~java
本文章是Vuex
系列的最後一篇,主要總結的是如何使用mapState
和mapGetters
訪問Vuex
中的state
和getters
。web
上一篇文章 [手把手式教程,適合新手入門Vuex]-Vuex入門實踐(中) 裏面咱們總結的是多模塊的內容,因此關於store.js
、moduleA.js
和moduleB.js
的代碼保持不變。vuex
在此爲了方便觀看,我將這三個文件的代碼在貼在這裏。數組
// E:\MyStudy\test\VueDemo\src\vuex\store.js
import Vue from 'vue'
import Vuex from 'vuex'
import moduleA from './moduleA'
import moduleB from './moduleB'
Vue.use(Vuex)
export default new Vuex.Store({
state: {
counter: 1000
},
mutations: {
//遞增
increase(state) {
console.log("store-increase")
state.counter++
},
//遞減
decrement(state) {
state.counter--
}
},
actions: {
increaseAction(context) {
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('increase');
},3000)
},
decrementAction(context){
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('decrement');
},3000)
}
},
getters: {
doubleCounter(state) {
return state.counter*state.counter
}
},
modules: {
a: moduleA,
b: moduleB
}
})
複製代碼
// E:\MyStudy\test\VueDemo\src\vuex\moduleA.js
const moduleA = {
namespaced: true,
state:{
counter: 100
},
mutations: {
//遞增
increase(state) {
console.log("moduleA-increase")
state.counter++
},
//遞減
decrement(state) {
state.counter--
}
},
actions: {
increaseAction(context) {
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('increase');
},3000)
},
decrementAction(context){
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('decrement');
},3000)
}
},
getters: {
doubleCounter(state) {
return state.counter*state.counter
}
}
}
export default moduleA
複製代碼
// E:\MyStudy\test\VueDemo\src\vuex\moduleB.js
const moduleB = {
namespaced: true,
state:{
counter: 5
},
mutations: {
//遞增
increase(state) {
console.log("moduleB-increase")
state.counter++
},
//遞減
decrementAction(state) {
state.counter--
}
},
actions: {
increaseAction(context) {
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('increase');
},3000)
},
decrementAction(context){
setTimeout(function(){
//action經過提交mutation改變共享數據狀態
context.commit('decrement');
},3000)
}
},
getters: {
doubleCounter(state){
return state.counter*state.counter
}
}
}
export default moduleB
複製代碼
注意這裏不能缺乏
命令空間
的配置哦瀏覽器
如今須要在組件中使用mapState
、mapGetters
對state
和getters
進行訪問,仍是按照以前的套路:
在App.vue組件中訪問store根模塊、a模塊的state和getters
在Index.vue組件中訪問b模塊的state和getters
複製代碼
使用mapState
訪問state
的寫法也有多種,咱們一個一個來實踐。
咱們先直接上代碼。
<!-- E:\MyStudy\test\VueDemo\src\App.vue -->
<template>
<div id="app">
<img src="./assets/logo.png">
<!-- 獲取共享數據 -->
<h1>這裏是App組件</h1>
<h3> App組件獲取共享數據 </h3>
<h3>使用mapState訪問根組件counter : {{counter}}</h3>
<h3>使用mapState訪問a組件counter : {{counterA}}</h3>
<hr/>
<Index></Index>
</div>
</template>
<script> import Index from './components/Index' import { mapState } from 'vuex' export default { name: 'App', components: { Index }, computed: mapState({ //訪問store根模塊 counter: function(state){ return state.counter }, //訪問a模塊 counterA: function(state){ return state.a.counter } }) } </script>
<style> #app { font-family: 'Avenir', Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50; margin-top: 60px; } </style>
複製代碼
<!-- E:\MyStudy\test\VueDemo\src\components\Index.vue -->
<template>
<div>
<h1>這裏是Index.vue組件</h1>
<h3>Index組件獲取共享數據 </h3>
<h3>使用mapState訪問b模塊counter :{{ counterB }}</h3>
</div>
</template>
<script> import { mapState } from 'vuex' export default { name: 'Index', computed: mapState({ counterB: function(state){ return state.b.counter } }) } </script>
複製代碼
在組件中使用mapState
,首先第一步
須要引入mapState
。
import { mapState } from 'vuex'
複製代碼
接着就是在組件的計算屬性computed
使用mapState
,以Index
組件中的代碼爲例。
computed: mapState({
counterB: function(state){
return state.b.counter
}
})
複製代碼
能夠看到mapState
關聯到Vue
的計算屬性中。
獲取b
模塊的state
,只須要以Vue
計算屬性的形式在函數中返回state.b.counter
便可。(獲取根模塊state
返回state.counter
;獲取a
模塊state
返回state.a.counter
)
這樣在模板中就可使用計算屬性的語法訪問state
。
第二種寫法和第一種有些相似,只是以字符串
的形式返回計算屬性。
咱們先在Index.vue
組件中訪問b
模塊的數據。
<!-- E:\MyStudy\test\VueDemo\src\components\Index.vue -->
<template>
<div>
<h1>這裏是Index.vue組件</h1>
<h3>Index組件獲取共享數據 </h3>
<h3>使用mapState訪問b模塊counter :{{ counterB }}</h3>
</div>
</template>
<script> import { mapState } from 'vuex' export default { name: 'Index', computed: mapState('b',{ counterB: 'counter' }) } </script>
複製代碼
核心代碼以下:
computed: mapState('b',{
counterB: 'counter'
})
複製代碼
能夠看到,這種寫法mapState
第一個參數限定了模塊名稱
。接着就是以counter
字符串的形式返回了b
模塊的counter
值。那麼咱們就能夠知道訪問store
跟模塊、a
模塊的方法以下:
訪問根模塊的數據,不須要限定第一個參數
訪問a模塊的數據,須要限定第一個參數爲a
複製代碼
接着就有個問題了:訪問store
根模塊、a
模塊的state
代碼同在App.vue
組件中,那麼由於mapState
第一個參數限定的問題,咱們須要編寫兩個mapState
。
如今直接上代碼(只把computed
中的核心代碼貼上)。
// E:\MyStudy\test\VueDemo\src\App.vue 
computed: {
...mapState({
//訪問store根模塊
counter: 'counter',
}),
...mapState('a',{
//訪問a模塊
counterA: 'counter'
})
}
複製代碼
能夠看到,我寫了兩個mapState
,仍是...mapState
這樣的形式。
...mapState
它是ES6
中擴展運算符
的語法,應用在mapState
上,官方文檔是這樣說的:
若對此有疑問,能夠在去仔細研究一下對象擴展運算符的內容
我這裏貼一個簡單的示例
最終newObj
的打印結果爲 相信這個示例能夠很清楚的解釋咱們寫的兩個...mapState
的寫法
官方文檔處提到這個對象展開運算符
的場景是爲了將一個組件中本來的計算屬性和mapState混合使用
。
混合使用這個點平常開發會用到,很實用的一個點
最後咱們在使用瀏覽器查看一下最終App.vue
和Index.vue
中的結果。
注意:
這種關於
mapState
的寫法不能刪除moduleA
和moduleB
中關於命令空間的配置,不然會報錯。最後做者還嘗試了一個問題,就是將
moduleA.js
中的state
屬性改成counterA
。而後修改了
最後發現這樣並不能正常訪問到App.vue
組件中computed
訪問a
模塊數據的代碼a
模塊的state
數據(刪除a
模塊的命名空間配置也沒法正常訪問)這個嘗試僅給你們一個反面的示例,具體爲何不能訪問應該須要去閱讀
Vuex
的源碼才能知曉,所以這裏不在探究。
前面使用mapState
訪問了state
數據,那麼如今咱們使用mapGetters
訪問一下Vuex
中的getters
。
在嘗試以後發現,暫時發現使用
mapGetters
訪問Vuex
中的getters
只有字符串的形式
<!-- E:\MyStudy\test\VueDemo\src\App.vue -->
<template>
<div id="app">
<img src="./assets/logo.png">
<!-- 獲取共享數據 -->
<h1>這裏是App組件</h1>
<h3> App組件獲取共享數據 </h3>
<h3>使用mapState訪問根組件counter : {{counter}}</h3>
<h3>使用mapState訪問a組件counter : {{counterA}}</h3>
<h3>使用mapGetters訪問根組件doubleCounter : {{doubleCounter}}</h3>
<h3>使用mapGetters訪問a組件doubleCounter : {{doubleCounterA}}</h3>
<hr/>
<Index></Index>
</div>
</template>
<script> import Index from './components/Index' import { mapState,mapGetters } from 'vuex' export default { name: 'App', components: { Index }, computed: { ...mapState({ //訪問store根模塊 counter: 'counter', }), ...mapState('a',{ //訪問a模塊 counterA: 'counter' }), ...mapGetters({ //訪問store根模塊 doubleCounter: 'doubleCounter' }), ...mapGetters('a',{ //訪問store根模塊 doubleCounterA: 'doubleCounter' }) } } </script>
<style> #app { font-family: 'Avenir', Helvetica, Arial, sans-serif; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-align: center; color: #2c3e50; margin-top: 60px; } </style>
複製代碼
<!-- E:\MyStudy\test\VueDemo\src\components\Index.vue -->
<template>
<div>
<h1>這裏是Index.vue組件</h1>
<h3>Index組件獲取共享數據 </h3>
<h3>使用mapState訪問b模塊counter :{{ counterB }}</h3>
<h3>使用mapGetters訪問b組件doubleCounter : {{doubleCounterB}}</h3>
</div>
</template>
<script> import { mapState,mapGetters } from 'vuex' export default { name: 'Index', computed: { ...mapState('b',{ counterB: 'counter' }), ...mapGetters('b',{ doubleCounterB: 'doubleCounter' }), } } </script>
複製代碼
App組件中關於mapGetters
的核心代碼以下:
computed: {
...mapGetters({
//訪問store根模塊
doubleCounter: 'doubleCounter'
}),
...mapGetters('a',{
//訪問store根模塊
doubleCounterA: 'doubleCounter'
})
}
複製代碼
Index組件中關於mapGetters
的核心代碼以下:
computed: {
...mapGetters('b',{
doubleCounterB: 'doubleCounter'
}),
}
複製代碼
瀏覽器查看結果:
到此本篇文章基本已經結束了。
在最後呢,再補充一點,不論是mapState
和mapGetters
,咱們給傳入的都是一個字典。
...mapState({
counter: 'counter',
}),
...mapGetters({
doubleCounter: 'doubleCounter'
}),
複製代碼
簡單一些的,假如咱們的state
和getters
不重名,咱們能夠給mapState
和mapGetters
傳入一個數組。
mapState([
'counterA','counterB',...
])
mapGetters([
'dobuleCounterA','dobuleCounterB',...
])
複製代碼
這樣數組中的字符串元素會直接去映射對應的state
和getters
。
字典形式至關因而將
state
和getters
中的名稱在映射過程當中進行重命名
到此[手把手式教程,適合新手入門Vuex]-Vuex入門實踐
這整個系列就結束了,都是一些關於Vuex
基礎的用法,比較適合新手剛開始學習和實踐Vuex
。
最後呢,將這個系列的全部文章連接整理到這裏,方便你們觀看。
[手把手式教程,適合新手入門Vuex]-Vuex入門實踐(上)
[手把手式教程,適合新手入門Vuex]-Vuex入門實踐(中)
[手把手式教程,適合新手入門Vuex]-Vuex入門實踐(下)
小土豆biubiubiu
一個努力學習的前端小菜鳥,知識是無限的。堅信只要不停下學習的腳步,總能到達本身指望的地方
同時仍是一個喜歡小貓咪的人,家裏有一隻美短小母貓,名叫土豆
土豆媽的碎碎念
微信公衆號的初衷是記錄本身和身邊的一些故事,同時會不按期更新一些技術文章
歡迎你們掃碼關注,一塊兒吸貓,一塊兒聽故事,一塊兒學習前端技術
歡迎你們掃描微信二維碼進入羣聊討論問題(若二維碼失效可添加微信JEmbrace拉你進羣)
小小總結,歡迎你們指導~