前言
上一篇《前端mvvm框架学习(四、json对象+数组处理)》介绍了我们如何实现一个简单的MVVM处理内含数组对象数据的例子。真实项目中,我们要处理的内容其实不只是数据,还有css及style样式处理,怎么简单怎么来吧,我们还是引用lodash库和还是用传统的方式拼接html字符串的方式来处理View层吧,还是使用模版函数来处理,直接用lodash的template函数,然后我们引入了virtual node虚拟节点的概念,专门用来处理后期样式处理。
接着上一篇的代码,添加对json对象中的数组的处理,使用lodash模版函数生成html串
See the Pen MVVM Object with Style and ClassNames by Nelson Kuang (@nelsonkuang) on CodePen
1
VIEW层代码:
<div id="school" class="school">
<h3>XX Middle School</h3>
<ul>
<li>Class 18</li>
<li>Grade 03</li>
</ul>
</div>
MODEL层代码 :
// --------- Model层 ----------
var newPerson = {
school: {
name: "XX Middle School",
classNumber: "18",
grade: "03",
vitualNode: {
selector: "#school"
}
}
};
VIEWMODEL层代码:
// --------- viewModel层 ---------- function updateSchool(newVal, oldVal) { var el = document.querySelector(newVal.vitualNode.selector || "#school") // 传统的拼接html字符串的方式实现更新视图View var compiled = _.template( " <h3>${ name }</h3> <ul> <li>Class ${ classNumber }</li> <li>Grade ${ grade }</li> </ul> " ); el.innerHTML = compiled(newVal) if (newVal.vitualNode.data) { newVal.vitualNode.data.classNames && (el.className = newVal.vitualNode.data.classNames) // className处理 if (newVal.vitualNode.data.style) { Object.keys(newVal.vitualNode.data.style).forEach(function(key) { // style处理 el.style[key] = newVal.vitualNode.data.style[key] }); } } } Object.defineProperty(newPerson, "school", { set: function(x) { if (!_.isEqual(x, this.oldPropValue)) { // 数组或者对象的比较与普通的数值的比较不一样,要深度遍历进行比较 console.log(x) updateSchool(x, this.oldPropValue) this.oldPropValue = x } else { console.log("school的值没变") } }, get: function() { console.log("in property get accessor") return this.oldPropValue }, enumerable: true, configurable: true });
现在尝试更新MODEL层数据,VIEW层应该就可以自动更新了。
setTimeout(function() {
newPerson.school = {
name: "YY Middle School",
classNumber: "10",
grade: "01",
vitualNode: { // 引入了Virtual Node概念
selector: "#school",
data: {
classNames: "school school--yellow",
style: {
textShadow:
"3px 3px 3px #720005, -3px -3px 3px #720005,3px 0 3px #720005,0 3px 3px #720005,0 -3px 3px #720005, -3px 0 3px #720005",
borderRadius: "10px"
}
}
}
};
}, 5000);
结束语
通过上面的demo我们可以知道,处理带css或者style样式的json对象其实在实际项目中也是必然会遇到的,上面我们开始使用在模版函数的字符串里嵌入可执行Js代码的方式处理方式来处理并生成html做出MVVM的风格,然后生成Dom节点后再根据virtual dom的样式来相应添加classNames及style,这种做法感觉还是比较原始,但勉强达到我们要变更节点样式的要求,下一篇我们继续来优化上面的Demo,看看可以玩出什么花样。