首页 > 代码库 > 一个简单的MVVM雏形
一个简单的MVVM雏形
这是@尚春实现的MVVM,使用定时器轮询,只支持{{}}与input.value的修改。
这只能算是一个玩具,真正的MVVM需要有更复杂的扫描机制,JS解析器,双向绑定链什么的。
<!DOCTYPE html><html><head><script src="http://cdnjs.cloudflare.com/ajax/libs/lodash.js/2.4.1/lodash.min.js"></script> <meta charset="utf-8"> <title>JS Bin</title> </head><body> <div data-component="input"> <template> <input type="text" name="username" tb-model="username" value="" /> <span>{{ username }}</span> </template> </div> <script>var DIRECTIVE_ATTR_MODEL = ‘tb-model‘, regMustache = /\{\{\s*(\w+)\s*\}\}/g, slice = Array.prototype.slice;function boot() { var components = slice.call(document.querySelectorAll(‘[data-component]‘), 0); components.forEach(function (el) { var component = el.getAttribute(‘data-component‘); bootComponent(el, window[component + ‘Controller‘]); });}function bootComponent(el, controller) { var $scope = {}, elFrag = el.querySelector(‘template‘).content.cloneNode(true); traverse(elFrag, $scope); el.appendChild(elFrag); controller($scope);}function traverse(root, $scope) { for (var el = root.firstChild; el; el = el.nextSibling) { parseElement(el, $scope); if (el) { traverse(el, $scope); } }}function parseElement(el, $scope) { if (el.nodeType === 1) { // element if (el.hasAttribute(DIRECTIVE_ATTR_MODEL)) { var model = el.getAttribute(DIRECTIVE_ATTR_MODEL); el.removeAttribute(DIRECTIVE_ATTR_MODEL); el.addEventListener(‘input‘, function () { $scope[model] = this.value; }); } } else if (el.nodeType === 3) { // text node var text = el.textContent, tpl = [], lastIndex = 0, match = regMustache.exec(text); while (match) { tpl.push(text.substring(lastIndex, regMustache.lastIndex - match[0].length)); tpl.push({ type: ‘var‘, content: match[1] }); lastIndex = regMustache.lastIndex; match = regMustache.exec(text); } watch($scope, function () { text = ‘‘; tpl.forEach(function (item) { text += typeof item === ‘string‘ ? item : $scope[item.content]; }); el.textContent = text; }); }}function watch($scope, cb) { var old = _.cloneDeep($scope), timer; timer = setInterval(function () { if (!_.isEqual($scope, old)) { cb($scope, old); old = _.cloneDeep($scope); } }, 50);}function inputController($scope) { $scope.username = ‘spring‘;}boot(); </script></body></html>
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。