diff --git a/dist/sigpro.esm.js b/dist/sigpro.esm.js index 2bf4841..5c27245 100644 --- a/dist/sigpro.esm.js +++ b/dist/sigpro.esm.js @@ -33,7 +33,7 @@ var dispose = (eff) => { } } }; -var _onUnmount = (fn) => { +var onUnmount = (fn) => { if (activeOwner) (activeOwner._cleanups ||= new Set).add(fn); }; @@ -151,7 +151,7 @@ var $ = (val, key = null) => { computed._disposed = false; computed.stop = () => {}; if (activeOwner) - _onUnmount(computed.stop); + onUnmount(computed.stop); return computed; } if (key) @@ -175,44 +175,44 @@ var $ = (val, key = null) => { var $$ = (target) => { if (!isObj(target)) return target; - let proxy = proxyCache.get(target); - if (proxy) - return proxy; - const subsMap = new Map; - const getSubs = (k) => { - let s = subsMap.get(k); - if (!s) - subsMap.set(k, s = new Set); - return s; + const cached = proxyCache.get(target); + if (cached) + return cached; + const subs = new Map; + const getSubs = (key) => { + let set = subs.get(key); + if (!set) + subs.set(key, set = new Set); + return set; }; - proxy = new Proxy(target, { - get(t, k, receiver) { - if (typeof k !== "symbol") - trackUpdate(getSubs(k)); - return $$(Reflect.get(t, k, receiver)); + const proxy = new Proxy(target, { + get(target2, key, receiver) { + if (typeof key !== "symbol") + trackUpdate(getSubs(key)); + return $$(Reflect.get(target2, key, receiver)); }, - set(t, k, v, receiver) { - const isNew = !Reflect.has(t, k); - const oldV = Reflect.get(t, k, receiver); - const result = Reflect.set(t, k, v, receiver); - if (result && !Object.is(oldV, v)) { - trackUpdate(getSubs(k), true); - if (isNew) + set(target2, key, value, receiver) { + const hadKey = Reflect.has(target2, key); + const oldValue = Reflect.get(target2, key, receiver); + const result = Reflect.set(target2, key, value, receiver); + if (result && !Object.is(oldValue, value)) { + trackUpdate(getSubs(key), true); + if (!hadKey) trackUpdate(getSubs(ITER), true); } return result; }, - deleteProperty(t, k) { - const result = Reflect.deleteProperty(t, k); + deleteProperty(target2, key) { + const result = Reflect.deleteProperty(target2, key); if (result) { - trackUpdate(getSubs(k), true); + trackUpdate(getSubs(key), true); trackUpdate(getSubs(ITER), true); } return result; }, - ownKeys(t) { + ownKeys(target2) { trackUpdate(getSubs(ITER)); - return Reflect.ownKeys(t); + return Reflect.ownKeys(target2); } }); proxyCache.set(target, proxy); @@ -305,7 +305,7 @@ var h = (tag, props = {}, children = []) => { el.addEventListener(ev, v); const off = () => el.removeEventListener(ev, v); el._cleanups.add(off); - _onUnmount(off); + onUnmount(off); } else if (isFunc(v)) { const effect = createEffect(() => { const val = validateAttr(k, v()); @@ -320,7 +320,7 @@ var h = (tag, props = {}, children = []) => { }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); if (/^(INPUT|TEXTAREA|SELECT)$/.test(el.tagName) && (k === "value" || k === "checked")) { const evType = k === "checked" ? "change" : "input"; el.addEventListener(evType, (ev) => v(ev.target[k])); @@ -366,7 +366,7 @@ var h = (tag, props = {}, children = []) => { }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); } else { const node = ensureNode(c); el.appendChild(node); @@ -379,13 +379,12 @@ var h = (tag, props = {}, children = []) => { }; var render = (renderFn) => { const cleanups = new Set; - const mounts = []; const previousOwner = activeOwner; const previousEffect = activeEffect; const container = doc.createElement("div"); container.style.display = "contents"; container.setAttribute("role", "presentation"); - activeOwner = { _cleanups: cleanups, _mounts: mounts }; + activeOwner = { _cleanups: cleanups }; activeEffect = null; const processResult = (result) => { if (!result) @@ -405,7 +404,6 @@ var render = (renderFn) => { activeOwner = previousOwner; activeEffect = previousEffect; } - mounts.forEach((fn) => fn()); return { _isRuntime: true, container, @@ -449,7 +447,7 @@ var when = (cond, render2, { enter, leave } = {}) => { } } }); - return _onUnmount(() => view?.destroy()), wrap; + return onUnmount(() => view?.destroy()), wrap; }; var each = (src, itemFn, keyFn) => { const anchor = doc.createTextNode(""); @@ -488,7 +486,7 @@ var router = (routes) => { const path = $(getHash()); const handler = () => path(getHash()); window.addEventListener("hashchange", handler); - _onUnmount(() => window.removeEventListener("hashchange", handler)); + onUnmount(() => window.removeEventListener("hashchange", handler)); const hook = h("div", { class: "router-hook" }); let currentView = null; watch([path], () => { diff --git a/dist/sigpro.esm.min.js b/dist/sigpro.esm.min.js index bcac585..816de36 100644 --- a/dist/sigpro.esm.min.js +++ b/dist/sigpro.esm.min.js @@ -1 +1 @@ -var y=(e)=>typeof e==="function",j=(e)=>e&&typeof e==="object",b=Array.isArray,E=typeof document<"u"?document:null,B=(e)=>e?._isRuntime?e.container:e instanceof Node?e:E.createTextNode(e==null?"":String(e)),u=null,_=null,S=!1,O=0,A=new Set,k=new WeakMap,T=Symbol("iter"),L=new WeakMap,g=(e)=>{if(!e||e._disposed)return;e._disposed=!0;let n=[e];while(n.length){let t=n.pop();if(t._cleanups)t._cleanups.forEach((r)=>r()),t._cleanups.clear();if(t._children)t._children.forEach((r)=>n.push(r)),t._children.clear();if(t._deps)t._deps.forEach((r)=>r.delete(t)),t._deps.clear()}},v=(e)=>{if(_)(_._cleanups||=new Set).add(e)},W=(e)=>{let n=u;u=null;try{return e()}finally{u=n}},x=(e,n=!1)=>{let t=()=>{if(t._disposed)return;if(t._deps)t._deps.forEach((c)=>c.delete(t));if(t._cleanups)t._cleanups.forEach((c)=>c()),t._cleanups.clear();let r=u,s=_;u=_=t;try{return t._result=e()}catch(c){console.error("[SigPro]",c)}finally{u=r,_=s}};if(t._deps=t._cleanups=t._children=null,t._disposed=!1,t._isComputed=n,t._depth=u?u._depth+1:0,t._mounts=[],t._parent=_,_)(_._children||=new Set).add(t);return t},D=()=>{if(S)return;S=!0;let e=Array.from(A).sort((n,t)=>n._depth-t._depth);A.clear();for(let n of e)if(!n._disposed)n();S=!1},q=(e)=>{O++;try{return e()}finally{if(O--,O===0&&A.size>0&&!S)D()}},m=(e,n=!1)=>{if(!n&&u&&!u._disposed)e.add(u),(u._deps||=new Set).add(e);else if(n&&e.size>0){let t=!1;for(let r of e){if(r===u||r._disposed)continue;if(r._isComputed){if(r._dirty=!0,r._subs)m(r._subs,!0)}else A.add(r),t=!0}if(t&&!S&&O===0)queueMicrotask(D)}},P=(e,n=null)=>{let t=new Set;if(y(e)){let r,s=()=>{if(s._dirty){let c=u;u=s;try{let i=e();if(!Object.is(r,i))r=i,m(t,!0)}finally{u=c}s._dirty=!1}return m(t),r};if(s._isComputed=!0,s._subs=t,s._dirty=!0,s._deps=null,s._disposed=!1,s.stop=()=>{},_)v(s.stop);return s}if(n)try{e=JSON.parse(localStorage.getItem(n))??e}catch(r){}return(...r)=>{if(r.length){let s=y(r[0])?r[0](e):r[0];if(!Object.is(e,s)){if(e=s,n)localStorage.setItem(n,JSON.stringify(e));m(t,!0)}}return m(t),e}},I=(e)=>{if(!j(e))return e;let n=k.get(e);if(n)return n;let t=new Map,r=(s)=>{let c=t.get(s);if(!c)t.set(s,c=new Set);return c};return n=new Proxy(e,{get(s,c,i){if(typeof c!=="symbol")m(r(c));return I(Reflect.get(s,c,i))},set(s,c,i,o){let l=!Reflect.has(s,c),a=Reflect.get(s,c,o),f=Reflect.set(s,c,i,o);if(f&&!Object.is(a,i)){if(m(r(c),!0),l)m(r(T),!0)}return f},deleteProperty(s,c){let i=Reflect.deleteProperty(s,c);if(i)m(r(c),!0),m(r(T),!0);return i},ownKeys(s){return m(r(T)),Reflect.ownKeys(s)}}),k.set(e,n),n},R=(e,n)=>{if(n===void 0){let r=x(e);return r(),()=>g(r)}let t=x(()=>{let r=Array.isArray(e)?e.map((s)=>s()):e();W(()=>n(r))});return t(),()=>g(t)},M=(e)=>{if(e._cleanups)e._cleanups.forEach((n)=>n()),e._cleanups.clear();if(e._ownerEffect)g(e._ownerEffect);if(e.childNodes)e.childNodes.forEach(M)},z=/^\s*(javascript|data|vbscript):/i,G=(e)=>e==="src"||e==="href"||e.startsWith("on"),U=(e,n)=>{if(n==null||n===!1)return null;if(G(e)){let t=String(n);if(z.test(t))return console.warn(`[SigPro] Bloqueado protocolo peligroso en ${e}`),"#"}return n},C=(e,n={},t=[])=>{if(n instanceof Node||b(n)||!j(n))t=n,n={};if(y(e)){let i=x(()=>{let f=e(n,{children:t,emit:(d,...h)=>n[`on${d[0].toUpperCase()}${d.slice(1)}`]?.(...h)});return i._result=f,f});i();let o=i._result;if(o==null)return null;let l=o instanceof Node||b(o)&&o.every((f)=>f instanceof Node)?o:E.createTextNode(String(o)),a=(f)=>{if(j(f)&&!f._isRuntime)f._mounts=i._mounts||[],f._cleanups=i._cleanups||new Set,f._ownerEffect=i};return b(l)?l.forEach(a):a(l),l}let r=/^(svg|path|circle|rect|line|poly(line|gon)|g|defs|text(path)?|tspan|use|symbol|image|marker|ellipse)$/i.test(e),s=r?E.createElementNS("http://www.w3.org/2000/svg",e):E.createElement(e);s._cleanups=new Set;for(let i in n){if(!n.hasOwnProperty(i))continue;let o=n[i];if(i==="ref"){y(o)?o(s):o.current=s;continue}if(r&&i.startsWith("xlink:")){o==null?s.removeAttributeNS("http://www.w3.org/1999/xlink",i.slice(6)):s.setAttributeNS("http://www.w3.org/1999/xlink",i.slice(6),o);continue}if(i.startsWith("on")){let l=i.slice(2).toLowerCase();s.addEventListener(l,o);let a=()=>s.removeEventListener(l,o);s._cleanups.add(a),v(a)}else if(y(o)){let l=x(()=>{let a=U(i,o());if(i==="class")s.className=a||"";else if(a==null)s.removeAttribute(i);else if(i in s&&!r)s[i]=a;else s.setAttribute(i,a===!0?"":a)});if(l(),s._cleanups.add(()=>g(l)),v(()=>g(l)),/^(INPUT|TEXTAREA|SELECT)$/.test(s.tagName)&&(i==="value"||i==="checked")){let a=i==="checked"?"change":"input";s.addEventListener(a,(f)=>o(f.target[i]))}}else{let l=U(i,o);if(l!=null)if(i in s&&!r)s[i]=l;else s.setAttribute(i,l===!0?"":l)}}let c=(i)=>{if(b(i))return i.forEach(c);if(y(i)){let o=E.createTextNode("");s.appendChild(o);let l=[],a=x(()=>{let f=i(),d=(b(f)?f:[f]).map(B);l.forEach((p)=>{if(p._isRuntime)p.destroy();else M(p);if(p.parentNode)p.remove()});let h=o;for(let p=d.length-1;p>=0;p--){let w=d[p];if(w.parentNode!==h.parentNode)h.parentNode?.insertBefore(w,h);if(w._mounts)w._mounts.forEach((V)=>V());h=w}l=d});a(),s._cleanups.add(()=>g(a)),v(()=>g(a))}else{let o=B(i);if(s.appendChild(o),o._mounts)o._mounts.forEach((l)=>l())}};return c(t),s},$=(e)=>{let n=new Set,t=[],r=_,s=u,c=E.createElement("div");c.style.display="contents",c.setAttribute("role","presentation"),_={_cleanups:n,_mounts:t},u=null;let i=(o)=>{if(!o)return;if(o._isRuntime)n.add(o.destroy),c.appendChild(o.container);else if(b(o))o.forEach(i);else c.appendChild(o instanceof Node?o:E.createTextNode(String(o==null?"":o)))};try{i(e({onCleanup:(o)=>n.add(o)}))}finally{_=r,u=s}return t.forEach((o)=>o()),{_isRuntime:!0,container:c,destroy:()=>{n.forEach((o)=>o()),M(c),c.remove()}}},J=(e,n,{enter:t,leave:r}={})=>{let s=C("div",{style:"display:contents"}),c=null,i=(o,l)=>{if(!o)return l();let a=!1,f=()=>!a&&(a=!0,l());o.addEventListener("transitionend",f,{once:!0}),o.addEventListener("animationend",f,{once:!0}),setTimeout(f,500)};return R(e,(o)=>{if(o&&!c){let l=(c=n(n)).container.firstChild;if(s.appendChild(c.container),t&&l)l.classList.add(t),l.clientTop,l.classList.add(t+"-active"),i(l,()=>l.classList.remove(t,t+"-active"))}else if(!o&&c){let l=c.container.firstChild,a=()=>(c.destroy(),c=null);if(r&&l)l.classList.add(r),i(l,a);else a()}}),v(()=>c?.destroy()),s},K=(e,n,t)=>{let r=E.createTextNode(""),s=C("div",{style:"display:contents"},[r]),c=new Map;return R(()=>(y(e)?e():e)||[],(i)=>{let o=new Map,l=[],a=i||[];for(let d=0;dn(h,d));else c.delete(p);o.set(p,w),l.push(w)}c.forEach((d)=>d.destroy());let f=r;for(let d=l.length-1;d>=0;d--){let p=l[d].container;if(p.nextSibling!==f)s.insertBefore(p,f);f=p}c=o}),s},N=(e)=>{let n=()=>window.location.hash.slice(1)||"/",t=P(n()),r=()=>t(n());window.addEventListener("hashchange",r),v(()=>window.removeEventListener("hashchange",r));let s=C("div",{class:"router-hook"}),c=null;return R([t],()=>{let i=t(),o=e.find((l)=>{let a=l.path.split("/").filter(Boolean),f=i.split("/").filter(Boolean);return a.length===f.length&&a.every((d,h)=>d[0]===":"||d===f[h])})||e.find((l)=>l.path==="*");if(o){c?.destroy();let l={};o.path.split("/").filter(Boolean).forEach((a,f)=>{if(a[0]===":")l[a.slice(1)]=i.split("/").filter(Boolean)[f]}),N.params(l),c=$(()=>y(o.component)?o.component(l):o.component),s.replaceChildren(c.container)}}),s};N.params=P({});N.to=(e)=>window.location.hash=e.replace(/^#?\/?/,"#/");N.back=()=>window.history.back();N.path=()=>window.location.hash.replace(/^#/,"")||"/";var Q=(e,n)=>{let t=typeof n==="string"?E.querySelector(n):n;if(!t)return;if(L.has(t))L.get(t).destroy();let r=$(y(e)?e:()=>e);return t.replaceChildren(r.container),L.set(t,r),r},F=Object.freeze({$:P,$$:I,watch:R,h:C,when:J,each:K,router:N,mount:Q,batch:q});if(typeof window<"u")Object.assign(window,F),"a abbr article aside audio b blockquote br button canvas caption cite code col colgroup datalist dd del details dfn dialog div dl dt em embed fieldset figcaption figure footer form h1 h2 h3 h4 h5 h6 header hr i iframe img input ins kbd label legend li main mark meter nav object ol optgroup option output p picture pre progress section select slot small source span strong sub summary sup svg table tbody td template textarea tfoot th thead time tr u ul video".split(" ").forEach((e)=>{window[e]=(n,t)=>C(e,n,t)});export{J as when,R as watch,N as router,Q as mount,C as h,K as each,q as batch,I as $$,P as $}; +var y=(e)=>typeof e==="function",j=(e)=>e&&typeof e==="object",b=Array.isArray,E=typeof document<"u"?document:null,M=(e)=>e?._isRuntime?e.container:e instanceof Node?e:E.createTextNode(e==null?"":String(e)),u=null,_=null,N=!1,O=0,A=new Set,k=new WeakMap,T=Symbol("iter"),L=new WeakMap,g=(e)=>{if(!e||e._disposed)return;e._disposed=!0;let s=[e];while(s.length){let n=s.pop();if(n._cleanups)n._cleanups.forEach((r)=>r()),n._cleanups.clear();if(n._children)n._children.forEach((r)=>s.push(r)),n._children.clear();if(n._deps)n._deps.forEach((r)=>r.delete(n)),n._deps.clear()}},v=(e)=>{if(_)(_._cleanups||=new Set).add(e)},W=(e)=>{let s=u;u=null;try{return e()}finally{u=s}},x=(e,s=!1)=>{let n=()=>{if(n._disposed)return;if(n._deps)n._deps.forEach((l)=>l.delete(n));if(n._cleanups)n._cleanups.forEach((l)=>l()),n._cleanups.clear();let r=u,o=_;u=_=n;try{return n._result=e()}catch(l){console.error("[SigPro]",l)}finally{u=r,_=o}};if(n._deps=n._cleanups=n._children=null,n._disposed=!1,n._isComputed=s,n._depth=u?u._depth+1:0,n._mounts=[],n._parent=_,_)(_._children||=new Set).add(n);return n},D=()=>{if(N)return;N=!0;let e=Array.from(A).sort((s,n)=>s._depth-n._depth);A.clear();for(let s of e)if(!s._disposed)s();N=!1},q=(e)=>{O++;try{return e()}finally{if(O--,O===0&&A.size>0&&!N)D()}},m=(e,s=!1)=>{if(!s&&u&&!u._disposed)e.add(u),(u._deps||=new Set).add(e);else if(s&&e.size>0){let n=!1;for(let r of e){if(r===u||r._disposed)continue;if(r._isComputed){if(r._dirty=!0,r._subs)m(r._subs,!0)}else A.add(r),n=!0}if(n&&!N&&O===0)queueMicrotask(D)}},P=(e,s=null)=>{let n=new Set;if(y(e)){let r,o=()=>{if(o._dirty){let l=u;u=o;try{let t=e();if(!Object.is(r,t))r=t,m(n,!0)}finally{u=l}o._dirty=!1}return m(n),r};if(o._isComputed=!0,o._subs=n,o._dirty=!0,o._deps=null,o._disposed=!1,o.stop=()=>{},_)v(o.stop);return o}if(s)try{e=JSON.parse(localStorage.getItem(s))??e}catch(r){}return(...r)=>{if(r.length){let o=y(r[0])?r[0](e):r[0];if(!Object.is(e,o)){if(e=o,s)localStorage.setItem(s,JSON.stringify(e));m(n,!0)}}return m(n),e}},I=(e)=>{if(!j(e))return e;let s=k.get(e);if(s)return s;let n=new Map,r=(l)=>{let t=n.get(l);if(!t)n.set(l,t=new Set);return t},o=new Proxy(e,{get(l,t,c){if(typeof t!=="symbol")m(r(t));return I(Reflect.get(l,t,c))},set(l,t,c,i){let a=Reflect.has(l,t),d=Reflect.get(l,t,i),f=Reflect.set(l,t,c,i);if(f&&!Object.is(d,c)){if(m(r(t),!0),!a)m(r(T),!0)}return f},deleteProperty(l,t){let c=Reflect.deleteProperty(l,t);if(c)m(r(t),!0),m(r(T),!0);return c},ownKeys(l){return m(r(T)),Reflect.ownKeys(l)}});return k.set(e,o),o},R=(e,s)=>{if(s===void 0){let r=x(e);return r(),()=>g(r)}let n=x(()=>{let r=Array.isArray(e)?e.map((o)=>o()):e();W(()=>s(r))});return n(),()=>g(n)},$=(e)=>{if(e._cleanups)e._cleanups.forEach((s)=>s()),e._cleanups.clear();if(e._ownerEffect)g(e._ownerEffect);if(e.childNodes)e.childNodes.forEach($)},z=/^\s*(javascript|data|vbscript):/i,K=(e)=>e==="src"||e==="href"||e.startsWith("on"),U=(e,s)=>{if(s==null||s===!1)return null;if(K(e)){let n=String(s);if(z.test(n))return console.warn(`[SigPro] Bloqueado protocolo peligroso en ${e}`),"#"}return s},C=(e,s={},n=[])=>{if(s instanceof Node||b(s)||!j(s))n=s,s={};if(y(e)){let t=x(()=>{let d=e(s,{children:n,emit:(f,...h)=>s[`on${f[0].toUpperCase()}${f.slice(1)}`]?.(...h)});return t._result=d,d});t();let c=t._result;if(c==null)return null;let i=c instanceof Node||b(c)&&c.every((d)=>d instanceof Node)?c:E.createTextNode(String(c)),a=(d)=>{if(j(d)&&!d._isRuntime)d._mounts=t._mounts||[],d._cleanups=t._cleanups||new Set,d._ownerEffect=t};return b(i)?i.forEach(a):a(i),i}let r=/^(svg|path|circle|rect|line|poly(line|gon)|g|defs|text(path)?|tspan|use|symbol|image|marker|ellipse)$/i.test(e),o=r?E.createElementNS("http://www.w3.org/2000/svg",e):E.createElement(e);o._cleanups=new Set;for(let t in s){if(!s.hasOwnProperty(t))continue;let c=s[t];if(t==="ref"){y(c)?c(o):c.current=o;continue}if(r&&t.startsWith("xlink:")){c==null?o.removeAttributeNS("http://www.w3.org/1999/xlink",t.slice(6)):o.setAttributeNS("http://www.w3.org/1999/xlink",t.slice(6),c);continue}if(t.startsWith("on")){let i=t.slice(2).toLowerCase();o.addEventListener(i,c);let a=()=>o.removeEventListener(i,c);o._cleanups.add(a),v(a)}else if(y(c)){let i=x(()=>{let a=U(t,c());if(t==="class")o.className=a||"";else if(a==null)o.removeAttribute(t);else if(t in o&&!r)o[t]=a;else o.setAttribute(t,a===!0?"":a)});if(i(),o._cleanups.add(()=>g(i)),v(()=>g(i)),/^(INPUT|TEXTAREA|SELECT)$/.test(o.tagName)&&(t==="value"||t==="checked")){let a=t==="checked"?"change":"input";o.addEventListener(a,(d)=>c(d.target[t]))}}else{let i=U(t,c);if(i!=null)if(t in o&&!r)o[t]=i;else o.setAttribute(t,i===!0?"":i)}}let l=(t)=>{if(b(t))return t.forEach(l);if(y(t)){let c=E.createTextNode("");o.appendChild(c);let i=[],a=x(()=>{let d=t(),f=(b(d)?d:[d]).map(M);i.forEach((p)=>{if(p._isRuntime)p.destroy();else $(p);if(p.parentNode)p.remove()});let h=c;for(let p=f.length-1;p>=0;p--){let w=f[p];if(w.parentNode!==h.parentNode)h.parentNode?.insertBefore(w,h);if(w._mounts)w._mounts.forEach((V)=>V());h=w}i=f});a(),o._cleanups.add(()=>g(a)),v(()=>g(a))}else{let c=M(t);if(o.appendChild(c),c._mounts)c._mounts.forEach((i)=>i())}};return l(n),o},B=(e)=>{let s=new Set,n=_,r=u,o=E.createElement("div");o.style.display="contents",o.setAttribute("role","presentation"),_={_cleanups:s},u=null;let l=(t)=>{if(!t)return;if(t._isRuntime)s.add(t.destroy),o.appendChild(t.container);else if(b(t))t.forEach(l);else o.appendChild(t instanceof Node?t:E.createTextNode(String(t==null?"":t)))};try{l(e({onCleanup:(t)=>s.add(t)}))}finally{_=n,u=r}return{_isRuntime:!0,container:o,destroy:()=>{s.forEach((t)=>t()),$(o),o.remove()}}},G=(e,s,{enter:n,leave:r}={})=>{let o=C("div",{style:"display:contents"}),l=null,t=(c,i)=>{if(!c)return i();let a=!1,d=()=>!a&&(a=!0,i());c.addEventListener("transitionend",d,{once:!0}),c.addEventListener("animationend",d,{once:!0}),setTimeout(d,500)};return R(e,(c)=>{if(c&&!l){let i=(l=s(s)).container.firstChild;if(o.appendChild(l.container),n&&i)i.classList.add(n),i.clientTop,i.classList.add(n+"-active"),t(i,()=>i.classList.remove(n,n+"-active"))}else if(!c&&l){let i=l.container.firstChild,a=()=>(l.destroy(),l=null);if(r&&i)i.classList.add(r),t(i,a);else a()}}),v(()=>l?.destroy()),o},J=(e,s,n)=>{let r=E.createTextNode(""),o=C("div",{style:"display:contents"},[r]),l=new Map;return R(()=>(y(e)?e():e)||[],(t)=>{let c=new Map,i=[],a=t||[];for(let f=0;fs(h,f));else l.delete(p);c.set(p,w),i.push(w)}l.forEach((f)=>f.destroy());let d=r;for(let f=i.length-1;f>=0;f--){let p=i[f].container;if(p.nextSibling!==d)o.insertBefore(p,d);d=p}l=c}),o},S=(e)=>{let s=()=>window.location.hash.slice(1)||"/",n=P(s()),r=()=>n(s());window.addEventListener("hashchange",r),v(()=>window.removeEventListener("hashchange",r));let o=C("div",{class:"router-hook"}),l=null;return R([n],()=>{let t=n(),c=e.find((i)=>{let a=i.path.split("/").filter(Boolean),d=t.split("/").filter(Boolean);return a.length===d.length&&a.every((f,h)=>f[0]===":"||f===d[h])})||e.find((i)=>i.path==="*");if(c){l?.destroy();let i={};c.path.split("/").filter(Boolean).forEach((a,d)=>{if(a[0]===":")i[a.slice(1)]=t.split("/").filter(Boolean)[d]}),S.params(i),l=B(()=>y(c.component)?c.component(i):c.component),o.replaceChildren(l.container)}}),o};S.params=P({});S.to=(e)=>window.location.hash=e.replace(/^#?\/?/,"#/");S.back=()=>window.history.back();S.path=()=>window.location.hash.replace(/^#/,"")||"/";var Q=(e,s)=>{let n=typeof s==="string"?E.querySelector(s):s;if(!n)return;if(L.has(n))L.get(n).destroy();let r=B(y(e)?e:()=>e);return n.replaceChildren(r.container),L.set(n,r),r},F=Object.freeze({$:P,$$:I,watch:R,h:C,when:G,each:J,router:S,mount:Q,batch:q});if(typeof window<"u")Object.assign(window,F),"a abbr article aside audio b blockquote br button canvas caption cite code col colgroup datalist dd del details dfn dialog div dl dt em embed fieldset figcaption figure footer form h1 h2 h3 h4 h5 h6 header hr i iframe img input ins kbd label legend li main mark meter nav object ol optgroup option output p picture pre progress section select slot small source span strong sub summary sup svg table tbody td template textarea tfoot th thead time tr u ul video".split(" ").forEach((e)=>{window[e]=(s,n)=>C(e,s,n)});export{G as when,R as watch,S as router,Q as mount,C as h,J as each,q as batch,I as $$,P as $}; diff --git a/dist/sigpro.js b/dist/sigpro.js index 571e9fb..e33e608 100644 --- a/dist/sigpro.js +++ b/dist/sigpro.js @@ -86,7 +86,7 @@ } } }; - var _onUnmount = (fn) => { + var onUnmount = (fn) => { if (activeOwner) (activeOwner._cleanups ||= new Set).add(fn); }; @@ -204,7 +204,7 @@ computed._disposed = false; computed.stop = () => {}; if (activeOwner) - _onUnmount(computed.stop); + onUnmount(computed.stop); return computed; } if (key) @@ -228,44 +228,44 @@ var $$ = (target) => { if (!isObj(target)) return target; - let proxy = proxyCache.get(target); - if (proxy) - return proxy; - const subsMap = new Map; - const getSubs = (k) => { - let s = subsMap.get(k); - if (!s) - subsMap.set(k, s = new Set); - return s; + const cached = proxyCache.get(target); + if (cached) + return cached; + const subs = new Map; + const getSubs = (key) => { + let set = subs.get(key); + if (!set) + subs.set(key, set = new Set); + return set; }; - proxy = new Proxy(target, { - get(t, k, receiver) { - if (typeof k !== "symbol") - trackUpdate(getSubs(k)); - return $$(Reflect.get(t, k, receiver)); + const proxy = new Proxy(target, { + get(target2, key, receiver) { + if (typeof key !== "symbol") + trackUpdate(getSubs(key)); + return $$(Reflect.get(target2, key, receiver)); }, - set(t, k, v, receiver) { - const isNew = !Reflect.has(t, k); - const oldV = Reflect.get(t, k, receiver); - const result = Reflect.set(t, k, v, receiver); - if (result && !Object.is(oldV, v)) { - trackUpdate(getSubs(k), true); - if (isNew) + set(target2, key, value, receiver) { + const hadKey = Reflect.has(target2, key); + const oldValue = Reflect.get(target2, key, receiver); + const result = Reflect.set(target2, key, value, receiver); + if (result && !Object.is(oldValue, value)) { + trackUpdate(getSubs(key), true); + if (!hadKey) trackUpdate(getSubs(ITER), true); } return result; }, - deleteProperty(t, k) { - const result = Reflect.deleteProperty(t, k); + deleteProperty(target2, key) { + const result = Reflect.deleteProperty(target2, key); if (result) { - trackUpdate(getSubs(k), true); + trackUpdate(getSubs(key), true); trackUpdate(getSubs(ITER), true); } return result; }, - ownKeys(t) { + ownKeys(target2) { trackUpdate(getSubs(ITER)); - return Reflect.ownKeys(t); + return Reflect.ownKeys(target2); } }); proxyCache.set(target, proxy); @@ -358,7 +358,7 @@ el.addEventListener(ev, v); const off = () => el.removeEventListener(ev, v); el._cleanups.add(off); - _onUnmount(off); + onUnmount(off); } else if (isFunc(v)) { const effect = createEffect(() => { const val = validateAttr(k, v()); @@ -373,7 +373,7 @@ }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); if (/^(INPUT|TEXTAREA|SELECT)$/.test(el.tagName) && (k === "value" || k === "checked")) { const evType = k === "checked" ? "change" : "input"; el.addEventListener(evType, (ev) => v(ev.target[k])); @@ -419,7 +419,7 @@ }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); } else { const node = ensureNode(c); el.appendChild(node); @@ -432,13 +432,12 @@ }; var render = (renderFn) => { const cleanups = new Set; - const mounts = []; const previousOwner = activeOwner; const previousEffect = activeEffect; const container = doc.createElement("div"); container.style.display = "contents"; container.setAttribute("role", "presentation"); - activeOwner = { _cleanups: cleanups, _mounts: mounts }; + activeOwner = { _cleanups: cleanups }; activeEffect = null; const processResult = (result) => { if (!result) @@ -458,7 +457,6 @@ activeOwner = previousOwner; activeEffect = previousEffect; } - mounts.forEach((fn) => fn()); return { _isRuntime: true, container, @@ -502,7 +500,7 @@ } } }); - return _onUnmount(() => view?.destroy()), wrap; + return onUnmount(() => view?.destroy()), wrap; }; var each = (src, itemFn, keyFn) => { const anchor = doc.createTextNode(""); @@ -541,7 +539,7 @@ const path = $(getHash()); const handler = () => path(getHash()); window.addEventListener("hashchange", handler); - _onUnmount(() => window.removeEventListener("hashchange", handler)); + onUnmount(() => window.removeEventListener("hashchange", handler)); const hook = h("div", { class: "router-hook" }); let currentView = null; watch([path], () => { diff --git a/dist/sigpro.min.js b/dist/sigpro.min.js index 7c57d64..392df87 100644 --- a/dist/sigpro.min.js +++ b/dist/sigpro.min.js @@ -1 +1 @@ -(()=>{var{defineProperty:L,getOwnPropertyNames:Q,getOwnPropertyDescriptor:F}=Object,H=Object.prototype.hasOwnProperty;function X(e){return this[e]}var Y=(e)=>{var n=(U??=new WeakMap).get(e),t;if(n)return n;if(n=L({},"__esModule",{value:!0}),e&&typeof e==="object"||typeof e==="function"){for(var o of Q(e))if(!H.call(n,o))L(n,o,{get:X.bind(e,o),enumerable:!(t=F(e,o))||t.enumerable})}return U.set(e,n),n},U;var Z=(e)=>e;function ee(e,n){this[e]=Z.bind(null,n)}var te=(e,n)=>{for(var t in n)L(e,t,{get:n[t],enumerable:!0,configurable:!0,set:ee.bind(n,t)})};var ie={};te(ie,{when:()=>z,watch:()=>O,router:()=>b,mount:()=>J,h:()=>S,each:()=>G,batch:()=>q,$$:()=>$,$:()=>T});var y=(e)=>typeof e==="function",M=(e)=>e&&typeof e==="object",v=Array.isArray,E=typeof document<"u"?document:null,D=(e)=>e?._isRuntime?e.container:e instanceof Node?e:E.createTextNode(e==null?"":String(e)),u=null,_=null,x=!1,A=0,R=new Set,I=new WeakMap,j=Symbol("iter"),P=new WeakMap,g=(e)=>{if(!e||e._disposed)return;e._disposed=!0;let n=[e];while(n.length){let t=n.pop();if(t._cleanups)t._cleanups.forEach((o)=>o()),t._cleanups.clear();if(t._children)t._children.forEach((o)=>n.push(o)),t._children.clear();if(t._deps)t._deps.forEach((o)=>o.delete(t)),t._deps.clear()}},N=(e)=>{if(_)(_._cleanups||=new Set).add(e)},ne=(e)=>{let n=u;u=null;try{return e()}finally{u=n}},C=(e,n=!1)=>{let t=()=>{if(t._disposed)return;if(t._deps)t._deps.forEach((c)=>c.delete(t));if(t._cleanups)t._cleanups.forEach((c)=>c()),t._cleanups.clear();let o=u,s=_;u=_=t;try{return t._result=e()}catch(c){console.error("[SigPro]",c)}finally{u=o,_=s}};if(t._deps=t._cleanups=t._children=null,t._disposed=!1,t._isComputed=n,t._depth=u?u._depth+1:0,t._mounts=[],t._parent=_,_)(_._children||=new Set).add(t);return t},W=()=>{if(x)return;x=!0;let e=Array.from(R).sort((n,t)=>n._depth-t._depth);R.clear();for(let n of e)if(!n._disposed)n();x=!1},q=(e)=>{A++;try{return e()}finally{if(A--,A===0&&R.size>0&&!x)W()}},m=(e,n=!1)=>{if(!n&&u&&!u._disposed)e.add(u),(u._deps||=new Set).add(e);else if(n&&e.size>0){let t=!1;for(let o of e){if(o===u||o._disposed)continue;if(o._isComputed){if(o._dirty=!0,o._subs)m(o._subs,!0)}else R.add(o),t=!0}if(t&&!x&&A===0)queueMicrotask(W)}},T=(e,n=null)=>{let t=new Set;if(y(e)){let o,s=()=>{if(s._dirty){let c=u;u=s;try{let i=e();if(!Object.is(o,i))o=i,m(t,!0)}finally{u=c}s._dirty=!1}return m(t),o};if(s._isComputed=!0,s._subs=t,s._dirty=!0,s._deps=null,s._disposed=!1,s.stop=()=>{},_)N(s.stop);return s}if(n)try{e=JSON.parse(localStorage.getItem(n))??e}catch(o){}return(...o)=>{if(o.length){let s=y(o[0])?o[0](e):o[0];if(!Object.is(e,s)){if(e=s,n)localStorage.setItem(n,JSON.stringify(e));m(t,!0)}}return m(t),e}},$=(e)=>{if(!M(e))return e;let n=I.get(e);if(n)return n;let t=new Map,o=(s)=>{let c=t.get(s);if(!c)t.set(s,c=new Set);return c};return n=new Proxy(e,{get(s,c,i){if(typeof c!=="symbol")m(o(c));return $(Reflect.get(s,c,i))},set(s,c,i,r){let l=!Reflect.has(s,c),a=Reflect.get(s,c,r),f=Reflect.set(s,c,i,r);if(f&&!Object.is(a,i)){if(m(o(c),!0),l)m(o(j),!0)}return f},deleteProperty(s,c){let i=Reflect.deleteProperty(s,c);if(i)m(o(c),!0),m(o(j),!0);return i},ownKeys(s){return m(o(j)),Reflect.ownKeys(s)}}),I.set(e,n),n},O=(e,n)=>{if(n===void 0){let o=C(e);return o(),()=>g(o)}let t=C(()=>{let o=Array.isArray(e)?e.map((s)=>s()):e();ne(()=>n(o))});return t(),()=>g(t)},B=(e)=>{if(e._cleanups)e._cleanups.forEach((n)=>n()),e._cleanups.clear();if(e._ownerEffect)g(e._ownerEffect);if(e.childNodes)e.childNodes.forEach(B)},se=/^\s*(javascript|data|vbscript):/i,oe=(e)=>e==="src"||e==="href"||e.startsWith("on"),V=(e,n)=>{if(n==null||n===!1)return null;if(oe(e)){let t=String(n);if(se.test(t))return console.warn(`[SigPro] Bloqueado protocolo peligroso en ${e}`),"#"}return n},S=(e,n={},t=[])=>{if(n instanceof Node||v(n)||!M(n))t=n,n={};if(y(e)){let i=C(()=>{let f=e(n,{children:t,emit:(d,...h)=>n[`on${d[0].toUpperCase()}${d.slice(1)}`]?.(...h)});return i._result=f,f});i();let r=i._result;if(r==null)return null;let l=r instanceof Node||v(r)&&r.every((f)=>f instanceof Node)?r:E.createTextNode(String(r)),a=(f)=>{if(M(f)&&!f._isRuntime)f._mounts=i._mounts||[],f._cleanups=i._cleanups||new Set,f._ownerEffect=i};return v(l)?l.forEach(a):a(l),l}let o=/^(svg|path|circle|rect|line|poly(line|gon)|g|defs|text(path)?|tspan|use|symbol|image|marker|ellipse)$/i.test(e),s=o?E.createElementNS("http://www.w3.org/2000/svg",e):E.createElement(e);s._cleanups=new Set;for(let i in n){if(!n.hasOwnProperty(i))continue;let r=n[i];if(i==="ref"){y(r)?r(s):r.current=s;continue}if(o&&i.startsWith("xlink:")){r==null?s.removeAttributeNS("http://www.w3.org/1999/xlink",i.slice(6)):s.setAttributeNS("http://www.w3.org/1999/xlink",i.slice(6),r);continue}if(i.startsWith("on")){let l=i.slice(2).toLowerCase();s.addEventListener(l,r);let a=()=>s.removeEventListener(l,r);s._cleanups.add(a),N(a)}else if(y(r)){let l=C(()=>{let a=V(i,r());if(i==="class")s.className=a||"";else if(a==null)s.removeAttribute(i);else if(i in s&&!o)s[i]=a;else s.setAttribute(i,a===!0?"":a)});if(l(),s._cleanups.add(()=>g(l)),N(()=>g(l)),/^(INPUT|TEXTAREA|SELECT)$/.test(s.tagName)&&(i==="value"||i==="checked")){let a=i==="checked"?"change":"input";s.addEventListener(a,(f)=>r(f.target[i]))}}else{let l=V(i,r);if(l!=null)if(i in s&&!o)s[i]=l;else s.setAttribute(i,l===!0?"":l)}}let c=(i)=>{if(v(i))return i.forEach(c);if(y(i)){let r=E.createTextNode("");s.appendChild(r);let l=[],a=C(()=>{let f=i(),d=(v(f)?f:[f]).map(D);l.forEach((p)=>{if(p._isRuntime)p.destroy();else B(p);if(p.parentNode)p.remove()});let h=r;for(let p=d.length-1;p>=0;p--){let w=d[p];if(w.parentNode!==h.parentNode)h.parentNode?.insertBefore(w,h);if(w._mounts)w._mounts.forEach((K)=>K());h=w}l=d});a(),s._cleanups.add(()=>g(a)),N(()=>g(a))}else{let r=D(i);if(s.appendChild(r),r._mounts)r._mounts.forEach((l)=>l())}};return c(t),s},k=(e)=>{let n=new Set,t=[],o=_,s=u,c=E.createElement("div");c.style.display="contents",c.setAttribute("role","presentation"),_={_cleanups:n,_mounts:t},u=null;let i=(r)=>{if(!r)return;if(r._isRuntime)n.add(r.destroy),c.appendChild(r.container);else if(v(r))r.forEach(i);else c.appendChild(r instanceof Node?r:E.createTextNode(String(r==null?"":r)))};try{i(e({onCleanup:(r)=>n.add(r)}))}finally{_=o,u=s}return t.forEach((r)=>r()),{_isRuntime:!0,container:c,destroy:()=>{n.forEach((r)=>r()),B(c),c.remove()}}},z=(e,n,{enter:t,leave:o}={})=>{let s=S("div",{style:"display:contents"}),c=null,i=(r,l)=>{if(!r)return l();let a=!1,f=()=>!a&&(a=!0,l());r.addEventListener("transitionend",f,{once:!0}),r.addEventListener("animationend",f,{once:!0}),setTimeout(f,500)};return O(e,(r)=>{if(r&&!c){let l=(c=n(n)).container.firstChild;if(s.appendChild(c.container),t&&l)l.classList.add(t),l.clientTop,l.classList.add(t+"-active"),i(l,()=>l.classList.remove(t,t+"-active"))}else if(!r&&c){let l=c.container.firstChild,a=()=>(c.destroy(),c=null);if(o&&l)l.classList.add(o),i(l,a);else a()}}),N(()=>c?.destroy()),s},G=(e,n,t)=>{let o=E.createTextNode(""),s=S("div",{style:"display:contents"},[o]),c=new Map;return O(()=>(y(e)?e():e)||[],(i)=>{let r=new Map,l=[],a=i||[];for(let d=0;dn(h,d));else c.delete(p);r.set(p,w),l.push(w)}c.forEach((d)=>d.destroy());let f=o;for(let d=l.length-1;d>=0;d--){let p=l[d].container;if(p.nextSibling!==f)s.insertBefore(p,f);f=p}c=r}),s},b=(e)=>{let n=()=>window.location.hash.slice(1)||"/",t=T(n()),o=()=>t(n());window.addEventListener("hashchange",o),N(()=>window.removeEventListener("hashchange",o));let s=S("div",{class:"router-hook"}),c=null;return O([t],()=>{let i=t(),r=e.find((l)=>{let a=l.path.split("/").filter(Boolean),f=i.split("/").filter(Boolean);return a.length===f.length&&a.every((d,h)=>d[0]===":"||d===f[h])})||e.find((l)=>l.path==="*");if(r){c?.destroy();let l={};r.path.split("/").filter(Boolean).forEach((a,f)=>{if(a[0]===":")l[a.slice(1)]=i.split("/").filter(Boolean)[f]}),b.params(l),c=k(()=>y(r.component)?r.component(l):r.component),s.replaceChildren(c.container)}}),s};b.params=T({});b.to=(e)=>window.location.hash=e.replace(/^#?\/?/,"#/");b.back=()=>window.history.back();b.path=()=>window.location.hash.replace(/^#/,"")||"/";var J=(e,n)=>{let t=typeof n==="string"?E.querySelector(n):n;if(!t)return;if(P.has(t))P.get(t).destroy();let o=k(y(e)?e:()=>e);return t.replaceChildren(o.container),P.set(t,o),o},re=Object.freeze({$:T,$$:$,watch:O,h:S,when:z,each:G,router:b,mount:J,batch:q});if(typeof window<"u")Object.assign(window,re),"a abbr article aside audio b blockquote br button canvas caption cite code col colgroup datalist dd del details dfn dialog div dl dt em embed fieldset figcaption figure footer form h1 h2 h3 h4 h5 h6 header hr i iframe img input ins kbd label legend li main mark meter nav object ol optgroup option output p picture pre progress section select slot small source span strong sub summary sup svg table tbody td template textarea tfoot th thead time tr u ul video".split(" ").forEach((e)=>{window[e]=(n,t)=>S(e,n,t)});})(); +(()=>{var{defineProperty:L,getOwnPropertyNames:Q,getOwnPropertyDescriptor:F}=Object,H=Object.prototype.hasOwnProperty;function X(e){return this[e]}var Y=(e)=>{var n=(U??=new WeakMap).get(e),t;if(n)return n;if(n=L({},"__esModule",{value:!0}),e&&typeof e==="object"||typeof e==="function"){for(var o of Q(e))if(!H.call(n,o))L(n,o,{get:X.bind(e,o),enumerable:!(t=F(e,o))||t.enumerable})}return U.set(e,n),n},U;var Z=(e)=>e;function ee(e,n){this[e]=Z.bind(null,n)}var te=(e,n)=>{for(var t in n)L(e,t,{get:n[t],enumerable:!0,configurable:!0,set:ee.bind(n,t)})};var ie={};te(ie,{when:()=>z,watch:()=>O,router:()=>b,mount:()=>G,h:()=>N,each:()=>K,batch:()=>q,$$:()=>B,$:()=>T});var y=(e)=>typeof e==="function",$=(e)=>e&&typeof e==="object",v=Array.isArray,E=typeof document<"u"?document:null,D=(e)=>e?._isRuntime?e.container:e instanceof Node?e:E.createTextNode(e==null?"":String(e)),u=null,_=null,x=!1,A=0,R=new Set,I=new WeakMap,j=Symbol("iter"),P=new WeakMap,g=(e)=>{if(!e||e._disposed)return;e._disposed=!0;let n=[e];while(n.length){let t=n.pop();if(t._cleanups)t._cleanups.forEach((o)=>o()),t._cleanups.clear();if(t._children)t._children.forEach((o)=>n.push(o)),t._children.clear();if(t._deps)t._deps.forEach((o)=>o.delete(t)),t._deps.clear()}},S=(e)=>{if(_)(_._cleanups||=new Set).add(e)},ne=(e)=>{let n=u;u=null;try{return e()}finally{u=n}},C=(e,n=!1)=>{let t=()=>{if(t._disposed)return;if(t._deps)t._deps.forEach((l)=>l.delete(t));if(t._cleanups)t._cleanups.forEach((l)=>l()),t._cleanups.clear();let o=u,r=_;u=_=t;try{return t._result=e()}catch(l){console.error("[SigPro]",l)}finally{u=o,_=r}};if(t._deps=t._cleanups=t._children=null,t._disposed=!1,t._isComputed=n,t._depth=u?u._depth+1:0,t._mounts=[],t._parent=_,_)(_._children||=new Set).add(t);return t},W=()=>{if(x)return;x=!0;let e=Array.from(R).sort((n,t)=>n._depth-t._depth);R.clear();for(let n of e)if(!n._disposed)n();x=!1},q=(e)=>{A++;try{return e()}finally{if(A--,A===0&&R.size>0&&!x)W()}},m=(e,n=!1)=>{if(!n&&u&&!u._disposed)e.add(u),(u._deps||=new Set).add(e);else if(n&&e.size>0){let t=!1;for(let o of e){if(o===u||o._disposed)continue;if(o._isComputed){if(o._dirty=!0,o._subs)m(o._subs,!0)}else R.add(o),t=!0}if(t&&!x&&A===0)queueMicrotask(W)}},T=(e,n=null)=>{let t=new Set;if(y(e)){let o,r=()=>{if(r._dirty){let l=u;u=r;try{let s=e();if(!Object.is(o,s))o=s,m(t,!0)}finally{u=l}r._dirty=!1}return m(t),o};if(r._isComputed=!0,r._subs=t,r._dirty=!0,r._deps=null,r._disposed=!1,r.stop=()=>{},_)S(r.stop);return r}if(n)try{e=JSON.parse(localStorage.getItem(n))??e}catch(o){}return(...o)=>{if(o.length){let r=y(o[0])?o[0](e):o[0];if(!Object.is(e,r)){if(e=r,n)localStorage.setItem(n,JSON.stringify(e));m(t,!0)}}return m(t),e}},B=(e)=>{if(!$(e))return e;let n=I.get(e);if(n)return n;let t=new Map,o=(l)=>{let s=t.get(l);if(!s)t.set(l,s=new Set);return s},r=new Proxy(e,{get(l,s,c){if(typeof s!=="symbol")m(o(s));return B(Reflect.get(l,s,c))},set(l,s,c,i){let a=Reflect.has(l,s),d=Reflect.get(l,s,i),f=Reflect.set(l,s,c,i);if(f&&!Object.is(d,c)){if(m(o(s),!0),!a)m(o(j),!0)}return f},deleteProperty(l,s){let c=Reflect.deleteProperty(l,s);if(c)m(o(s),!0),m(o(j),!0);return c},ownKeys(l){return m(o(j)),Reflect.ownKeys(l)}});return I.set(e,r),r},O=(e,n)=>{if(n===void 0){let o=C(e);return o(),()=>g(o)}let t=C(()=>{let o=Array.isArray(e)?e.map((r)=>r()):e();ne(()=>n(o))});return t(),()=>g(t)},M=(e)=>{if(e._cleanups)e._cleanups.forEach((n)=>n()),e._cleanups.clear();if(e._ownerEffect)g(e._ownerEffect);if(e.childNodes)e.childNodes.forEach(M)},se=/^\s*(javascript|data|vbscript):/i,oe=(e)=>e==="src"||e==="href"||e.startsWith("on"),V=(e,n)=>{if(n==null||n===!1)return null;if(oe(e)){let t=String(n);if(se.test(t))return console.warn(`[SigPro] Bloqueado protocolo peligroso en ${e}`),"#"}return n},N=(e,n={},t=[])=>{if(n instanceof Node||v(n)||!$(n))t=n,n={};if(y(e)){let s=C(()=>{let d=e(n,{children:t,emit:(f,...h)=>n[`on${f[0].toUpperCase()}${f.slice(1)}`]?.(...h)});return s._result=d,d});s();let c=s._result;if(c==null)return null;let i=c instanceof Node||v(c)&&c.every((d)=>d instanceof Node)?c:E.createTextNode(String(c)),a=(d)=>{if($(d)&&!d._isRuntime)d._mounts=s._mounts||[],d._cleanups=s._cleanups||new Set,d._ownerEffect=s};return v(i)?i.forEach(a):a(i),i}let o=/^(svg|path|circle|rect|line|poly(line|gon)|g|defs|text(path)?|tspan|use|symbol|image|marker|ellipse)$/i.test(e),r=o?E.createElementNS("http://www.w3.org/2000/svg",e):E.createElement(e);r._cleanups=new Set;for(let s in n){if(!n.hasOwnProperty(s))continue;let c=n[s];if(s==="ref"){y(c)?c(r):c.current=r;continue}if(o&&s.startsWith("xlink:")){c==null?r.removeAttributeNS("http://www.w3.org/1999/xlink",s.slice(6)):r.setAttributeNS("http://www.w3.org/1999/xlink",s.slice(6),c);continue}if(s.startsWith("on")){let i=s.slice(2).toLowerCase();r.addEventListener(i,c);let a=()=>r.removeEventListener(i,c);r._cleanups.add(a),S(a)}else if(y(c)){let i=C(()=>{let a=V(s,c());if(s==="class")r.className=a||"";else if(a==null)r.removeAttribute(s);else if(s in r&&!o)r[s]=a;else r.setAttribute(s,a===!0?"":a)});if(i(),r._cleanups.add(()=>g(i)),S(()=>g(i)),/^(INPUT|TEXTAREA|SELECT)$/.test(r.tagName)&&(s==="value"||s==="checked")){let a=s==="checked"?"change":"input";r.addEventListener(a,(d)=>c(d.target[s]))}}else{let i=V(s,c);if(i!=null)if(s in r&&!o)r[s]=i;else r.setAttribute(s,i===!0?"":i)}}let l=(s)=>{if(v(s))return s.forEach(l);if(y(s)){let c=E.createTextNode("");r.appendChild(c);let i=[],a=C(()=>{let d=s(),f=(v(d)?d:[d]).map(D);i.forEach((p)=>{if(p._isRuntime)p.destroy();else M(p);if(p.parentNode)p.remove()});let h=c;for(let p=f.length-1;p>=0;p--){let w=f[p];if(w.parentNode!==h.parentNode)h.parentNode?.insertBefore(w,h);if(w._mounts)w._mounts.forEach((J)=>J());h=w}i=f});a(),r._cleanups.add(()=>g(a)),S(()=>g(a))}else{let c=D(s);if(r.appendChild(c),c._mounts)c._mounts.forEach((i)=>i())}};return l(t),r},k=(e)=>{let n=new Set,t=_,o=u,r=E.createElement("div");r.style.display="contents",r.setAttribute("role","presentation"),_={_cleanups:n},u=null;let l=(s)=>{if(!s)return;if(s._isRuntime)n.add(s.destroy),r.appendChild(s.container);else if(v(s))s.forEach(l);else r.appendChild(s instanceof Node?s:E.createTextNode(String(s==null?"":s)))};try{l(e({onCleanup:(s)=>n.add(s)}))}finally{_=t,u=o}return{_isRuntime:!0,container:r,destroy:()=>{n.forEach((s)=>s()),M(r),r.remove()}}},z=(e,n,{enter:t,leave:o}={})=>{let r=N("div",{style:"display:contents"}),l=null,s=(c,i)=>{if(!c)return i();let a=!1,d=()=>!a&&(a=!0,i());c.addEventListener("transitionend",d,{once:!0}),c.addEventListener("animationend",d,{once:!0}),setTimeout(d,500)};return O(e,(c)=>{if(c&&!l){let i=(l=n(n)).container.firstChild;if(r.appendChild(l.container),t&&i)i.classList.add(t),i.clientTop,i.classList.add(t+"-active"),s(i,()=>i.classList.remove(t,t+"-active"))}else if(!c&&l){let i=l.container.firstChild,a=()=>(l.destroy(),l=null);if(o&&i)i.classList.add(o),s(i,a);else a()}}),S(()=>l?.destroy()),r},K=(e,n,t)=>{let o=E.createTextNode(""),r=N("div",{style:"display:contents"},[o]),l=new Map;return O(()=>(y(e)?e():e)||[],(s)=>{let c=new Map,i=[],a=s||[];for(let f=0;fn(h,f));else l.delete(p);c.set(p,w),i.push(w)}l.forEach((f)=>f.destroy());let d=o;for(let f=i.length-1;f>=0;f--){let p=i[f].container;if(p.nextSibling!==d)r.insertBefore(p,d);d=p}l=c}),r},b=(e)=>{let n=()=>window.location.hash.slice(1)||"/",t=T(n()),o=()=>t(n());window.addEventListener("hashchange",o),S(()=>window.removeEventListener("hashchange",o));let r=N("div",{class:"router-hook"}),l=null;return O([t],()=>{let s=t(),c=e.find((i)=>{let a=i.path.split("/").filter(Boolean),d=s.split("/").filter(Boolean);return a.length===d.length&&a.every((f,h)=>f[0]===":"||f===d[h])})||e.find((i)=>i.path==="*");if(c){l?.destroy();let i={};c.path.split("/").filter(Boolean).forEach((a,d)=>{if(a[0]===":")i[a.slice(1)]=s.split("/").filter(Boolean)[d]}),b.params(i),l=k(()=>y(c.component)?c.component(i):c.component),r.replaceChildren(l.container)}}),r};b.params=T({});b.to=(e)=>window.location.hash=e.replace(/^#?\/?/,"#/");b.back=()=>window.history.back();b.path=()=>window.location.hash.replace(/^#/,"")||"/";var G=(e,n)=>{let t=typeof n==="string"?E.querySelector(n):n;if(!t)return;if(P.has(t))P.get(t).destroy();let o=k(y(e)?e:()=>e);return t.replaceChildren(o.container),P.set(t,o),o},re=Object.freeze({$:T,$$:B,watch:O,h:N,when:z,each:K,router:b,mount:G,batch:q});if(typeof window<"u")Object.assign(window,re),"a abbr article aside audio b blockquote br button canvas caption cite code col colgroup datalist dd del details dfn dialog div dl dt em embed fieldset figcaption figure footer form h1 h2 h3 h4 h5 h6 header hr i iframe img input ins kbd label legend li main mark meter nav object ol optgroup option output p picture pre progress section select slot small source span strong sub summary sup svg table tbody td template textarea tfoot th thead time tr u ul video".split(" ").forEach((e)=>{window[e]=(n,t)=>N(e,n,t)});})(); diff --git a/docs/sigpro.js b/docs/sigpro.js index 571e9fb..e33e608 100644 --- a/docs/sigpro.js +++ b/docs/sigpro.js @@ -86,7 +86,7 @@ } } }; - var _onUnmount = (fn) => { + var onUnmount = (fn) => { if (activeOwner) (activeOwner._cleanups ||= new Set).add(fn); }; @@ -204,7 +204,7 @@ computed._disposed = false; computed.stop = () => {}; if (activeOwner) - _onUnmount(computed.stop); + onUnmount(computed.stop); return computed; } if (key) @@ -228,44 +228,44 @@ var $$ = (target) => { if (!isObj(target)) return target; - let proxy = proxyCache.get(target); - if (proxy) - return proxy; - const subsMap = new Map; - const getSubs = (k) => { - let s = subsMap.get(k); - if (!s) - subsMap.set(k, s = new Set); - return s; + const cached = proxyCache.get(target); + if (cached) + return cached; + const subs = new Map; + const getSubs = (key) => { + let set = subs.get(key); + if (!set) + subs.set(key, set = new Set); + return set; }; - proxy = new Proxy(target, { - get(t, k, receiver) { - if (typeof k !== "symbol") - trackUpdate(getSubs(k)); - return $$(Reflect.get(t, k, receiver)); + const proxy = new Proxy(target, { + get(target2, key, receiver) { + if (typeof key !== "symbol") + trackUpdate(getSubs(key)); + return $$(Reflect.get(target2, key, receiver)); }, - set(t, k, v, receiver) { - const isNew = !Reflect.has(t, k); - const oldV = Reflect.get(t, k, receiver); - const result = Reflect.set(t, k, v, receiver); - if (result && !Object.is(oldV, v)) { - trackUpdate(getSubs(k), true); - if (isNew) + set(target2, key, value, receiver) { + const hadKey = Reflect.has(target2, key); + const oldValue = Reflect.get(target2, key, receiver); + const result = Reflect.set(target2, key, value, receiver); + if (result && !Object.is(oldValue, value)) { + trackUpdate(getSubs(key), true); + if (!hadKey) trackUpdate(getSubs(ITER), true); } return result; }, - deleteProperty(t, k) { - const result = Reflect.deleteProperty(t, k); + deleteProperty(target2, key) { + const result = Reflect.deleteProperty(target2, key); if (result) { - trackUpdate(getSubs(k), true); + trackUpdate(getSubs(key), true); trackUpdate(getSubs(ITER), true); } return result; }, - ownKeys(t) { + ownKeys(target2) { trackUpdate(getSubs(ITER)); - return Reflect.ownKeys(t); + return Reflect.ownKeys(target2); } }); proxyCache.set(target, proxy); @@ -358,7 +358,7 @@ el.addEventListener(ev, v); const off = () => el.removeEventListener(ev, v); el._cleanups.add(off); - _onUnmount(off); + onUnmount(off); } else if (isFunc(v)) { const effect = createEffect(() => { const val = validateAttr(k, v()); @@ -373,7 +373,7 @@ }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); if (/^(INPUT|TEXTAREA|SELECT)$/.test(el.tagName) && (k === "value" || k === "checked")) { const evType = k === "checked" ? "change" : "input"; el.addEventListener(evType, (ev) => v(ev.target[k])); @@ -419,7 +419,7 @@ }); effect(); el._cleanups.add(() => dispose(effect)); - _onUnmount(() => dispose(effect)); + onUnmount(() => dispose(effect)); } else { const node = ensureNode(c); el.appendChild(node); @@ -432,13 +432,12 @@ }; var render = (renderFn) => { const cleanups = new Set; - const mounts = []; const previousOwner = activeOwner; const previousEffect = activeEffect; const container = doc.createElement("div"); container.style.display = "contents"; container.setAttribute("role", "presentation"); - activeOwner = { _cleanups: cleanups, _mounts: mounts }; + activeOwner = { _cleanups: cleanups }; activeEffect = null; const processResult = (result) => { if (!result) @@ -458,7 +457,6 @@ activeOwner = previousOwner; activeEffect = previousEffect; } - mounts.forEach((fn) => fn()); return { _isRuntime: true, container, @@ -502,7 +500,7 @@ } } }); - return _onUnmount(() => view?.destroy()), wrap; + return onUnmount(() => view?.destroy()), wrap; }; var each = (src, itemFn, keyFn) => { const anchor = doc.createTextNode(""); @@ -541,7 +539,7 @@ const path = $(getHash()); const handler = () => path(getHash()); window.addEventListener("hashchange", handler); - _onUnmount(() => window.removeEventListener("hashchange", handler)); + onUnmount(() => window.removeEventListener("hashchange", handler)); const hook = h("div", { class: "router-hook" }); let currentView = null; watch([path], () => { diff --git a/package.json b/package.json index 21249e1..feb802a 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "sigpro", - "version": "1.2.14", + "version": "1.2.15", "type": "module", "license": "MIT", "main": "./dist/sigpro.esm.min.js", diff --git a/sigpro.js b/sigpro.js index ab53e35..c47f945 100644 --- a/sigpro.js +++ b/sigpro.js @@ -1,4 +1,4 @@ -// sigpro 1.2.14 +// sigpro 1.2.15 const isFunc = f => typeof f === "function" const isObj = o => o && typeof o === "object" const isArr = Array.isArray @@ -35,7 +35,7 @@ const dispose = eff => { } } -const _onUnmount = fn => { +const onUnmount = fn => { if (activeOwner) (activeOwner._cleanups ||= new Set()).add(fn) } @@ -144,7 +144,7 @@ const $ = (val, key = null) => { computed._deps = null computed._disposed = false computed.stop = () => { } - if (activeOwner) _onUnmount(computed.stop) + if (activeOwner) onUnmount(computed.stop) return computed } if (key) try { val = JSON.parse(localStorage.getItem(key)) ?? val } catch (e) { } @@ -165,43 +165,42 @@ const $ = (val, key = null) => { const $$ = (target) => { if (!isObj(target)) return target - let proxy = proxyCache.get(target) - if (proxy) return proxy + const cached = proxyCache.get(target) + if (cached) return cached - const subsMap = new Map() - const getSubs = (k) => { - let s = subsMap.get(k) - if (!s) subsMap.set(k, (s = new Set())) - return s + const subs = new Map() + const getSubs = (key) => { + let set = subs.get(key) + if (!set) subs.set(key, set = new Set()) + return set } - proxy = new Proxy(target, { - get(t, k, receiver) { - if (typeof k !== 'symbol') trackUpdate(getSubs(k)) - return $$(Reflect.get(t, k, receiver)) + const proxy = new Proxy(target, { + get(target, key, receiver) { + if (typeof key !== 'symbol') trackUpdate(getSubs(key)) + return $$(Reflect.get(target, key, receiver)) }, - set(t, k, v, receiver) { - const isNew = !Reflect.has(t, k) - const oldV = Reflect.get(t, k, receiver) - const result = Reflect.set(t, k, v, receiver) - - if (result && !Object.is(oldV, v)) { - trackUpdate(getSubs(k), true) - if (isNew) trackUpdate(getSubs(ITER), true) + set(target, key, value, receiver) { + const hadKey = Reflect.has(target, key) + const oldValue = Reflect.get(target, key, receiver) + const result = Reflect.set(target, key, value, receiver) + if (result && !Object.is(oldValue, value)) { + trackUpdate(getSubs(key), true) + if (!hadKey) trackUpdate(getSubs(ITER), true) } return result }, - deleteProperty(t, k) { - const result = Reflect.deleteProperty(t, k) + deleteProperty(target, key) { + const result = Reflect.deleteProperty(target, key) if (result) { - trackUpdate(getSubs(k), true) + trackUpdate(getSubs(key), true) trackUpdate(getSubs(ITER), true) } return result }, - ownKeys(t) { + ownKeys(target) { trackUpdate(getSubs(ITER)) - return Reflect.ownKeys(t) + return Reflect.ownKeys(target) } }) @@ -252,6 +251,7 @@ const h = (tag, props = {}, children = []) => { children = props props = {} } + if (isFunc(tag)) { const effect = createEffect(() => { const result = tag(props, { @@ -302,7 +302,7 @@ const h = (tag, props = {}, children = []) => { el.addEventListener(ev, v) const off = () => el.removeEventListener(ev, v) el._cleanups.add(off) - _onUnmount(off) + onUnmount(off) } else if (isFunc(v)) { const effect = createEffect(() => { const val = validateAttr(k, v()) @@ -313,7 +313,7 @@ const h = (tag, props = {}, children = []) => { }) effect() el._cleanups.add(() => dispose(effect)) - _onUnmount(() => dispose(effect)) + onUnmount(() => dispose(effect)) if (/^(INPUT|TEXTAREA|SELECT)$/.test(el.tagName) && (k === "value" || k === "checked")) { const evType = k === "checked" ? "change" : "input" el.addEventListener(evType, ev => v(ev.target[k])) @@ -352,7 +352,7 @@ const h = (tag, props = {}, children = []) => { }) effect() el._cleanups.add(() => dispose(effect)) - _onUnmount(() => dispose(effect)) + onUnmount(() => dispose(effect)) } else { const node = ensureNode(c) el.appendChild(node) @@ -365,13 +365,12 @@ const h = (tag, props = {}, children = []) => { const render = renderFn => { const cleanups = new Set() - const mounts = [] const previousOwner = activeOwner const previousEffect = activeEffect const container = doc.createElement("div") container.style.display = "contents" container.setAttribute("role", "presentation") - activeOwner = { _cleanups: cleanups, _mounts: mounts } + activeOwner = { _cleanups: cleanups } activeEffect = null const processResult = result => { @@ -393,7 +392,6 @@ const render = renderFn => { activeEffect = previousEffect } - mounts.forEach(fn => fn()) return { _isRuntime: true, container, @@ -439,7 +437,7 @@ const when = (cond, render, { enter, leave } = {}) => { } }) - return _onUnmount(() => view?.destroy()), wrap + return onUnmount(() => view?.destroy()), wrap } const each = (src, itemFn, keyFn) => { @@ -477,7 +475,7 @@ const router = routes => { const path = $(getHash()) const handler = () => path(getHash()) window.addEventListener("hashchange", handler) - _onUnmount(() => window.removeEventListener("hashchange", handler)) + onUnmount(() => window.removeEventListener("hashchange", handler)) const hook = h("div", { class: "router-hook" }) let currentView = null watch([path], () => {