Open hysryt opened 6 years ago
子コンポーネントからアクセスする際の算出プロパティ用のヘルパー関数
// mapStateなし
const ChildComponent = {
computed: {
count() {
return this.$store.state.count
}
}
}
// mapStateあり
import { mapState } from 'vuex'
const ChildComponent = {
computed: mapState({
count: state => state.count
})
}
// または
import { mapState } from 'vuex'
const ChildComponent = {
computed: mapState([
'count'
])
}
引数でthis.$store.state
を取得できるので記述量が減り、さらにthisが必要ないのでアロー関数で書ける
ストアは複数のゲッターを持つことができる ゲッターは、ステートの値をフィルタリングや加工したい場合などに使用する Vue.jsでの算出プロパティに近い
ストアにフィルタリングまたは加工処理を登録することで、複数のコンポーネントで処理を共有できる
import Vuex from 'vuex'
const store = new Vuex.Store({
state: {
count: 0
},
getters: {
nextCount: state => {
return state.count + 1
}
}
})
const ChildComponent = {
computed: {
nextCount() {
return this.$store.getters.nextCount
}
}
}
ゲッターの返り値は関数にすることもできる
子コンポーネントからゲッターにアクセスする際のヘルパー関数
// mapGettersなし
const ChildComponent = {
computed: {
nextCount() {
return this.$store.getters.nextCount
}
}
}
// mapGettersあり
import { mapGetters } from 'vuex'
const ChildComponent = {
computed: mapGetters([
'nextCount'
])
}
ストアは複数のミューテーションを持つことができる ミューテーションはステートの値を変更するイベント ステートの値の変更はミューテーションを介してのみ行われる
import Vuex from 'vuex'
const store = new Vuex.Store({
state: {
count: 0
},
getters: {
nextCount: state => {
return state.count + 1
}
},
mutations: {
increment: state => {
state.count += 1
}
}
})
ミューテーション名を引数にcommit()
することでミューテーションを実行できる
const ChildComponent = {
methods: {
increment: function() {
this.$store.commit('increment')
}
}
}
commit()
は第二引数でペイロードを渡すことができる
const ChildComponent = {
methods: {
increment: function() {
this.$store.commit('increment', {
num: 10
})
}
}
}
ミューテーション側は第二引数でペイロードを受け取ることができる
mutations: {
increment: (state, payload) => {
state.count += payload.num;
}
}
ミューテーション実行関数のヘルパー関数
// mapMutationsなし
const ChildComponent = {
methods: {
increment: function() {
this.$store.commit('increment')
}
}
}
// mapMutationsあり
import { mapMutations } from 'vuex'
const ChildComponent = {
methods: mapMutations([
'increment'
])
}
ストアは複数のアクションを持つことができる アクションはミューテーションをコミットする ミューテーションは即座に(同期的に)処理をする必要があるのに対し、 アクションは非同期処理を含むことができる
import Vuex from 'vuex'
const store = new Vuex.Store({
state: {
count: 0
},
getters: {
nextCount: state => {
return state.count + 1
}
},
mutations: {
increment: state => {
state.count += 1
}
},
actions: {
increment: context => {
setTimeout(() => {
context.commit('increment');
}, 1000)
}
}
})
アクションが実行されてから1秒後にミューテーションを実行している
アクション名を引数にdispatch()
することでアクションを実行できる
const ChildComponent = {
methods: {
increment: function() {
this.$store.dispatch('increment')
}
}
}
ミューテーションと同じように、dispatch()
は第二引数でペイロードを渡すことができる
const ChildComponent = {
methods: {
increment: function() {
this.$store.dispatch('increment', {
num: 10
})
}
}
}
アクション側は第二引数でペイロードを受け取ることができる
actions: {
increment: (context, payload) => {
setTimeout(() => {
console.log(payload.num);
context.commit('increment');
}, 1000)
}
}
Promise
オブジェクトを返した場合、dispatch()
もPromise
オブジェクトを返す
// ストア側
actions: {
increment: context => {
return new Promise( resolve => { // Promiseオブジェクトを返す
context.commit('increment')
resolve()
})
}
}
// コンポーネント側
const ChildComponent = {
methods: {
increment: function() {
this.$store.dispatch('increment').then(() => { // dispatch()もPromiseオブジェクトを返す
console.log('アクション完了')
});
}
}
}
アクション実行関数用のヘルパー関数
// mapActionsなし
const ChildComponent = {
methods: {
increment: function() {
this.$store.dispatch('increment')
}
}
}
// mapActionsあり
import { mapActions } from 'vuex'
const ChildComponent = {
methods: mapActions([
'increment'
])
}
ストアはモジュールという単位で分割できる。 モジュールは、ステート、ゲッター、ミューテーション、アクション、モジュールを内包できる。
// モジュールA - ステートとミューテーションを持つ
const moduleA = {
state: {
count: 0
},
mutations: {
increment(state) {
state.count++
}
}
}
// ストア - モジュールAを持つ
const store = new Vuex.Store({
modules: {
a: moduleA
}
});
ステートとゲッター、ミューテーション、アクションでアクセス方法が異なる。 ゲッター、ミューテーション、アクションはどのモジュールで定義されたとしても、全て同じ名前空間に配置される。
$store.state.モジュール名.ステート名
モジュールがさらにモジュールを内包している場合は$store.state.モジュール名.モジュール名.ステート名
となる。
つまりモジュールごとに名前空間を持つことになる。
const ChildComponent = {
computed: {
count() {
return this.$store.state.a.count
}
}
}
ゲッター、ミューテーション、アクションへのアクセス。 全て同じ名前空間に配置されるため、 ストア直下のミューテーションと同じように呼び出すことができる。 同じ名前のミューテーションが複数ある場合、実行時に全て実行される
const ChildComponent = {
created() {
this.$store.commit('increment')
}
}
ゲッター、ミューテーション、アクションは名前空間内に配置することもできる
namespaced:true
を追加する
const moduleA = {
namespaced: true,
state: {
count: 0
},
mutations: {
increment(state) {
state.count++
}
}
}
呼び出す場合は名前空間付きでa/increment
のように指定する
export default {
created() {
this.$store.commit('a/increment')
}
}
https://vuex.vuejs.org/ja/structure.html
例:https://github.com/vuejs/vuex/tree/dev/examples/shopping-cart
Vuexではv-model
での双方向バイディングは許されていない
:value
と@input
またはget
とset
で代用する必要がある
https://vuex.vuejs.org/ja/forms.html
ストアの作成
ストアは複数のステート、ゲッターを持つ ステートとデータはほぼ同義
ルートコンポーネントにストアを登録
ルートコンポーネントに登録したストアは全ての子コンポーネントに注入される
子コンポーネントからのアクセス