You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
234 lines
4.8 KiB
234 lines
4.8 KiB
|
2 weeks ago
|
const $boot = (cb) => {
|
||
|
|
document.addEventListener("DOMContentLoaded", cb);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $sanitize = (badHTML) => {
|
||
|
|
// this Option hack courtesy of stackoverflow
|
||
|
|
return new Option(badHTML).innerHTML;
|
||
|
|
}
|
||
|
|
|
||
|
|
const validate_sanitized = (sanitized) => {
|
||
|
|
const check = JSON.stringify(sanitized);
|
||
|
|
console.assert(!check.includes("<"),
|
||
|
|
"YOU BEEN HACKED! Send Zed this:", sanitized);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $sanitize_data = (data) => {
|
||
|
|
const sanitized = $sanitize(JSON.stringify(data));
|
||
|
|
validate_sanitized(sanitized);
|
||
|
|
return JSON.parse(sanitized);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $render = (template, data) => {
|
||
|
|
const sanitized = $sanitize_data(data);
|
||
|
|
|
||
|
|
const args = Object.keys(sanitized);
|
||
|
|
const values = Object.values(sanitized)
|
||
|
|
|
||
|
|
const render_func = new Function(...args,
|
||
|
|
`return \`${template.innerHTML}\``)
|
||
|
|
|
||
|
|
const text = render_func(...values);
|
||
|
|
|
||
|
|
return $html(text);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $render_data = (template_id, target_id, data) => {
|
||
|
|
const target = $id(target_id);
|
||
|
|
const template = $id(template_id);
|
||
|
|
let new_data = [];
|
||
|
|
|
||
|
|
if(Array.isArray(data)) {
|
||
|
|
new_data = data.map((item, i) => {
|
||
|
|
return $render(template, {i, item});
|
||
|
|
});
|
||
|
|
} else if(data instanceof Object) {
|
||
|
|
console.log("object rendering", data);
|
||
|
|
new_data.push($render(template, data));
|
||
|
|
} else {
|
||
|
|
console.error("$render only works with {} or [] data", data);
|
||
|
|
new_data.push($html("<b>ERROR LOOK IN CONSOLE</b>"));
|
||
|
|
}
|
||
|
|
|
||
|
|
$replace_with(target, new_data);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $get = (name, inChildren) => {
|
||
|
|
if(inChildren) {
|
||
|
|
return inChildren.querySelector(name);
|
||
|
|
} else {
|
||
|
|
return document.querySelector(name);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
const $all = (name, inChildren) => {
|
||
|
|
if(inChildren) {
|
||
|
|
return inChildren.querySelectorAll(name);
|
||
|
|
} else {
|
||
|
|
return document.querySelectorAll(name);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
const $id = (name, inChildren) => {
|
||
|
|
if(inChildren) {
|
||
|
|
return inChildren.children.namedItem(name);
|
||
|
|
} else {
|
||
|
|
return document.getElementById(name);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
const $class = (name) => {
|
||
|
|
return document.getElementsByClassName(name);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $name = (name) => {
|
||
|
|
return document.getElementsByTagName(name);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $filter = (nodes, fn) => {
|
||
|
|
return Array.prototype.filter.call(nodes, fn);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $next = (node) => {
|
||
|
|
return node.nextElementSibling;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $previous = (node) => {
|
||
|
|
return node.previousElementSibling;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $siblings = (node) => {
|
||
|
|
return $filter(node.parentNode.children,
|
||
|
|
child => { return child !== node; });
|
||
|
|
}
|
||
|
|
|
||
|
|
const $style_toggle = (node, className) => {
|
||
|
|
node.classList.toggle(className);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $style_add = (node, className) => {
|
||
|
|
node.classList.add(className);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $style_del = (node, className) => {
|
||
|
|
node.classList.remove(className);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $style_of = (node, ruleName) => {
|
||
|
|
return getComputedStyle(node)[ruleName]
|
||
|
|
}
|
||
|
|
|
||
|
|
const $new = (tag, id, html) => {
|
||
|
|
let new_tag = document.createElement(tag);
|
||
|
|
new_tag.id = id;
|
||
|
|
new_tag.innerHTML = html;
|
||
|
|
return new_tag.cloneNode(true);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $append = (parent, child) => {
|
||
|
|
parent.appendChild(child);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $prepend = (parent, node) => {
|
||
|
|
parent.insertBefore(node, parent.firstChild);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $remove = (parent, child) => {
|
||
|
|
parent.removeChild(child);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $clone = (node) => {
|
||
|
|
return node.cloneNode(true);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $contains = (node, child) => {
|
||
|
|
return node !== child && node.contains(child);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $has = (node, selector) => {
|
||
|
|
return node.querySelector(selector) !== null;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $empty = (node) => {
|
||
|
|
return node.innerHTML == '';
|
||
|
|
}
|
||
|
|
|
||
|
|
const $attribute_of = (node, name) => {
|
||
|
|
return node.getAttribute(name);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $attribute = (node, name, value) => {
|
||
|
|
return node.setAttribute(name, value);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $contents_of = (node) => {
|
||
|
|
return node.innerHTML;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $contents = (node, newhtml) => {
|
||
|
|
node.innerHTML = newhtml;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $has_class = (node, className) => {
|
||
|
|
return node.classList.contains(className);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $outer_html = (node) => {
|
||
|
|
return node.outerHTML;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $replace_with = (node, newNodes) => {
|
||
|
|
node.replaceChildren(...newNodes);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $matches = (node, selector) => {
|
||
|
|
return node.matches(selector);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $parent = (node) => {
|
||
|
|
return node.parentNode;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $text_of = (node) => {
|
||
|
|
return node.textContent;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $text = (node, newtext) => {
|
||
|
|
node.textContent = newtext;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $off = (node, eventName, eventHandler) => {
|
||
|
|
node.removeEventListener(eventName, eventHandler);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $on = (node, eventName, eventHandler) => {
|
||
|
|
node.addEventListener(eventName, eventHandler);
|
||
|
|
}
|
||
|
|
|
||
|
|
const $now = () => {
|
||
|
|
return Date.now();
|
||
|
|
}
|
||
|
|
|
||
|
|
const $html = (htmlString) => {
|
||
|
|
const temp = document.createElement('template');
|
||
|
|
temp.innerHTML = htmlString;
|
||
|
|
return temp.content;
|
||
|
|
}
|
||
|
|
|
||
|
|
const $observe = (node_id, cb) => {
|
||
|
|
const options = {
|
||
|
|
root: document,
|
||
|
|
rootMargin: "0px",
|
||
|
|
scrollMargin: "0px",
|
||
|
|
threshold: 1.0,
|
||
|
|
delay: 200,
|
||
|
|
};
|
||
|
|
|
||
|
|
const callback = (entries, observer) => {
|
||
|
|
cb();
|
||
|
|
}
|
||
|
|
|
||
|
|
const observer = new IntersectionObserver(callback, options);
|
||
|
|
observer.observe($id(node_id));
|
||
|
|
}
|