根据vue的官网介绍,可以得知vue是一个mvvm框架,且是响应式的。为了更深入了理解其内涵,本人以及理解实现了一个简单的mvvm学习的demo。下面分享给大家,欢迎大家一起讨论。
指令集合,如:text、model等
数据模型,与视图交互的数据
组件的支持:也就是部分html代码的动态更新

立即学习“前端免费学习笔记(深入)”;
var directives = {}; //指令集合var vNodes = new Array(); //解析的Dom集合var dataModel = {
name:"name",
title: "title"}; //数据Modelvar Watch = {
isInit: false,
watchs: new Array(),
run: function(newValue, expOrfn){ var self = this;if(!self.isInit){
expOrfn.call(vModel);
}this.watchs.map(function(data,index){
data.nodes.map(function(d,i){if(self.isInit){
d.directive.init(newValue, d, data); //绑定初始化值, 以及初始化一些事件}else{
d.directive.update(newValue, d, data); //只更新值,此时run的调用来值value-set }
});
});
self.watchs = [];
},
push:function(watch){this.watchs.push(watch);
}
} //任务管理说明:
Watch的push方法,用于依赖的添加,然后run来执行所以依赖,执行完成后,需要清理当前依赖的集合。在vue中依赖的收集是在dep中完成的,而watch提供的任务管理(不知道理解是否正确)
directives.text = {
init: function(value, vNode){
vNode.elm.textContent = value;
},
update: function(value, vNode){
vNode.elm.textContent = value;
}
}//需要响应事件的怎么办directives.model ={
init: function(value, vNode, _watch){
vNode.elm.value = value; //判断自己发生的改变,不应该再改变自己 vNode.elm.addEventListener('keyup',function(evt){
vNode.model[_watch.key] = vNode.elm.value;
});
},
update:function(){
}
}说明:
由于是demo学习示例,所以只定义了简单的text和model两个指定,text:用于数据的显示,而model用于input(输入框)的响应
一、源码特点采用典型的三层架构进行开发,包含购物车、登陆注册、个人中心、留言板、新闻系统,前台页面、后台管理等二、功能介绍本源码是一个三层购物网站源码,功能齐全,界面美观简洁,非常适合二次开发和学习,欢迎下载三、菜单功能前台页面1、注册2、登陆3、首页4、购物车5、会员中心6、收藏家7、客服中心8、留言板后台管理1、管理员系统:管理员列表;管理员添加2、会员管理系统:会员列表3、新闻系统:新闻列表
0
//转换vModel,暂支持一级var properties = Object.getOwnPropertyNames(dataModel);var vModel = {}, formSetting = false;for( var index in properties){
(function refreshData(_index){var key = properties[_index];var property = Object.getOwnPropertyDescriptor(dataModel, key);var setter = property.set;var getter = property.get;var _val = property.value;var _getter = function(){var val = getter ? getter.call(vModel) : _val;//收集依赖,与watch要分开 Watch.push({
key: key,
nodes: vNodes.filter(function(data,index){return data.modelKey == key ? true : false;
}),
getter: _getter
});return val;
};
Object.defineProperty(vModel, key, {
configurable: true,
enumerable: true,
set: function(value){if(setter){
setter.call(vModel, value);
} //处理依赖 Watch.run(value, _getter);//this.value = value; },
get: _getter
})
})(index);
}说明:
vModel是根据dataModel生成的,也就是自定义了每个属性的get和set方法,在es6中也可以用proxy实现(是否说对了)。
在属性set的时候,会先调用get方法来收集依赖。方便值改变后,能将所影响的内容都修改掉。
//解析vNodesvar app = document.getElementById('app');
app.childNodes.forEach(function(data,index){if(data.nodeType != 1) return;var hv = data.getAttribute('data-hv');var hvs = hv.split(',');
hvs.forEach(function(item,row){var keyValue = item.split(':'); //vNode对象上一定要有model,这是方便vNode相应时候的找vModel vNodes.push({
directive: directives[keyValue[0]],
modelKey: keyValue[1],
model: vModel,
elm: data
});
});
});说明:
这里说解析为vNode很是牵强,因为此只是收集了dom上data-hv指定的指令,并将对就的指令、元素、vModel等组成一个对象存储在vNodes中,以供vModel各属性的get方法收集依赖时引用。
//调用所有的get一次Watch.isInit = true;var _keys = Object.getOwnPropertyNames(vModel);
_keys.map(function(key,data){var data = vModel[key];
Watch.run(data);
});
Watch.isInit = false;说明:
将初始化的vModel的值渲染到Dom上,这里是主动执行每个的get,然后运行watch.run方法。
此处设计和实现本人感觉与vue的思路不对,如有高人看见,麻烦提点与指引。
<div id="app"><span data-hv="text:title"></span><span data-hv="text:title"></span><input data-hv="model:title" /></div>
以上就是一起学习理解vue源码的详细内容,更多请关注php中文网其它相关文章!
每个人都需要一台速度更快、更稳定的 PC。随着时间的推移,垃圾文件、旧注册表数据和不必要的后台进程会占用资源并降低性能。幸运的是,许多工具可以让 Windows 保持平稳运行。
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号