// Generated, do not edit. sha256:db0c8db151ef8689662b07ab525d02d912551c1706e34e778f8bcf4190dc7dc0 const VOID = new Set(['area', 'base', 'br', 'col', 'embed', 'hr', 'img', 'input', 'link', 'meta', 'source', 'track', 'wbr']); const RAW_TEXT = new Set(['textarea', 'script', 'style', 'title']); const SELF_CLOSING_OK = new Set(['svg', 'path', 'line', 'circle', 'rect', 'polyline', 'polygon', 'g', 'use']); const ENTITIES = { amp: '&', lt: '<', gt: '>', quot: '"', apos: "'" }; export function decodeEntities(s) { return s.replace(/&(#x[0-9a-f]+|#\d+|[a-z]+);/gi, (all, name) => { if (name[0] === '#') { const code = name[1] === 'x' || name[1] === 'X' ? parseInt(name.slice(2), 16) : parseInt(name.slice(1), 10); return Number.isFinite(code) ? String.fromCodePoint(code) : all; } return Object.prototype.hasOwnProperty.call(ENTITIES, name.toLowerCase()) ? ENTITIES[name.toLowerCase()] : all; }); } const escText = s => String(s).replace(/&/g, '&').replace(//g, '>'); const escAttr = s => String(s).replace(/&/g, '&').replace(/"/g, '"'); const hidden = (obj, key, value) => Object.defineProperty(obj, key, { value, writable: true, enumerable: false, configurable: true }); class Node { constructor(doc) { hidden(this, 'ownerDocument', doc); hidden(this, 'parentNode', null); this.childNodes = []; } get parentElement() { return this.parentNode instanceof Element ? this.parentNode : null; } get isConnected() { let n = this; while (n) { if (n === this.ownerDocument) return true; n = n.parentNode; } return false; } appendChild(child) { if (child.parentNode) child.parentNode._removeChild(child); child.parentNode = this; this.childNodes.push(child); return child; } append(...children) { for (const c of children) this.appendChild(c); } _removeChild(child) { const i = this.childNodes.indexOf(child); if (i >= 0) this.childNodes.splice(i, 1); child.parentNode = null; } remove() { if (this.parentNode) this.parentNode._removeChild(this); } contains(other) { for (let n = other; n; n = n.parentNode) if (n === this) return true; return false; } } class Text extends Node { constructor(doc, data) { super(doc); this.nodeType = 3; this.data = data; } get textContent() { return this.data; } set textContent(v) { this.data = String(v); } } class ClassList { constructor(el) { this.el = el; } _get() { return (this.el.getAttribute('class') || '').split(/\s+/).filter(Boolean); } _set(list) { this.el.setAttribute('class', list.join(' ')); } contains(c) { return this._get().includes(c); } add(...cs) { const l = this._get(); for (const c of cs) if (c && !l.includes(c)) l.push(c); this._set(l); } remove(...cs) { this._set(this._get().filter(c => !cs.includes(c))); } toggle(c, force) { const on = force === undefined ? !this.contains(c) : !!force; if (on) this.add(c); else this.remove(c); return on; } } const kebab = s => s.replace(/[A-Z]/g, m => '-' + m.toLowerCase()); const camel = s => s.replace(/-([a-z])/g, (_, c) => c.toUpperCase()); function makeStyle() { const props = new Map(); return new Proxy({ setProperty(k, v) { props.set(k, String(v)); }, getPropertyValue(k) { return props.get(k) ?? ''; }, removeProperty(k) { props.delete(k); }, }, { get(target, key) { return key in target ? target[key] : (props.get(kebab(String(key))) ?? ''); }, set(_t, key, v) { props.set(kebab(String(key)), String(v)); return true; }, }); } export class Element extends Node { constructor(doc, tag) { super(doc); this.nodeType = 1; this.localName = tag.toLowerCase(); this.attrs = new Map(); hidden(this, 'style', makeStyle()); hidden(this, 'classList', new ClassList(this)); hidden(this, 'listeners', []); this.scrollTop = 0; this.scrollLeft = 0; } get tagName() { return this.localName.toUpperCase(); } [Symbol.for('nodejs.util.inspect.custom')]() { const attrs = [...this.attrs].map(([k, v]) => (v === '' ? ` ${k}` : ` ${k}="${v}"`)).join(''); return `<${this.localName}${attrs}>`; } getAttribute(n) { return this.attrs.has(n.toLowerCase()) ? this.attrs.get(n.toLowerCase()) : null; } setAttribute(n, v) { this.attrs.set(n.toLowerCase(), String(v)); } removeAttribute(n) { this.attrs.delete(n.toLowerCase()); } hasAttribute(n) { return this.attrs.has(n.toLowerCase()); } get id() { return this.getAttribute('id') || ''; } set id(v) { this.setAttribute('id', v); } get className() { return this.getAttribute('class') || ''; } set className(v) { this.setAttribute('class', v); } get title() { return this.getAttribute('title') || ''; } set title(v) { this.setAttribute('title', v); } get src() { return this.getAttribute('src') || ''; } set src(v) { this.setAttribute('src', v); } get type() { return this.localName === 'input' ? (this.getAttribute('type') || 'text').toLowerCase() : (this.getAttribute('type') || ''); } set type(v) { this.setAttribute('type', v); } get disabled() { return this.hasAttribute('disabled'); } set disabled(v) { if (v) this.setAttribute('disabled', ''); else this.removeAttribute('disabled'); } get dataset() { const el = this; return new Proxy({}, { get(_t, key) { return typeof key === 'string' ? (el.getAttribute('data-' + kebab(key)) ?? undefined) : undefined; }, set(_t, key, v) { el.setAttribute('data-' + kebab(String(key)), v); return true; }, has(_t, key) { return el.hasAttribute('data-' + kebab(String(key))); }, ownKeys() { return [...el.attrs.keys()].filter(k => k.startsWith('data-')).map(k => camel(k.slice(5))); }, getOwnPropertyDescriptor(_t, key) { const v = el.getAttribute('data-' + kebab(String(key))); return v === null ? undefined : { value: v, enumerable: true, configurable: true }; }, }); } get children() { return this.childNodes.filter(n => n instanceof Element); } get value() { if (this.localName === 'select') { if (this._value !== undefined) return this._value; const opts = this.querySelectorAll('option'); const sel = opts.find(o => o.hasAttribute('selected')) || opts[0]; return sel ? sel.value : ''; } if (this.localName === 'option') return this.getAttribute('value') ?? this.textContent; if (this.localName === 'textarea') return this._value !== undefined ? this._value : this.textContent; return this._value !== undefined ? this._value : (this.getAttribute('value') ?? ''); } set value(v) { this._value = String(v); } get checked() { return this._checked !== undefined ? this._checked : this.hasAttribute('checked'); } set checked(v) { this._checked = !!v; } get selectionStart() { return this._selStart ?? this.value.length; } get selectionEnd() { return this._selEnd ?? this.value.length; } setSelectionRange(a, b) { this._selStart = a; this._selEnd = b; } get offsetHeight() { return 0; } get offsetWidth() { return 0; } get scrollHeight() { return 0; } get clientHeight() { return 0; } get clientWidth() { return 0; } getBoundingClientRect() { return { left: 0, top: 0, right: 0, bottom: 0, width: 0, height: 0 }; } scrollIntoView(opts) { this.ownerDocument.scrolledIntoView.push({ el: this, opts }); } focus() { this.ownerDocument.activeElement = this; } blur() { if (this.ownerDocument.activeElement === this) this.ownerDocument.activeElement = this.ownerDocument.body; } get innerHTML() { return this.childNodes.map(serialize).join(''); } set innerHTML(html) { for (const c of [...this.childNodes]) this._removeChild(c); for (const c of parseHTML(this.ownerDocument, String(html), this.localName)) this.appendChild(c); this._value = undefined; } get outerHTML() { return serialize(this); } get textContent() { return this.childNodes.map(n => n.textContent).join(''); } set textContent(v) { for (const c of [...this.childNodes]) this._removeChild(c); if (v !== '' && v != null) this.appendChild(new Text(this.ownerDocument, String(v))); } querySelectorAll(sel) { const list = parseSelector(sel); const out = []; walk(this, el => { if (list.some(s => matchComplex(el, s, this))) out.push(el); }); return out; } querySelector(sel) { return this.querySelectorAll(sel)[0] || null; } matches(sel) { return parseSelector(sel).some(s => matchComplex(this, s, null)); } closest(sel) { const list = parseSelector(sel); for (let n = this; n instanceof Element; n = n.parentNode) if (list.some(s => matchComplex(n, s, null))) return n; return null; } addEventListener(type, fn, opts) { this.listeners.push({ type, fn, capture: opts === true || !!(opts && opts.capture) }); } removeEventListener(type, fn, opts) { const capture = opts === true || !!(opts && opts.capture); this.listeners = this.listeners.filter(l => !(l.type === type && l.fn === fn && l.capture === capture)); } dispatchEvent(ev) { return dispatch(this, ev.type, { bubbles: ev.bubbles, ...pickInit(ev) }); } } function pickInit(ev) { const init = {}; for (const k of ['key', 'ctrlKey', 'metaKey', 'shiftKey', 'altKey', 'relatedTarget', 'detail']) if (ev[k] !== undefined) init[k] = ev[k]; return init; } function walk(root, fn) { for (const c of root.childNodes) { if (c instanceof Element) { fn(c); walk(c, fn); } } } function serialize(n) { if (n instanceof Text) return escText(n.data); if (!(n instanceof Element)) return ''; const attrs = [...n.attrs].map(([k, v]) => (v === '' ? ` ${k}` : ` ${k}="${escAttr(v)}"`)).join(''); if (VOID.has(n.localName)) return `<${n.localName}${attrs}>`; return `<${n.localName}${attrs}>${n.childNodes.map(serialize).join('')}`; } export function parseHTML(doc, html) { const root = new Element(doc, '#fragment'); const stack = [root]; const top = () => stack[stack.length - 1]; let i = 0; while (i < html.length) { if (html.startsWith('', i + 4); i = end < 0 ? html.length : end + 3; continue; } if (html[i] === '<' && html[i + 1] === '/') { const end = html.indexOf('>', i); const name = html.slice(i + 2, end < 0 ? html.length : end).trim().toLowerCase(); i = end < 0 ? html.length : end + 1; const at = stack.map(n => n.localName).lastIndexOf(name); if (at > 0) stack.length = at; continue; } if (html[i] === '<' && /[a-zA-Z]/.test(html[i + 1] || '')) { let j = i + 1, quote = null; for (; j < html.length; j++) { const ch = html[j]; if (quote) { if (ch === quote) quote = null; continue; } if (ch === '"' || ch === "'") { quote = ch; continue; } if (ch === '>') break; } let body = html.slice(i + 1, j); i = j + 1; const selfClose = body.endsWith('/'); if (selfClose) body = body.slice(0, -1); const name = body.match(/^[^\s/>]+/)[0].toLowerCase(); const el = new Element(doc, name); const attrRe = /([^\s"'>\/=]+)(?:\s*=\s*(?:"([^"]*)"|'([^']*)'|([^\s"'=<>`]+)))?/g; const rest = body.slice(name.length); let m; while ((m = attrRe.exec(rest))) { const v = m[2] ?? m[3] ?? m[4] ?? ''; el.setAttribute(m[1], decodeEntities(v)); } top().appendChild(el); if (VOID.has(name) || (selfClose && SELF_CLOSING_OK.has(name))) continue; if (RAW_TEXT.has(name)) { const close = html.toLowerCase().indexOf(`', close); i = end < 0 ? html.length : end + 1; continue; } stack.push(el); continue; } const next = html.indexOf('<', i + 1); const text = html.slice(i, next < 0 ? html.length : next); i = next < 0 ? html.length : next; if (text) top().appendChild(new Text(doc, decodeEntities(text))); } const nodes = [...root.childNodes]; for (const n of nodes) root._removeChild(n); return nodes; } const cache = new Map(); export function parseSelector(sel) { if (cache.has(sel)) return cache.get(sel); const list = splitTop(sel, ',').map(s => s.trim()).filter(Boolean).map(parseComplex); if (!list.length) throw new Error(`mini-dom: empty selector "${sel}"`); cache.set(sel, list); return list; } function splitTop(s, sep) { const out = []; let depth = 0, quote = null, start = 0; for (let i = 0; i < s.length; i++) { const ch = s[i]; if (quote) { if (ch === quote) quote = null; continue; } if (ch === '"' || ch === "'") quote = ch; else if (ch === '(' || ch === '[') depth++; else if (ch === ')' || ch === ']') depth--; else if (ch === sep && depth === 0) { out.push(s.slice(start, i)); start = i + 1; } } out.push(s.slice(start)); return out; } function parseComplex(s) { const parts = []; let i = 0; let combinator = null; while (i < s.length) { if (/\s/.test(s[i]) || s[i] === '>') { let comb = ' '; while (i < s.length && (/\s/.test(s[i]) || s[i] === '>')) { if (s[i] === '>') comb = '>'; i++; } if (parts.length) combinator = comb; continue; } const [compound, next] = parseCompound(s, i); if (parts.length) parts[parts.length - 1].combinator = combinator || ' '; parts.push({ compound, combinator: null }); combinator = null; i = next; } return parts; } function parseCompound(s, i) { const c = { tag: null, id: null, classes: [], attrs: [], nots: [] }; const ident = (k) => { const m = s.slice(k).match(/^[A-Za-z0-9_-]+/); if (!m) throw new Error(`mini-dom: unsupported selector "${s}"`); return m[0]; }; if (s[i] === '*') i++; else if (/[A-Za-z]/.test(s[i])) { c.tag = ident(i).toLowerCase(); i += c.tag.length; } while (i < s.length && !/[\s>]/.test(s[i])) { const ch = s[i]; if (ch === '#') { const n = ident(i + 1); c.id = n; i += 1 + n.length; } else if (ch === '.') { const n = ident(i + 1); c.classes.push(n); i += 1 + n.length; } else if (ch === '[') { const end = findClose(s, i, '[', ']'); const inner = s.slice(i + 1, end).trim(); const m = inner.match(/^([A-Za-z0-9_:-]+)\s*(?:=\s*(?:"([^"]*)"|'([^']*)'|([^\s\]]+)))?$/); if (!m) throw new Error(`mini-dom: unsupported attribute selector "[${inner}]"`); c.attrs.push({ name: m[1].toLowerCase(), value: m[2] ?? m[3] ?? m[4] ?? null }); i = end + 1; } else if (s.startsWith(':not(', i)) { const end = findClose(s, i + 4, '(', ')'); c.nots.push(parseSelector(s.slice(i + 5, end))); i = end + 1; } else { throw new Error(`mini-dom: unsupported selector "${s}" at "${s.slice(i)}"`); } } return [c, i]; } function findClose(s, open, a, b) { let depth = 0, quote = null; for (let k = open; k < s.length; k++) { const ch = s[k]; if (quote) { if (ch === quote) quote = null; continue; } if (ch === '"' || ch === "'") quote = ch; else if (ch === a) depth++; else if (ch === b && --depth === 0) return k; } throw new Error(`mini-dom: unclosed "${a}" in selector "${s}"`); } function matchCompound(el, c) { if (!(el instanceof Element)) return false; if (c.tag && el.localName !== c.tag) return false; if (c.id && el.getAttribute('id') !== c.id) return false; for (const k of c.classes) if (!el.classList.contains(k)) return false; for (const a of c.attrs) { if (!el.hasAttribute(a.name)) return false; if (a.value !== null && el.getAttribute(a.name) !== a.value) return false; } for (const list of c.nots) if (list.some(s => matchComplex(el, s, null))) return false; return true; } function matchComplex(el, parts, _scope) { const at = (k, node) => { if (!matchCompound(node, parts[k].compound)) return false; if (k === 0) return true; const comb = parts[k - 1].combinator; if (comb === '>') return node.parentNode instanceof Element && at(k - 1, node.parentNode); for (let p = node.parentNode; p instanceof Element; p = p.parentNode) if (at(k - 1, p)) return true; return false; }; return at(parts.length - 1, el); } export function dispatch(target, type, init = {}) { const doc = target.ownerDocument || target; let stopped = false; const ev = { type, target, bubbles: init.bubbles !== false, defaultPrevented: false, currentTarget: null, key: init.key, ctrlKey: !!init.ctrlKey, metaKey: !!init.metaKey, shiftKey: !!init.shiftKey, altKey: !!init.altKey, relatedTarget: init.relatedTarget ?? null, detail: init.detail ?? null, stopPropagation() { stopped = true; }, stopImmediatePropagation() { stopped = true; }, preventDefault() { this.defaultPrevented = true; }, }; const path = []; for (let n = target; n; n = n.parentNode) path.push(n); if (path[path.length - 1] !== doc) path.push(doc); const run = (node, capture) => { ev.currentTarget = node; if (!capture && typeof node['on' + type] === 'function') node['on' + type](ev); for (const l of [...(node.listeners || [])]) if (l.type === type && l.capture === capture) l.fn(ev); }; for (let k = path.length - 1; k > 0 && !stopped; k--) run(path[k], true); if (!stopped) { run(target, true); if (!stopped) run(target, false); } if (ev.bubbles) for (let k = 1; k < path.length && !stopped; k++) run(path[k], false); return !ev.defaultPrevented; } class Document extends Node { constructor() { super(null); this.ownerDocument = this; this.listeners = []; this.documentElement = new Element(this, 'html'); this.head = new Element(this, 'head'); this.body = new Element(this, 'body'); this.appendChild(this.documentElement); this.documentElement.appendChild(this.head); this.documentElement.appendChild(this.body); this.activeElement = this.body; this.scrolledIntoView = []; } [Symbol.for('nodejs.util.inspect.custom')]() { return '#document'; } createElement(tag) { return new Element(this, tag); } createTextNode(t) { return new Text(this, t); } querySelectorAll(sel) { return this.documentElement.querySelectorAll(sel); } querySelector(sel) { return this.documentElement.querySelector(sel); } getElementById(id) { return this.querySelector(`#${id}`); } addEventListener(type, fn, opts) { Element.prototype.addEventListener.call(this, type, fn, opts); } removeEventListener(type, fn, opts) { Element.prototype.removeEventListener.call(this, type, fn, opts); } dispatchEvent(ev) { return dispatch(this, ev.type, { bubbles: ev.bubbles, ...pickInit(ev) }); } } export function installDom() { const document = new Document(); const frames = []; const win = { innerWidth: 1280, innerHeight: 800, listeners: [], addEventListener(type, fn, opts) { Element.prototype.addEventListener.call(this, type, fn, opts); }, removeEventListener(type, fn, opts) { Element.prototype.removeEventListener.call(this, type, fn, opts); }, }; globalThis.document = document; globalThis.window = win; globalThis.requestAnimationFrame = fn => { frames.push(fn); return frames.length; }; globalThis.getComputedStyle = el => ({ getPropertyValue: k => el.style.getPropertyValue(k) }); const fire = (el, type, init) => dispatch(el, type, init); return { document, window: win, fire, click: el => fire(el, 'click'), type(el, value) { el.value = value; fire(el, 'input'); fire(el, 'change'); }, choose(el, value) { el.value = value; fire(el, 'change'); }, key: (el, key, mods = {}) => fire(el, 'keydown', { key, ...mods }), flushFrames() { while (frames.length) frames.shift()(); }, host() { const el = document.createElement('div'); document.body.appendChild(el); return el; }, }; }