static/js/util/render.js (85 lines of code) (raw):

var util = { isObject: function (object) { return Object.prototype.toString.call(object) === '[object Object]'; }, isArray: function (object) { return Object.prototype.toString.call(object) === '[object Array]'; }, selectorPatterns: [ { name: 'class', regex: new RegExp('\\.([a-zA-Z0-9-_])*') }, { name: 'id', regex: new RegExp('#([a-zA-Z0-9-_])*') } ], parseSelector: function (selector) { var patterns = util.selectorPatterns, props = {}, value = ''; for (var i = 0, len = patterns.length; i < len; i++) { var pattern = patterns[i]; var regex = pattern.regex; while (regex.test(selector)) { var matches = regex.exec(selector); selector = selector.replace(matches[0], ''); value = matches[0].substring(1); if (pattern.name in props) { props[pattern.name] += ' ' + value; } else { props[pattern.name] = value; } } } if (selector !== '') { props['tag'] = selector; } else { props['tag'] = 'div'; } return props; } }; /** * @param {Array} data * @param {HTMLElement} target [optional] * @returns {DocumentFragment} */ function render(data, target) { var context = target || document.createDocumentFragment(), dataLength = data.length, i, item, elem, props, attrName, isNull; for (i = 0; i < dataLength; i++) { item = data[i]; isNull = item === null || item === undefined || item === false; if (isNull) { continue; } // text node if (typeof item === 'string' || typeof item === 'number') { context.appendChild(document.createTextNode(item)); continue; } // _elem if (typeof item[0] === 'string') { props = util.parseSelector(item[0]); elem = document.createElement(props.tag); item.shift(); delete props.tag; if (util.isObject(item[0])) { for (attrName in item[0]) { props[attrName] = item[0][attrName]; } } for (attrName in props) { elem.setAttribute(attrName, props[attrName]); delete props[attrName]; } context.appendChild(render(item, elem)); continue; } // node if (item.nodeType !== undefined) { context.appendChild(item); continue; } render(item, context); } return context; } module.exports = render;