当前位置:
首页
文章
前端
详情

第四十四节:Vuex状态管理:辅助函数mapMutations与mapActions

前言说明:
  1. 大家已经知道vuex提供了mapStatemapGetter方法,方便我们获取stategetters

  2. 同样的vuex也提供了mapMutationsmapActions方便操作mutationsactions方法

  3. 需要注意的是mapStatemapGetter是映射为计算属性,获取数据

  4. mapMutationsmapActions是映射为组件methods方法,修改数据的

1. 未使用辅助函数修改转台

1.1 设置修改状态的mutations和actions

代码如下

let store = new Vuex.Store({
    state:{
        count:0,
        user:{
            name:"张三",
            age:20
        },
        fruits:[{
            name:"苹果",
            price: 22
        },{
            name:"梨子",
            price: 25
        },{
            name:"西瓜",
            price: 16
        },{
            name:"香蕉",
            price: 18
        }]
    },
    getters:{
        filterFruits(state){
            return state.fruits.filter(fruit => fruit.price > 20)
        }
    },
    // 定义mutations
    mutations:{
        // 同步修改状态count
        increment(state, payload){
            state.count++
        }
    },
    actions:{
        // 异步修改状态count
        asyncIncrement(context){
            setTimeout(function(){
                context.commit({
                    type:"increment"
                })
            },1000)
        }
    },

})

示例说明

  1. 组件中如果通过commit触发mutation函数,就会同步更改状态count
  2. 组件中如果通过dispath异步触发action函数,
  3. action会异步触发mutation函数,通过mutation修改状态
1.2 组件中触发mutation和action
<template>
<div>
    <div>数字: {{ count }}</div>
    <button @click="increment">同步++</button>
    <button @click="asyncincrement">异步++</button>

    </div>
</template>

<script>
    // 获取辅助函数
    import {mapState,mapGetters} from 'vuex'

    export default {
        name: 'Home',
        data(){
            return {
                // count: 10
                price: 10
            }
        },
        computed:{
            computePrice(){
                return this.price * 2
            },
            ... mapState([
                "count",
                "user",
                "fruits"
            ]),
            ...mapGetters([
                "filterFruits"
            ])
        },
        methods:{
            increment(){
                // 同步,通过commit触发mutation函数
                this.$store.commit({
                    type:"increment"
                })

            },
            asyncincrement(){
                // 异步,通过dispatch 触发action函数
                this.$store.dispatch({
                    type:"asyncIncrement"
                })
            }
        }
    }
</script>

示例说明:

  1. increment是触发mutation同步修改状态的方法
  2. asyncIncrement是触发action异步修改状态的方法

2. 使用mapMutations

说明:

  1. 之前如果我们需要在组件中修改store的状态都需要额外定义一个方法
  2. 如果这个方法里有大量的逻辑代码还好
  3. 如果这个方法只是为了触发mutation函数,每个组件都这样定义就会比较繁琐
  4. 因此vuex提供了mapMutations辅助函数,可以将mutations函数映射为组件methods方法
2.1 方法同名

方法同名意思就是组件用来触发mutation函数的方法和mutation函数重名

就可以采用字符串数组的的方式将mutation函数通过函数名映射methods方法

数组里的字符串为mutations的函数名

代码如下:

// 通过vuex获取辅助函数
import {
    mapState,   // 获取state辅助函数
    mapGetters, // 获取getters 辅助函数
    mapMutations, // 操作mutations辅助函数
} from 'vuex'

export default {
    name: 'Home',
    data(){
        return {
            // count: 10
            price: 10
        }
    },
    computed:{
        computePrice(){
            return this.price * 2
        },
        ... mapState([
            "count",
            "user",
            "fruits"
        ]),
        ...mapGetters([
            "filterFruits"
        ])
    },
    methods:{
        ...mapMutations([
            'increment'  
            //  将this.increment 映射为 this.$store.commit("increment")
        ]),
        asyncincrement(){
            // 异步,通过dispatch 触发action函数
            this.$store.dispatch({
                type:"asyncIncrement"
            })
        }
    }
}

2.2 关于载荷

此时是将mutation函数映射为组件methods方法,

如果此时调用这个方法不传参数时, 那么将没有载荷

例如:

 &lt;button @click="increment"&gt;同步++&lt;/button&gt;

如果在调用这个映射方法是传递一个数据,那么这个数据将成为mutation函数的载荷

 &lt;button @click="increment(10)"&gt;同步++&lt;/button&gt;

一般来说,载荷会选择对象方式传递数据

 &lt;button @click="increment({num:10})"&gt;同步++&lt;/button&gt;

2.3 方法不同名

也就是需要映射到组件方法中的mutation函数,在组件中已经有同名的函数了

因此在映射时,就需要另外定义方法名

此时组件中被映射的方法名和mutation函数名就不同名了

此时需要选择对象的方式映射

代码如下:

// 通过vuex获取辅助函数
import {
    mapState,   // 获取state辅助函数
    mapGetters, // 获取getters 辅助函数
    mapMutations, // 操作mutations辅助函数
} from 'vuex'

export default {
    name: 'Home',
    data(){
        return {
            // count: 10
            price: 10
        }
    },
    computed:{
        computePrice(){
            return this.price * 2
        },
        ... mapState([
            "count",
            "user",
            "fruits"
        ]),
        ...mapGetters([
            "filterFruits"
        ])
    },
    methods:{
        ...mapMutations({
            // 方法名: mutation函数名
            add:'increment'  

            //  将this.add 映射为 this.$store.commit("increment")
        }),
        asyncincrement(){
            // 异步,通过dispatch 触发action函数
            this.$store.dispatch({
                type:"asyncIncrement"
            })
        }
    }
}

3. 使用mapActions

mapActions辅助函数的使用和mapMutations一样

同样也可以传递载荷

因此可以将代码修改如下

// 通过vuex获取辅助函数
import {
    mapState,   // 获取state辅助函数
    mapGetters, // 获取getters 辅助函数
    mapMutations, // 操作mutations辅助函数
    mapActions    // 操作actions辅助函数
} from 'vuex'

export default {
    name: 'Home',
    data(){
        return {
            // count: 10
            price: 10
        }
    },
    computed:{
        computePrice(){
            return this.price * 2
        },
        ... mapState([
            "count",
            "user",
            "fruits"
        ]),
        ...mapGetters([
            "filterFruits"
        ])
    },
    methods:{
        ...mapMutations({
            // 方法名: mutation函数名
            add:'increment'  

            //  将this.add 映射为 this.$store.commit("increment")
        }),
        ...mapActions([
            "asyncIncrement"

            // 将this.asyncIncrement 
            // 映射为 this.$store.dispatch("asyncIncrement")
        ])
    }
}

免责申明:本站发布的内容(图片、视频和文字)以转载和分享为主,文章观点不代表本站立场,如涉及侵权请联系站长邮箱:xbc-online@qq.com进行反馈,一经查实,将立刻删除涉嫌侵权内容。