@layoutit/polycss-morph 0.2.10 → 0.2.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/prepare.cjs CHANGED
@@ -1 +1 @@
1
- "use strict";var Be=Object.defineProperty;var Ln=Object.getOwnPropertyDescriptor;var En=Object.getOwnPropertyNames;var Nn=Object.prototype.hasOwnProperty;var Vn=(n,e)=>{for(var r in e)Be(n,r,{get:e[r],enumerable:!0})},Bn=(n,e,r,o)=>{if(e&&typeof e=="object"||typeof e=="function")for(let a of En(e))!Nn.call(n,a)&&a!==r&&Be(n,a,{get:()=>e[a],enumerable:!(o=Ln(e,a))||o.enumerable});return n};var _n=n=>Bn(Be({},"__esModule",{value:!0}),n);var Zr={};Vn(Zr,{POLY_MORPH_CATALOG_SCHEMA:()=>te,POLY_MORPH_MODEL_SCHEMA:()=>oe,POLY_MORPH_PACKAGE_SCHEMA:()=>ae,POLY_MORPH_PREPARE_SCHEMA:()=>ue,PolyMorphContractError:()=>ge,PolyMorphPackageError:()=>j,PolyMorphPrepareError:()=>Me,assertPolyMorphPackageModelBinding:()=>fn,buildPolyMorphCatalog:()=>un,buildPolyMorphPackage:()=>Se,buildPolyMorphPreparedPackage:()=>Te,compilePolyMorphSource:()=>Ze,decodePolyMorphJson:()=>ln,encodePolyMorphCanonicalJson:()=>me,failPolyMorphPrepare:()=>y,hashPolyMorphBytes:()=>ie,isPolyMorphId:()=>ye,isPolyMorphResourcePath:()=>ke,loadPolyMorphGltf:()=>Le,parsePolyMorphPrepareConfig:()=>qe,preparePolyMorphModel:()=>jn,readPolyMorphPrepareConfig:()=>Ae,resolvePolyMorphSourcePath:()=>Re,stringifyPolyMorphCanonicalJson:()=>Ue,validatePolyMorphCatalog:()=>Ie,validatePolyMorphModel:()=>pe,validatePolyMorphPackageManifest:()=>we});module.exports=_n(Zr);var oe="polycss-morph.model@1",te="polycss-morph.catalog@1",ae="polycss-morph.package@1";var tn=/^[a-z][a-z0-9]*(?:-[a-z0-9]+)*$/,Jn=/^[a-z0-9][a-z0-9._-]*$/,on=/^\d+\.\d+\.\d+$/,Un=/^[a-f0-9]{64}$/,Dn=new Set(["joint-skin","morph-regions","prepared-playback","static-prepared"]),Fn=new Set(["animation","joint-skinning","morph-targets","prepared-playback","retained-render","semantic-controls","sparse-updates","springs"]),Hn=new Set(["atlas-slice","direct-image","solid-quad","solid-triangle"]),zn=new Set(["control-value","joint-rotation","joint-scale","joint-translation","morph-weight","shape-matrix"]),ge=class extends TypeError{constructor(e,r,o){super(`${r}: ${o}`),this.name="PolyMorphContractError",this.code=e,this.path=r}};function u(n,e,r){throw new ge(n,e,r)}function I(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&u("invalid-type",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&u("invalid-keys",e,`expected exactly ${a.join(", ")}`),n}function A(n,e){return Array.isArray(n)||u("invalid-type",e,"expected an array"),n}function z(n,e){return(typeof n!="string"||n.length===0)&&u("invalid-string",e,"expected a non-empty string"),n}function V(n,e){return(typeof n!="number"||!Number.isFinite(n))&&u("invalid-number",e,"expected a finite number"),n}function F(n,e,r=0){let o=V(n,e);return(!Number.isSafeInteger(o)||o<r)&&u("invalid-integer",e,`expected an integer >= ${r}`),o}function _e(n,e){return typeof n!="boolean"&&u("invalid-boolean",e,"expected a boolean"),n}function E(n,e){let r=z(n,e);return tn.test(r)||u("invalid-id",e,"expected a normalized kebab-case id"),r}function B(n,e){let r=new Set;for(let o of n)r.has(o)&&u("duplicate-id",e,`duplicate id ${o}`),r.add(o)}function de(n,e){let r=A(n,e);return r.length!==3&&u("invalid-vector",e,"expected three components"),r.map((o,a)=>V(o,`${e}[${a}]`))}function X(n,e){let r=A(n,e);return r.length!==16&&u("invalid-matrix",e,"expected sixteen components"),r.map((o,a)=>V(o,`${e}[${a}]`))}function an(n,e){let r=z(n,e);return r.split("/").some(o=>!Jn.test(o))&&u("invalid-path",e,"expected lowercase URL-safe package path segments"),r}function ve(n,e,r){let o=F(n,e);return o>=r&&u("out-of-range",e,`expected an index below ${r}`),o}function Gn(n,e){let r=I(n,e,["normals","polygons","vertices"]),o=A(r.vertices,`${e}.vertices`).map((i,c)=>de(i,`${e}.vertices[${c}]`)),a=A(r.normals,`${e}.normals`).map((i,c)=>de(i,`${e}.normals[${c}]`));o.length===0&&u("missing-topology",`${e}.vertices`,"expected at least one vertex"),a.length===0&&u("missing-topology",`${e}.normals`,"expected at least one normal");let t=A(r.polygons,`${e}.polygons`).map((i,c)=>{let s=`${e}.polygons[${c}]`,l=I(i,s,["id","normalIndices","vertexIndices"]),d=A(l.vertexIndices,`${s}.vertexIndices`).map((m,M)=>ve(m,`${s}.vertexIndices[${M}]`,o.length)),p=A(l.normalIndices,`${s}.normalIndices`).map((m,M)=>ve(m,`${s}.normalIndices[${M}]`,a.length));return d.length<3&&u("invalid-polygon",s,"expected at least three vertices"),p.length!==d.length&&u("invalid-polygon",s,"normal and vertex index counts must match"),new Set(d).size!==d.length&&u("invalid-polygon",s,"vertex indices must be unique"),{id:E(l.id,`${s}.id`),vertexIndices:d,normalIndices:p}});return t.length===0&&u("missing-topology",`${e}.polygons`,"expected at least one polygon"),B(t.map(i=>i.id),`${e}.polygons`),{vertices:o,normals:a,polygons:t}}function qn(n,e,r){let o=I(n,e,["atlas","fallback","height","id","materialId","matrix","polygonId","shapeId","strategy","width"]),a=z(o.strategy,`${e}.strategy`);Hn.has(a)||u("invalid-strategy",`${e}.strategy`,"unknown render strategy");let t=E(o.polygonId,`${e}.polygonId`),i=E(o.shapeId,`${e}.shapeId`),c=E(o.materialId,`${e}.materialId`);r.polygonIds.has(t)||u("unknown-reference",`${e}.polygonId`,t),r.shapeIds.has(i)||u("unknown-reference",`${e}.shapeId`,i),r.materialIds.has(c)||u("unknown-reference",`${e}.materialId`,c);let s=V(o.width,`${e}.width`),l=V(o.height,`${e}.height`);(s<=0||l<=0)&&u("invalid-size",e,"leaf dimensions must be positive");let d=a==="atlas-slice"||a==="direct-image",p=o.atlas===null?null:sn(o.atlas,`${e}.atlas`);d!==(p!==null)&&u("invalid-strategy",`${e}.atlas`,d?"image strategies require an atlas/source slice":"solid strategies cannot declare an atlas/source slice");let m=o.fallback===null?null:Wn(o.fallback,`${e}.fallback`);return m!==null&&a!=="solid-triangle"&&u("invalid-strategy",`${e}.fallback`,"only solid-triangle leaves may declare a prepared fallback"),{id:E(o.id,`${e}.id`),polygonId:t,shapeId:i,materialId:c,strategy:a,width:s,height:l,matrix:X(o.matrix,`${e}.matrix`),atlas:p,fallback:m}}function Wn(n,e){let r=I(n,e,["atlas","height","matrixFromLeaf","width"]),o=F(r.width,`${e}.width`,1),a=F(r.height,`${e}.height`,1),t=sn(r.atlas,`${e}.atlas`);return(t.width!==o||t.height!==a)&&u("invalid-size",e,"fallback dimensions must match its per-polygon atlas slice"),{width:o,height:a,matrixFromLeaf:X(r.matrixFromLeaf,`${e}.matrixFromLeaf`),atlas:t}}function sn(n,e){let r=I(n,e,["height","pageHeight","pageWidth","resourcePath","width","x","y"]),o={resourcePath:an(r.resourcePath,`${e}.resourcePath`),x:F(r.x,`${e}.x`),y:F(r.y,`${e}.y`),width:F(r.width,`${e}.width`,1),height:F(r.height,`${e}.height`,1),pageWidth:F(r.pageWidth,`${e}.pageWidth`,1),pageHeight:F(r.pageHeight,`${e}.pageHeight`,1)};return(o.x+o.width>o.pageWidth||o.y+o.height>o.pageHeight)&&u("out-of-range",e,"slice must fit inside its page"),o}function Yn(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&u("invalid-type",e,"expected a deformation object");let o=z(n.kind,`${e}.kind`);if(o==="none")return I(n,e,["kind"]),{kind:o};if(o==="morph-regions"){let a=I(n,e,["kind","targets"]),t=A(a.targets,`${e}.targets`).map((i,c)=>{let s=`${e}.targets[${c}]`,l=I(i,s,["deltas","id"]),d=A(l.deltas,`${s}.deltas`).map((m,M)=>{let P=`${s}.deltas[${M}]`,x=I(m,P,["normal","position","vertexIndex"]),f=x.position===null?null:de(x.position,`${P}.position`),$=x.normal===null?null:de(x.normal,`${P}.normal`);return f===null&&$===null&&u("empty-delta",P,"expected a position or normal delta"),{vertexIndex:ve(x.vertexIndex,`${P}.vertexIndex`,r.vertices.length),position:f,normal:$}});d.length===0&&u("missing-deltas",`${s}.deltas`,"expected at least one delta");let p=d.map(m=>String(m.vertexIndex));return B(p,`${s}.deltas`),{id:E(l.id,`${s}.id`),deltas:d}});return t.length===0&&u("missing-targets",`${e}.targets`,"expected at least one target"),B(t.map(i=>i.id),`${e}.targets`),{kind:o,targets:t}}if(o==="joint-skin"){let a=I(n,e,["joints","kind","vertices"]),t=A(a.joints,`${e}.joints`).map((l,d)=>{let p=`${e}.joints[${d}]`,m=I(l,p,["id","inverseBindMatrix","parentId","restMatrix"]);return{id:E(m.id,`${p}.id`),parentId:m.parentId===null?null:E(m.parentId,`${p}.parentId`),restMatrix:X(m.restMatrix,`${p}.restMatrix`),inverseBindMatrix:X(m.inverseBindMatrix,`${p}.inverseBindMatrix`)}});t.length===0&&u("missing-joints",`${e}.joints`,"expected at least one joint"),B(t.map(l=>l.id),`${e}.joints`),Kn(t,`${e}.joints`);let i=new Set(t.map(l=>l.id)),c=A(a.vertices,`${e}.vertices`).map((l,d)=>{let p=`${e}.vertices[${d}]`,m=I(l,p,["influences","vertexIndex"]),M=ve(m.vertexIndex,`${p}.vertexIndex`,r.vertices.length),P=A(m.influences,`${p}.influences`).map((f,$)=>{let v=`${p}.influences[${$}]`,O=I(f,v,["jointId","weight"]),C=E(O.jointId,`${v}.jointId`);i.has(C)||u("unknown-reference",`${v}.jointId`,C);let q=V(O.weight,`${v}.weight`);return(q<=0||q>1)&&u("invalid-weight",`${v}.weight`,"expected 0 < weight <= 1"),{jointId:C,weight:q}});P.length===0&&u("missing-influences",`${p}.influences`,"expected at least one influence"),B(P.map(f=>f.jointId),`${p}.influences`);let x=P.reduce((f,$)=>f+$.weight,0);return Math.abs(x-1)>1e-6&&u("invalid-weight",`${p}.influences`,"weights must sum to 1"),{vertexIndex:M,influences:P}});c.length!==r.vertices.length&&u("missing-skin-vertex",`${e}.vertices`,"every topology vertex must have one skin record");let s=c.map(l=>String(l.vertexIndex));return B(s,`${e}.vertices`),{kind:o,joints:t,vertices:c}}u("invalid-deformation",`${e}.kind`,`unknown deformation kind ${o}`)}function Kn(n,e){let r=new Map(n.map(a=>[a.id,a]));n.filter(a=>a.parentId===null).length!==1&&u("invalid-hierarchy",e,"expected exactly one root joint");for(let a of n){a.parentId!==null&&!r.has(a.parentId)&&u("unknown-reference",e,`joint ${a.id} references ${a.parentId}`);let t=new Set,i=a;for(;i;)t.has(i.id)&&u("invalid-hierarchy",e,`cycle at joint ${i.id}`),t.add(i.id),i=i.parentId===null?void 0:r.get(i.parentId)}}function Zn(n){return n==="control-value"||n==="morph-weight"?1:n==="joint-rotation"?4:n==="shape-matrix"?16:3}function Qn(n,e,r,o){let a=I(n,e,["interpolation","target","targetId","timesMs","values"]),t=z(a.target,`${e}.target`);zn.has(t)||u("invalid-animation-target",`${e}.target`,t);let i=E(a.targetId,`${e}.targetId`);(t==="control-value"?r.controlIds:t==="morph-weight"?r.targetIds:t==="shape-matrix"?r.shapeIds:r.jointIds).has(i)||u("unknown-reference",`${e}.targetId`,i);let s=z(a.interpolation,`${e}.interpolation`);s!=="linear"&&s!=="step"&&u("invalid-interpolation",`${e}.interpolation`,s),t==="shape-matrix"&&s!=="step"&&u("invalid-interpolation",`${e}.interpolation`,"shape matrices require step interpolation");let l=A(a.timesMs,`${e}.timesMs`).map((p,m)=>V(p,`${e}.timesMs[${m}]`)),d=A(a.values,`${e}.values`).map((p,m)=>{let M=A(p,`${e}.values[${m}]`),P=Zn(t);M.length!==P&&u("invalid-animation-value",`${e}.values[${m}]`,`expected ${P} components`);let x=M.map((f,$)=>V(f,`${e}.values[${m}][${$}]`));return t==="joint-rotation"&&Math.hypot(...x)<=1e-12&&u("invalid-animation-value",`${e}.values[${m}]`,"quaternion must be non-zero"),x});return(l.length===0||l.length!==d.length)&&u("invalid-animation-samples",e,"times and values must have the same non-zero length"),(l[0]!==0||l.some((p,m)=>p<0||p>o||m>0&&p<=l[m-1]))&&u("invalid-animation-time",`${e}.timesMs`,"times must start at zero and increase within the clip"),{target:t,targetId:i,interpolation:s,timesMs:l,values:d}}function Xn(n,e,r,o){let a=I(n,e,["durationMs","frames","loop"]),t=V(a.durationMs,`${e}.durationMs`);t<=0&&u("invalid-duration",`${e}.durationMs`,"expected a positive duration");let i=A(a.frames,`${e}.frames`).map((c,s)=>{let l=`${e}.frames[${s}]`,d=I(c,l,["leaves","modelMatrix","shapes","timeMs"]),p=V(d.timeMs,`${l}.timeMs`),m=A(d.shapes,`${l}.shapes`).map((P,x)=>{let f=`${l}.shapes[${x}]`,$=I(P,f,["matrix","shapeId"]),v=E($.shapeId,`${f}.shapeId`);return o.has(v)||u("unknown-reference",`${f}.shapeId`,v),{shapeId:v,matrix:X($.matrix,`${f}.matrix`)}});B(m.map(P=>P.shapeId),`${l}.shapes`);let M=A(d.leaves,`${l}.leaves`).map((P,x)=>{let f=`${l}.leaves[${x}]`,$=I(P,f,["atlasRow","leafId","matrix","opacity","visible"]),v=E($.leafId,`${f}.leafId`);r.has(v)||u("unknown-reference",`${f}.leafId`,v);let O=$.opacity===null?null:V($.opacity,`${f}.opacity`);return O!==null&&(O<0||O>1)&&u("out-of-range",`${f}.opacity`,"expected 0 <= opacity <= 1"),{leafId:v,matrix:$.matrix===null?null:X($.matrix,`${f}.matrix`),visible:$.visible===null?null:_e($.visible,`${f}.visible`),opacity:O,atlasRow:$.atlasRow===null?null:F($.atlasRow,`${f}.atlasRow`)}});return B(M.map(P=>P.leafId),`${l}.leaves`),{timeMs:p,modelMatrix:d.modelMatrix===null?null:X(d.modelMatrix,`${l}.modelMatrix`),shapes:m,leaves:M}});return i.length===0&&u("missing-frames",`${e}.frames`,"expected at least one frame"),(i[0].timeMs!==0||i.some((c,s)=>c.timeMs<0||c.timeMs>t||s>0&&c.timeMs<=i[s-1].timeMs))&&u("invalid-frame-time",`${e}.frames`,"frames must start at zero and increase within the timeline"),{durationMs:t,loop:_e(a.loop,`${e}.loop`),frames:i}}function er(n,e){let r=["retained-render"];return n==="morph-regions"&&r.push("morph-targets","sparse-updates"),n==="joint-skin"&&r.push("joint-skinning","sparse-updates"),n==="prepared-playback"&&r.push("prepared-playback","sparse-updates"),e.controls.length>0&&r.push("semantic-controls"),e.springs.length>0&&r.push("springs"),e.animations.length>0&&r.push("animation"),r}function pe(n){let r=I(n,"$",["animations","budgets","capabilities","controls","deformation","identity","materials","playback","profile","provenance","render","schema","springs","topology"]);r.schema!==oe&&u("invalid-schema","$.schema",`expected ${oe}`);let o=I(r.identity,"$.identity",["id","name","revision"]),a={id:E(o.id,"$.identity.id"),name:z(o.name,"$.identity.name"),revision:z(o.revision,"$.identity.revision")};on.test(a.revision)||u("invalid-revision","$.identity.revision","expected x.y.z");let t=z(r.profile,"$.profile");Dn.has(t)||u("invalid-profile","$.profile",t);let i=A(r.capabilities,"$.capabilities").map((b,R)=>{let h=z(b,`$.capabilities[${R}]`);return Fn.has(h)||u("invalid-capability",`$.capabilities[${R}]`,h),h});B(i,"$.capabilities"),i.some((b,R)=>R>0&&b<=i[R-1])&&u("non-canonical-order","$.capabilities","capabilities must be sorted");let c=I(r.budgets,"$.budgets",["maxBytes","maxFrames","maxJoints","maxLeaves","maxPolygons","maxResources","maxVertices"]),s={maxVertices:F(c.maxVertices,"$.budgets.maxVertices"),maxPolygons:F(c.maxPolygons,"$.budgets.maxPolygons"),maxLeaves:F(c.maxLeaves,"$.budgets.maxLeaves"),maxFrames:F(c.maxFrames,"$.budgets.maxFrames"),maxJoints:F(c.maxJoints,"$.budgets.maxJoints"),maxResources:F(c.maxResources,"$.budgets.maxResources"),maxBytes:F(c.maxBytes,"$.budgets.maxBytes")},l=Gn(r.topology,"$.topology"),d=A(r.materials,"$.materials").map((b,R)=>{let h=`$.materials[${R}]`,w=I(b,h,["color","id"]),L=A(w.color,`${h}.color`);L.length!==4&&u("invalid-color",`${h}.color`,"expected four components");let D=L.map((W,Q)=>{let re=V(W,`${h}.color[${Q}]`);return(re<0||re>1)&&u("out-of-range",`${h}.color[${Q}]`,"expected 0 <= component <= 1"),re});return{id:E(w.id,`${h}.id`),color:D}});d.length===0&&u("missing-materials","$.materials","expected at least one material"),B(d.map(b=>b.id),"$.materials");let p=I(r.render,"$.render",["leaves","modelMatrix","shapes"]),m=A(p.shapes,"$.render.shapes").map((b,R)=>{let h=`$.render.shapes[${R}]`,w=I(b,h,["id","matrix"]);return{id:E(w.id,`${h}.id`),matrix:X(w.matrix,`${h}.matrix`)}});m.length===0&&u("missing-shapes","$.render.shapes","expected at least one shape"),B(m.map(b=>b.id),"$.render.shapes");let M=A(p.leaves,"$.render.leaves").map((b,R)=>qn(b,`$.render.leaves[${R}]`,{polygonIds:new Set(l.polygons.map(h=>h.id)),shapeIds:new Set(m.map(h=>h.id)),materialIds:new Set(d.map(h=>h.id))}));B(M.map(b=>b.id),"$.render.leaves"),B(M.map(b=>b.polygonId),"$.render.leaves[*].polygonId"),M.length!==l.polygons.length&&u("unstable-topology","$.render.leaves","every polygon must bind exactly one retained leaf");let P={modelMatrix:X(p.modelMatrix,"$.render.modelMatrix"),shapes:m,leaves:M},x=Yn(r.deformation,"$.deformation",l);(t==="static-prepared"||t==="prepared-playback"?x.kind!=="none":x.kind!==t)&&u("profile-mismatch","$.deformation.kind",`does not match profile ${t}`);let f=new Set(x.kind==="morph-regions"?x.targets.map(b=>b.id):[]),$=new Set(x.kind==="joint-skin"?x.joints.map(b=>b.id):[]),v=A(r.controls,"$.controls").map((b,R)=>{let h=`$.controls[${R}]`,w=I(b,h,["anchor","axis","id","initial","maximum","minimum","radius","targets"]),L=V(w.minimum,`${h}.minimum`),D=V(w.maximum,`${h}.maximum`),W=V(w.initial,`${h}.initial`);(L>D||W<L||W>D)&&u("invalid-control-bounds",h,"expected minimum <= initial <= maximum");let Q=de(w.anchor,`${h}.anchor`),re=de(w.axis,`${h}.axis`);Math.hypot(...re)<1e-9&&u("invalid-control-axis",`${h}.axis`,"axis must be non-zero");let en=V(w.radius,`${h}.radius`);en<=0&&u("invalid-control-radius",`${h}.radius`,"radius must be positive");let nn=A(w.targets,`${h}.targets`).map((Ne,Tn)=>{let $e=`${h}.targets[${Tn}]`,rn=I(Ne,$e,["scale","targetId"]),Ve=E(rn.targetId,`${$e}.targetId`);return f.has(Ve)||u("unknown-reference",`${$e}.targetId`,Ve),{targetId:Ve,scale:V(rn.scale,`${$e}.scale`)}});return B(nn.map(Ne=>Ne.targetId),`${h}.targets`),{id:E(w.id,`${h}.id`),anchor:Q,axis:re,radius:en,minimum:L,maximum:D,initial:W,targets:nn}});B(v.map(b=>b.id),"$.controls");let O=new Set(v.map(b=>b.id)),C=A(r.springs,"$.springs").map((b,R)=>{let h=`$.springs[${R}]`,w=I(b,h,["controlId","damping","id","stiffness"]),L=E(w.controlId,`${h}.controlId`);O.has(L)||u("unknown-reference",`${h}.controlId`,L);let D=V(w.stiffness,`${h}.stiffness`),W=V(w.damping,`${h}.damping`);return(D<=0||W<0)&&u("invalid-spring",h,"expected stiffness > 0 and damping >= 0"),{id:E(w.id,`${h}.id`),controlId:L,stiffness:D,damping:W}});B(C.map(b=>b.id),"$.springs");let q=new Set(m.map(b=>b.id)),g=A(r.animations,"$.animations").map((b,R)=>{let h=`$.animations[${R}]`,w=I(b,h,["channels","durationMs","id","loop"]),L=V(w.durationMs,`${h}.durationMs`);L<=0&&u("invalid-duration",`${h}.durationMs`,"expected a positive duration");let D=A(w.channels,`${h}.channels`).map((Q,re)=>Qn(Q,`${h}.channels[${re}]`,{controlIds:O,jointIds:$,shapeIds:q,targetIds:f},L));D.length===0&&u("missing-channels",`${h}.channels`,"expected at least one channel");let W=D.map(Q=>`${Q.target}:${Q.targetId}`);return B(W,`${h}.channels`),{id:E(w.id,`${h}.id`),durationMs:L,loop:_e(w.loop,`${h}.loop`),channels:D}});B(g.map(b=>b.id),"$.animations");let k=r.playback===null?null:Xn(r.playback,"$.playback",new Set(M.map(b=>b.id)),q);t==="prepared-playback"!=(k!==null)&&u("profile-mismatch","$.playback","playback is required only by the prepared-playback profile");let S=I(r.provenance,"$.provenance",["generator","generatorVersion","sources"]),J=A(S.sources,"$.provenance.sources").map((b,R)=>{let h=`$.provenance.sources[${R}]`,w=I(b,h,["id","kind","license","sha256","uri"]),L=z(w.kind,`${h}.kind`);L!=="authored"&&L!=="generated"&&L!=="open-data"&&u("invalid-source-kind",`${h}.kind`,L);let D=z(w.uri,`${h}.uri`);(D.startsWith("/")||D.startsWith("file:")||D.includes("\\"))&&u("invalid-source-uri",`${h}.uri`,"local filesystem paths are forbidden");let W=w.sha256===null?null:z(w.sha256,`${h}.sha256`);return W!==null&&!Un.test(W)&&u("invalid-hash",`${h}.sha256`,"expected lowercase SHA-256"),{id:E(w.id,`${h}.id`),kind:L,uri:D,sha256:W,license:z(w.license,`${h}.license`)}});J.length===0&&u("missing-provenance","$.provenance.sources","expected at least one source"),B(J.map(b=>b.id),"$.provenance.sources");let H={generator:E(S.generator,"$.provenance.generator"),generatorVersion:z(S.generatorVersion,"$.provenance.generatorVersion"),sources:J};on.test(H.generatorVersion)||u("invalid-revision","$.provenance.generatorVersion","expected x.y.z");let Ee=er(t,{controls:v,springs:C,animations:g});for(let b of Ee)i.includes(b)||u("missing-capability","$.capabilities",`profile requires ${b}`);let ce=x.kind==="joint-skin"?x.joints.length:0,U=k?.frames.length??0,Z=[["maxVertices",l.vertices.length,s.maxVertices],["maxPolygons",l.polygons.length,s.maxPolygons],["maxLeaves",M.length,s.maxLeaves],["maxFrames",U,s.maxFrames],["maxJoints",ce,s.maxJoints]];for(let[b,R,h]of Z)R>h&&u("budget-exceeded",`$.budgets.${b}`,`${R} exceeds ${h}`);return{schema:oe,identity:a,profile:t,capabilities:i,budgets:s,topology:l,materials:d,render:P,deformation:x,controls:v,springs:C,animations:g,playback:k,provenance:H}}function ye(n){return tn.test(n)}function ke(n){try{return an(n,"$"),!0}catch{return!1}}var j=class extends Error{constructor(e,r,o,a={}){super(`${r}: ${o}`),this.name="PolyMorphPackageError",this.code=e,this.path=r,"cause"in a&&(this.cause=a.cause)}};function Je(n,e,r){if(n===null)return"null";if(typeof n=="string"||typeof n=="boolean")return JSON.stringify(n);if(typeof n=="number"){if(!Number.isFinite(n))throw new j("invalid-json",e,"numbers must be finite");return JSON.stringify(Object.is(n,-0)?0:n)}if(Array.isArray(n)){if(r.has(n))throw new j("invalid-json",e,"cycles are forbidden");r.add(n);let o=`[${n.map((a,t)=>Je(a,`${e}[${t}]`,r)).join(",")}]`;return r.delete(n),o}if(typeof n=="object"&&n){if(r.has(n))throw new j("invalid-json",e,"cycles are forbidden");let o=Object.getPrototypeOf(n);if(o!==Object.prototype&&o!==null)throw new j("invalid-json",e,"expected a plain object");r.add(n);let a=n,t=`{${Object.keys(a).sort().map(i=>{let c=a[i];if(c===void 0||typeof c=="function"||typeof c=="symbol")throw new j("invalid-json",`${e}.${i}`,"value is not JSON");return`${JSON.stringify(i)}:${Je(c,`${e}.${i}`,r)}`}).join(",")}}`;return r.delete(n),t}throw new j("invalid-json",e,"value is not JSON")}function Ue(n){return Je(n,"$",new WeakSet)}function me(n){return new TextEncoder().encode(Ue(n))}function ln(n,e="$"){let r;try{r=new TextDecoder("utf-8",{fatal:!0}).decode(n)}catch{throw new j("invalid-utf8",e,"expected UTF-8 bytes")}try{return JSON.parse(r)}catch{throw new j("invalid-json",e,"expected valid JSON")}}async function ie(n){if(!globalThis.crypto?.subtle)throw new j("missing-crypto","$","Web Crypto is required");let e=Uint8Array.from(n),r=await globalThis.crypto.subtle.digest("SHA-256",e);return[...new Uint8Array(r)].map(o=>o.toString(16).padStart(2,"0")).join("")}var nr=/^[a-f0-9]{64}$/,rr=/^\d+\.\d+\.\d+$/,or=/^[a-z0-9!#$&^_.+-]+\/[a-z0-9!#$&^_.+-]+$/,tr=new Set(["joint-skin","morph-regions","prepared-playback","static-prepared"]),ar=new Set(["data","image","model"]);function T(n,e,r){throw new j(n,e,r)}function Pe(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&T("invalid-type",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&T("invalid-keys",e,`expected exactly ${a.join(", ")}`),n}function cn(n,e){return Array.isArray(n)||T("invalid-type",e,"expected an array"),n}function ee(n,e){return(typeof n!="string"||n.length===0)&&T("invalid-string",e,"expected a non-empty string"),n}function Fe(n,e){let r=ee(n,e);return ye(r)||T("invalid-id",e,"expected a normalized kebab-case id"),r}function He(n,e){let r=ee(n,e);return ke(r)||T("invalid-path",e,"expected a normalized package-relative path"),r}function dn(n,e){let r=ee(n,e);return rr.test(r)||T("invalid-revision",e,"expected x.y.z"),r}function pn(n,e){let r=ee(n,e);return tr.has(r)||T("invalid-profile",e,r),r}function yn(n,e){let r=ee(n,e);return nr.test(r)||T("invalid-hash",e,"expected lowercase SHA-256"),r}function ir(n,e){return(typeof n!="number"||!Number.isSafeInteger(n)||n<0)&&T("invalid-bytes",e,"expected a non-negative safe integer"),n}function sr(n,e){let r=Pe(n,e,["bytes","mediaType","path","role","sha256"]),o=ee(r.role,`${e}.role`);ar.has(o)||T("invalid-role",`${e}.role`,o);let a=ee(r.mediaType,`${e}.mediaType`).toLowerCase();return(!or.test(a)||a!==r.mediaType)&&T("invalid-media-type",`${e}.mediaType`,"expected a normalized type/subtype"),o==="image"&&!a.startsWith("image/")&&T("invalid-media-type",`${e}.mediaType`,"image resources require an image media type"),{path:He(r.path,`${e}.path`),role:o,mediaType:a,bytes:ir(r.bytes,`${e}.bytes`),sha256:yn(r.sha256,`${e}.sha256`)}}function De(n,e){let r=new Set;for(let o of n)r.has(o)&&T("duplicate",e,o),r.add(o)}function mn(n,e){n.some((r,o)=>o>0&&r<=n[o-1])&&T("non-canonical-order",e,"entries must be unique and sorted")}function we(n){let e=Pe(n,"$",["identity","modelPath","profile","resources","schema"]);e.schema!==ae&&T("invalid-schema","$.schema",`expected ${ae}`);let r=Pe(e.identity,"$.identity",["id","name","revision"]),o={id:Fe(r.id,"$.identity.id"),name:ee(r.name,"$.identity.name"),revision:dn(r.revision,"$.identity.revision")},a=cn(e.resources,"$.resources").map((s,l)=>sr(s,`$.resources[${l}]`));a.length===0&&T("missing-resource","$.resources","expected at least the model resource");let t=a.map(s=>s.path);De(t,"$.resources"),mn(t,"$.resources");let i=He(e.modelPath,"$.modelPath"),c=a.filter(s=>s.role==="model");return(c.length!==1||c[0].path!==i)&&T("invalid-model-resource","$.resources","expected exactly one model resource matching modelPath"),c[0].mediaType!=="application/json"&&T("invalid-model-resource","$.resources","model resource must be application/json"),{schema:ae,identity:o,profile:pn(e.profile,"$.profile"),modelPath:i,resources:a}}function lr(n,e){let r=Pe(n,e,["id","manifestPath","manifestSha256","name","profile","revision"]),o=He(r.manifestPath,`${e}.manifestPath`);return o.endsWith("/manifest.json")||T("invalid-manifest-path",`${e}.manifestPath`,"expected a package manifest.json path"),{id:Fe(r.id,`${e}.id`),name:ee(r.name,`${e}.name`),revision:dn(r.revision,`${e}.revision`),profile:pn(r.profile,`${e}.profile`),manifestPath:o,manifestSha256:yn(r.manifestSha256,`${e}.manifestSha256`)}}function Ie(n){let e=Pe(n,"$",["defaultId","packages","schema"]);e.schema!==te&&T("invalid-schema","$.schema",`expected ${te}`);let r=cn(e.packages,"$.packages").map((t,i)=>lr(t,`$.packages[${i}]`));r.length===0&&T("missing-package","$.packages","expected at least one package");let o=r.map(t=>t.id);De(o,"$.packages"),mn(o,"$.packages"),De(r.map(t=>t.manifestPath),"$.packages[*].manifestPath");let a=Fe(e.defaultId,"$.defaultId");return o.includes(a)||T("unknown-default","$.defaultId",a),{schema:te,defaultId:a,packages:r}}var ze="model.json";function cr(n){return[...new Set(n.render.leaves.flatMap(e=>[...e.atlas?[e.atlas.resourcePath]:[],...e.fallback?[e.fallback.atlas.resourcePath]:[]]))].sort()}async function Se(n,e=[]){let r=pe(n),o=me(r),a=new Map([[ze,o]]),t=[{path:ze,role:"model",mediaType:"application/json",bytes:o.byteLength,sha256:await ie(o)}];for(let l of e){if(a.has(l.path))throw new j("duplicate",l.path,"resource path is already present");let d=Uint8Array.from(l.bytes);a.set(l.path,d),t.push({path:l.path,role:l.role,mediaType:l.mediaType,bytes:d.byteLength,sha256:await ie(d)})}for(let l of cr(r)){let d=t.find(p=>p.path===l);if(!d)throw new j("missing-resource",l,"model image is not included in the package");if(d.role!=="image")throw new j("invalid-role",l,"model image resource must use the image role")}t.sort((l,d)=>l.path<d.path?-1:l.path>d.path?1:0);let i=we({schema:ae,identity:r.identity,profile:r.profile,modelPath:ze,resources:t}),c=t.reduce((l,d)=>l+d.bytes,0);if(t.length>r.budgets.maxResources)throw new j("budget-exceeded","$.budgets.maxResources",`${t.length} resources exceed ${r.budgets.maxResources}`);if(c>r.budgets.maxBytes)throw new j("budget-exceeded","$.budgets.maxBytes",`${c} bytes exceed ${r.budgets.maxBytes}`);let s=me(i);return{manifest:i,manifestBytes:s,manifestSha256:await ie(s),files:a}}async function un(n,e){let r=e.map(t=>({id:t.manifest.identity.id,name:t.manifest.identity.name,revision:t.manifest.identity.revision,profile:t.manifest.profile,manifestPath:t.manifestPath,manifestSha256:t.manifestSha256}));r.sort((t,i)=>t.id<i.id?-1:t.id>i.id?1:0);let o=Ie({schema:te,defaultId:n,packages:r}),a=me(o);return{catalog:o,bytes:a,sha256:await ie(a)}}function fn(n,e){if(e.identity.id!==n.identity.id||e.identity.name!==n.identity.name||e.identity.revision!==n.identity.revision||e.profile!==n.profile)throw new j("profile-mismatch","$.model","model identity or profile does not match its manifest")}var hn=require("fs/promises"),K=require("path");var Me=class extends Error{constructor(e,r,o){super(`${r}: ${o}`),this.name="PolyMorphPrepareError",this.code=e,this.path=r}};function y(n,e,r){throw new Me(n,e,r)}var ue="polycss-morph.prepare@1";function fe(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&y("invalid-config",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&y("invalid-config",e,`expected exactly ${a.join(", ")}`),n}function be(n,e){return Array.isArray(n)||y("invalid-config",e,"expected an array"),n}function ne(n,e){return(typeof n!="string"||n.length===0||n!==n.trim())&&y("invalid-config",e,"expected non-empty trimmed text"),n}function Ge(n,e){let r=ne(n,e);return ye(r)||y("invalid-config",e,"expected a normalized kebab-case id"),r}function gn(n,e){return(typeof n!="number"||!Number.isFinite(n))&&y("invalid-config",e,"expected a finite number"),n}function se(n,e){let r=gn(n,e);return(!Number.isSafeInteger(r)||r<1)&&y("invalid-config",e,"expected a positive integer"),r}function dr(n){let e=fe(n,"$.budgets",["maxBytes","maxFrames","maxJoints","maxLeaves","maxPolygons","maxResources","maxVertices"]);return{maxVertices:se(e.maxVertices,"$.budgets.maxVertices"),maxPolygons:se(e.maxPolygons,"$.budgets.maxPolygons"),maxLeaves:se(e.maxLeaves,"$.budgets.maxLeaves"),maxFrames:se(e.maxFrames,"$.budgets.maxFrames"),maxJoints:se(e.maxJoints,"$.budgets.maxJoints"),maxResources:se(e.maxResources,"$.budgets.maxResources"),maxBytes:se(e.maxBytes,"$.budgets.maxBytes")}}function qe(n){let e=fe(n,"$",["animations","budgets","controls","identity","morphAliases","profile","schema","source","springs","transform"]);e.schema!==ue&&y("invalid-config","$.schema",`expected ${ue}`);let r=fe(e.identity,"$.identity",["id","name","revision"]),o={id:Ge(r.id,"$.identity.id"),name:ne(r.name,"$.identity.name"),revision:ne(r.revision,"$.identity.revision")};/^\d+\.\d+\.\d+$/u.test(o.revision)||y("invalid-config","$.identity.revision","expected x.y.z");let a=ne(e.profile,"$.profile");a!=="morph-regions"&&a!=="static-prepared"&&y("invalid-config","$.profile","generic preparation supports morph-regions or static-prepared");let t=fe(e.source,"$.source",["id","kind","license","path","uri"]),i=ne(t.kind,"$.source.kind");i!=="authored"&&i!=="generated"&&i!=="open-data"&&y("invalid-config","$.source.kind","unknown source kind");let c=ne(t.path,"$.source.path");((0,K.isAbsolute)(c)||c.includes("\\")||c.split("/").some(f=>f===""||f==="."||f===".."))&&y("unsafe-path","$.source.path","expected a normalized config-relative path");let s={id:Ge(t.id,"$.source.id"),kind:i,path:c,uri:ne(t.uri,"$.source.uri"),license:ne(t.license,"$.source.license")};(s.uri.startsWith("/")||s.uri.startsWith("file:")||s.uri.includes("\\"))&&y("invalid-config","$.source.uri","local filesystem paths are forbidden");let l=fe(e.transform,"$.transform",["axes","center","scale","signs"]),d=be(l.axes,"$.transform.axes");(d.length!==3||d.some(f=>f!=="x"&&f!=="y"&&f!=="z")||new Set(d).size!==3)&&y("invalid-config","$.transform.axes","expected each source axis exactly once");let p=be(l.signs,"$.transform.signs");(p.length!==3||p.some(f=>f!==-1&&f!==1))&&y("invalid-config","$.transform.signs","expected three values of -1 or 1");let m=gn(l.scale,"$.transform.scale");m>0||y("invalid-config","$.transform.scale","expected a positive scale"),typeof l.center!="boolean"&&y("invalid-config","$.transform.center","expected a boolean");let M=fe(e.morphAliases,"$.morphAliases",Object.keys(e.morphAliases??{})),P=Object.fromEntries(Object.entries(M).map(([f,$])=>[ne(f,"$.morphAliases key"),Ge($,`$.morphAliases.${f}`)]).sort(([f],[$])=>f<$?-1:f>$?1:0));return new Set(Object.values(P)).size!==Object.keys(P).length&&y("invalid-config","$.morphAliases","prepared target ids must be unique"),a==="morph-regions"!=Object.keys(P).length>0&&y("invalid-config","$.morphAliases","morph-regions requires aliases and static-prepared forbids them"),{schema:ue,identity:o,profile:a,source:s,transform:{axes:d,signs:p,scale:m,center:l.center},morphAliases:P,controls:structuredClone(be(e.controls,"$.controls")),springs:structuredClone(be(e.springs,"$.springs")),animations:structuredClone(be(e.animations,"$.animations")),budgets:dr(e.budgets)}}async function Ae(n){let e;try{e=JSON.parse(await(0,hn.readFile)(n,"utf8"))}catch{y("invalid-config","$","config is not readable UTF-8 JSON")}return qe(e)}function Re(n,e){let r=(0,K.resolve)((0,K.dirname)(n)),o=(0,K.resolve)(r,e),a=(0,K.relative)(r,o);return(a===".."||a.startsWith(`..${K.sep}`)||(0,K.isAbsolute)(a))&&y("unsafe-path","$.source.path","source escapes its authoring directory"),o}var xe=require("@layoutit/polycss");var Mn=require("zlib"),Ce=require("@layoutit/polycss");var Oe=1.5,he=4,pr=Uint8Array.from([137,80,78,71,13,10,26,10]);function G(n){let e=Number(n.toFixed(10));return Object.is(e,-0)?0:e}function bn(n,e){let r=n.split(",").map(Number);return(r.length!==16||r.some(o=>!Number.isFinite(o)))&&y("unrenderable-triangle",e,"PolyCSS produced an invalid fallback matrix"),r.map(G)}function yr(n,e){let r=new Array(16).fill(0);for(let o=0;o<4;o+=1)for(let a=0;a<4;a+=1){let t=0;for(let i=0;i<4;i+=1)t+=n[i*4+a]*e[o*4+i];r[o*4+a]=G(t)}return r}function mr(n,e){let r=n[0],o=n[4],a=n[8],t=n[1],i=n[5],c=n[9],s=n[2],l=n[6],d=n[10],p=r*(i*d-c*l)-o*(t*d-c*s)+a*(t*l-i*s);(!Number.isFinite(p)||Math.abs(p)<=1e-12)&&y("unrenderable-triangle",e,"solid triangle matrix is not invertible");let m=1/p,M=(i*d-c*l)*m,P=(a*l-o*d)*m,x=(o*c-a*i)*m,f=(c*s-t*d)*m,$=(r*d-a*s)*m,v=(a*t-r*c)*m,O=(t*l-i*s)*m,C=(o*s-r*l)*m,q=(r*i-o*t)*m,g=n[12],k=n[13],S=n[14];return[G(M),G(f),G(O),0,G(P),G($),G(C),0,G(x),G(v),G(q),0,G(-(M*g+P*k+x*S)),G(-(f*g+$*k+v*S)),G(-(O*g+C*k+q*S)),1]}function ur(n,e){if(e===0)return n;let r=bn(n,"$.render.fallback"),o=[...r];return o[12]-=e*r[0]+e*r[4],o[13]-=e*r[1]+e*r[5],o[14]-=e*r[2]+e*r[6],o.map(G).join(",")}function fr(n){let[e,r,o]=n,a=[r[0]-e[0],r[1]-e[1],r[2]-e[2]],t=[o[0]-e[0],o[1]-e[1],o[2]-e[2]],i=[a[1]*t[2]-a[2]*t[1],a[2]*t[0]-a[0]*t[2],a[0]*t[1]-a[1]*t[0]],c=Math.hypot(...i);if(c<=1e-12)return null;let s=[i[0]/c,i[1]/c,i[2]/c];return{normal:s,plane:s[0]*e[0]+s[1]*e[1]+s[2]*e[2]}}function hr(n){let e=n.map(a=>fr(a.vertices)),r=new Map;for(let a=0;a<n.length;a+=1){let t=n[a].vertexIndices;for(let i=0;i<3;i+=1){let c=t[i],s=t[(i+1)%3],l=c<s?`${c}:${s}`:`${s}:${c}`,d={polygonIndex:a,edgeIndex:i},p=r.get(l);p?p.push(d):r.set(l,[d])}}let o=Array.from({length:n.length},()=>new Set);for(let a of r.values())for(let t=0;t<a.length;t+=1)for(let i=t+1;i<a.length;i+=1){let c=a[t],s=a[i],l=n[c.polygonIndex],d=n[s.polygonIndex],p=e[c.polygonIndex],m=e[s.polygonIndex];l.materialId!==d.materialId||!p||!m||p.normal[0]*m.normal[0]+p.normal[1]*m.normal[1]+p.normal[2]*m.normal[2]<1-1e-6||Math.abs(p.plane-m.plane)>1e-5||(o[c.polygonIndex].add(c.edgeIndex),o[s.polygonIndex].add(s.edgeIndex))}return o}function gr(n,e){return n.map((r,o)=>{let a={color:"#ffffff",vertices:r.vertices.map(([s,l,d])=>[l,s,d])},t=(0,Ce.computeTextureAtlasPlanPublic)(a,o,{tileSize:1,layerElevation:1,seamBleed:0});t||y("unrenderable-triangle",`$.render.leaves[${o}].fallback`,"PolyCSS produced no per-polygon atlas plan");let i=e[o],c=i.size>0?Math.ceil(Oe):0;return{...t,matrix:ur(t.matrix,c),canvasW:t.canvasW+c*2,canvasH:t.canvasH+c*2,screenPts:t.screenPts.map(s=>s+c),seamBleed:i.size>0?Oe:void 0,seamBleedEdges:new Set(i),seamBleedEdgeAmounts:i.size>0?new Map([...i].map(s=>[s,Oe])):void 0}})}function Pr(n,e,r,o){let a=0;for(let i=0;i<n.length;i+=2){let c=(i+2)%n.length;a+=n[i]*n[c+1]-n[c]*n[i+1]}let t=a>=0?1:-1;for(let i=0;i<n.length;i+=2){let c=i/2,s=(i+2)%n.length,l=n[i],d=n[i+1],p=n[s],m=n[s+1],M=p-l,P=m-d,x=Math.hypot(M,P);if(x<=1e-12||t*(M*(o-d)-P*(r-l))/x<-(e.has(c)?Oe:0))return!1}return!0}function Mr(n,e,r){let o=0,a=n.seamBleedEdges??new Set;for(let t=0;t<he;t+=1)for(let i=0;i<he;i+=1)Pr(n.screenPts,a,e+(i+.5)/he,r+(t+.5)/he)&&(o+=1);return Math.round(o*255/(he*he))}function br(n){let e=4294967295;for(let r of n){e^=r;for(let o=0;o<8;o+=1)e=e>>>1^3988292384&-(e&1)}return(e^4294967295)>>>0}function We(n,e){let r=new TextEncoder().encode(n),o=new Uint8Array(12+e.byteLength),a=new DataView(o.buffer);return a.setUint32(0,e.byteLength),o.set(r,4),o.set(e,8),a.setUint32(8+e.byteLength,br(o.subarray(4,8+e.byteLength))),o}function xr(n){let e=new Uint8Array(n.reduce((o,a)=>o+a.byteLength,0)),r=0;for(let o of n)e.set(o,r),r+=o.byteLength;return e}function $r(n,e,r){let o=1+n*4,a=new Uint8Array(e*o);for(let c of r)for(let s=0;s<c.canvasH;s+=1)for(let l=0;l<c.canvasW;l+=1){let d=Mr(c,l,s);if(d===0)continue;let p=(c.y+s)*o+1+(c.x+l)*4;a[p]=255,a[p+1]=255,a[p+2]=255,a[p+3]=d}let t=new Uint8Array(13),i=new DataView(t.buffer);return i.setUint32(0,n),i.setUint32(4,e),t[8]=8,t[9]=6,xr([pr,We("IHDR",t),We("IDAT",(0,Mn.deflateSync)(a,{level:9})),We("IEND",new Uint8Array)])}function Pn(n){return`assets/solid-triangles-${String(n).padStart(3,"0")}.png`}function xn(n){let e=gr(n,hr(n)),{packed:r,atlasScale:o}=(0,Ce.packTextureAtlasPlansWithScale)(e,1,null,"local");o!==1&&y("invalid-atlas","$.render.fallback","per-polygon fallback atlas must retain CSS-pixel resolution");let a=n.map((i,c)=>{let s=r.entries[c];s||y("invalid-atlas",`$.render.leaves[${c}].fallback`,"per-polygon fallback was not packed");let l=r.pages[s.pageIndex],d=bn(s.atlasMatrix,`$.render.leaves[${c}].fallback.matrix`);return{width:s.canvasW,height:s.canvasH,matrixFromLeaf:yr(mr(i.leafMatrix,`$.render.leaves[${c}].matrix`),d),atlas:{resourcePath:Pn(s.pageIndex),x:s.x,y:s.y,width:s.canvasW,height:s.canvasH,pageWidth:l.width,pageHeight:l.height}}}),t=r.pages.map((i,c)=>({path:Pn(c),width:i.width,height:i.height,bytes:$r(i.width,i.height,i.entries)}));return{fallbacks:a,pages:t}}var $n={name:"@layoutit/polycss-morph",version:"0.2.10",description:"Prepared retained-model deformation and playback for PolyCSS.",type:"module",main:"dist/index.cjs",module:"dist/index.js",types:"dist/index.d.ts",keywords:["polycss","morph","animation","skinning","3d","css","matrix3d","dom"],license:"MIT",repository:{type:"git",url:"https://github.com/LayoutitStudio/polycss.git",directory:"packages/morph"},bugs:{url:"https://github.com/LayoutitStudio/polycss/issues"},homepage:"https://github.com/LayoutitStudio/polycss#readme",files:["dist"],exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.js",require:"./dist/index.cjs"},"./prepare":{types:"./dist/prepare.d.ts",import:"./dist/prepare.js",require:"./dist/prepare.cjs"}},typesVersions:{"*":{prepare:["dist/prepare.d.ts"]}},scripts:{build:"tsup",test:"vitest run","test:package":"node scripts/certify-package.mjs","test:package:registry":"node scripts/certify-package.mjs --registry-dependencies","test:coverage":"vitest run --coverage",prepack:"node ../../.github/scripts/sync-package-readmes.mjs",prepublishOnly:"npm run build"},publishConfig:{access:"public"},dependencies:{"@layoutit/polycss":"workspace:^"},devDependencies:{"@types/node":"^25.0.0","@vitest/coverage-v8":"^3.1.1","happy-dom":"^20.7.0",tsup:"^8.0.1",typescript:"^5.3.3",vitest:"^3.1.1"}};var vn=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],kr=$n.version;function je(n){let e=Number(n.toFixed(10));return Object.is(e,-0)?0:e}function Ke(n){return[je(n[0]),je(n[1]),je(n[2])]}function kn(n,e){let o=n.normalize("NFKD").replace(/([a-z0-9])([A-Z])/gu,"$1-$2").replace(/[^A-Za-z0-9]+/gu,"-").replace(/^-+|-+$/gu,"").toLowerCase()||e;return/^[a-z]/u.test(o)?o:`item-${o}`}function wr(n,[e,r,o]){let a=n[3]*e+n[7]*r+n[11]*o+n[15];return(!Number.isFinite(a)||Math.abs(a)<1e-12)&&y("invalid-transform","$.source.nodes","node has a singular projective transform"),[(n[0]*e+n[4]*r+n[8]*o+n[12])/a,(n[1]*e+n[5]*r+n[9]*o+n[13])/a,(n[2]*e+n[6]*r+n[10]*o+n[14])/a]}function In(n,[e,r,o]){return[n[0]*e+n[4]*r+n[8]*o,n[1]*e+n[5]*r+n[9]*o,n[2]*e+n[6]*r+n[10]*o]}function wn(n,e){let r={x:n[0],y:n[1],z:n[2]};return Ke(e.transform.axes.map((o,a)=>r[o]*e.transform.signs[a]*e.transform.scale))}function Ir(n,e){let o=[[1,0,0],[0,1,0],[0,0,1]].map(s=>{let l=In(n,s),d={x:l[0],y:l[1],z:l[2]};return e.transform.axes.map((p,m)=>d[p]*e.transform.signs[m]*e.transform.scale)}),[a,t,i]=o;return a[0]*(t[1]*i[2]-t[2]*i[1])-t[0]*(a[1]*i[2]-a[2]*i[1])+i[0]*(a[1]*t[2]-a[2]*t[1])<0}function Ye(n,e){return[n[0]-e[0],n[1]-e[1],n[2]-e[2]]}function Sr(n,e){return[n[1]*e[2]-n[2]*e[1],n[2]*e[0]-n[0]*e[2],n[0]*e[1]-n[1]*e[0]]}function Ar(n,e){let r=Math.hypot(...n);return r>1e-10||y("degenerate-triangle",e,"triangle has zero area"),Ke(n.map(o=>o/r))}function Rr(n,e){let r=Array.from({length:n.length},()=>[0,0,0]);for(let o of e){let[a,t,i]=o.vertexIndices.map(s=>n[s]),c=Sr(Ye(t,a),Ye(i,a));Math.hypot(...c)<=1e-10&&y("degenerate-triangle",`$.topology.${o.id}`,"triangle has zero area");for(let s of o.vertexIndices)r[s][0]+=c[0],r[s][1]+=c[1],r[s][2]+=c[2]}return r.map((o,a)=>Ar(o,`$.topology.normals[${a}]`))}function Or(n,e){let r={vertices:n.map(l=>[...l])},[o,a,t]=n,i=(0,xe.computeSolidTrianglePlanFromCssPoints)(r,0,{seamBleed:0},{includeColor:!1,matrixDecimals:10,primitive:"border"},o[0],o[1],o[2],a[0],a[1],a[2],t[0],t[1],t[2]),s=/^matrix3d\(([^)]+)\)$/u.exec(i?.transformText??"")?.[1]?.split(",").map(Number);return(!s||s.length!==16||s.some(l=>!Number.isFinite(l)))&&y("unrenderable-triangle",e,"PolyCSS produced no stable matrix"),s.map(je)}function Cr(n){let e=new Set(["retained-render"]);return n.profile==="morph-regions"&&(e.add("morph-targets"),e.add("sparse-updates")),n.controls.length>0&&e.add("semantic-controls"),n.springs.length>0&&e.add("springs"),n.animations.length>0&&e.add("animation"),[...e].sort()}async function Ze(n,e){let r=[],o=[],a=[],t=Object.entries(e.morphAliases),i=new Map(t.map(([,g])=>[g,[]])),c=new Set,s=0,l=0;for(let g of n.instances){let k=Ir(g.matrix,e);for(let S of g.primitives){let J=`shape-${String(s).padStart(4,"0")}-${kn(`${g.meshName}-${S.primitiveIndex}`,"mesh")}`;a.push({id:J,matrix:vn});let H=new Map(S.targets.map(U=>[U.name,U]));t.some(([U])=>!H.has(U))&&y("missing-morph",`$.source.${J}`,"every primitive must contain every configured morph target");let Ee=[...new Set(S.triangles.flat())].sort((U,Z)=>U-Z),ce=new Map;for(let U of Ee){let Z=S.positions[U];ce.set(U,r.length);let b=wr(g.matrix,Z);r.push(wn(b,e));for(let[R,h]of t){let w=H.get(R).positionDeltas[U],L=In(g.matrix,w);i.get(h).push(wn(L,e))}}c.add(S.materialIndex);for(let U of S.triangles){let Z=k?[U[0],U[2],U[1]]:U;o.push({id:`polygon-${String(l).padStart(6,"0")}`,shapeId:J,materialIndex:S.materialIndex,vertexIndices:[ce.get(Z[0]),ce.get(Z[1]),ce.get(Z[2])]}),l+=1}s+=1}}if(e.transform.center){let g=[1/0,1/0,1/0],k=[-1/0,-1/0,-1/0];for(let J of r)for(let H=0;H<3;H+=1)g[H]=Math.min(g[H],J[H]),k[H]=Math.max(k[H],J[H]);let S=g.map((J,H)=>(J+k[H])/2);for(let J=0;J<r.length;J+=1)r[J]=Ke(Ye(r[J],S))}let d=[...c].sort((g,k)=>g-k),p=new Map(n.materials.map(g=>[g.sourceIndex,g])),m=d.map(g=>{let k=g===-1?{name:"Default",color:[1,1,1,1]}:p.get(g);return k||y("invalid-material","$.source.materials",`primitive references missing material ${g}`),{sourceIndex:g,id:g===-1?"material-default":`material-${String(g).padStart(4,"0")}-${kn(k.name,"source")}`,color:k.color}}),M=new Map(m.map(g=>[g.sourceIndex,g.id])),P=o.map(g=>({id:g.id,vertexIndices:g.vertexIndices,normalIndices:g.vertexIndices})),x=Rr(r,P),f=t.map(([,g])=>({id:g,deltas:i.get(g).map((k,S)=>({position:k,vertexIndex:S})).filter(({position:k})=>Math.hypot(...k)>1e-12).map(({position:k,vertexIndex:S})=>({vertexIndex:S,position:k,normal:null}))}));f.some(g=>g.deltas.length===0)&&y("empty-morph","$.morphAliases","every configured morph target must move at least one vertex");let $=o.map(g=>{let k=M.get(g.materialIndex);return{id:`leaf-${g.id}`,polygonId:g.id,shapeId:g.shapeId,materialId:k,strategy:"solid-triangle",width:xe.SOLID_TRIANGLE_CANONICAL_SIZE,height:xe.SOLID_TRIANGLE_CANONICAL_SIZE,matrix:Or(g.vertexIndices.map(S=>r[S]),`$.render.${g.id}`),atlas:null,fallback:null}}),v=xn(o.map((g,k)=>({vertexIndices:g.vertexIndices,vertices:g.vertexIndices.map(S=>r[S]),materialId:M.get(g.materialIndex),leafMatrix:$[k].matrix}))),O=$.map((g,k)=>({...g,fallback:v.fallbacks[k]})),C={schema:oe,identity:e.identity,profile:e.profile,capabilities:Cr(e),budgets:e.budgets,topology:{vertices:r,normals:x,polygons:P},materials:m.map(({id:g,color:k})=>({id:g,color:k})),render:{modelMatrix:vn,shapes:a,leaves:O},deformation:e.profile==="morph-regions"?{kind:"morph-regions",targets:f}:{kind:"none"},controls:e.controls,springs:e.springs,animations:e.animations,playback:null,provenance:{generator:"polycss-morph",generatorVersion:kr,sources:[{id:e.source.id,kind:e.source.kind,uri:e.source.uri,sha256:n.contentSha256,license:e.source.license}]}};return{model:pe(C),fallbackAtlasPages:v.pages}}async function Te(n,e){let r=await Ze(n,e),o=await Se(r.model,[...r.fallbackAtlasPages.map(a=>({path:a.path,role:"image",mediaType:"image/png",bytes:a.bytes}))]);return{source:n,prepared:r,package:o}}var An=require("crypto"),Xe=require("fs/promises"),Y=require("path");var jr={SCALAR:1,VEC2:2,VEC3:3,VEC4:4,MAT4:16},Tr={5120:1,5121:1,5122:2,5123:2,5125:4,5126:4};function Qe(n){return(0,An.createHash)("sha256").update(n).digest("hex")}function Rn(n,e){try{let r=JSON.parse(new TextDecoder("utf-8",{fatal:!0}).decode(n));return(!r||typeof r!="object"||Array.isArray(r))&&y("invalid-gltf",e,"expected a JSON object"),r}catch(r){if(r instanceof Error&&r.name==="PolyMorphPrepareError")throw r;y("invalid-gltf",e,"expected UTF-8 JSON")}}function Lr(n){n.byteLength<20&&y("invalid-glb","$.source","GLB is truncated");let e=new DataView(n.buffer,n.byteOffset,n.byteLength);(e.getUint32(0,!0)!==1179937895||e.getUint32(4,!0)!==2||e.getUint32(8,!0)!==n.byteLength)&&y("invalid-glb","$.source","invalid GLB header");let r=12,o=null,a=null;for(;r<n.byteLength;){r+8>n.byteLength&&y("invalid-glb","$.source","truncated GLB chunk header");let t=e.getUint32(r,!0),i=e.getUint32(r+4,!0),c=r+8,s=c+t;(t%4!==0||s>n.byteLength)&&y("invalid-glb","$.source","invalid GLB chunk bounds"),i===1313821514?(o&&y("invalid-glb","$.source","duplicate JSON chunk"),o=Rn(n.subarray(c,s),"$.source.json")):i===5130562?(a&&y("invalid-glb","$.source","duplicate binary chunk"),a=n.subarray(c,s)):y("invalid-glb","$.source",`unsupported GLB chunk type ${i}`),r=s}return o||y("invalid-glb","$.source","missing JSON chunk"),{json:o,binary:a}}function Er(n,e){return(typeof n!="string"||n.length===0||(0,Y.isAbsolute)(n)||n.includes("\\")||n.includes("?")||n.includes("#")||n.split("/").some(r=>r===""||r==="."||r===".."))&&y("unsafe-path",e,"expected a normalized source-relative path"),n}function Nr(n,e){let r=/^data:application\/(?:octet-stream|gltf-buffer);base64,([A-Za-z0-9+/]*={0,2})$/u.exec(n);return r||y("unsupported-uri",e,"expected a base64 glTF buffer data URI"),Uint8Array.from(Buffer.from(r[1],"base64"))}async function Vr(n,e,r){let o=Array.isArray(n.buffers)?n.buffers:[];o.length===0&&y("missing-buffer","$.source.buffers","expected at least one buffer");let a=(0,Y.dirname)(e),t=[],i=[];for(let[c,s]of o.entries()){let l=`$.source.buffers[${c}]`;(!Number.isSafeInteger(s?.byteLength)||s.byteLength<0)&&y("invalid-buffer",l,"invalid byteLength");let d,p;if(s.uri===void 0)(c!==0||!r)&&y("missing-buffer",l,"missing URI or GLB binary chunk"),d=r,p="<glb-bin>";else if(typeof s.uri=="string"&&s.uri.startsWith("data:"))d=Nr(s.uri,`${l}.uri`),p="<embedded-base64>";else{let P=Er(s.uri,`${l}.uri`),x=(0,Y.resolve)(a,P),f=(0,Y.relative)(a,x);(f===".."||f.startsWith(`..${Y.sep}`)||(0,Y.isAbsolute)(f))&&y("unsafe-path",`${l}.uri`,"buffer escapes source directory"),d=new Uint8Array(await(0,Xe.readFile)(x)),p=P}let m=s.byteLength;(d.byteLength<m||d.byteLength-m>3)&&y("invalid-buffer",l,"buffer length disagrees with byteLength");let M=d.subarray(0,m);t.push(M),i.push({path:p,sha256:Qe(M)})}return{buffers:t,files:i}}function Br(n,e,r){switch(e){case 5120:return n.getInt8(r);case 5121:return n.getUint8(r);case 5122:return n.getInt16(r,!0);case 5123:return n.getUint16(r,!0);case 5125:return n.getUint32(r,!0);case 5126:return n.getFloat32(r,!0);default:y("invalid-accessor","$.source.accessors",`unsupported component type ${e}`)}}function _r(n,e){switch(e){case 5120:return Math.max(-1,n/127);case 5121:return n/255;case 5122:return Math.max(-1,n/32767);case 5123:return n/65535;case 5125:return n/4294967295;default:return n}}function Jr(n,e){let r=Array.isArray(n.accessors)?n.accessors:[],o=Array.isArray(n.bufferViews)?n.bufferViews:[];return(a,t)=>{let i=r[a];(!i||i.sparse!==void 0||!Number.isSafeInteger(i.count)||i.count<0)&&y("invalid-accessor",t,"missing, sparse, or invalid accessor");let c=jr[i.type],s=Tr[i.componentType],l=o[i.bufferView];(!c||!s||!l||!Number.isSafeInteger(i.bufferView)||!Number.isSafeInteger(l.buffer))&&y("invalid-accessor",t,"unsupported accessor metadata");let d=e[l.buffer];d||y("invalid-accessor",t,"references an absent buffer");let p=c*s,m=l.byteStride??p,M=l.byteOffset??0,P=i.byteOffset??0,x=l.byteLength,f=M+P,$=f+Math.max(0,i.count-1)*m+p;(!Number.isSafeInteger(M)||M<0||!Number.isSafeInteger(x)||x<0||M+x>d.byteLength||!Number.isSafeInteger(P)||P<0||P%s!==0||!Number.isSafeInteger(m)||m<p||l.byteStride!==void 0&&(m>252||m%4!==0)||!Number.isSafeInteger(f)||f<0||f%s!==0||$>M+x)&&y("invalid-accessor",t,"invalid accessor byte layout");let v=new DataView(d.buffer,d.byteOffset,d.byteLength),O=[];for(let C=0;C<i.count;C+=1){let q=[];for(let g=0;g<c;g+=1){let k=Br(v,i.componentType,f+C*m+g*s),S=i.normalized?_r(k,i.componentType):k;Number.isFinite(S)||y("invalid-accessor",`${t}[${C}][${g}]`,"non-finite component"),q.push(Object.is(S,-0)?0:S)}O.push(c===1?q[0]:q)}return O}}function Sn(n,e){return n.map((r,o)=>((!Array.isArray(r)||r.length!==3)&&y("invalid-accessor",`${e}[${o}]`,"expected VEC3"),[r[0],r[1],r[2]]))}function Ur(n,e,r){let o=e.map((t,i)=>((!Number.isSafeInteger(t)||t<0)&&y("invalid-index",`${r}[${i}]`,"expected an unsigned integer"),t)),a=[];if(n===4){o.length%3!==0&&y("invalid-primitive",r,"incomplete triangle list");for(let t=0;t<o.length;t+=3)a.push([o[t],o[t+1],o[t+2]])}else if(n===5)for(let t=2;t<o.length;t+=1)a.push(t%2===0?[o[t-2],o[t-1],o[t]]:[o[t-1],o[t-2],o[t]]);else if(n===6)for(let t=2;t<o.length;t+=1)a.push([o[0],o[t-1],o[t]]);else y("unsupported-primitive",r,`mode ${n} is not triangles, triangle strip, or triangle fan`);return a.filter(([t,i,c])=>t!==i&&i!==c&&t!==c)}var Dr=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1];function Fr(n,e){let r=new Array(16).fill(0);for(let o=0;o<4;o+=1)for(let a=0;a<4;a+=1)for(let t=0;t<4;t+=1)r[o*4+a]+=n[t*4+a]*e[o*4+t];return r}function Hr(n,e){if(n.matrix!==void 0)return(!Array.isArray(n.matrix)||n.matrix.length!==16||n.matrix.some(C=>typeof C!="number"||!Number.isFinite(C))||n.translation!==void 0||n.rotation!==void 0||n.scale!==void 0)&&y("invalid-node",e,"invalid or ambiguous node matrix"),n.matrix;let r=n.translation??[0,0,0],o=n.rotation??[0,0,0,1],a=n.scale??[1,1,1];(!Array.isArray(r)||r.length!==3||!Array.isArray(o)||o.length!==4||!Array.isArray(a)||a.length!==3||[...r,...o,...a].some(C=>typeof C!="number"||!Number.isFinite(C)))&&y("invalid-node",e,"invalid node TRS");let[t,i,c,s]=o,l=Math.hypot(t,i,c,s);l>0||y("invalid-node",`${e}.rotation`,"zero quaternion");let d=t/l,p=i/l,m=c/l,M=s/l,[P,x,f]=a,[$,v,O]=r;return[(1-2*(p*p+m*m))*P,2*(d*p+m*M)*P,2*(d*m-p*M)*P,0,2*(d*p-m*M)*x,(1-2*(d*d+m*m))*x,2*(p*m+d*M)*x,0,2*(d*m+p*M)*f,2*(p*m-d*M)*f,(1-2*(d*d+p*p))*f,0,$,v,O,1]}function zr(n){let e=Array.isArray(n.nodes)?n.nodes:[],r=Array.isArray(n.scenes)?n.scenes:[],o;if(r.length>0){let i=n.scene??0,c=r[i]?.nodes;Array.isArray(c)||y("invalid-scene","$.source.scene","default scene has no nodes"),o=c}else{let i=new Set(e.flatMap(c=>Array.isArray(c.children)?c.children:[]));o=e.map((c,s)=>s).filter(c=>!i.has(c))}let a=[],t=(i,c,s)=>{(!Number.isSafeInteger(i)||i<0||i>=e.length)&&y("invalid-node","$.source.nodes",`unknown node ${i}`),s.has(i)&&y("invalid-node","$.source.nodes",`node cycle at ${i}`);let l=e[i],d=Fr(c,Hr(l,`$.source.nodes[${i}]`));l.mesh!==void 0&&((!Number.isSafeInteger(l.mesh)||l.mesh<0)&&y("invalid-node",`$.source.nodes[${i}].mesh`,"invalid mesh index"),a.push({nodeIndex:i,nodeName:typeof l.name=="string"&&l.name.length>0?l.name:`node-${i}`,meshIndex:l.mesh,matrix:d}));let p=new Set(s).add(i),m=l.children??[];Array.isArray(m)||y("invalid-node",`$.source.nodes[${i}].children`,"expected an array");for(let M of m)t(M,d,p)};for(let i of o)t(i,Dr,new Set);return a}function Gr(n){return(Array.isArray(n.materials)?n.materials:[]).map((r,o)=>{(!r||typeof r!="object"||Array.isArray(r))&&y("invalid-material",`$.source.materials[${o}]`,"expected a material object");let a=r.pbrMetallicRoughness?.baseColorFactor??[1,1,1,1];return(!Array.isArray(a)||a.length!==4||a.some(t=>typeof t!="number"||!Number.isFinite(t)||t<0||t>1))&&y("invalid-material",`$.source.materials[${o}]`,"baseColorFactor must have four unit components"),{sourceIndex:o,name:typeof r.name=="string"&&r.name.length>0?r.name:`material-${o}`,color:[a[0],a[1],a[2],a[3]]}})}function qr(n,e,r){let o=Jr(n,e),a=Array.isArray(n.meshes)?n.meshes:[];return r.map(t=>{let i=a[t.meshIndex];(!i||!Array.isArray(i.primitives)||i.primitives.length===0)&&y("invalid-mesh",`$.source.meshes[${t.meshIndex}]`,"mesh has no primitives");let c=Array.isArray(i.extras?.targetNames)?i.extras.targetNames.map(String):[],s=i.primitives.map((l,d)=>{let p=`$.source.meshes[${t.meshIndex}].primitives[${d}]`;(!l?.attributes||!Number.isSafeInteger(l.attributes.POSITION))&&y("invalid-primitive",p,"missing POSITION accessor");let m=Sn(o(l.attributes.POSITION,`${p}.POSITION`),`${p}.POSITION`),M=l.indices===void 0?m.map(($,v)=>v):o(l.indices,`${p}.indices`),P=Ur(l.mode??4,M,`${p}.indices`);(P.length===0||P.some($=>$.some(v=>v>=m.length)))&&y("invalid-index",p,"triangle indices are empty or out of range");let x=Array.isArray(l.targets)?l.targets.map(($,v)=>{Number.isSafeInteger($.POSITION)||y("invalid-morph",`${p}.targets[${v}]`,"missing POSITION accessor");let O=Sn(o($.POSITION,`${p}.targets[${v}].POSITION`),`${p}.targets[${v}].POSITION`);return O.length!==m.length&&y("invalid-morph",`${p}.targets[${v}]`,"target does not cover POSITION"),{index:v,name:c[v]??`morph-${v}`,positionDeltas:O}}):[],f=l.material??-1;return(!Number.isSafeInteger(f)||f<-1)&&y("invalid-material",`${p}.material`,"invalid material index"),{primitiveIndex:d,materialIndex:f,positions:m,triangles:P,targets:x}});return{...t,meshName:typeof i.name=="string"&&i.name.length>0?i.name:`mesh-${t.meshIndex}`,primitives:s}})}async function Le(n){let e=(0,Y.resolve)(n),r=new Uint8Array(await(0,Xe.readFile)(e)),o=(0,Y.extname)(e).toLowerCase(),a,t,i=null;o===".glb"?(a="glb",{json:t,binary:i}=Lr(r)):o===".gltf"?(a="gltf",t=Rn(r,"$.source")):y("unsupported-format","$.source.path","expected .gltf or .glb"),(t.asset?.version!=="2.0"||Array.isArray(t.extensionsRequired)&&t.extensionsRequired.length>0)&&y("unsupported-gltf","$.source","expected core glTF 2.0 without required extensions");let c=await Vr(t,e,i),s=qr(t,c.buffers,zr(t));s.length===0&&y("empty-model","$.source","default scene has no mesh instances");let l=Qe(r),d=Qe(new TextEncoder().encode(JSON.stringify({source:l,buffers:c.files})));return{format:a,sourceBytes:r.byteLength,sourceSha256:l,contentSha256:d,materials:Gr(t),instances:s}}var le=require("fs"),_=require("fs/promises"),N=require("path");function Wr(n){(typeof n!="string"||n.length===0)&&y("invalid-argument","$.outputRoot","expected a path");let e=(0,N.resolve)(n);return e===(0,N.parse)(e).root&&y("unsafe-path","$.outputRoot","filesystem root is forbidden"),e}async function On(n,e=""){let r=(0,N.join)(n,e),o=await(0,_.readdir)(r,{withFileTypes:!0}),a=[];for(let t of o.sort((i,c)=>i.name<c.name?-1:i.name>c.name?1:0)){let i=e===""?t.name:`${e}/${t.name}`;t.isSymbolicLink()&&y("unsafe-output",i,"symbolic links are forbidden"),t.isDirectory()?a.push(...await On(n,i)):t.isFile()?a.push(i):y("unsafe-output",i,"unsupported filesystem entry")}return a}async function Cn(n,e){if(!(0,le.existsSync)(n))return{path:"$.outputRoot",message:"prepared package is missing"};let r=await On(n),o=[...e.keys()].sort();if(r.length!==o.length||r.some((a,t)=>a!==o[t]))return{path:"$.outputRoot",message:`inventory differs: expected ${o.join(", ")}`};for(let a of o){let t=new Uint8Array(await(0,_.readFile)((0,N.join)(n,a))),i=e.get(a);if(t.byteLength!==i.byteLength||t.some((c,s)=>c!==i[s]))return{path:a,message:"prepared bytes differ"}}return null}async function Yr(n,e){let r=await Cn(n,e);r&&y("drift",r.path,r.message)}async function Kr(n,e){let r=(0,N.dirname)(n);await(0,_.mkdir)(r,{recursive:!0});let o=await(0,_.mkdtemp)((0,N.join)(r,`.polycss-morph-${(0,N.basename)(n)}-`)),a=`${n}.previous-${process.pid}`,i=[...[...e.keys()].filter(s=>s!=="manifest.json").sort(),"manifest.json"],c=!1;try{for(let s of i){let l=(0,N.resolve)(o,s),d=(0,N.relative)(o,l);(d===".."||d.startsWith(`..${N.sep}`)||(0,N.isAbsolute)(d))&&y("unsafe-path",s,"package path escapes staging"),await(0,_.mkdir)((0,N.dirname)(l),{recursive:!0}),await(0,_.writeFile)(l,e.get(s))}return(0,le.existsSync)(a)&&y("unsafe-output","$.outputRoot",`backup already exists at ${a}`),(0,le.existsSync)(n)&&(await(0,_.rename)(n,a),c=!0),await(0,_.rename)(o,n),c&&await(0,_.rm)(a,{recursive:!0,force:!0}).catch(()=>{}),i}catch(s){throw c&&!(0,le.existsSync)(n)&&(0,le.existsSync)(a)&&await(0,_.rename)(a,n),s}finally{(0,le.existsSync)(o)&&await(0,_.rm)(o,{recursive:!0,force:!0})}}async function jn(n){(!n||typeof n!="object")&&y("invalid-argument","$","expected prepare options"),(typeof n.configPath!="string"||n.configPath.length===0)&&y("invalid-argument","$.configPath","expected a path"),n.check!==void 0&&typeof n.check!="boolean"&&y("invalid-argument","$.check","expected a boolean");let e=(0,N.resolve)(n.configPath),r=Wr(n.outputRoot),o=await Ae(e),a=Re(e,o.source.path),t=await Le(a),i=await Te(t,o),c=new Map(i.package.files);c.set("manifest.json",i.package.manifestBytes);let s=[...c.keys()].sort();if(n.check)return await Yr(r,c),{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:[],checked:!0,changed:!1};if(await Cn(r,c)===null)return{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:[],checked:!1,changed:!1};let l=await Kr(r,c);return{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:l,checked:!1,changed:!0}}0&&(module.exports={POLY_MORPH_CATALOG_SCHEMA,POLY_MORPH_MODEL_SCHEMA,POLY_MORPH_PACKAGE_SCHEMA,POLY_MORPH_PREPARE_SCHEMA,PolyMorphContractError,PolyMorphPackageError,PolyMorphPrepareError,assertPolyMorphPackageModelBinding,buildPolyMorphCatalog,buildPolyMorphPackage,buildPolyMorphPreparedPackage,compilePolyMorphSource,decodePolyMorphJson,encodePolyMorphCanonicalJson,failPolyMorphPrepare,hashPolyMorphBytes,isPolyMorphId,isPolyMorphResourcePath,loadPolyMorphGltf,parsePolyMorphPrepareConfig,preparePolyMorphModel,readPolyMorphPrepareConfig,resolvePolyMorphSourcePath,stringifyPolyMorphCanonicalJson,validatePolyMorphCatalog,validatePolyMorphModel,validatePolyMorphPackageManifest});
1
+ "use strict";var Be=Object.defineProperty;var Ln=Object.getOwnPropertyDescriptor;var En=Object.getOwnPropertyNames;var Nn=Object.prototype.hasOwnProperty;var Vn=(n,e)=>{for(var r in e)Be(n,r,{get:e[r],enumerable:!0})},Bn=(n,e,r,o)=>{if(e&&typeof e=="object"||typeof e=="function")for(let a of En(e))!Nn.call(n,a)&&a!==r&&Be(n,a,{get:()=>e[a],enumerable:!(o=Ln(e,a))||o.enumerable});return n};var _n=n=>Bn(Be({},"__esModule",{value:!0}),n);var Zr={};Vn(Zr,{POLY_MORPH_CATALOG_SCHEMA:()=>te,POLY_MORPH_MODEL_SCHEMA:()=>oe,POLY_MORPH_PACKAGE_SCHEMA:()=>ae,POLY_MORPH_PREPARE_SCHEMA:()=>ue,PolyMorphContractError:()=>ge,PolyMorphPackageError:()=>j,PolyMorphPrepareError:()=>Me,assertPolyMorphPackageModelBinding:()=>fn,buildPolyMorphCatalog:()=>un,buildPolyMorphPackage:()=>Se,buildPolyMorphPreparedPackage:()=>Te,compilePolyMorphSource:()=>Ze,decodePolyMorphJson:()=>ln,encodePolyMorphCanonicalJson:()=>me,failPolyMorphPrepare:()=>y,hashPolyMorphBytes:()=>ie,isPolyMorphId:()=>ye,isPolyMorphResourcePath:()=>ke,loadPolyMorphGltf:()=>Le,parsePolyMorphPrepareConfig:()=>qe,preparePolyMorphModel:()=>jn,readPolyMorphPrepareConfig:()=>Ae,resolvePolyMorphSourcePath:()=>Re,stringifyPolyMorphCanonicalJson:()=>Ue,validatePolyMorphCatalog:()=>Ie,validatePolyMorphModel:()=>pe,validatePolyMorphPackageManifest:()=>we});module.exports=_n(Zr);var oe="polycss-morph.model@1",te="polycss-morph.catalog@1",ae="polycss-morph.package@1";var tn=/^[a-z][a-z0-9]*(?:-[a-z0-9]+)*$/,Jn=/^[a-z0-9][a-z0-9._-]*$/,on=/^\d+\.\d+\.\d+$/,Un=/^[a-f0-9]{64}$/,Dn=new Set(["joint-skin","morph-regions","prepared-playback","static-prepared"]),Fn=new Set(["animation","joint-skinning","morph-targets","prepared-playback","retained-render","semantic-controls","sparse-updates","springs"]),Hn=new Set(["atlas-slice","direct-image","solid-quad","solid-triangle"]),zn=new Set(["control-value","joint-rotation","joint-scale","joint-translation","morph-weight","shape-matrix"]),ge=class extends TypeError{constructor(e,r,o){super(`${r}: ${o}`),this.name="PolyMorphContractError",this.code=e,this.path=r}};function u(n,e,r){throw new ge(n,e,r)}function I(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&u("invalid-type",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&u("invalid-keys",e,`expected exactly ${a.join(", ")}`),n}function A(n,e){return Array.isArray(n)||u("invalid-type",e,"expected an array"),n}function z(n,e){return(typeof n!="string"||n.length===0)&&u("invalid-string",e,"expected a non-empty string"),n}function V(n,e){return(typeof n!="number"||!Number.isFinite(n))&&u("invalid-number",e,"expected a finite number"),n}function F(n,e,r=0){let o=V(n,e);return(!Number.isSafeInteger(o)||o<r)&&u("invalid-integer",e,`expected an integer >= ${r}`),o}function _e(n,e){return typeof n!="boolean"&&u("invalid-boolean",e,"expected a boolean"),n}function E(n,e){let r=z(n,e);return tn.test(r)||u("invalid-id",e,"expected a normalized kebab-case id"),r}function B(n,e){let r=new Set;for(let o of n)r.has(o)&&u("duplicate-id",e,`duplicate id ${o}`),r.add(o)}function de(n,e){let r=A(n,e);return r.length!==3&&u("invalid-vector",e,"expected three components"),r.map((o,a)=>V(o,`${e}[${a}]`))}function X(n,e){let r=A(n,e);return r.length!==16&&u("invalid-matrix",e,"expected sixteen components"),r.map((o,a)=>V(o,`${e}[${a}]`))}function an(n,e){let r=z(n,e);return r.split("/").some(o=>!Jn.test(o))&&u("invalid-path",e,"expected lowercase URL-safe package path segments"),r}function ve(n,e,r){let o=F(n,e);return o>=r&&u("out-of-range",e,`expected an index below ${r}`),o}function Gn(n,e){let r=I(n,e,["normals","polygons","vertices"]),o=A(r.vertices,`${e}.vertices`).map((i,c)=>de(i,`${e}.vertices[${c}]`)),a=A(r.normals,`${e}.normals`).map((i,c)=>de(i,`${e}.normals[${c}]`));o.length===0&&u("missing-topology",`${e}.vertices`,"expected at least one vertex"),a.length===0&&u("missing-topology",`${e}.normals`,"expected at least one normal");let t=A(r.polygons,`${e}.polygons`).map((i,c)=>{let s=`${e}.polygons[${c}]`,l=I(i,s,["id","normalIndices","vertexIndices"]),d=A(l.vertexIndices,`${s}.vertexIndices`).map((m,M)=>ve(m,`${s}.vertexIndices[${M}]`,o.length)),p=A(l.normalIndices,`${s}.normalIndices`).map((m,M)=>ve(m,`${s}.normalIndices[${M}]`,a.length));return d.length<3&&u("invalid-polygon",s,"expected at least three vertices"),p.length!==d.length&&u("invalid-polygon",s,"normal and vertex index counts must match"),new Set(d).size!==d.length&&u("invalid-polygon",s,"vertex indices must be unique"),{id:E(l.id,`${s}.id`),vertexIndices:d,normalIndices:p}});return t.length===0&&u("missing-topology",`${e}.polygons`,"expected at least one polygon"),B(t.map(i=>i.id),`${e}.polygons`),{vertices:o,normals:a,polygons:t}}function qn(n,e,r){let o=I(n,e,["atlas","fallback","height","id","materialId","matrix","polygonId","shapeId","strategy","width"]),a=z(o.strategy,`${e}.strategy`);Hn.has(a)||u("invalid-strategy",`${e}.strategy`,"unknown render strategy");let t=E(o.polygonId,`${e}.polygonId`),i=E(o.shapeId,`${e}.shapeId`),c=E(o.materialId,`${e}.materialId`);r.polygonIds.has(t)||u("unknown-reference",`${e}.polygonId`,t),r.shapeIds.has(i)||u("unknown-reference",`${e}.shapeId`,i),r.materialIds.has(c)||u("unknown-reference",`${e}.materialId`,c);let s=V(o.width,`${e}.width`),l=V(o.height,`${e}.height`);(s<=0||l<=0)&&u("invalid-size",e,"leaf dimensions must be positive");let d=a==="atlas-slice"||a==="direct-image",p=o.atlas===null?null:sn(o.atlas,`${e}.atlas`);d!==(p!==null)&&u("invalid-strategy",`${e}.atlas`,d?"image strategies require an atlas/source slice":"solid strategies cannot declare an atlas/source slice");let m=o.fallback===null?null:Wn(o.fallback,`${e}.fallback`);return m!==null&&a!=="solid-triangle"&&u("invalid-strategy",`${e}.fallback`,"only solid-triangle leaves may declare a prepared fallback"),{id:E(o.id,`${e}.id`),polygonId:t,shapeId:i,materialId:c,strategy:a,width:s,height:l,matrix:X(o.matrix,`${e}.matrix`),atlas:p,fallback:m}}function Wn(n,e){let r=I(n,e,["atlas","height","matrixFromLeaf","width"]),o=F(r.width,`${e}.width`,1),a=F(r.height,`${e}.height`,1),t=sn(r.atlas,`${e}.atlas`);return(t.width!==o||t.height!==a)&&u("invalid-size",e,"fallback dimensions must match its per-polygon atlas slice"),{width:o,height:a,matrixFromLeaf:X(r.matrixFromLeaf,`${e}.matrixFromLeaf`),atlas:t}}function sn(n,e){let r=I(n,e,["height","pageHeight","pageWidth","resourcePath","width","x","y"]),o={resourcePath:an(r.resourcePath,`${e}.resourcePath`),x:F(r.x,`${e}.x`),y:F(r.y,`${e}.y`),width:F(r.width,`${e}.width`,1),height:F(r.height,`${e}.height`,1),pageWidth:F(r.pageWidth,`${e}.pageWidth`,1),pageHeight:F(r.pageHeight,`${e}.pageHeight`,1)};return(o.x+o.width>o.pageWidth||o.y+o.height>o.pageHeight)&&u("out-of-range",e,"slice must fit inside its page"),o}function Yn(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&u("invalid-type",e,"expected a deformation object");let o=z(n.kind,`${e}.kind`);if(o==="none")return I(n,e,["kind"]),{kind:o};if(o==="morph-regions"){let a=I(n,e,["kind","targets"]),t=A(a.targets,`${e}.targets`).map((i,c)=>{let s=`${e}.targets[${c}]`,l=I(i,s,["deltas","id"]),d=A(l.deltas,`${s}.deltas`).map((m,M)=>{let P=`${s}.deltas[${M}]`,x=I(m,P,["normal","position","vertexIndex"]),f=x.position===null?null:de(x.position,`${P}.position`),$=x.normal===null?null:de(x.normal,`${P}.normal`);return f===null&&$===null&&u("empty-delta",P,"expected a position or normal delta"),{vertexIndex:ve(x.vertexIndex,`${P}.vertexIndex`,r.vertices.length),position:f,normal:$}});d.length===0&&u("missing-deltas",`${s}.deltas`,"expected at least one delta");let p=d.map(m=>String(m.vertexIndex));return B(p,`${s}.deltas`),{id:E(l.id,`${s}.id`),deltas:d}});return t.length===0&&u("missing-targets",`${e}.targets`,"expected at least one target"),B(t.map(i=>i.id),`${e}.targets`),{kind:o,targets:t}}if(o==="joint-skin"){let a=I(n,e,["joints","kind","vertices"]),t=A(a.joints,`${e}.joints`).map((l,d)=>{let p=`${e}.joints[${d}]`,m=I(l,p,["id","inverseBindMatrix","parentId","restMatrix"]);return{id:E(m.id,`${p}.id`),parentId:m.parentId===null?null:E(m.parentId,`${p}.parentId`),restMatrix:X(m.restMatrix,`${p}.restMatrix`),inverseBindMatrix:X(m.inverseBindMatrix,`${p}.inverseBindMatrix`)}});t.length===0&&u("missing-joints",`${e}.joints`,"expected at least one joint"),B(t.map(l=>l.id),`${e}.joints`),Kn(t,`${e}.joints`);let i=new Set(t.map(l=>l.id)),c=A(a.vertices,`${e}.vertices`).map((l,d)=>{let p=`${e}.vertices[${d}]`,m=I(l,p,["influences","vertexIndex"]),M=ve(m.vertexIndex,`${p}.vertexIndex`,r.vertices.length),P=A(m.influences,`${p}.influences`).map((f,$)=>{let v=`${p}.influences[${$}]`,O=I(f,v,["jointId","weight"]),C=E(O.jointId,`${v}.jointId`);i.has(C)||u("unknown-reference",`${v}.jointId`,C);let q=V(O.weight,`${v}.weight`);return(q<=0||q>1)&&u("invalid-weight",`${v}.weight`,"expected 0 < weight <= 1"),{jointId:C,weight:q}});P.length===0&&u("missing-influences",`${p}.influences`,"expected at least one influence"),B(P.map(f=>f.jointId),`${p}.influences`);let x=P.reduce((f,$)=>f+$.weight,0);return Math.abs(x-1)>1e-6&&u("invalid-weight",`${p}.influences`,"weights must sum to 1"),{vertexIndex:M,influences:P}});c.length!==r.vertices.length&&u("missing-skin-vertex",`${e}.vertices`,"every topology vertex must have one skin record");let s=c.map(l=>String(l.vertexIndex));return B(s,`${e}.vertices`),{kind:o,joints:t,vertices:c}}u("invalid-deformation",`${e}.kind`,`unknown deformation kind ${o}`)}function Kn(n,e){let r=new Map(n.map(a=>[a.id,a]));n.filter(a=>a.parentId===null).length!==1&&u("invalid-hierarchy",e,"expected exactly one root joint");for(let a of n){a.parentId!==null&&!r.has(a.parentId)&&u("unknown-reference",e,`joint ${a.id} references ${a.parentId}`);let t=new Set,i=a;for(;i;)t.has(i.id)&&u("invalid-hierarchy",e,`cycle at joint ${i.id}`),t.add(i.id),i=i.parentId===null?void 0:r.get(i.parentId)}}function Zn(n){return n==="control-value"||n==="morph-weight"?1:n==="joint-rotation"?4:n==="shape-matrix"?16:3}function Qn(n,e,r,o){let a=I(n,e,["interpolation","target","targetId","timesMs","values"]),t=z(a.target,`${e}.target`);zn.has(t)||u("invalid-animation-target",`${e}.target`,t);let i=E(a.targetId,`${e}.targetId`);(t==="control-value"?r.controlIds:t==="morph-weight"?r.targetIds:t==="shape-matrix"?r.shapeIds:r.jointIds).has(i)||u("unknown-reference",`${e}.targetId`,i);let s=z(a.interpolation,`${e}.interpolation`);s!=="linear"&&s!=="step"&&u("invalid-interpolation",`${e}.interpolation`,s),t==="shape-matrix"&&s!=="step"&&u("invalid-interpolation",`${e}.interpolation`,"shape matrices require step interpolation");let l=A(a.timesMs,`${e}.timesMs`).map((p,m)=>V(p,`${e}.timesMs[${m}]`)),d=A(a.values,`${e}.values`).map((p,m)=>{let M=A(p,`${e}.values[${m}]`),P=Zn(t);M.length!==P&&u("invalid-animation-value",`${e}.values[${m}]`,`expected ${P} components`);let x=M.map((f,$)=>V(f,`${e}.values[${m}][${$}]`));return t==="joint-rotation"&&Math.hypot(...x)<=1e-12&&u("invalid-animation-value",`${e}.values[${m}]`,"quaternion must be non-zero"),x});return(l.length===0||l.length!==d.length)&&u("invalid-animation-samples",e,"times and values must have the same non-zero length"),(l[0]!==0||l.some((p,m)=>p<0||p>o||m>0&&p<=l[m-1]))&&u("invalid-animation-time",`${e}.timesMs`,"times must start at zero and increase within the clip"),{target:t,targetId:i,interpolation:s,timesMs:l,values:d}}function Xn(n,e,r,o){let a=I(n,e,["durationMs","frames","loop"]),t=V(a.durationMs,`${e}.durationMs`);t<=0&&u("invalid-duration",`${e}.durationMs`,"expected a positive duration");let i=A(a.frames,`${e}.frames`).map((c,s)=>{let l=`${e}.frames[${s}]`,d=I(c,l,["leaves","modelMatrix","shapes","timeMs"]),p=V(d.timeMs,`${l}.timeMs`),m=A(d.shapes,`${l}.shapes`).map((P,x)=>{let f=`${l}.shapes[${x}]`,$=I(P,f,["matrix","shapeId"]),v=E($.shapeId,`${f}.shapeId`);return o.has(v)||u("unknown-reference",`${f}.shapeId`,v),{shapeId:v,matrix:X($.matrix,`${f}.matrix`)}});B(m.map(P=>P.shapeId),`${l}.shapes`);let M=A(d.leaves,`${l}.leaves`).map((P,x)=>{let f=`${l}.leaves[${x}]`,$=I(P,f,["atlasRow","leafId","matrix","opacity","visible"]),v=E($.leafId,`${f}.leafId`);r.has(v)||u("unknown-reference",`${f}.leafId`,v);let O=$.opacity===null?null:V($.opacity,`${f}.opacity`);return O!==null&&(O<0||O>1)&&u("out-of-range",`${f}.opacity`,"expected 0 <= opacity <= 1"),{leafId:v,matrix:$.matrix===null?null:X($.matrix,`${f}.matrix`),visible:$.visible===null?null:_e($.visible,`${f}.visible`),opacity:O,atlasRow:$.atlasRow===null?null:F($.atlasRow,`${f}.atlasRow`)}});return B(M.map(P=>P.leafId),`${l}.leaves`),{timeMs:p,modelMatrix:d.modelMatrix===null?null:X(d.modelMatrix,`${l}.modelMatrix`),shapes:m,leaves:M}});return i.length===0&&u("missing-frames",`${e}.frames`,"expected at least one frame"),(i[0].timeMs!==0||i.some((c,s)=>c.timeMs<0||c.timeMs>t||s>0&&c.timeMs<=i[s-1].timeMs))&&u("invalid-frame-time",`${e}.frames`,"frames must start at zero and increase within the timeline"),{durationMs:t,loop:_e(a.loop,`${e}.loop`),frames:i}}function er(n,e){let r=["retained-render"];return n==="morph-regions"&&r.push("morph-targets","sparse-updates"),n==="joint-skin"&&r.push("joint-skinning","sparse-updates"),n==="prepared-playback"&&r.push("prepared-playback","sparse-updates"),e.controls.length>0&&r.push("semantic-controls"),e.springs.length>0&&r.push("springs"),e.animations.length>0&&r.push("animation"),r}function pe(n){let r=I(n,"$",["animations","budgets","capabilities","controls","deformation","identity","materials","playback","profile","provenance","render","schema","springs","topology"]);r.schema!==oe&&u("invalid-schema","$.schema",`expected ${oe}`);let o=I(r.identity,"$.identity",["id","name","revision"]),a={id:E(o.id,"$.identity.id"),name:z(o.name,"$.identity.name"),revision:z(o.revision,"$.identity.revision")};on.test(a.revision)||u("invalid-revision","$.identity.revision","expected x.y.z");let t=z(r.profile,"$.profile");Dn.has(t)||u("invalid-profile","$.profile",t);let i=A(r.capabilities,"$.capabilities").map((b,R)=>{let h=z(b,`$.capabilities[${R}]`);return Fn.has(h)||u("invalid-capability",`$.capabilities[${R}]`,h),h});B(i,"$.capabilities"),i.some((b,R)=>R>0&&b<=i[R-1])&&u("non-canonical-order","$.capabilities","capabilities must be sorted");let c=I(r.budgets,"$.budgets",["maxBytes","maxFrames","maxJoints","maxLeaves","maxPolygons","maxResources","maxVertices"]),s={maxVertices:F(c.maxVertices,"$.budgets.maxVertices"),maxPolygons:F(c.maxPolygons,"$.budgets.maxPolygons"),maxLeaves:F(c.maxLeaves,"$.budgets.maxLeaves"),maxFrames:F(c.maxFrames,"$.budgets.maxFrames"),maxJoints:F(c.maxJoints,"$.budgets.maxJoints"),maxResources:F(c.maxResources,"$.budgets.maxResources"),maxBytes:F(c.maxBytes,"$.budgets.maxBytes")},l=Gn(r.topology,"$.topology"),d=A(r.materials,"$.materials").map((b,R)=>{let h=`$.materials[${R}]`,w=I(b,h,["color","id"]),L=A(w.color,`${h}.color`);L.length!==4&&u("invalid-color",`${h}.color`,"expected four components");let D=L.map((W,Q)=>{let re=V(W,`${h}.color[${Q}]`);return(re<0||re>1)&&u("out-of-range",`${h}.color[${Q}]`,"expected 0 <= component <= 1"),re});return{id:E(w.id,`${h}.id`),color:D}});d.length===0&&u("missing-materials","$.materials","expected at least one material"),B(d.map(b=>b.id),"$.materials");let p=I(r.render,"$.render",["leaves","modelMatrix","shapes"]),m=A(p.shapes,"$.render.shapes").map((b,R)=>{let h=`$.render.shapes[${R}]`,w=I(b,h,["id","matrix"]);return{id:E(w.id,`${h}.id`),matrix:X(w.matrix,`${h}.matrix`)}});m.length===0&&u("missing-shapes","$.render.shapes","expected at least one shape"),B(m.map(b=>b.id),"$.render.shapes");let M=A(p.leaves,"$.render.leaves").map((b,R)=>qn(b,`$.render.leaves[${R}]`,{polygonIds:new Set(l.polygons.map(h=>h.id)),shapeIds:new Set(m.map(h=>h.id)),materialIds:new Set(d.map(h=>h.id))}));B(M.map(b=>b.id),"$.render.leaves"),B(M.map(b=>b.polygonId),"$.render.leaves[*].polygonId"),M.length!==l.polygons.length&&u("unstable-topology","$.render.leaves","every polygon must bind exactly one retained leaf");let P={modelMatrix:X(p.modelMatrix,"$.render.modelMatrix"),shapes:m,leaves:M},x=Yn(r.deformation,"$.deformation",l);(t==="static-prepared"||t==="prepared-playback"?x.kind!=="none":x.kind!==t)&&u("profile-mismatch","$.deformation.kind",`does not match profile ${t}`);let f=new Set(x.kind==="morph-regions"?x.targets.map(b=>b.id):[]),$=new Set(x.kind==="joint-skin"?x.joints.map(b=>b.id):[]),v=A(r.controls,"$.controls").map((b,R)=>{let h=`$.controls[${R}]`,w=I(b,h,["anchor","axis","id","initial","maximum","minimum","radius","targets"]),L=V(w.minimum,`${h}.minimum`),D=V(w.maximum,`${h}.maximum`),W=V(w.initial,`${h}.initial`);(L>D||W<L||W>D)&&u("invalid-control-bounds",h,"expected minimum <= initial <= maximum");let Q=de(w.anchor,`${h}.anchor`),re=de(w.axis,`${h}.axis`);Math.hypot(...re)<1e-9&&u("invalid-control-axis",`${h}.axis`,"axis must be non-zero");let en=V(w.radius,`${h}.radius`);en<=0&&u("invalid-control-radius",`${h}.radius`,"radius must be positive");let nn=A(w.targets,`${h}.targets`).map((Ne,Tn)=>{let $e=`${h}.targets[${Tn}]`,rn=I(Ne,$e,["scale","targetId"]),Ve=E(rn.targetId,`${$e}.targetId`);return f.has(Ve)||u("unknown-reference",`${$e}.targetId`,Ve),{targetId:Ve,scale:V(rn.scale,`${$e}.scale`)}});return B(nn.map(Ne=>Ne.targetId),`${h}.targets`),{id:E(w.id,`${h}.id`),anchor:Q,axis:re,radius:en,minimum:L,maximum:D,initial:W,targets:nn}});B(v.map(b=>b.id),"$.controls");let O=new Set(v.map(b=>b.id)),C=A(r.springs,"$.springs").map((b,R)=>{let h=`$.springs[${R}]`,w=I(b,h,["controlId","damping","id","stiffness"]),L=E(w.controlId,`${h}.controlId`);O.has(L)||u("unknown-reference",`${h}.controlId`,L);let D=V(w.stiffness,`${h}.stiffness`),W=V(w.damping,`${h}.damping`);return(D<=0||W<0)&&u("invalid-spring",h,"expected stiffness > 0 and damping >= 0"),{id:E(w.id,`${h}.id`),controlId:L,stiffness:D,damping:W}});B(C.map(b=>b.id),"$.springs");let q=new Set(m.map(b=>b.id)),g=A(r.animations,"$.animations").map((b,R)=>{let h=`$.animations[${R}]`,w=I(b,h,["channels","durationMs","id","loop"]),L=V(w.durationMs,`${h}.durationMs`);L<=0&&u("invalid-duration",`${h}.durationMs`,"expected a positive duration");let D=A(w.channels,`${h}.channels`).map((Q,re)=>Qn(Q,`${h}.channels[${re}]`,{controlIds:O,jointIds:$,shapeIds:q,targetIds:f},L));D.length===0&&u("missing-channels",`${h}.channels`,"expected at least one channel");let W=D.map(Q=>`${Q.target}:${Q.targetId}`);return B(W,`${h}.channels`),{id:E(w.id,`${h}.id`),durationMs:L,loop:_e(w.loop,`${h}.loop`),channels:D}});B(g.map(b=>b.id),"$.animations");let k=r.playback===null?null:Xn(r.playback,"$.playback",new Set(M.map(b=>b.id)),q);t==="prepared-playback"!=(k!==null)&&u("profile-mismatch","$.playback","playback is required only by the prepared-playback profile");let S=I(r.provenance,"$.provenance",["generator","generatorVersion","sources"]),J=A(S.sources,"$.provenance.sources").map((b,R)=>{let h=`$.provenance.sources[${R}]`,w=I(b,h,["id","kind","license","sha256","uri"]),L=z(w.kind,`${h}.kind`);L!=="authored"&&L!=="generated"&&L!=="open-data"&&u("invalid-source-kind",`${h}.kind`,L);let D=z(w.uri,`${h}.uri`);(D.startsWith("/")||D.startsWith("file:")||D.includes("\\"))&&u("invalid-source-uri",`${h}.uri`,"local filesystem paths are forbidden");let W=w.sha256===null?null:z(w.sha256,`${h}.sha256`);return W!==null&&!Un.test(W)&&u("invalid-hash",`${h}.sha256`,"expected lowercase SHA-256"),{id:E(w.id,`${h}.id`),kind:L,uri:D,sha256:W,license:z(w.license,`${h}.license`)}});J.length===0&&u("missing-provenance","$.provenance.sources","expected at least one source"),B(J.map(b=>b.id),"$.provenance.sources");let H={generator:E(S.generator,"$.provenance.generator"),generatorVersion:z(S.generatorVersion,"$.provenance.generatorVersion"),sources:J};on.test(H.generatorVersion)||u("invalid-revision","$.provenance.generatorVersion","expected x.y.z");let Ee=er(t,{controls:v,springs:C,animations:g});for(let b of Ee)i.includes(b)||u("missing-capability","$.capabilities",`profile requires ${b}`);let ce=x.kind==="joint-skin"?x.joints.length:0,U=k?.frames.length??0,Z=[["maxVertices",l.vertices.length,s.maxVertices],["maxPolygons",l.polygons.length,s.maxPolygons],["maxLeaves",M.length,s.maxLeaves],["maxFrames",U,s.maxFrames],["maxJoints",ce,s.maxJoints]];for(let[b,R,h]of Z)R>h&&u("budget-exceeded",`$.budgets.${b}`,`${R} exceeds ${h}`);return{schema:oe,identity:a,profile:t,capabilities:i,budgets:s,topology:l,materials:d,render:P,deformation:x,controls:v,springs:C,animations:g,playback:k,provenance:H}}function ye(n){return tn.test(n)}function ke(n){try{return an(n,"$"),!0}catch{return!1}}var j=class extends Error{constructor(e,r,o,a={}){super(`${r}: ${o}`),this.name="PolyMorphPackageError",this.code=e,this.path=r,"cause"in a&&(this.cause=a.cause)}};function Je(n,e,r){if(n===null)return"null";if(typeof n=="string"||typeof n=="boolean")return JSON.stringify(n);if(typeof n=="number"){if(!Number.isFinite(n))throw new j("invalid-json",e,"numbers must be finite");return JSON.stringify(Object.is(n,-0)?0:n)}if(Array.isArray(n)){if(r.has(n))throw new j("invalid-json",e,"cycles are forbidden");r.add(n);let o=`[${n.map((a,t)=>Je(a,`${e}[${t}]`,r)).join(",")}]`;return r.delete(n),o}if(typeof n=="object"&&n){if(r.has(n))throw new j("invalid-json",e,"cycles are forbidden");let o=Object.getPrototypeOf(n);if(o!==Object.prototype&&o!==null)throw new j("invalid-json",e,"expected a plain object");r.add(n);let a=n,t=`{${Object.keys(a).sort().map(i=>{let c=a[i];if(c===void 0||typeof c=="function"||typeof c=="symbol")throw new j("invalid-json",`${e}.${i}`,"value is not JSON");return`${JSON.stringify(i)}:${Je(c,`${e}.${i}`,r)}`}).join(",")}}`;return r.delete(n),t}throw new j("invalid-json",e,"value is not JSON")}function Ue(n){return Je(n,"$",new WeakSet)}function me(n){return new TextEncoder().encode(Ue(n))}function ln(n,e="$"){let r;try{r=new TextDecoder("utf-8",{fatal:!0}).decode(n)}catch{throw new j("invalid-utf8",e,"expected UTF-8 bytes")}try{return JSON.parse(r)}catch{throw new j("invalid-json",e,"expected valid JSON")}}async function ie(n){if(!globalThis.crypto?.subtle)throw new j("missing-crypto","$","Web Crypto is required");let e=Uint8Array.from(n),r=await globalThis.crypto.subtle.digest("SHA-256",e);return[...new Uint8Array(r)].map(o=>o.toString(16).padStart(2,"0")).join("")}var nr=/^[a-f0-9]{64}$/,rr=/^\d+\.\d+\.\d+$/,or=/^[a-z0-9!#$&^_.+-]+\/[a-z0-9!#$&^_.+-]+$/,tr=new Set(["joint-skin","morph-regions","prepared-playback","static-prepared"]),ar=new Set(["data","image","model"]);function T(n,e,r){throw new j(n,e,r)}function Pe(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&T("invalid-type",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&T("invalid-keys",e,`expected exactly ${a.join(", ")}`),n}function cn(n,e){return Array.isArray(n)||T("invalid-type",e,"expected an array"),n}function ee(n,e){return(typeof n!="string"||n.length===0)&&T("invalid-string",e,"expected a non-empty string"),n}function Fe(n,e){let r=ee(n,e);return ye(r)||T("invalid-id",e,"expected a normalized kebab-case id"),r}function He(n,e){let r=ee(n,e);return ke(r)||T("invalid-path",e,"expected a normalized package-relative path"),r}function dn(n,e){let r=ee(n,e);return rr.test(r)||T("invalid-revision",e,"expected x.y.z"),r}function pn(n,e){let r=ee(n,e);return tr.has(r)||T("invalid-profile",e,r),r}function yn(n,e){let r=ee(n,e);return nr.test(r)||T("invalid-hash",e,"expected lowercase SHA-256"),r}function ir(n,e){return(typeof n!="number"||!Number.isSafeInteger(n)||n<0)&&T("invalid-bytes",e,"expected a non-negative safe integer"),n}function sr(n,e){let r=Pe(n,e,["bytes","mediaType","path","role","sha256"]),o=ee(r.role,`${e}.role`);ar.has(o)||T("invalid-role",`${e}.role`,o);let a=ee(r.mediaType,`${e}.mediaType`).toLowerCase();return(!or.test(a)||a!==r.mediaType)&&T("invalid-media-type",`${e}.mediaType`,"expected a normalized type/subtype"),o==="image"&&!a.startsWith("image/")&&T("invalid-media-type",`${e}.mediaType`,"image resources require an image media type"),{path:He(r.path,`${e}.path`),role:o,mediaType:a,bytes:ir(r.bytes,`${e}.bytes`),sha256:yn(r.sha256,`${e}.sha256`)}}function De(n,e){let r=new Set;for(let o of n)r.has(o)&&T("duplicate",e,o),r.add(o)}function mn(n,e){n.some((r,o)=>o>0&&r<=n[o-1])&&T("non-canonical-order",e,"entries must be unique and sorted")}function we(n){let e=Pe(n,"$",["identity","modelPath","profile","resources","schema"]);e.schema!==ae&&T("invalid-schema","$.schema",`expected ${ae}`);let r=Pe(e.identity,"$.identity",["id","name","revision"]),o={id:Fe(r.id,"$.identity.id"),name:ee(r.name,"$.identity.name"),revision:dn(r.revision,"$.identity.revision")},a=cn(e.resources,"$.resources").map((s,l)=>sr(s,`$.resources[${l}]`));a.length===0&&T("missing-resource","$.resources","expected at least the model resource");let t=a.map(s=>s.path);De(t,"$.resources"),mn(t,"$.resources");let i=He(e.modelPath,"$.modelPath"),c=a.filter(s=>s.role==="model");return(c.length!==1||c[0].path!==i)&&T("invalid-model-resource","$.resources","expected exactly one model resource matching modelPath"),c[0].mediaType!=="application/json"&&T("invalid-model-resource","$.resources","model resource must be application/json"),{schema:ae,identity:o,profile:pn(e.profile,"$.profile"),modelPath:i,resources:a}}function lr(n,e){let r=Pe(n,e,["id","manifestPath","manifestSha256","name","profile","revision"]),o=He(r.manifestPath,`${e}.manifestPath`);return o.endsWith("/manifest.json")||T("invalid-manifest-path",`${e}.manifestPath`,"expected a package manifest.json path"),{id:Fe(r.id,`${e}.id`),name:ee(r.name,`${e}.name`),revision:dn(r.revision,`${e}.revision`),profile:pn(r.profile,`${e}.profile`),manifestPath:o,manifestSha256:yn(r.manifestSha256,`${e}.manifestSha256`)}}function Ie(n){let e=Pe(n,"$",["defaultId","packages","schema"]);e.schema!==te&&T("invalid-schema","$.schema",`expected ${te}`);let r=cn(e.packages,"$.packages").map((t,i)=>lr(t,`$.packages[${i}]`));r.length===0&&T("missing-package","$.packages","expected at least one package");let o=r.map(t=>t.id);De(o,"$.packages"),mn(o,"$.packages"),De(r.map(t=>t.manifestPath),"$.packages[*].manifestPath");let a=Fe(e.defaultId,"$.defaultId");return o.includes(a)||T("unknown-default","$.defaultId",a),{schema:te,defaultId:a,packages:r}}var ze="model.json";function cr(n){return[...new Set(n.render.leaves.flatMap(e=>[...e.atlas?[e.atlas.resourcePath]:[],...e.fallback?[e.fallback.atlas.resourcePath]:[]]))].sort()}async function Se(n,e=[]){let r=pe(n),o=me(r),a=new Map([[ze,o]]),t=[{path:ze,role:"model",mediaType:"application/json",bytes:o.byteLength,sha256:await ie(o)}];for(let l of e){if(a.has(l.path))throw new j("duplicate",l.path,"resource path is already present");let d=Uint8Array.from(l.bytes);a.set(l.path,d),t.push({path:l.path,role:l.role,mediaType:l.mediaType,bytes:d.byteLength,sha256:await ie(d)})}for(let l of cr(r)){let d=t.find(p=>p.path===l);if(!d)throw new j("missing-resource",l,"model image is not included in the package");if(d.role!=="image")throw new j("invalid-role",l,"model image resource must use the image role")}t.sort((l,d)=>l.path<d.path?-1:l.path>d.path?1:0);let i=we({schema:ae,identity:r.identity,profile:r.profile,modelPath:ze,resources:t}),c=t.reduce((l,d)=>l+d.bytes,0);if(t.length>r.budgets.maxResources)throw new j("budget-exceeded","$.budgets.maxResources",`${t.length} resources exceed ${r.budgets.maxResources}`);if(c>r.budgets.maxBytes)throw new j("budget-exceeded","$.budgets.maxBytes",`${c} bytes exceed ${r.budgets.maxBytes}`);let s=me(i);return{manifest:i,manifestBytes:s,manifestSha256:await ie(s),files:a}}async function un(n,e){let r=e.map(t=>({id:t.manifest.identity.id,name:t.manifest.identity.name,revision:t.manifest.identity.revision,profile:t.manifest.profile,manifestPath:t.manifestPath,manifestSha256:t.manifestSha256}));r.sort((t,i)=>t.id<i.id?-1:t.id>i.id?1:0);let o=Ie({schema:te,defaultId:n,packages:r}),a=me(o);return{catalog:o,bytes:a,sha256:await ie(a)}}function fn(n,e){if(e.identity.id!==n.identity.id||e.identity.name!==n.identity.name||e.identity.revision!==n.identity.revision||e.profile!==n.profile)throw new j("profile-mismatch","$.model","model identity or profile does not match its manifest")}var hn=require("fs/promises"),K=require("path");var Me=class extends Error{constructor(e,r,o){super(`${r}: ${o}`),this.name="PolyMorphPrepareError",this.code=e,this.path=r}};function y(n,e,r){throw new Me(n,e,r)}var ue="polycss-morph.prepare@1";function fe(n,e,r){(!n||typeof n!="object"||Array.isArray(n))&&y("invalid-config",e,"expected an object");let o=Object.keys(n).sort(),a=[...r].sort();return(o.length!==a.length||o.some((t,i)=>t!==a[i]))&&y("invalid-config",e,`expected exactly ${a.join(", ")}`),n}function be(n,e){return Array.isArray(n)||y("invalid-config",e,"expected an array"),n}function ne(n,e){return(typeof n!="string"||n.length===0||n!==n.trim())&&y("invalid-config",e,"expected non-empty trimmed text"),n}function Ge(n,e){let r=ne(n,e);return ye(r)||y("invalid-config",e,"expected a normalized kebab-case id"),r}function gn(n,e){return(typeof n!="number"||!Number.isFinite(n))&&y("invalid-config",e,"expected a finite number"),n}function se(n,e){let r=gn(n,e);return(!Number.isSafeInteger(r)||r<1)&&y("invalid-config",e,"expected a positive integer"),r}function dr(n){let e=fe(n,"$.budgets",["maxBytes","maxFrames","maxJoints","maxLeaves","maxPolygons","maxResources","maxVertices"]);return{maxVertices:se(e.maxVertices,"$.budgets.maxVertices"),maxPolygons:se(e.maxPolygons,"$.budgets.maxPolygons"),maxLeaves:se(e.maxLeaves,"$.budgets.maxLeaves"),maxFrames:se(e.maxFrames,"$.budgets.maxFrames"),maxJoints:se(e.maxJoints,"$.budgets.maxJoints"),maxResources:se(e.maxResources,"$.budgets.maxResources"),maxBytes:se(e.maxBytes,"$.budgets.maxBytes")}}function qe(n){let e=fe(n,"$",["animations","budgets","controls","identity","morphAliases","profile","schema","source","springs","transform"]);e.schema!==ue&&y("invalid-config","$.schema",`expected ${ue}`);let r=fe(e.identity,"$.identity",["id","name","revision"]),o={id:Ge(r.id,"$.identity.id"),name:ne(r.name,"$.identity.name"),revision:ne(r.revision,"$.identity.revision")};/^\d+\.\d+\.\d+$/u.test(o.revision)||y("invalid-config","$.identity.revision","expected x.y.z");let a=ne(e.profile,"$.profile");a!=="morph-regions"&&a!=="static-prepared"&&y("invalid-config","$.profile","generic preparation supports morph-regions or static-prepared");let t=fe(e.source,"$.source",["id","kind","license","path","uri"]),i=ne(t.kind,"$.source.kind");i!=="authored"&&i!=="generated"&&i!=="open-data"&&y("invalid-config","$.source.kind","unknown source kind");let c=ne(t.path,"$.source.path");((0,K.isAbsolute)(c)||c.includes("\\")||c.split("/").some(f=>f===""||f==="."||f===".."))&&y("unsafe-path","$.source.path","expected a normalized config-relative path");let s={id:Ge(t.id,"$.source.id"),kind:i,path:c,uri:ne(t.uri,"$.source.uri"),license:ne(t.license,"$.source.license")};(s.uri.startsWith("/")||s.uri.startsWith("file:")||s.uri.includes("\\"))&&y("invalid-config","$.source.uri","local filesystem paths are forbidden");let l=fe(e.transform,"$.transform",["axes","center","scale","signs"]),d=be(l.axes,"$.transform.axes");(d.length!==3||d.some(f=>f!=="x"&&f!=="y"&&f!=="z")||new Set(d).size!==3)&&y("invalid-config","$.transform.axes","expected each source axis exactly once");let p=be(l.signs,"$.transform.signs");(p.length!==3||p.some(f=>f!==-1&&f!==1))&&y("invalid-config","$.transform.signs","expected three values of -1 or 1");let m=gn(l.scale,"$.transform.scale");m>0||y("invalid-config","$.transform.scale","expected a positive scale"),typeof l.center!="boolean"&&y("invalid-config","$.transform.center","expected a boolean");let M=fe(e.morphAliases,"$.morphAliases",Object.keys(e.morphAliases??{})),P=Object.fromEntries(Object.entries(M).map(([f,$])=>[ne(f,"$.morphAliases key"),Ge($,`$.morphAliases.${f}`)]).sort(([f],[$])=>f<$?-1:f>$?1:0));return new Set(Object.values(P)).size!==Object.keys(P).length&&y("invalid-config","$.morphAliases","prepared target ids must be unique"),a==="morph-regions"!=Object.keys(P).length>0&&y("invalid-config","$.morphAliases","morph-regions requires aliases and static-prepared forbids them"),{schema:ue,identity:o,profile:a,source:s,transform:{axes:d,signs:p,scale:m,center:l.center},morphAliases:P,controls:structuredClone(be(e.controls,"$.controls")),springs:structuredClone(be(e.springs,"$.springs")),animations:structuredClone(be(e.animations,"$.animations")),budgets:dr(e.budgets)}}async function Ae(n){let e;try{e=JSON.parse(await(0,hn.readFile)(n,"utf8"))}catch{y("invalid-config","$","config is not readable UTF-8 JSON")}return qe(e)}function Re(n,e){let r=(0,K.resolve)((0,K.dirname)(n)),o=(0,K.resolve)(r,e),a=(0,K.relative)(r,o);return(a===".."||a.startsWith(`..${K.sep}`)||(0,K.isAbsolute)(a))&&y("unsafe-path","$.source.path","source escapes its authoring directory"),o}var xe=require("@layoutit/polycss");var Mn=require("zlib"),Ce=require("@layoutit/polycss");var Oe=1.5,he=4,pr=Uint8Array.from([137,80,78,71,13,10,26,10]);function G(n){let e=Number(n.toFixed(10));return Object.is(e,-0)?0:e}function bn(n,e){let r=n.split(",").map(Number);return(r.length!==16||r.some(o=>!Number.isFinite(o)))&&y("unrenderable-triangle",e,"PolyCSS produced an invalid fallback matrix"),r.map(G)}function yr(n,e){let r=new Array(16).fill(0);for(let o=0;o<4;o+=1)for(let a=0;a<4;a+=1){let t=0;for(let i=0;i<4;i+=1)t+=n[i*4+a]*e[o*4+i];r[o*4+a]=G(t)}return r}function mr(n,e){let r=n[0],o=n[4],a=n[8],t=n[1],i=n[5],c=n[9],s=n[2],l=n[6],d=n[10],p=r*(i*d-c*l)-o*(t*d-c*s)+a*(t*l-i*s);(!Number.isFinite(p)||Math.abs(p)<=1e-12)&&y("unrenderable-triangle",e,"solid triangle matrix is not invertible");let m=1/p,M=(i*d-c*l)*m,P=(a*l-o*d)*m,x=(o*c-a*i)*m,f=(c*s-t*d)*m,$=(r*d-a*s)*m,v=(a*t-r*c)*m,O=(t*l-i*s)*m,C=(o*s-r*l)*m,q=(r*i-o*t)*m,g=n[12],k=n[13],S=n[14];return[G(M),G(f),G(O),0,G(P),G($),G(C),0,G(x),G(v),G(q),0,G(-(M*g+P*k+x*S)),G(-(f*g+$*k+v*S)),G(-(O*g+C*k+q*S)),1]}function ur(n,e){if(e===0)return n;let r=bn(n,"$.render.fallback"),o=[...r];return o[12]-=e*r[0]+e*r[4],o[13]-=e*r[1]+e*r[5],o[14]-=e*r[2]+e*r[6],o.map(G).join(",")}function fr(n){let[e,r,o]=n,a=[r[0]-e[0],r[1]-e[1],r[2]-e[2]],t=[o[0]-e[0],o[1]-e[1],o[2]-e[2]],i=[a[1]*t[2]-a[2]*t[1],a[2]*t[0]-a[0]*t[2],a[0]*t[1]-a[1]*t[0]],c=Math.hypot(...i);if(c<=1e-12)return null;let s=[i[0]/c,i[1]/c,i[2]/c];return{normal:s,plane:s[0]*e[0]+s[1]*e[1]+s[2]*e[2]}}function hr(n){let e=n.map(a=>fr(a.vertices)),r=new Map;for(let a=0;a<n.length;a+=1){let t=n[a].vertexIndices;for(let i=0;i<3;i+=1){let c=t[i],s=t[(i+1)%3],l=c<s?`${c}:${s}`:`${s}:${c}`,d={polygonIndex:a,edgeIndex:i},p=r.get(l);p?p.push(d):r.set(l,[d])}}let o=Array.from({length:n.length},()=>new Set);for(let a of r.values())for(let t=0;t<a.length;t+=1)for(let i=t+1;i<a.length;i+=1){let c=a[t],s=a[i],l=n[c.polygonIndex],d=n[s.polygonIndex],p=e[c.polygonIndex],m=e[s.polygonIndex];l.materialId!==d.materialId||!p||!m||p.normal[0]*m.normal[0]+p.normal[1]*m.normal[1]+p.normal[2]*m.normal[2]<1-1e-6||Math.abs(p.plane-m.plane)>1e-5||(o[c.polygonIndex].add(c.edgeIndex),o[s.polygonIndex].add(s.edgeIndex))}return o}function gr(n,e){return n.map((r,o)=>{let a={color:"#ffffff",vertices:r.vertices.map(([s,l,d])=>[l,s,d])},t=(0,Ce.computeTextureAtlasPlanPublic)(a,o,{tileSize:1,layerElevation:1,seamBleed:0});t||y("unrenderable-triangle",`$.render.leaves[${o}].fallback`,"PolyCSS produced no per-polygon atlas plan");let i=e[o],c=i.size>0?Math.ceil(Oe):0;return{...t,matrix:ur(t.matrix,c),canvasW:t.canvasW+c*2,canvasH:t.canvasH+c*2,screenPts:t.screenPts.map(s=>s+c),seamBleed:i.size>0?Oe:void 0,seamBleedEdges:new Set(i),seamBleedEdgeAmounts:i.size>0?new Map([...i].map(s=>[s,Oe])):void 0}})}function Pr(n,e,r,o){let a=0;for(let i=0;i<n.length;i+=2){let c=(i+2)%n.length;a+=n[i]*n[c+1]-n[c]*n[i+1]}let t=a>=0?1:-1;for(let i=0;i<n.length;i+=2){let c=i/2,s=(i+2)%n.length,l=n[i],d=n[i+1],p=n[s],m=n[s+1],M=p-l,P=m-d,x=Math.hypot(M,P);if(x<=1e-12||t*(M*(o-d)-P*(r-l))/x<-(e.has(c)?Oe:0))return!1}return!0}function Mr(n,e,r){let o=0,a=n.seamBleedEdges??new Set;for(let t=0;t<he;t+=1)for(let i=0;i<he;i+=1)Pr(n.screenPts,a,e+(i+.5)/he,r+(t+.5)/he)&&(o+=1);return Math.round(o*255/(he*he))}function br(n){let e=4294967295;for(let r of n){e^=r;for(let o=0;o<8;o+=1)e=e>>>1^3988292384&-(e&1)}return(e^4294967295)>>>0}function We(n,e){let r=new TextEncoder().encode(n),o=new Uint8Array(12+e.byteLength),a=new DataView(o.buffer);return a.setUint32(0,e.byteLength),o.set(r,4),o.set(e,8),a.setUint32(8+e.byteLength,br(o.subarray(4,8+e.byteLength))),o}function xr(n){let e=new Uint8Array(n.reduce((o,a)=>o+a.byteLength,0)),r=0;for(let o of n)e.set(o,r),r+=o.byteLength;return e}function $r(n,e,r){let o=1+n*4,a=new Uint8Array(e*o);for(let c of r)for(let s=0;s<c.canvasH;s+=1)for(let l=0;l<c.canvasW;l+=1){let d=Mr(c,l,s);if(d===0)continue;let p=(c.y+s)*o+1+(c.x+l)*4;a[p]=255,a[p+1]=255,a[p+2]=255,a[p+3]=d}let t=new Uint8Array(13),i=new DataView(t.buffer);return i.setUint32(0,n),i.setUint32(4,e),t[8]=8,t[9]=6,xr([pr,We("IHDR",t),We("IDAT",(0,Mn.deflateSync)(a,{level:9})),We("IEND",new Uint8Array)])}function Pn(n){return`assets/solid-triangles-${String(n).padStart(3,"0")}.png`}function xn(n){let e=gr(n,hr(n)),{packed:r,atlasScale:o}=(0,Ce.packTextureAtlasPlansWithScale)(e,1,null,"local");o!==1&&y("invalid-atlas","$.render.fallback","per-polygon fallback atlas must retain CSS-pixel resolution");let a=n.map((i,c)=>{let s=r.entries[c];s||y("invalid-atlas",`$.render.leaves[${c}].fallback`,"per-polygon fallback was not packed");let l=r.pages[s.pageIndex],d=bn(s.atlasMatrix,`$.render.leaves[${c}].fallback.matrix`);return{width:s.canvasW,height:s.canvasH,matrixFromLeaf:yr(mr(i.leafMatrix,`$.render.leaves[${c}].matrix`),d),atlas:{resourcePath:Pn(s.pageIndex),x:s.x,y:s.y,width:s.canvasW,height:s.canvasH,pageWidth:l.width,pageHeight:l.height}}}),t=r.pages.map((i,c)=>({path:Pn(c),width:i.width,height:i.height,bytes:$r(i.width,i.height,i.entries)}));return{fallbacks:a,pages:t}}var $n={name:"@layoutit/polycss-morph",version:"0.2.11",description:"Prepared retained-model deformation and playback for PolyCSS.",type:"module",main:"dist/index.cjs",module:"dist/index.js",types:"dist/index.d.ts",keywords:["polycss","morph","animation","skinning","3d","css","matrix3d","dom"],license:"MIT",repository:{type:"git",url:"https://github.com/LayoutitStudio/polycss.git",directory:"packages/morph"},bugs:{url:"https://github.com/LayoutitStudio/polycss/issues"},homepage:"https://github.com/LayoutitStudio/polycss#readme",files:["dist"],exports:{".":{types:"./dist/index.d.ts",import:"./dist/index.js",require:"./dist/index.cjs"},"./prepare":{types:"./dist/prepare.d.ts",import:"./dist/prepare.js",require:"./dist/prepare.cjs"}},typesVersions:{"*":{prepare:["dist/prepare.d.ts"]}},scripts:{build:"tsup",test:"vitest run","test:package":"node scripts/certify-package.mjs","test:package:registry":"node scripts/certify-package.mjs --registry-dependencies","test:coverage":"vitest run --coverage",prepack:"node ../../.github/scripts/sync-package-readmes.mjs",prepublishOnly:"npm run build"},publishConfig:{access:"public"},dependencies:{"@layoutit/polycss":"workspace:^"},devDependencies:{"@types/node":"^25.0.0","@vitest/coverage-v8":"^3.1.1","happy-dom":"^20.7.0",tsup:"^8.0.1",typescript:"^5.3.3",vitest:"^3.1.1"}};var vn=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],kr=$n.version;function je(n){let e=Number(n.toFixed(10));return Object.is(e,-0)?0:e}function Ke(n){return[je(n[0]),je(n[1]),je(n[2])]}function kn(n,e){let o=n.normalize("NFKD").replace(/([a-z0-9])([A-Z])/gu,"$1-$2").replace(/[^A-Za-z0-9]+/gu,"-").replace(/^-+|-+$/gu,"").toLowerCase()||e;return/^[a-z]/u.test(o)?o:`item-${o}`}function wr(n,[e,r,o]){let a=n[3]*e+n[7]*r+n[11]*o+n[15];return(!Number.isFinite(a)||Math.abs(a)<1e-12)&&y("invalid-transform","$.source.nodes","node has a singular projective transform"),[(n[0]*e+n[4]*r+n[8]*o+n[12])/a,(n[1]*e+n[5]*r+n[9]*o+n[13])/a,(n[2]*e+n[6]*r+n[10]*o+n[14])/a]}function In(n,[e,r,o]){return[n[0]*e+n[4]*r+n[8]*o,n[1]*e+n[5]*r+n[9]*o,n[2]*e+n[6]*r+n[10]*o]}function wn(n,e){let r={x:n[0],y:n[1],z:n[2]};return Ke(e.transform.axes.map((o,a)=>r[o]*e.transform.signs[a]*e.transform.scale))}function Ir(n,e){let o=[[1,0,0],[0,1,0],[0,0,1]].map(s=>{let l=In(n,s),d={x:l[0],y:l[1],z:l[2]};return e.transform.axes.map((p,m)=>d[p]*e.transform.signs[m]*e.transform.scale)}),[a,t,i]=o;return a[0]*(t[1]*i[2]-t[2]*i[1])-t[0]*(a[1]*i[2]-a[2]*i[1])+i[0]*(a[1]*t[2]-a[2]*t[1])<0}function Ye(n,e){return[n[0]-e[0],n[1]-e[1],n[2]-e[2]]}function Sr(n,e){return[n[1]*e[2]-n[2]*e[1],n[2]*e[0]-n[0]*e[2],n[0]*e[1]-n[1]*e[0]]}function Ar(n,e){let r=Math.hypot(...n);return r>1e-10||y("degenerate-triangle",e,"triangle has zero area"),Ke(n.map(o=>o/r))}function Rr(n,e){let r=Array.from({length:n.length},()=>[0,0,0]);for(let o of e){let[a,t,i]=o.vertexIndices.map(s=>n[s]),c=Sr(Ye(t,a),Ye(i,a));Math.hypot(...c)<=1e-10&&y("degenerate-triangle",`$.topology.${o.id}`,"triangle has zero area");for(let s of o.vertexIndices)r[s][0]+=c[0],r[s][1]+=c[1],r[s][2]+=c[2]}return r.map((o,a)=>Ar(o,`$.topology.normals[${a}]`))}function Or(n,e){let r={vertices:n.map(l=>[...l])},[o,a,t]=n,i=(0,xe.computeSolidTrianglePlanFromCssPoints)(r,0,{seamBleed:0},{includeColor:!1,matrixDecimals:10,primitive:"border"},o[0],o[1],o[2],a[0],a[1],a[2],t[0],t[1],t[2]),s=/^matrix3d\(([^)]+)\)$/u.exec(i?.transformText??"")?.[1]?.split(",").map(Number);return(!s||s.length!==16||s.some(l=>!Number.isFinite(l)))&&y("unrenderable-triangle",e,"PolyCSS produced no stable matrix"),s.map(je)}function Cr(n){let e=new Set(["retained-render"]);return n.profile==="morph-regions"&&(e.add("morph-targets"),e.add("sparse-updates")),n.controls.length>0&&e.add("semantic-controls"),n.springs.length>0&&e.add("springs"),n.animations.length>0&&e.add("animation"),[...e].sort()}async function Ze(n,e){let r=[],o=[],a=[],t=Object.entries(e.morphAliases),i=new Map(t.map(([,g])=>[g,[]])),c=new Set,s=0,l=0;for(let g of n.instances){let k=Ir(g.matrix,e);for(let S of g.primitives){let J=`shape-${String(s).padStart(4,"0")}-${kn(`${g.meshName}-${S.primitiveIndex}`,"mesh")}`;a.push({id:J,matrix:vn});let H=new Map(S.targets.map(U=>[U.name,U]));t.some(([U])=>!H.has(U))&&y("missing-morph",`$.source.${J}`,"every primitive must contain every configured morph target");let Ee=[...new Set(S.triangles.flat())].sort((U,Z)=>U-Z),ce=new Map;for(let U of Ee){let Z=S.positions[U];ce.set(U,r.length);let b=wr(g.matrix,Z);r.push(wn(b,e));for(let[R,h]of t){let w=H.get(R).positionDeltas[U],L=In(g.matrix,w);i.get(h).push(wn(L,e))}}c.add(S.materialIndex);for(let U of S.triangles){let Z=k?[U[0],U[2],U[1]]:U;o.push({id:`polygon-${String(l).padStart(6,"0")}`,shapeId:J,materialIndex:S.materialIndex,vertexIndices:[ce.get(Z[0]),ce.get(Z[1]),ce.get(Z[2])]}),l+=1}s+=1}}if(e.transform.center){let g=[1/0,1/0,1/0],k=[-1/0,-1/0,-1/0];for(let J of r)for(let H=0;H<3;H+=1)g[H]=Math.min(g[H],J[H]),k[H]=Math.max(k[H],J[H]);let S=g.map((J,H)=>(J+k[H])/2);for(let J=0;J<r.length;J+=1)r[J]=Ke(Ye(r[J],S))}let d=[...c].sort((g,k)=>g-k),p=new Map(n.materials.map(g=>[g.sourceIndex,g])),m=d.map(g=>{let k=g===-1?{name:"Default",color:[1,1,1,1]}:p.get(g);return k||y("invalid-material","$.source.materials",`primitive references missing material ${g}`),{sourceIndex:g,id:g===-1?"material-default":`material-${String(g).padStart(4,"0")}-${kn(k.name,"source")}`,color:k.color}}),M=new Map(m.map(g=>[g.sourceIndex,g.id])),P=o.map(g=>({id:g.id,vertexIndices:g.vertexIndices,normalIndices:g.vertexIndices})),x=Rr(r,P),f=t.map(([,g])=>({id:g,deltas:i.get(g).map((k,S)=>({position:k,vertexIndex:S})).filter(({position:k})=>Math.hypot(...k)>1e-12).map(({position:k,vertexIndex:S})=>({vertexIndex:S,position:k,normal:null}))}));f.some(g=>g.deltas.length===0)&&y("empty-morph","$.morphAliases","every configured morph target must move at least one vertex");let $=o.map(g=>{let k=M.get(g.materialIndex);return{id:`leaf-${g.id}`,polygonId:g.id,shapeId:g.shapeId,materialId:k,strategy:"solid-triangle",width:xe.SOLID_TRIANGLE_CANONICAL_SIZE,height:xe.SOLID_TRIANGLE_CANONICAL_SIZE,matrix:Or(g.vertexIndices.map(S=>r[S]),`$.render.${g.id}`),atlas:null,fallback:null}}),v=xn(o.map((g,k)=>({vertexIndices:g.vertexIndices,vertices:g.vertexIndices.map(S=>r[S]),materialId:M.get(g.materialIndex),leafMatrix:$[k].matrix}))),O=$.map((g,k)=>({...g,fallback:v.fallbacks[k]})),C={schema:oe,identity:e.identity,profile:e.profile,capabilities:Cr(e),budgets:e.budgets,topology:{vertices:r,normals:x,polygons:P},materials:m.map(({id:g,color:k})=>({id:g,color:k})),render:{modelMatrix:vn,shapes:a,leaves:O},deformation:e.profile==="morph-regions"?{kind:"morph-regions",targets:f}:{kind:"none"},controls:e.controls,springs:e.springs,animations:e.animations,playback:null,provenance:{generator:"polycss-morph",generatorVersion:kr,sources:[{id:e.source.id,kind:e.source.kind,uri:e.source.uri,sha256:n.contentSha256,license:e.source.license}]}};return{model:pe(C),fallbackAtlasPages:v.pages}}async function Te(n,e){let r=await Ze(n,e),o=await Se(r.model,[...r.fallbackAtlasPages.map(a=>({path:a.path,role:"image",mediaType:"image/png",bytes:a.bytes}))]);return{source:n,prepared:r,package:o}}var An=require("crypto"),Xe=require("fs/promises"),Y=require("path");var jr={SCALAR:1,VEC2:2,VEC3:3,VEC4:4,MAT4:16},Tr={5120:1,5121:1,5122:2,5123:2,5125:4,5126:4};function Qe(n){return(0,An.createHash)("sha256").update(n).digest("hex")}function Rn(n,e){try{let r=JSON.parse(new TextDecoder("utf-8",{fatal:!0}).decode(n));return(!r||typeof r!="object"||Array.isArray(r))&&y("invalid-gltf",e,"expected a JSON object"),r}catch(r){if(r instanceof Error&&r.name==="PolyMorphPrepareError")throw r;y("invalid-gltf",e,"expected UTF-8 JSON")}}function Lr(n){n.byteLength<20&&y("invalid-glb","$.source","GLB is truncated");let e=new DataView(n.buffer,n.byteOffset,n.byteLength);(e.getUint32(0,!0)!==1179937895||e.getUint32(4,!0)!==2||e.getUint32(8,!0)!==n.byteLength)&&y("invalid-glb","$.source","invalid GLB header");let r=12,o=null,a=null;for(;r<n.byteLength;){r+8>n.byteLength&&y("invalid-glb","$.source","truncated GLB chunk header");let t=e.getUint32(r,!0),i=e.getUint32(r+4,!0),c=r+8,s=c+t;(t%4!==0||s>n.byteLength)&&y("invalid-glb","$.source","invalid GLB chunk bounds"),i===1313821514?(o&&y("invalid-glb","$.source","duplicate JSON chunk"),o=Rn(n.subarray(c,s),"$.source.json")):i===5130562?(a&&y("invalid-glb","$.source","duplicate binary chunk"),a=n.subarray(c,s)):y("invalid-glb","$.source",`unsupported GLB chunk type ${i}`),r=s}return o||y("invalid-glb","$.source","missing JSON chunk"),{json:o,binary:a}}function Er(n,e){return(typeof n!="string"||n.length===0||(0,Y.isAbsolute)(n)||n.includes("\\")||n.includes("?")||n.includes("#")||n.split("/").some(r=>r===""||r==="."||r===".."))&&y("unsafe-path",e,"expected a normalized source-relative path"),n}function Nr(n,e){let r=/^data:application\/(?:octet-stream|gltf-buffer);base64,([A-Za-z0-9+/]*={0,2})$/u.exec(n);return r||y("unsupported-uri",e,"expected a base64 glTF buffer data URI"),Uint8Array.from(Buffer.from(r[1],"base64"))}async function Vr(n,e,r){let o=Array.isArray(n.buffers)?n.buffers:[];o.length===0&&y("missing-buffer","$.source.buffers","expected at least one buffer");let a=(0,Y.dirname)(e),t=[],i=[];for(let[c,s]of o.entries()){let l=`$.source.buffers[${c}]`;(!Number.isSafeInteger(s?.byteLength)||s.byteLength<0)&&y("invalid-buffer",l,"invalid byteLength");let d,p;if(s.uri===void 0)(c!==0||!r)&&y("missing-buffer",l,"missing URI or GLB binary chunk"),d=r,p="<glb-bin>";else if(typeof s.uri=="string"&&s.uri.startsWith("data:"))d=Nr(s.uri,`${l}.uri`),p="<embedded-base64>";else{let P=Er(s.uri,`${l}.uri`),x=(0,Y.resolve)(a,P),f=(0,Y.relative)(a,x);(f===".."||f.startsWith(`..${Y.sep}`)||(0,Y.isAbsolute)(f))&&y("unsafe-path",`${l}.uri`,"buffer escapes source directory"),d=new Uint8Array(await(0,Xe.readFile)(x)),p=P}let m=s.byteLength;(d.byteLength<m||d.byteLength-m>3)&&y("invalid-buffer",l,"buffer length disagrees with byteLength");let M=d.subarray(0,m);t.push(M),i.push({path:p,sha256:Qe(M)})}return{buffers:t,files:i}}function Br(n,e,r){switch(e){case 5120:return n.getInt8(r);case 5121:return n.getUint8(r);case 5122:return n.getInt16(r,!0);case 5123:return n.getUint16(r,!0);case 5125:return n.getUint32(r,!0);case 5126:return n.getFloat32(r,!0);default:y("invalid-accessor","$.source.accessors",`unsupported component type ${e}`)}}function _r(n,e){switch(e){case 5120:return Math.max(-1,n/127);case 5121:return n/255;case 5122:return Math.max(-1,n/32767);case 5123:return n/65535;case 5125:return n/4294967295;default:return n}}function Jr(n,e){let r=Array.isArray(n.accessors)?n.accessors:[],o=Array.isArray(n.bufferViews)?n.bufferViews:[];return(a,t)=>{let i=r[a];(!i||i.sparse!==void 0||!Number.isSafeInteger(i.count)||i.count<0)&&y("invalid-accessor",t,"missing, sparse, or invalid accessor");let c=jr[i.type],s=Tr[i.componentType],l=o[i.bufferView];(!c||!s||!l||!Number.isSafeInteger(i.bufferView)||!Number.isSafeInteger(l.buffer))&&y("invalid-accessor",t,"unsupported accessor metadata");let d=e[l.buffer];d||y("invalid-accessor",t,"references an absent buffer");let p=c*s,m=l.byteStride??p,M=l.byteOffset??0,P=i.byteOffset??0,x=l.byteLength,f=M+P,$=f+Math.max(0,i.count-1)*m+p;(!Number.isSafeInteger(M)||M<0||!Number.isSafeInteger(x)||x<0||M+x>d.byteLength||!Number.isSafeInteger(P)||P<0||P%s!==0||!Number.isSafeInteger(m)||m<p||l.byteStride!==void 0&&(m>252||m%4!==0)||!Number.isSafeInteger(f)||f<0||f%s!==0||$>M+x)&&y("invalid-accessor",t,"invalid accessor byte layout");let v=new DataView(d.buffer,d.byteOffset,d.byteLength),O=[];for(let C=0;C<i.count;C+=1){let q=[];for(let g=0;g<c;g+=1){let k=Br(v,i.componentType,f+C*m+g*s),S=i.normalized?_r(k,i.componentType):k;Number.isFinite(S)||y("invalid-accessor",`${t}[${C}][${g}]`,"non-finite component"),q.push(Object.is(S,-0)?0:S)}O.push(c===1?q[0]:q)}return O}}function Sn(n,e){return n.map((r,o)=>((!Array.isArray(r)||r.length!==3)&&y("invalid-accessor",`${e}[${o}]`,"expected VEC3"),[r[0],r[1],r[2]]))}function Ur(n,e,r){let o=e.map((t,i)=>((!Number.isSafeInteger(t)||t<0)&&y("invalid-index",`${r}[${i}]`,"expected an unsigned integer"),t)),a=[];if(n===4){o.length%3!==0&&y("invalid-primitive",r,"incomplete triangle list");for(let t=0;t<o.length;t+=3)a.push([o[t],o[t+1],o[t+2]])}else if(n===5)for(let t=2;t<o.length;t+=1)a.push(t%2===0?[o[t-2],o[t-1],o[t]]:[o[t-1],o[t-2],o[t]]);else if(n===6)for(let t=2;t<o.length;t+=1)a.push([o[0],o[t-1],o[t]]);else y("unsupported-primitive",r,`mode ${n} is not triangles, triangle strip, or triangle fan`);return a.filter(([t,i,c])=>t!==i&&i!==c&&t!==c)}var Dr=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1];function Fr(n,e){let r=new Array(16).fill(0);for(let o=0;o<4;o+=1)for(let a=0;a<4;a+=1)for(let t=0;t<4;t+=1)r[o*4+a]+=n[t*4+a]*e[o*4+t];return r}function Hr(n,e){if(n.matrix!==void 0)return(!Array.isArray(n.matrix)||n.matrix.length!==16||n.matrix.some(C=>typeof C!="number"||!Number.isFinite(C))||n.translation!==void 0||n.rotation!==void 0||n.scale!==void 0)&&y("invalid-node",e,"invalid or ambiguous node matrix"),n.matrix;let r=n.translation??[0,0,0],o=n.rotation??[0,0,0,1],a=n.scale??[1,1,1];(!Array.isArray(r)||r.length!==3||!Array.isArray(o)||o.length!==4||!Array.isArray(a)||a.length!==3||[...r,...o,...a].some(C=>typeof C!="number"||!Number.isFinite(C)))&&y("invalid-node",e,"invalid node TRS");let[t,i,c,s]=o,l=Math.hypot(t,i,c,s);l>0||y("invalid-node",`${e}.rotation`,"zero quaternion");let d=t/l,p=i/l,m=c/l,M=s/l,[P,x,f]=a,[$,v,O]=r;return[(1-2*(p*p+m*m))*P,2*(d*p+m*M)*P,2*(d*m-p*M)*P,0,2*(d*p-m*M)*x,(1-2*(d*d+m*m))*x,2*(p*m+d*M)*x,0,2*(d*m+p*M)*f,2*(p*m-d*M)*f,(1-2*(d*d+p*p))*f,0,$,v,O,1]}function zr(n){let e=Array.isArray(n.nodes)?n.nodes:[],r=Array.isArray(n.scenes)?n.scenes:[],o;if(r.length>0){let i=n.scene??0,c=r[i]?.nodes;Array.isArray(c)||y("invalid-scene","$.source.scene","default scene has no nodes"),o=c}else{let i=new Set(e.flatMap(c=>Array.isArray(c.children)?c.children:[]));o=e.map((c,s)=>s).filter(c=>!i.has(c))}let a=[],t=(i,c,s)=>{(!Number.isSafeInteger(i)||i<0||i>=e.length)&&y("invalid-node","$.source.nodes",`unknown node ${i}`),s.has(i)&&y("invalid-node","$.source.nodes",`node cycle at ${i}`);let l=e[i],d=Fr(c,Hr(l,`$.source.nodes[${i}]`));l.mesh!==void 0&&((!Number.isSafeInteger(l.mesh)||l.mesh<0)&&y("invalid-node",`$.source.nodes[${i}].mesh`,"invalid mesh index"),a.push({nodeIndex:i,nodeName:typeof l.name=="string"&&l.name.length>0?l.name:`node-${i}`,meshIndex:l.mesh,matrix:d}));let p=new Set(s).add(i),m=l.children??[];Array.isArray(m)||y("invalid-node",`$.source.nodes[${i}].children`,"expected an array");for(let M of m)t(M,d,p)};for(let i of o)t(i,Dr,new Set);return a}function Gr(n){return(Array.isArray(n.materials)?n.materials:[]).map((r,o)=>{(!r||typeof r!="object"||Array.isArray(r))&&y("invalid-material",`$.source.materials[${o}]`,"expected a material object");let a=r.pbrMetallicRoughness?.baseColorFactor??[1,1,1,1];return(!Array.isArray(a)||a.length!==4||a.some(t=>typeof t!="number"||!Number.isFinite(t)||t<0||t>1))&&y("invalid-material",`$.source.materials[${o}]`,"baseColorFactor must have four unit components"),{sourceIndex:o,name:typeof r.name=="string"&&r.name.length>0?r.name:`material-${o}`,color:[a[0],a[1],a[2],a[3]]}})}function qr(n,e,r){let o=Jr(n,e),a=Array.isArray(n.meshes)?n.meshes:[];return r.map(t=>{let i=a[t.meshIndex];(!i||!Array.isArray(i.primitives)||i.primitives.length===0)&&y("invalid-mesh",`$.source.meshes[${t.meshIndex}]`,"mesh has no primitives");let c=Array.isArray(i.extras?.targetNames)?i.extras.targetNames.map(String):[],s=i.primitives.map((l,d)=>{let p=`$.source.meshes[${t.meshIndex}].primitives[${d}]`;(!l?.attributes||!Number.isSafeInteger(l.attributes.POSITION))&&y("invalid-primitive",p,"missing POSITION accessor");let m=Sn(o(l.attributes.POSITION,`${p}.POSITION`),`${p}.POSITION`),M=l.indices===void 0?m.map(($,v)=>v):o(l.indices,`${p}.indices`),P=Ur(l.mode??4,M,`${p}.indices`);(P.length===0||P.some($=>$.some(v=>v>=m.length)))&&y("invalid-index",p,"triangle indices are empty or out of range");let x=Array.isArray(l.targets)?l.targets.map(($,v)=>{Number.isSafeInteger($.POSITION)||y("invalid-morph",`${p}.targets[${v}]`,"missing POSITION accessor");let O=Sn(o($.POSITION,`${p}.targets[${v}].POSITION`),`${p}.targets[${v}].POSITION`);return O.length!==m.length&&y("invalid-morph",`${p}.targets[${v}]`,"target does not cover POSITION"),{index:v,name:c[v]??`morph-${v}`,positionDeltas:O}}):[],f=l.material??-1;return(!Number.isSafeInteger(f)||f<-1)&&y("invalid-material",`${p}.material`,"invalid material index"),{primitiveIndex:d,materialIndex:f,positions:m,triangles:P,targets:x}});return{...t,meshName:typeof i.name=="string"&&i.name.length>0?i.name:`mesh-${t.meshIndex}`,primitives:s}})}async function Le(n){let e=(0,Y.resolve)(n),r=new Uint8Array(await(0,Xe.readFile)(e)),o=(0,Y.extname)(e).toLowerCase(),a,t,i=null;o===".glb"?(a="glb",{json:t,binary:i}=Lr(r)):o===".gltf"?(a="gltf",t=Rn(r,"$.source")):y("unsupported-format","$.source.path","expected .gltf or .glb"),(t.asset?.version!=="2.0"||Array.isArray(t.extensionsRequired)&&t.extensionsRequired.length>0)&&y("unsupported-gltf","$.source","expected core glTF 2.0 without required extensions");let c=await Vr(t,e,i),s=qr(t,c.buffers,zr(t));s.length===0&&y("empty-model","$.source","default scene has no mesh instances");let l=Qe(r),d=Qe(new TextEncoder().encode(JSON.stringify({source:l,buffers:c.files})));return{format:a,sourceBytes:r.byteLength,sourceSha256:l,contentSha256:d,materials:Gr(t),instances:s}}var le=require("fs"),_=require("fs/promises"),N=require("path");function Wr(n){(typeof n!="string"||n.length===0)&&y("invalid-argument","$.outputRoot","expected a path");let e=(0,N.resolve)(n);return e===(0,N.parse)(e).root&&y("unsafe-path","$.outputRoot","filesystem root is forbidden"),e}async function On(n,e=""){let r=(0,N.join)(n,e),o=await(0,_.readdir)(r,{withFileTypes:!0}),a=[];for(let t of o.sort((i,c)=>i.name<c.name?-1:i.name>c.name?1:0)){let i=e===""?t.name:`${e}/${t.name}`;t.isSymbolicLink()&&y("unsafe-output",i,"symbolic links are forbidden"),t.isDirectory()?a.push(...await On(n,i)):t.isFile()?a.push(i):y("unsafe-output",i,"unsupported filesystem entry")}return a}async function Cn(n,e){if(!(0,le.existsSync)(n))return{path:"$.outputRoot",message:"prepared package is missing"};let r=await On(n),o=[...e.keys()].sort();if(r.length!==o.length||r.some((a,t)=>a!==o[t]))return{path:"$.outputRoot",message:`inventory differs: expected ${o.join(", ")}`};for(let a of o){let t=new Uint8Array(await(0,_.readFile)((0,N.join)(n,a))),i=e.get(a);if(t.byteLength!==i.byteLength||t.some((c,s)=>c!==i[s]))return{path:a,message:"prepared bytes differ"}}return null}async function Yr(n,e){let r=await Cn(n,e);r&&y("drift",r.path,r.message)}async function Kr(n,e){let r=(0,N.dirname)(n);await(0,_.mkdir)(r,{recursive:!0});let o=await(0,_.mkdtemp)((0,N.join)(r,`.polycss-morph-${(0,N.basename)(n)}-`)),a=`${n}.previous-${process.pid}`,i=[...[...e.keys()].filter(s=>s!=="manifest.json").sort(),"manifest.json"],c=!1;try{for(let s of i){let l=(0,N.resolve)(o,s),d=(0,N.relative)(o,l);(d===".."||d.startsWith(`..${N.sep}`)||(0,N.isAbsolute)(d))&&y("unsafe-path",s,"package path escapes staging"),await(0,_.mkdir)((0,N.dirname)(l),{recursive:!0}),await(0,_.writeFile)(l,e.get(s))}return(0,le.existsSync)(a)&&y("unsafe-output","$.outputRoot",`backup already exists at ${a}`),(0,le.existsSync)(n)&&(await(0,_.rename)(n,a),c=!0),await(0,_.rename)(o,n),c&&await(0,_.rm)(a,{recursive:!0,force:!0}).catch(()=>{}),i}catch(s){throw c&&!(0,le.existsSync)(n)&&(0,le.existsSync)(a)&&await(0,_.rename)(a,n),s}finally{(0,le.existsSync)(o)&&await(0,_.rm)(o,{recursive:!0,force:!0})}}async function jn(n){(!n||typeof n!="object")&&y("invalid-argument","$","expected prepare options"),(typeof n.configPath!="string"||n.configPath.length===0)&&y("invalid-argument","$.configPath","expected a path"),n.check!==void 0&&typeof n.check!="boolean"&&y("invalid-argument","$.check","expected a boolean");let e=(0,N.resolve)(n.configPath),r=Wr(n.outputRoot),o=await Ae(e),a=Re(e,o.source.path),t=await Le(a),i=await Te(t,o),c=new Map(i.package.files);c.set("manifest.json",i.package.manifestBytes);let s=[...c.keys()].sort();if(n.check)return await Yr(r,c),{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:[],checked:!0,changed:!1};if(await Cn(r,c)===null)return{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:[],checked:!1,changed:!1};let l=await Kr(r,c);return{config:o,source:t,model:i.prepared.model,manifest:i.package.manifest,manifestSha256:i.package.manifestSha256,outputRoot:r,files:s,writeOrder:l,checked:!1,changed:!0}}0&&(module.exports={POLY_MORPH_CATALOG_SCHEMA,POLY_MORPH_MODEL_SCHEMA,POLY_MORPH_PACKAGE_SCHEMA,POLY_MORPH_PREPARE_SCHEMA,PolyMorphContractError,PolyMorphPackageError,PolyMorphPrepareError,assertPolyMorphPackageModelBinding,buildPolyMorphCatalog,buildPolyMorphPackage,buildPolyMorphPreparedPackage,compilePolyMorphSource,decodePolyMorphJson,encodePolyMorphCanonicalJson,failPolyMorphPrepare,hashPolyMorphBytes,isPolyMorphId,isPolyMorphResourcePath,loadPolyMorphGltf,parsePolyMorphPrepareConfig,preparePolyMorphModel,readPolyMorphPrepareConfig,resolvePolyMorphSourcePath,stringifyPolyMorphCanonicalJson,validatePolyMorphCatalog,validatePolyMorphModel,validatePolyMorphPackageManifest});