zoukankan      html  css  js  c++  java
  • 简易vuex源码实现

    kvuex.js  文件    (实现vuex插件)

    // 1、维护状态state
    // 2、修改状态commit
    // 3、业务逻辑控制dispatch
    // 4、状态派发getter
    // 5、实现state响应式
    // 6、插件
    // 7、混入
    
    let Vue
    
    function install(_Vue, storeName = '$store') {
        Vue = _Vue
    
        // 混入:把store选项指定到Vue原型上
        Vue.mixin({
            beforeCreate() {
                // 判断main.js的当期组件选择中,是否有sotre   
                if(this.$options.store){
                    Vue.prototype[storeName] = this.$options.store 
                }
            }
        })
    }
    
    class Store {
        // options: { state: {count:0}, mutations:{count(state){}} }
        constructor(options = {}){
            // 利用vue数据响应式
            this.state = new Vue({
                data: options.state
            })
    
            // 初始化mutations
            this.mutations = options.mutations || {}
            this.actions = options.actions || {}
            options.getters && this.handleGetters(options.getters)
        }
    
        // 触发mutations,需要实现commit
        commit = (type, arg) => {
            // this只想Store实例
            const fn = this.mutations[type] // 获取状态变更函数
            fn(this.state, arg)
        } 
    
        dispatch = (type, arg) => {
            const fn = this.actions[type]
            return fn({commit: this.commit, state: this.state}, arg)
        }
    
        // {getters: {score(state){return state.xx}}}
        handleGetters(getters){
            this.getters = {} // store实例上的getters
    
            // 定义只读的属性
            Object.keys(getters).forEach(key => {
                Object.defineProperty(this.getters, key, {
                    get: () => {
                        return getters[key](this.state)
                    }
                })
            })
        }
    }
    
    export default {Store, install}

    kindex.js  文件  相当于store.js文件

    import Vue from 'vue'
    import KVuex from '../kvuex'
    
    Vue.use(KVuex)
    
    export default new KVuex.Store({
        state: {
            count: 0
        },
        mutations: {
            add(state, num = 1) {
                state.count += num
            }
        },
        getters: { // 相当于计算属性
            score(state) {
                return 'score:' + state.count
            }
        },
        actions: {
            // 处理复杂业务逻辑,类似于controller
            // 比如ajax请求
    
            asyncAdd({ commit }) { // 参数解构,拿到上下文
                setTimeout(() => {
                    commit('add')
                }, 1000);
            }
    
        }
    })

    测试文件---vue文件

    <template>
        <div>
            <h3>vuex test</h3>
            <p>{{$store.state.count}}</p>
            <p>{{$store.getters.score}}</p>
            <button @click="add">add</button>
            <button @click="asyncAdd">asyncAdd</button>
        </div>
    </template>
    
    <script>
    export default {
        methods: {
            add() {
                this.$store.commit('add', 2)
            },
            asyncAdd(){
                this.$store.dispatch('asyncAdd')
            }
        },
    }
    </script>
  • 相关阅读:
    2014-3-10 时间都去哪了,还没好好感受年轻就老了
    2014-3-4 思杨昨天已经顺利到老家 --------- 回忆思杨之2--“叫你不穿鞋鞋”
    2014-3-4 鬼脸笑笑的思杨
    路由
    视图
    请求与响应
    序列化组件
    APIView源码分析
    CBV源码分析
    DRF入门规范
  • 原文地址:https://www.cnblogs.com/haishen/p/11315669.html
Copyright © 2011-2022 走看看