你們好我是前端菜鳥林三心,今天給你們分享Vuex源碼的簡單實現。
這次只實現state,getters,mutations,actions。其實vuex的組成就是install方法和store類這兩個,而重點就是install裏的mixin,這是vuex的核心
這是文件目錄
vuex.js
let Vue;
const install = (v) => {
console.log(v)
Vue = v;
Vue.mixin({
beforeCreate() {
if (this.$options && this.$options.store) {
this.$store = this.$options.store;
} else {
this.$store = this.$parent && this.$parent.$store;
}
console.log(this.$store);
},
})
}
class Store {
constructor(options) {
this.vm = new Vue({
data: {
state: options.state
}
});
let getters = options.getters || {};
this.getters = {};
console.log(Object.keys(this.getters))
Object.keys(getters).forEach(getterName => {
Object.defineProperty(this.getters, getterName, {
get: () => {
return getters[getterName](this.state);
}
})
})
let mutations = options.mutations || {};
this.mutations = {};
Object.keys(mutations).forEach(mutationName => {
this.mutations[mutationName] = payload => {
mutations[mutationName](this.state, payload);
}
})
let actions = options.actions || {};
this.actions = {};
Object.keys(actions).forEach(actionName => {
this.actions[actionName] = payload => {
actions[actionName](this.state, payload);
}
})
}
get state() {
return this.vm.state;
}
commit(name, payload) {
this.mutations[name](payload);
}
dispatch(name, payload) {
this.actions[name](payload);
}
}
export default {
install,
Store
}
複製代碼
index.js
import Vue from 'vue';
import vuex from './vuex';
Vue.use(vuex);
export default new vuex.Store({
state: {
num: 1
},
getters: {
getNum(state) {
return state.num * 2;
}
},
mutations: { in (state, payload) {
state.num += payload;
},
de(state, payload) {
state.num -= payload;
}
},
actions: { in (state, payload) {
setTimeout(() => {
state.num += payload;
}, 2000)
}
}
})
複製代碼
main.js
import Vue from 'vue';
import App from './App.vue'
import store from './store/index';
new Vue({
store,
el: '#app',
components: {
App
},
template: '<App/>',
})
let linsanxin = 1;
console.log(linsanxin)
複製代碼
App.vue
// App.vue
<template>
<div>
{{this.$store.state.num}}
{{this.$store.getters.getNum}}
<button @click="addNum">呵呵</button>
<button @click="addNumByAsync">呵呵異步</button>
<div id="a">asadasd</div>
<button @click='add'>添加</button>
<ul v-for="(item,index) in list" :key="index">
<li class="ll">{{item.name}}</li>
</ul>
</div>
</template>
<script>
import img from "./asset/images/haha.jpg";
import "./asset/styles/test.css";
import "./asset/styles/global.stylus";
export default {
name: "App",
created() {
console.log(img);
},
data() {
return {
list: [
{ name: "lin" },
{ name: "lin" },
{ name: "lin" },
{ name: "lin" },
{ name: "lin" }
]
};
},
methods: {
add(){
this.list.push({name:'k'})
},
addNum(){
this.$store.commit('in',2);
},
addNumByAsync(){
this.$store.dispatch('in',3);
}
},
};
</script>
<style scoped lang='stylus'>
#a {
background: red;
}
</style>
複製代碼
效果
結語:我必定會成爲大神的,加油。