UNPKG

woby

Version:

A high-performance framework with fine-grained observable/signal-based reactivity for building rich applications.

80 lines (79 loc) 2.89 kB
"use strict"; const setters = require("./setters-CyO2VUT6.cjs"); const root = require("./root-D1a_tPqg.cjs"); const merge_style = require("./merge_style-DkxC2kon.cjs"); const render = (child, parent) => { if (!parent || !(parent instanceof HTMLElement)) throw new Error("Invalid parent node"); parent.textContent = ""; return root.root((stack, dispose) => { setters.setChild(parent, child, setters.FragmentUtils.make(), stack); return () => { dispose(stack); parent.textContent = ""; }; }); }; const Portal = ({ when = true, mount, wrapper, children }) => { const portal = setters.get(wrapper) || setters.createHTMLNode("div"); if (!(portal instanceof HTMLElement)) throw new Error("Invalid wrapper node"); const condition = merge_style.boolean(when); const stack = new Error(); setters.useRenderEffect(() => { if (!setters.get(condition)) return; const parent = setters.get(mount) || document.body; if (!(parent instanceof Element)) throw new Error("Invalid mount node"); parent.insertBefore(portal, null); return () => { parent.removeChild(portal); }; }, stack); setters.useRenderEffect(() => { if (!setters.get(condition)) return; return render(children, portal); }, stack); return setters.assign(() => setters.get(condition) || children, { metadata: { portal } }); }; const SuspenseCollector = { create: () => { const parent = SuspenseCollector.get(); const suspenses = merge_style.observable([]); const active = merge_style.memo(() => suspenses().some((suspense) => suspense.active())); const register = (suspense) => { parent == null ? void 0 : parent.register(suspense); suspenses((prev) => [...prev, suspense]); }; const unregister = (suspense) => { parent == null ? void 0 : parent.unregister(suspense); suspenses((prev) => prev.filter((other) => other !== suspense)); }; const data = { suspenses, active, register, unregister }; return data; }, get: () => { return setters.context(setters.SYMBOL_SUSPENSE_COLLECTOR); }, wrap: (fn) => { const data = SuspenseCollector.create(); return setters.context({ [setters.SYMBOL_SUSPENSE_COLLECTOR]: data }, () => { return merge_style.resolve(() => fn(data)); }); } }; const renderToString = (child) => { return new Promise((resolve) => { root.root((stack, dispose) => { setters.get(SuspenseCollector.wrap((suspenses) => { const { portal } = Portal({ children: child }).metadata; setters.effect((stack2) => { if (suspenses.active()) return; resolve(portal.innerHTML); dispose(stack2); }, { suspense: false, stack }); })); }); }); }; exports.Portal = Portal; exports.render = render; exports.renderToString = renderToString; //# sourceMappingURL=render_to_string-QEFRB-Fu.cjs.map