hmn/public/js/templates.js

69 lines
1.8 KiB
JavaScript

var domLookupCache = {};
var templatePathCache = {};
function getTemplateEl(id) {
if (!domLookupCache[id]) {
domLookupCache[id] = document.getElementById(id);
}
return domLookupCache[id];
}
function collectElements(paths, rootElement) {
var result = {};
for (var i = 0; i < paths.length; ++i) {
var path = paths[i];
var current = rootElement;
for (var j = 0; j < path[1].length; ++j) {
current = current.children[path[1][j]];
}
result[path[0]] = current;
}
return result;
}
function getTemplatePaths(id, rootElement) {
if (!templatePathCache[id]) {
var paths = [];
paths.push(["root", []]);
function descend(path, el) {
for (var i = 0; i < el.children.length; ++i) {
var child = el.children[i];
var childPath = path.concat([i]);
var tmplName = child.getAttribute("data-tmpl");
if (tmplName) {
paths.push([tmplName, childPath]);
}
if (child.children.length > 0) {
descend(childPath, child);
}
}
}
descend([], rootElement);
templatePathCache[id] = paths;
}
return templatePathCache[id];
}
function makeTemplateCloner(id) {
return function() {
var templateEl = getTemplateEl(id);
if (templateEl === null) {
throw new Error(`Couldn\'t find template with ID '${id}'`);
}
var root = templateEl.content.cloneNode(true);
var paths = getTemplatePaths(id, root);
var result = collectElements(paths, root);
return result;
};
}
function emptyElement(el) {
var newEl = el.cloneNode(false);
el.parentElement.insertBefore(newEl, el);
el.parentElement.removeChild(el);
return newEl;
}