vuex插件主要用於統一管理vue項目中的數據流動狀態。詳細介紹見官網:vuex.vuejs.org/vue
實現簡易版的vuex的步驟以下:vuex
直接上源碼,註釋比較清楚。bash
// rvuex.js let Vue; class Store{ constructor(options){ // 保存全部mutations this._mutations = options.mutations; // 保存全部actions this._actions = options.actions; // 處理全部getters // 定義computed選項 const { computed } = this.dealGetters(options.getters); // 響應化處理state,當state值發生變化時,觸發渲染函數從新渲染視圖 // 能夠經過實例化Vue,在data中設置使屬性變爲響應式 this._vm = new Vue({ data: { $$state: options.state }, computed }); // 綁定commit,dispatch的上下文爲當前store實例 this.commit = this.commit.bind(this); this.dispatch = this.dispatch.bind(this); } // store中getters定義方式{ doubleCounter(state){return state.counter * 2} } // store中讀取getters裏的值:{{$store.getters.doubleCounter}} dealGetters(getters = {}){ let computed = {}; let store = this; store.getters = {}; // 遍歷用戶定義的getters Object.keys(getters).forEach(key => { // 獲取用戶定義的getter const getter = getters[key]; // 好比 doubleCounter(state){return state.counter * 2} // 將getter轉換爲computed形式,computed裏的函數是無參數的 // computed計算屬性,其實是調用getters裏的方法 computed[key]= function(){ return getter(store.state); }; // 爲getters定義只讀屬性 // 當讀取getters裏面的屬性值時,實際上是讀取的vue實例裏的computed計算屬性 Object.defineProperty(store.getters, key, { get: () => store._vm[key] }); }); return { computed }; } // 存取器 get state(){ return this._vm._data.$$state; } set state(value){ console.error('不能直接設置state的值'); } // commit mutation來觸發state的更新 // $store.commit('add', 1) // params: // type: mutation的類型 // payload: 載荷,多餘的參數 commit(type, payload){ const entry = this._mutations[type]; if(entry) { entry(this.state, payload); } } dispatch(type, payload){ const entry = this._actions[type]; if(entry){ entry(this, payload); } } } function install(_Vue){ Vue = _Vue; // $store的全局掛載 Vue.mixin({ beforeCreate() { // 只有根組件(入口文件)纔會傳入store // 而後將this.$options.store掛載到vue原型上,這樣vue組件內部能夠經過this.$store來訪問 if(this.$options.store){ Vue.prototype.$store = this.$options.store; } } }) } // Vuex export default { Store, install } 複製代碼
先定義store.jsmarkdown
// store.js import Vue from 'vue' import Vuex from 'rvuex' // 上面rvuex.js文件 Vue.use(Vuex) export default new Vuex.Store({ state: { counter: 0 }, getters:{ doubleCounter(state){ return state.counter * 2 } }, mutations: { add(state){ state.counter ++ } }, actions: { // 參數爲執行上下文 add({commit}){ setTimeout(() => { commit('add') }, 1000) } } }) 複製代碼
在組件中使用store裏的數據。async
// index.vue <template> <div> <p @click="$store.commit('add')">counter: {{$store.state.counter}}</p> <p @click="$store.dispatch('add')">async counter: {{$store.state.counter}}</p> <p>double counter: {{$store.getters.doubleCounter}}</p> <router-view /> </div> </template> 複製代碼
以上內容爲網上學習課程的複習總結。函數