Vue2的源码学习3:mixin 原理的实现以及生命周期的调用

开始

前两节我们分别对Vue2中的响应式数据原理以及模板编译分别进行了总结整理,下面对Vue的mixin的实现和Vue的生命周期合并于调用进行总结整理。

Vue.mixin

Vue.mixin

Vue中的mixin的方法也是开发中一个很常用的方法,特别是在组件封装中,我们可以依赖它实现方法的复用,之前在总结Vuex的源码的时候,在实现全局安装Vuex的方法,同样也依赖它实现的。

juejin.im/post/5efdd3…

  Vue.mixin({

beforeCreate(){

//说明是根

if(this.$options && this.$options.store)

{

this.$store=this.$options.store;

}

else{

this.$store=this.$parent && this.$parent.$store;

}

}

})

实现

####思路

mixin 的本质还是对象之间的合并,但是对不同对象和方法右不同的处理方式,对于普通对象,就是简单的对象合并类似于Object.assign,对于基础类型就是后面的覆盖前面的,而对于生命周期上的方法,相同的则是合并到一个数组中,调用的时候依次调用。

####代码实现

  • 定义mixin 方法

import {  mergeOptions} from "./util/index.js";

/*

初始化全局的API

*/

exportfunction initGlobalApi(Vue){

Vue.options={};

Vue.mixin=function(mixin){

this.options=mergeOptions(this.options,mixin);

return this;

}

}

  • 合并对象的方法

exportfunction mergeOptions(parent,child){

const options={} ;

for(let key in parent)

{

mergeFields(key)

}

for(let key in child)

{

if(!parent.hasOwnProperty[key]){

mergeFields(key)

}

}

/**

* 合并属性

* @param {*} key

*/

function mergeFields(key){

//如果策略模式上存在

if(strats[key]){

options[key]=strats[key](parent[key],child[key])

}

//如果都是对象 {a:11,b:2},{a:12,c:14} =>{a:12,b:2,c:14}

elseif(isReallyObject(parent[key]) && isReallyObject(child[key] ))

{

options[key]={

...parent[key],

...child[key]

}

}

elseif(child[key]){

options[key]=child[key]

}

else{

options[key]=parent[key];

}

}

return options;

}

其实源码中合并的方法很复杂,包括对合并对象的响应式数据处理,还有组件中 minins的合并策略,如有兴趣,可查看源码中的options.js 文件。

生命周期

生命周期的合并

Vue2 中有如下几个生命周期

'beforeCreate',

'created',

'beforeMount',

'mounted',

'beforeUpdate',

'updated',

'beforeDestroy',

'destroyed',

每个组件都有自己的生命周期,组件之间生命周期的合并也是依赖Vue.mixin 实现的

合并方法

//存放策略(合并对象前会优先调用)

let strats={

}

const LIFECYCLE_HOOKS =[

'beforeCreate',

'created',

'beforeMount',

'mounted',

'beforeUpdate',

'updated',

'beforeDestroy',

'destroyed',

]

LIFECYCLE_HOOKS.forEach((hook)=>{

strats[hook]=mergeHook;

})

/**

* 合并生命周期的钩子

* @param {*} parentValue

* @param {*} childValue

*/

function mergeHook(parentValue,childValue){

//有子

if(childValue){

//有父

if(parentValue)

{

//合并

return parentValue.concat(childValue);

}

else{

//返回

return [childValue];

}

}

else{

return parentValue;

}

}

生命周期的调用

调用方法

exportfunction callHook(vm,hook){

const hookCallbacks=vm.$options[hook] ||[];

for(let i=0;i<hookCallbacks.length;i++)

{

hookCallbacks[i].call(vm)

}

}

调用

以beforeCreate 和created 为例,在实现响应式处理数据前后分别调用。

 Vue.prototype._init=function(options){

const vm=this;

//将参数挂载到 vm 上

vm.$options = mergeOptions(vm.constructor.options,options);

callHook(vm,'beforeCreate');

initState(vm);

callHook(vm,'created');

if(vm.$options.el)

{

this.$mount(vm.$options.el);

}

}

测试

 Vue.mixin({

name2:"sss",

obj:{

a:1,

b:2

},

created:function(){

console.log('初始化了1');

}

})

Vue.mixin({

name3:"ssse",

obj:{

a:1,

b:3,

c:4

},

created:function(){

console.log('初始化了2');

}

})

var vm=new Vue({

el:"#app",

created:function(){

console.log('初始化了3');

}

})

结果

结束

简单了总结了一下Vue.mixin 方法和Vue 2的生命周期合并与调用,仅仅讲述的它的基本原理和简单实现。下一节整理总结Vue2依赖收集。

链接

  • Vue2.0源码学习2:juejin.im/post/5f0112…

以上是 Vue2的源码学习3:mixin 原理的实现以及生命周期的调用 的全部内容, 来源链接: utcz.com/a/31843.html

回到顶部