@dcl-regenesislabs/web-editor 0.3.12 → 0.3.13

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.
Files changed (2) hide show
  1. package/editor.js +1 -1
  2. package/package.json +1 -1
package/editor.js CHANGED
@@ -34664,4 +34664,4 @@ ${n}
34664
34664
  ${r}`));return"w"+Array.from(new Uint8Array(a).slice(0,16),s=>s.toString(16).padStart(2,"0")).join("")}function Cwr(t){return`${t.file===void 0?"":`${t.file}:${t.line??1}:${t.column??0}: `}${t.severity==="error"?"ERROR":"WARNING"}: ${t.message}`}function Awr(t){return t.length<=3?t.join(", "):`${t.slice(0,3).join(", ")} and ${t.length-3} more`}function Owr(t,n){const r=R1(t.get("package.json"));for(const a of[r==null?void 0:r.devDependencies,r==null?void 0:r.dependencies]){const s=typeof a=="object"&&a!==null?a["@dcl/sdk"]:void 0;if(typeof s=="string"&&s!==n)return`⚠ This project asks for @dcl/sdk ${s}; the editor builds it with ${n}.`}return null}function Pwr(t){const{emit:n,log:r}=t;let a=null,s=!1,l=null,d=Promise.resolve();const m=A=>{const M=d.then(A,A);return d=M.catch(()=>{}),M};async function _(){if(s)throw new Error("The editor was closed");a===null&&(l=null);const A=a??Wvr(t.urls);a=A;try{const M=await A.ready;return{builder:A,sdkVersion:M.sdkVersion,info:M}}catch(M){throw A.dispose(),a===A&&(a=null),M}}async function x(A,M,F){const{builder:B,info:H}=await _();let ee=!1;const Z=await Swr(M,t.packages,H.snapshot,_e=>{t.onPackages(A,_e),F&&!ee&&r("Downloading packages from npm…"),ee=!0});Z.lockFile!==void 0&&(M.set(A3,Z.lockFile),await t.saveLock(A,Z.lockFile));const K=Z.lock===null?"":Czt(Z.lock);if(K!==l)try{await B.setPackages(Z.lock,t.packages),l=K}catch(_e){F&&r(`⚠ ${sOt(_e)}`),await B.setPackages(null),l=""}if(t.onPackages(A,Z.status),!(!F||Z.status===null)){if(Z.status.state==="error")r(`✖ ${Z.status.message??"The packages could not be installed"}`);else if(Z.downloaded>0){const _e=Object.entries(Z.status.installed).map(([he,te])=>`${he} ${te}`);r(`✔ Packages frozen into the scene: ${_e.join(", ")} (${Z.status.total} in all)`)}for(const _e of Z.status.warnings)r(`⚠ ${_e}`)}}function T(A,M,F=A){const B=lWe(t.pageDir,F),H=new Set;let ee=null,Z=null,K=!0,_e=!1,he=!1,te=null;const de=Et=>(n({type:"failed",message:Et}),r(`✖ Build failed: ${Et.split(`
34665
34665
  `)[0]}`),!1);async function Ee(Et){const _t=performance.now();n({type:"buildStarted",changed:Et}),r(Et.length===0?"Building the scene…":`Rebuilding: ${Awr(Et)}`);try{const{builder:At,sdkVersion:vt}=await _(),Ve=Et.length===0?Owr(M,vt):null;Ve!==null&&r(Ve);const Qt=Et.length===0||Et.includes("package.json")||Et.includes(A3),{snapshot:We,result:Fe}=await m(async()=>{(Qt||l!==te)&&(await x(A,M,!0),te=l);const xt=new Map(M);return{snapshot:xt,result:await At.build(xt)}});if(he)return!1;const zt=Fe.diagnostics.filter(xt=>xt.severity==="error"||xt.file===void 0||We.has(xt.file));n({type:"diagnostics",diagnostics:zt.map(({severity:xt,message:ht,file:Rt,line:qt,column:Wt})=>({severity:xt,message:ht,file:Rt,line:qt,column:Wt}))});for(const xt of zt)r(Cwr(xt));if(!Fe.ok){const xt=Fe.events.find(ht=>ht.type==="failed");return de((xt==null?void 0:xt.type)==="failed"?xt.message:"The build produced no bundle")}const ft=R1(We.get("scene.json"));return ft===null?de("scene.json is missing or is not valid JSON"):(await ebr({realmUrl:B,projectId:F,files:We,buildOutputs:Fe.outputs,sceneJson:ft,sdkVersion:vt,machineId:await t.machineId(F)}),he?!1:(n({type:"bundleSaved"}),r(`✔ Built in ${Math.round(performance.now()-_t)} ms`),!0))}catch(At){return he?!1:de(sOt(At))}}function lt(){return he?Promise.resolve(!1):(Z!==null||(Z=(async()=>{for(;(K||H.size>0)&&!he;){const Et=K?[]:[...H];K=!1,H.clear(),_e=await Ee(Et)}return _e&&!he})().finally(()=>{Z=null})),Z)}return{id:A,files:M,start:lt,flush(){return ee!==null&&clearTimeout(ee),ee=null,lt()},async published(){const Et=await(await caches.open(Txe)).match(uWe(B)),_t=await(Et==null?void 0:Et.json().catch(()=>{})),At=_t==null?void 0:_t.entity;return(At==null?void 0:At.id)===Nzt(F,await t.machineId(F))},changed(Et){he||(H.add(Et),ee!==null&&clearTimeout(ee),ee=setTimeout(()=>{ee=null,lt()},Twr))},stop(){he=!0,ee!==null&&clearTimeout(ee)}}}return{realmUrl:A=>lWe(t.pageDir,A),open:T,async build(A,M,F){const{builder:B,sdkVersion:H}=await _();return m(async()=>(await x(A,M,!1),{...await B.build(M,F),sdkVersion:H}))},install:(A,M)=>m(()=>x(A,M,!1)),dispose(){s=!0,a==null||a.dispose(),a=null}}}const Iwr=200,Nwr=2e3,Dwr=/^\((?:no logs|\+\d+ older entries not retained)\)$/;function Rwr(t,n){for(let r=Math.min(t.length,n.length);r>0;r--){const a=t.length-r;if(n.slice(0,r).every((s,l)=>s===t[a+l]))return n.slice(r)}return[...n]}function Mwr(t,n){let r=[],a=!1,s;const l=async()=>{try{const d=await t(`scene_logs ${Iwr} --server`);if(a)return;const m=d.split(`
34666
34666
  `).filter(_=>_.trim()!==""&&!Dwr.test(_.trim()));for(const _ of Rwr(r,m))n(_);r=m}catch{}a||(s=setTimeout(()=>void l(),Nwr))};return l(),()=>{a=!0,clearTimeout(s)}}function Lwr(t,n,r){r.throwIfAborted();const a=tt.scene,s=[...t].sort().join(";");return new Promise((l,d)=>{const m=()=>{clearTimeout(M),T(),r.removeEventListener("abort",A)},_=F=>{m(),d(F)},x=()=>{var B;tt.scene===a||tt.status!=="ready"||!tt.frozen||((B=tt.scene)==null?void 0:B.parcels.map(H=>`${H.x},${H.y}`).sort().join(";"))!==s||(m(),l())},T=vqe(x),A=()=>_(r.reason),M=setTimeout(()=>_(new Error("The preview has not loaded the new parcels. Retry sceneSettings before building outside the current layout.")),9e4);r.addEventListener("abort",A,{once:!0});try{n(),x()}catch(F){_(F)}})}const Fwr=new Set(["node_modules",".git","bin","dist"]),jwr=300*1024,Bwr=56,$wr=5;function Uwr(t){const n=t.origin,r=typeof n=="object"&&n!==null&&!Array.isArray(n)?n:null;return r!==null&&(r.source==="import"||r.source==="github")?r:{...r??{},source:"user"}}function zwr(t,n){const r=new Map;let a=new Map;function s(m,_){if(_.size>jwr)return t.blob(m,_.hash);let x=r.get(_.hash);return x===void 0&&(x=t.blob(m,_.hash),r.set(_.hash,x),x.catch(()=>r.delete(_.hash))),x}const l={async folders(){const m=await t.list();return a=new Map(m.map(x=>[x.name,x])),(await Promise.all(m.map(async x=>{const T=x.files["data.json"];if(T===void 0)return null;const A=await s(x.name,T).then(F=>new TextDecoder().decode(F),()=>null);if(A===null)return null;const M=Object.fromEntries(Object.entries(x.files).map(([F,B])=>[F,B.size]));return{name:x.name,data:A,files:M}}))).filter(x=>x!==null)},async read(m,_){var T;const x=(T=a.get(m.name))==null?void 0:T.files[_];if(x===void 0)throw new Error(`${m.name}/${_} is not in your library`);return s(m.name,x)}};async function d(m,_){const x={},T=new Map;for(const[M,F]of _){const B=await n(F);x[M]={hash:B,size:F.length},T.set(B,F)}const A=[...T].map(([M,F])=>({hash:M,size:F.length}));for(const M of await t.uploads(m,A)){const F=T.get(M.hash);F!==void 0&&await t.putBlob(M,F)}await t.put(m,x)}return{tree:l,async copyOut(m,_){const[x,T,A]=_.split("/");if(x!=="custom"||T===void 0||A!==void 0||!/^[A-Za-z0-9][A-Za-z0-9._-]*$/.test(T))throw new Error(`not a prefab folder: ${_}`);const M=`${_}/`,F=new Map;for(const[te,de]of m.files()){const Ee=te.slice(M.length);te.startsWith(M)&&!Ee.split("/").some(lt=>Fwr.has(lt))&&F.set(Ee,de)}const B=F.get("data.json"),H=B===void 0?null:Pq(new TextDecoder().decode(B));if(H===null)throw new Error(`${_} has no readable data.json`);const ee={...H,id:typeof H.id=="string"?H.id:crypto.randomUUID(),origin:Uwr(H)},Z=`${JSON.stringify(ee,null,2)}
34667
- `;F.set("data.json",new TextEncoder().encode(Z));const K=SWe(hVt(H,T)).slice(0,Bwr).replace(/_+$/,"")||"prefab",_e=new Set((await t.list()).map(te=>te.name));let he=1;for(let te=0;te<$wr;te++){let de=K;for(;_e.has(de);)de=`${K}_${++he}`;try{return await d(de,F),{ref:`user:${de}`,scope:"user",data:Z}}catch(Ee){if(!(Ee instanceof rVt))throw Ee;_e.add(de)}}throw new Error("could not find a free name in your library — try again")},remove:m=>t.remove(m)}}const oOt=new WeakMap;function Vwr(t){let n=oOt.get(t);return n===void 0&&(n=crypto.subtle.digest("SHA-256",new Uint8Array(t)).then(r=>[...new Uint8Array(r)].map(a=>a.toString(16).padStart(2,"0")).join("")),oOt.set(t,n)),n}async function Wwr(t){const n=t.get(".dclignore"),r=kXe(t.keys(),n===void 0?void 0:new TextDecoder().decode(n)).filter(l=>l!==A3),a=new Map;let s=0;for(const l of r){const d=t.get(l);d!==void 0&&(a.set(await Vwr(d),d.byteLength),s++)}return{bytes:[...a.values()].reduce((l,d)=>l+d,0),files:s}}const cOt=4e3,qwr=4e6,Gwr=ZIt*24*60*60*1e3,Jwr="assets/images",Hwr=3e3,Qwr=100,Ywr="Sign in to keep prefabs in your own library. The built-in prefabs work without it.",Xwr=t=>t instanceof Error?t.message:String(t);function GBe(t,n){var r,a,s;return{realm:n.replace(/\/$/,""),systemScene:"",position:((r=t.scene)==null?void 0:r.base)??((s=(a=t.scene)==null?void 0:a.parcels)==null?void 0:s[0])??"0,0",spawn:N1r(t),spawnPoints:JSON.stringify(Array.isArray(t.spawnPoints)?t.spawnPoints:[])}}const Zwr=({host:t,sceneCompiler:n})=>{const r=new fxr(axr()),a=JA(t),s=a===null||a.services.projects===null?null:nVt(a.services.projects,(Hn,Rr)=>a.signedFetch(Hn,Rr)),l=()=>{const{address:Hn,isGuest:Rr}=t.identity();return Rr||Hn===null?null:Hn.toLowerCase()},d=[],m=[],_=[],x=[],T=[],A=Hn=>{d.push(Hn),d.length>cOt&&d.splice(0,d.length-cOt);for(const Rr of m)Rr(Hn)},M=Hn=>{for(const Rr of _)Rr(Hn)},F=new Map,B=new Set,H=m3t.then(kwr),ee=Pwr({pageDir:t.pageDir,urls:n,machineId:async Hn=>Ewr(await H,l()??"guest",Hn),emit:M,log:A,packages:r.packages,saveLock:async(Hn,Rr)=>{await r.write(Hn,A3,Rr),ft.touched(Hn,A3),(K==null?void 0:K.id)===Hn&&K.files.set(A3,Rr)},onPackages:(Hn,Rr)=>{if(Rr===null){F.delete(Hn);return}F.set(Hn,Rr);for(const Fi of B)Fi(Hn,Rr)}});let Z=null,K=null,_e=null,he=null;async function te(Hn){var ta;const Rr=(ta=(await r.list()).find(xs=>xs.id===Hn))==null?void 0:ta.previewId;if(Rr!==void 0)return Rr;const Fi="p"+Array.from(crypto.getRandomValues(new Uint8Array(16)),xs=>xs.toString(16).padStart(2,"0")).join("");return await r.patch(Hn,{previewId:Fi}),Fi}async function de(Hn){const Rr=new URL("preview/",t.pageDir).href,Fi=await caches.open(Txe);for(const ta of await Fi.keys())ta.url.startsWith(Rr)&&(Hn===null||!ta.url.startsWith(Hn))&&await Fi.delete(ta)}let Ee=0,lt=Promise.resolve(),Et=Promise.resolve();const _t=obr({service:(a==null?void 0:a.services.projects)??null,fetch:(Hn,Rr)=>a===null?Promise.reject(new Error("The assistant service is not configured.")):a.signedFetch(Hn,Rr),wallet:l,memory:{read:async(Hn,Rr)=>{const Fi=await r.assistantMemory(Hn,Rr);return Cl(Fi)&&typeof Fi.id=="string"&&typeof Fi.key=="string"?{id:Fi.id,key:Fi.key}:null},write:(Hn,Rr,Fi)=>r.setAssistantMemory(Hn,Rr,Fi)},project:()=>{const Hn=si();return{id:Hn.id,tools:{files:()=>Hn.files,write:(Rr,Fi,ta,xs)=>Ve(Hn.id,Rr,Fi,{expected:ta,signal:xs}),assets:x1r({files:()=>Hn.files,write:(Rr,Fi,ta,xs)=>Ve(Hn.id,Rr,Fi,{expected:ta,signal:xs})}),scene:(Rr,Fi)=>EXe(Rr,Fi,async ta=>{var uf,di,Al;const xs=gl=>{var Jg,_u;return JSON.stringify([(Jg=gl==null?void 0:gl.scene)==null?void 0:Jg.parcels,(_u=gl==null?void 0:gl.scene)==null?void 0:_u.base])};await YA();const Lo=xs(R1(await vt(Hn.id,"scene.json")));await ot(Hn.id,gl=>L1r(gl,ta));const fl=R1(await vt(Hn.id,"scene.json")),Hd=xs(fl)!==Lo,cr=((uf=fl==null?void 0:fl.scene)==null?void 0:uf.parcels)??[],Hl=(di=tt.scene)==null?void 0:di.parcels.map(gl=>`${gl.x},${gl.y}`).sort().join(";");if(Hd||Hl!==[...cr].sort().join(";")){if(!await Hn.flush())throw new Error("The scene did not build. Fix the code and retry sceneSettings to load the new parcels.");Fi.throwIfAborted();const gl=await te(Hn.id);Z=GBe(fl??{},ee.realmUrl(gl)),await Lwr(cr,()=>{for(const Jg of x)Jg(Z)},Fi)}else if(Z!==null){const gl=GBe(fl??{},Z.realm);(gl.spawn!==Z.spawn||gl.spawnPoints!==Z.spawnPoints)&&(Z={...Z,spawn:gl.spawn,spawnPoints:gl.spawnPoints},tlr(gl.spawn,gl.spawnPoints))}return{requiredPermissions:(fl==null?void 0:fl.requiredPermissions)??[],spawnPoints:(fl==null?void 0:fl.spawnPoints)??[],parcels:cr,base:((Al=fl==null?void 0:fl.scene)==null?void 0:Al.base)??null,previewReady:!0}}),written:ubr(),view:(Rr,Fi)=>g1r(Rr,Fi),playtest:A1r,build:async Rr=>{Rr.throwIfAborted(),await Et;const Fi=await ee.build(Hn.id,new Map(Hn.files));if(Rr.throwIfAborted(),!Fi.ok)return{ok:!1,diagnostics:Fi.diagnostics};const ta=await T1r();return Rr.throwIfAborted(),{ok:!0,diagnostics:Fi.diagnostics,run:ta}}}}}});function At(){_t.reset(),he==null||he(),he=null,K!==null&&(K.stop(),r.close(K.id),ft.flush(K.id),K=null,_e=null)}async function vt(Hn,Rr){return(K==null?void 0:K.id)===Hn?K.files.get(Rr):r.read(Hn,Rr).catch(Fi=>{if(!uI(Fi))throw Fi})}function Ve(Hn,Rr,Fi,ta){const xs=Et.then(async()=>{if(ta==null||ta.signal.throwIfAborted(),ta!==void 0&&((K==null?void 0:K.id)!==Hn||!ibr(K.files.get(Rr),ta.expected)))throw new Error("This file changed. Read it again before writing.");await r.write(Hn,Rr,Fi),ft.touched(Hn,Rr),(K==null?void 0:K.id)===Hn&&(K.files.set(Rr,Fi),K.changed(Rr))});return Et=xs.catch(Lo=>console.error("[editor] file write failed",Lo)),xs}function Qt(Hn,Rr){const Fi=Et.then(async()=>{const ta=await r.remove(Hn,Rr);return ta&&ft.touched(Hn,Rr),ta&&(K==null?void 0:K.id)===Hn&&K.files.delete(Rr)&&K.changed(Rr),ta});return Et=Fi.catch(ta=>console.error("[editor] file removal failed",ta)),Fi}function We(Hn){const Rr=si();if(Rr.id!==Hn)throw new Error("that scene is not the one open");return{files:()=>Rr.files,write:(Fi,ta)=>Ve(Hn,Fi,ta),remove:async Fi=>{await Qt(Hn,Fi)}}}async function Fe(Hn){var ta;const Rr=R1(await vt(Hn,"scene.json").catch(()=>{})),Fi=(((ta=Rr==null?void 0:Rr.display)==null?void 0:ta.title)??"").replace(/[\x00-\x1f\x7f]/g,"").replace(new RegExp(tVt.source,"g"),"").trim().slice(0,Qwr);return Fi===""?Hn:Fi}async function zt(Hn,Rr){const Fi=(await r.list()).find(xs=>xs.id===Hn);if(Fi===void 0)return null;const ta=await r.duplicate(Hn,`${Fi.name} ${Rr}`,ft.remoteIds());return await ot(ta.id,xs=>{var Lo;return{...xs,display:{...xs.display??{},title:`${((Lo=xs.display)==null?void 0:Lo.title)||Fi.name} ${Rr}`}}}),ta.id}const ft=yxr({store:r,session:()=>{const Hn=l();return s===null||Hn===null?null:{api:s,wallet:Hn}},account:()=>s===null?"unavailable":l()===null?"guest":"on",hash:xxe,title:Fe,duplicate:async Hn=>{const Rr=await zt(Hn,XIt(new Date));if(Rr===null)throw new Error("The scene is no longer on this device");return Rr}});let xt=!1,ht=0;async function Rt(){const Hn=++ht,Rr=l()!==null&&(await _t.shell.aiProviders()).some(Fi=>Fi.available);Hn!==ht||Rr===xt||(xt=Rr,W0())}Rt();let qt=l();const Wt=setInterval(()=>{const Hn=l();Hn!==qt&&(qt=Hn,_t.reset(),W0(),Rt(),ft.refresh(!0),de(_e).catch(Rr=>console.warn("[editor] could not clear the previews",Rr)))},Hwr),Le=()=>{document.visibilityState==="hidden"&&ft.flush()};document.addEventListener("visibilitychange",Le);const Ze=new Set;async function ot(Hn,Rr){const Fi=R1(await vt(Hn,"scene.json"));if(Fi===null)throw new Error("scene.json is missing or is not valid JSON");await Ve(Hn,"scene.json",IAt(Rr(Fi)))}async function nn(Hn,Rr){if(Rr==null||Rr==="")return null;const Fi=await vt(Hn,Rr).catch(()=>{});return Fi===void 0||Fi.length>qwr?null:NAt(Rr,Fi)}async function On(Hn,Rr=ft.status().projects){var ta,xs,Lo,fl;const Fi=R1(await vt(Hn.id,"scene.json").catch(()=>{}));return{sync:Rr[Hn.id],path:Hn.id,name:Hn.name,title:((ta=Fi==null?void 0:Fi.display)==null?void 0:ta.title)||Hn.name,world:((xs=Fi==null?void 0:Fi.worldConfiguration)==null?void 0:xs.name)||null,parcels:Array.isArray((Lo=Fi==null?void 0:Fi.scene)==null?void 0:Lo.parcels)?Fi.scene.parcels.length:0,thumbnail:await nn(Hn.id,(fl=Fi==null?void 0:Fi.display)==null?void 0:fl.navmapThumbnail),favourite:Hn.favourite,lastOpened:Hn.lastOpened,published:Hn.published,deletedAt:Hn.deletedAt??void 0}}async function fn(Hn,Rr){var ta,xs;At(),d.length=0,M({type:"sessionStarted"});const Fi=Lo=>{if(At(),Rr===Ee){A(`✖ ${Lo}`);for(const fl of T)fl(Lo)}};try{if(await ft.prepareOpen(Hn,(uf,di)=>A(`Downloading from your account… ${uf}/${di}`)),Rr!==Ee)return;if(!await r.open(Hn)){Fi("This scene is open in another tab. Close it there to edit it here.");return}const Lo=await r.readAll(Hn).then(async uf=>{for(const[di,Al]of Qvr(uf))await Ve(Hn,di,Al),uf.set(di,Al);return uf}).catch(uf=>{throw r.close(Hn),uf});if(Rr!==Ee){r.close(Hn);return}const fl=await te(Hn);if(Rr!==Ee){r.close(Hn);return}const Hd=ee.open(Hn,Lo,fl);K=Hd;const cr=ee.realmUrl(fl);if(_e=cr,A(`▶ Opening ${((xs=(ta=R1(Hd.files.get("scene.json")))==null?void 0:ta.display)==null?void 0:xs.title)||Hn}`),!await Hd.start()&&!await Hd.published()){if(Rr!==Ee)return;A("✖ The scene did not build.");for(const uf of T)uf("The scene did not build.");return}if(await r.patch(Hn,{lastOpened:Date.now()}),Rr!==Ee){At();return}const Hl=R1(Hd.files.get("scene.json"))??{};Z=GBe(Hl,cr),he=Mwr(uf=>t.engineConsole(uf),A);for(const uf of x)uf(Z)}catch(Lo){Fi(Xwr(Lo))}}function kn(Hn){Z=null;const Rr=++Ee,Fi=_t.reset(),ta=lt.then(async()=>{await Fi,await Et,Rr===Ee&&await Hn(Rr)});return lt=ta.catch(xs=>console.error("[editor] project transition failed",xs)),ta}function si(){if(K===null)throw new Error("no project is open");return K}const St={saveFile:async({path:Hn,content:Rr})=>Ve(si().id,Hn,Rr),getFile:async({path:Hn})=>{const Rr=si().files.get(Hn)??fwr(Hn);if(Rr===void 0)throw new Error(`no such file: ${Hn}`);return{content:Rr}},removeFiles:async({filePaths:Hn})=>{const Rr=si(),Fi=[],ta=[];for(const xs of Hn)(await Qt(Rr.id,xs).catch(()=>!1)?Fi:ta).push(xs);return{success:Fi,failed:ta}},getFilesSizes:async({path:Hn,ignore:Rr})=>{const Fi=Hn===""?"":`${Hn.replace(/\/+$/,"")}/`;return{files:[...si().files.keys()].filter(xs=>xs.startsWith(Fi)&&!xs.split("/").some(Lo=>Rr.includes(Lo))).sort().map(xs=>({path:xs}))}}},Mi={async find(Hn){return(await r.list()).some(Rr=>Rr.id===Hn)?!0:(await ft.refresh(!0),ft.remoteOnly().some(Rr=>Rr.id===Hn))},files:async Hn=>(K==null?void 0:K.id)===Hn?new Map(K.files):r.readAll(Hn),manifest:Hn=>ft.manifest(Hn),build:async(Hn,Rr)=>ee.build(Hn,await Mi.files(Hn),Rr),dependencies:async Hn=>Xzt(await vt(Hn,"package.json")),onImported:Hn=>(Ze.add(Hn),()=>Ze.delete(Hn))},Br=a===null?null:ixr({host:a,setWorld:async(Hn,Rr)=>{var ta,xs;((xs=(ta=R1(await vt(Hn,"scene.json")))==null?void 0:ta.worldConfiguration)==null?void 0:xs.name)!==Rr&&await ot(Hn,Lo=>({...Lo,worldConfiguration:{...Lo.worldConfiguration??{},name:Rr}}))},files:Hn=>Mi.files(Hn),build:(Hn,Rr)=>ee.build(Hn,Rr,{production:!0}),published:(Hn,Rr)=>r.patch(Hn,{published:Rr})}),go=(a==null?void 0:a.services.projects)==null?null:zwr(mxr(a.services.projects,(Hn,Rr)=>a.signedFetch(Hn,Rr)),xxe);lur(Ubr(t.editorBase)),zbr(t.editorBase),Mdr(async()=>Wwr(await Mi.files(si().id)));const _a=bwr({builtin:Dxr(t.editorBase,mB("prefabs/catalog.json"),oTe),user:()=>go!==null&&l()!==null?go.tree:null}),fc={...(a==null?void 0:a.services.projects)==null?{}:{..._t.shell,aiOffered:()=>xt,aiTranscript:()=>{const Hn=qt;if(Hn===null||K===null)return null;const Rr=K.id;return{owner:`${Rr}@${Hn.toLowerCase()}`,load:()=>r.transcript(Rr,Hn),save:Fi=>r.setTranscript(Rr,Hn,Fi)}}},pickProject:async()=>{},openProject:Hn=>kn(Rr=>fn(Hn,Rr)),relaunchProject:Hn=>kn(Rr=>fn(Hn,Rr)),closeProject:()=>kn(async()=>{At(),M({type:"sessionStarted"}),A("■ Scene closed"),await de(null).catch(Hn=>console.warn("[editor] could not clear the previews",Hn))}),getState:async()=>{const Hn=await r.list(),Rr=ft.status().projects,Fi=ft.remoteOnly().map(ta=>({path:ta.id,name:ta.name,title:ta.name,world:null,parcels:0,thumbnail:null,remoteOnly:!0}));return{recentProjects:[...Hn].sort((ta,xs)=>xs.lastOpened-ta.lastOpened).map(ta=>ta.id),projects:[...await Promise.all(Hn.map(ta=>On(ta,Rr))),...Fi],logs:[...d],bevyWebDir:"",editorSceneDir:"",webPort:0,scenePort:0,editorScenePort:0,favourites:Hn.filter(ta=>ta.favourite).map(ta=>ta.id)}},onStackLog:Hn=>{m.push(Hn)},onBuildEvent:Hn=>{_.push(Hn)},onServersReady:Hn=>{x.push(Hn)},requestReady:async()=>Z,onServersError:Hn=>{T.push(Hn)},toggleFavourite:async Hn=>{const Rr=(await r.list()).find(Fi=>Fi.id===Hn);Rr!==void 0&&await r.patch(Hn,{favourite:!Rr.favourite})},deleteProject:async Hn=>{const Rr=await r.trash(Hn);return Rr&&ft.trashed(Hn),Rr},trashedProjects:async()=>Promise.all((await r.trashed()).map(Hn=>On(Hn))),restoreProject:async Hn=>{const Rr=await r.restore(Hn);return Rr&&ft.restored(Hn),Rr},syncStatus:async()=>(ft.refresh(),ft.status()),onSyncStatus:Hn=>ft.subscribe(Hn),resolveSyncConflict:(Hn,Rr)=>ft.resolve(Hn,Rr),exportProject:async Hn=>Pxr(await Fe(Hn),await Mi.files(Hn)),importProject:async Hn=>{const Rr=await Nxr(Hn,async(Fi,ta)=>{const xs=await r.create(Fi,ta,{taken:ft.remoteIds()});return ft.touched(xs.id,"scene.json"),xs.id});if((Rr==null?void 0:Rr.ok)===!0){const{id:Fi,needsPackages:ta}=Rr.report;Object.keys(ta).length>0&&r.readAll(Fi).then(xs=>ee.install(Fi,xs)).catch(xs=>console.warn("[editor] could not install the packages of",Fi,xs));for(const xs of Ze)xs(Rr.report)}return Rr},projectPackages:async Hn=>F.get(Hn)??null,onProjectPackages:Hn=>(B.add(Hn),()=>B.delete(Hn)),...Br===null||a===null?{}:{publishScene:(Hn,Rr,Fi)=>Br.publish(Hn,Rr,Fi),publishStop:async()=>Br.stop(),publishWorlds:async()=>{const Hn=l();return Hn===null?[]:nxr(Hn,a.services.worldsContent.replace(/\/+$/,""))}},canImportFolder:Oxr(),renameProject:(Hn,Rr)=>ot(Hn,Fi=>({...Fi,display:{...Fi.display??{},title:Rr.trim()}})),duplicateProject:Hn=>zt(Hn,"copy"),sceneTemplates:async()=>cwr(),createScene:async(Hn,Rr,Fi)=>{const ta=pVt(Fi),xs=R1(ta.get("scene.json"));if(xs===null)throw new Error(`template not found: ${Fi}`);ta.set("scene.json",IAt({...xs,display:{...xs.display??{},title:Rr.trim()}}));const Lo=await r.create(Rr,ta,{taken:ft.remoteIds()});return ft.touched(Lo.id,"scene.json"),Lo.id},openExternal:async Hn=>{/^https?:$/.test(new URL(Hn).protocol)&&window.open(Hn,"_blank","noopener,noreferrer")},compositeEntityIds:async Hn=>{for(const Rr of D1r){const Fi=await vt(Hn,Rr);if(Fi!==void 0)return R1r(new TextDecoder().decode(Fi))}return[]},sceneSettings:async Hn=>{const Rr=R1(await vt(Hn,"scene.json"));if(Rr===null)throw new Error("scene.json is missing or is not valid JSON");const Fi=O1r(Rr);return{...Fi,thumbnail:await nn(Hn,Fi.thumbnailPath)}},saveSceneSettings:async(Hn,Rr)=>{const Fi=P1r(Rr);return Fi!==null?Fi:(await ot(Hn,ta=>I1r(ta,Rr)),null)},pickSceneThumbnail:async Hn=>{const Rr=await dVt(Object.values(mWe).join(","));if(Rr===null)return null;const Fi=Qzt(Rr.name);if(mWe[Fi]===void 0)throw new Error("not a supported image (png, jpg, gif, webp)");const ta=`${Jwr}/scene-thumbnail${Fi}`,xs=new Uint8Array(await Rr.arrayBuffer());return await Ve(Hn,ta,xs),{path:ta,dataUrl:NAt(ta,xs)}},appVersion:async()=>tbr,prefabLibraryList:()=>_a.list(),prefabLibraryCopyIn:async(Hn,Rr)=>_a.copyIn(Hn,We(Rr)),prefabLibraryUpdateCopy:async(Hn,Rr)=>_a.updateCopy(Hn,We(Rr)),prefabUserLibrary:()=>go===null?"unavailable":l()===null?"guest":"on",...go===null?{}:{prefabLibraryCopyOut:async(Hn,Rr)=>{if(l()===null)throw new Error(Ywr);return go.copyOut(We(Hn),Rr)},prefabLibraryDelete:async Hn=>{const Rr=mVt(Hn);return(Rr==null?void 0:Rr.scope)==="user"&&l()!==null?go.remove(Rr.name):!1}}};async function Kc(){const Hn=new Set;for(const Rr of[...await r.list(),...await r.trashed()]){const Fi=Ezt(await vt(Rr.id,A3).catch(()=>{}));for(const ta of Object.keys((Fi==null?void 0:Fi.packages)??{}))Hn.add(ta);for(const[ta,xs]of Object.entries((Fi==null?void 0:Fi.dependencies)??{}))Hn.add($j(ta,xs))}for(const Rr of await r.packages.keys())Hn.has(Rr)||await r.packages.remove(Rr)}return r.purge(Date.now()-Gwr).then(async Hn=>{const Rr=await caches.open(Txe),Fi=Hn.map(({id:xs,previewId:Lo})=>ee.realmUrl(Lo??xs));for(const xs of await Rr.keys())Fi.some(Lo=>xs.url.startsWith(Lo))&&await Rr.delete(xs);const ta=await caches.open(K0r);for(const xs of Fi)await ta.delete(`${xs}__storage`);Hn.length>0&&await Kc()}).catch(Hn=>console.warn("[editor] could not empty the trash",Hn)),{shell:fc,projects:Mi,dataLayer:St,dispose:()=>{_t.dispose(),Ee++,At(),ee.dispose(),clearInterval(Wt),document.removeEventListener("visibilitychange",Le),ft.flush().finally(()=>ft.dispose())}}};let Uj=null,mG=null,Yne=null,lOt=!1;function Kwr(){if(Uj!==null)return Uj;const t=window.__dclEditorHost;if(t===void 0||t.version!==0&&t.version!==1)return console.error("[editor] window.__dclEditorHost (contract v0 or v1) is missing: nothing to mount into"),null;console.log("[editor] web build 2026-10-14T19:21:16.553Z"),fIt(t),sIt(a=>t.engineConsole(a)),w3t(()=>t.identity()),_qn.needed=!1;const n=Zwr({host:t,sceneCompiler:$br(t.editorBase)});window.editorShell=eSr(n.shell,t),UNt(n.dataLayer??null),bGe();const r=document.createElement("link");return r.rel="stylesheet",r.href=new URL("editor.css",t.editorBase).href,r.integrity=mB("editor.css"),r.crossOrigin="anonymous",r.onerror=()=>console.error("[editor] editor.css did not load or does not match the hash this editor was published with: its fonts are not applied"),document.head.appendChild(r),jA.project=null,jA.notice=null,Uj={host:t,web:n,fonts:r},Uj}function Axe(){const t=mG;mG=null,t==null||t.unmount()}function eSr(t,n){return{...t,openProject:async r=>{const a=mG;Axe(),a==null||a.api.close(),Yne??(Yne=dFt(n.container,O.jsx(Nvr,{}))),n.setMode("edit"),jA.project=r,jA.opens++,await t.openProject(r)}}}function tSr(t,n){var m;const r=Kwr();if(r===null)return()=>{};Axe();const a=document.createElement("div");a.style.cssText="position:relative;width:100%;height:100%",YWn(a),t.appendChild(a);const s=dFt(a,O.jsx(KWn,{}),"eui-create-root"),l={api:n,unmount:()=>{s(),a.remove()}};mG=l;const d=lOt?null:((m=JA(r.host))==null?void 0:m.openProject)??null;return lOt=!0,d!==null&&r.web.projects.find(d).catch(()=>!1).then(_=>{var x;mG===l&&(_?(x=window.editorShell)==null||x.openProject(d):jA.notice=`“${d}” is not on this device or on your account. Here are your scenes.`)}),()=>{mG===l&&Axe()}}function nSr(){Axe();const t=Uj;if(t===null)return;Uj=null;const n=YA();Yne==null||Yne(),Yne=null,t.fonts.remove(),jA.project=null,delete window.editorShell,w3t(null),sIt(null),fIt(null),t.host.setMode("off"),n.finally(()=>{var r,a;(a=(r=t.web).dispose)==null||a.call(r),Uj===null&&UNt(null)})}window.__dclEditor={mountHome:tSr,unmount:nSr};
34667
+ `;F.set("data.json",new TextEncoder().encode(Z));const K=SWe(hVt(H,T)).slice(0,Bwr).replace(/_+$/,"")||"prefab",_e=new Set((await t.list()).map(te=>te.name));let he=1;for(let te=0;te<$wr;te++){let de=K;for(;_e.has(de);)de=`${K}_${++he}`;try{return await d(de,F),{ref:`user:${de}`,scope:"user",data:Z}}catch(Ee){if(!(Ee instanceof rVt))throw Ee;_e.add(de)}}throw new Error("could not find a free name in your library — try again")},remove:m=>t.remove(m)}}const oOt=new WeakMap;function Vwr(t){let n=oOt.get(t);return n===void 0&&(n=crypto.subtle.digest("SHA-256",new Uint8Array(t)).then(r=>[...new Uint8Array(r)].map(a=>a.toString(16).padStart(2,"0")).join("")),oOt.set(t,n)),n}async function Wwr(t){const n=t.get(".dclignore"),r=kXe(t.keys(),n===void 0?void 0:new TextDecoder().decode(n)).filter(l=>l!==A3),a=new Map;let s=0;for(const l of r){const d=t.get(l);d!==void 0&&(a.set(await Vwr(d),d.byteLength),s++)}return{bytes:[...a.values()].reduce((l,d)=>l+d,0),files:s}}const cOt=4e3,qwr=4e6,Gwr=ZIt*24*60*60*1e3,Jwr="assets/images",Hwr=3e3,Qwr=100,Ywr="Sign in to keep prefabs in your own library. The built-in prefabs work without it.",Xwr=t=>t instanceof Error?t.message:String(t);function GBe(t,n){var r,a,s;return{realm:n.replace(/\/$/,""),systemScene:"",position:((r=t.scene)==null?void 0:r.base)??((s=(a=t.scene)==null?void 0:a.parcels)==null?void 0:s[0])??"0,0",spawn:N1r(t),spawnPoints:JSON.stringify(Array.isArray(t.spawnPoints)?t.spawnPoints:[])}}const Zwr=({host:t,sceneCompiler:n})=>{const r=new fxr(axr()),a=JA(t),s=a===null||a.services.projects===null?null:nVt(a.services.projects,(Hn,Rr)=>a.signedFetch(Hn,Rr)),l=()=>{const{address:Hn,isGuest:Rr}=t.identity();return Rr||Hn===null?null:Hn.toLowerCase()},d=[],m=[],_=[],x=[],T=[],A=Hn=>{d.push(Hn),d.length>cOt&&d.splice(0,d.length-cOt);for(const Rr of m)Rr(Hn)},M=Hn=>{for(const Rr of _)Rr(Hn)},F=new Map,B=new Set,H=m3t.then(kwr),ee=Pwr({pageDir:t.pageDir,urls:n,machineId:async Hn=>Ewr(await H,l()??"guest",Hn),emit:M,log:A,packages:r.packages,saveLock:async(Hn,Rr)=>{await r.write(Hn,A3,Rr),ft.touched(Hn,A3),(K==null?void 0:K.id)===Hn&&K.files.set(A3,Rr)},onPackages:(Hn,Rr)=>{if(Rr===null){F.delete(Hn);return}F.set(Hn,Rr);for(const Fi of B)Fi(Hn,Rr)}});let Z=null,K=null,_e=null,he=null;async function te(Hn){var ta;const Rr=(ta=(await r.list()).find(xs=>xs.id===Hn))==null?void 0:ta.previewId;if(Rr!==void 0)return Rr;const Fi="p"+Array.from(crypto.getRandomValues(new Uint8Array(16)),xs=>xs.toString(16).padStart(2,"0")).join("");return await r.patch(Hn,{previewId:Fi}),Fi}async function de(Hn){const Rr=new URL("preview/",t.pageDir).href,Fi=await caches.open(Txe);for(const ta of await Fi.keys())ta.url.startsWith(Rr)&&(Hn===null||!ta.url.startsWith(Hn))&&await Fi.delete(ta)}let Ee=0,lt=Promise.resolve(),Et=Promise.resolve();const _t=obr({service:(a==null?void 0:a.services.projects)??null,fetch:(Hn,Rr)=>a===null?Promise.reject(new Error("The assistant service is not configured.")):a.signedFetch(Hn,Rr),wallet:l,memory:{read:async(Hn,Rr)=>{const Fi=await r.assistantMemory(Hn,Rr);return Cl(Fi)&&typeof Fi.id=="string"&&typeof Fi.key=="string"?{id:Fi.id,key:Fi.key}:null},write:(Hn,Rr,Fi)=>r.setAssistantMemory(Hn,Rr,Fi)},project:()=>{const Hn=si();return{id:Hn.id,tools:{files:()=>Hn.files,write:(Rr,Fi,ta,xs)=>Ve(Hn.id,Rr,Fi,{expected:ta,signal:xs}),assets:x1r({files:()=>Hn.files,write:(Rr,Fi,ta,xs)=>Ve(Hn.id,Rr,Fi,{expected:ta,signal:xs})}),scene:(Rr,Fi)=>EXe(Rr,Fi,async ta=>{var uf,di,Al;const xs=gl=>{var Jg,_u;return JSON.stringify([(Jg=gl==null?void 0:gl.scene)==null?void 0:Jg.parcels,(_u=gl==null?void 0:gl.scene)==null?void 0:_u.base])};await YA();const Lo=xs(R1(await vt(Hn.id,"scene.json")));await ot(Hn.id,gl=>L1r(gl,ta));const fl=R1(await vt(Hn.id,"scene.json")),Hd=xs(fl)!==Lo,cr=((uf=fl==null?void 0:fl.scene)==null?void 0:uf.parcels)??[],Hl=(di=tt.scene)==null?void 0:di.parcels.map(gl=>`${gl.x},${gl.y}`).sort().join(";");if(Hd||Hl!==[...cr].sort().join(";")){if(!await Hn.flush())throw new Error("The scene did not build. Fix the code and retry sceneSettings to load the new parcels.");Fi.throwIfAborted();const gl=await te(Hn.id);Z=GBe(fl??{},ee.realmUrl(gl)),await Lwr(cr,()=>{for(const Jg of x)Jg(Z)},Fi)}else if(Z!==null){const gl=GBe(fl??{},Z.realm);(gl.spawn!==Z.spawn||gl.spawnPoints!==Z.spawnPoints)&&(Z={...Z,spawn:gl.spawn,spawnPoints:gl.spawnPoints},tlr(gl.spawn,gl.spawnPoints))}return{requiredPermissions:(fl==null?void 0:fl.requiredPermissions)??[],spawnPoints:(fl==null?void 0:fl.spawnPoints)??[],parcels:cr,base:((Al=fl==null?void 0:fl.scene)==null?void 0:Al.base)??null,previewReady:!0}}),written:ubr(),view:(Rr,Fi)=>g1r(Rr,Fi),playtest:A1r,build:async Rr=>{Rr.throwIfAborted(),await Et;const Fi=await ee.build(Hn.id,new Map(Hn.files));if(Rr.throwIfAborted(),!Fi.ok)return{ok:!1,diagnostics:Fi.diagnostics};const ta=await T1r();return Rr.throwIfAborted(),{ok:!0,diagnostics:Fi.diagnostics,run:ta}}}}}});function At(){_t.reset(),he==null||he(),he=null,K!==null&&(K.stop(),r.close(K.id),ft.flush(K.id),K=null,_e=null)}async function vt(Hn,Rr){return(K==null?void 0:K.id)===Hn?K.files.get(Rr):r.read(Hn,Rr).catch(Fi=>{if(!uI(Fi))throw Fi})}function Ve(Hn,Rr,Fi,ta){const xs=Et.then(async()=>{if(ta==null||ta.signal.throwIfAborted(),ta!==void 0&&((K==null?void 0:K.id)!==Hn||!ibr(K.files.get(Rr),ta.expected)))throw new Error("This file changed. Read it again before writing.");await r.write(Hn,Rr,Fi),ft.touched(Hn,Rr),(K==null?void 0:K.id)===Hn&&(K.files.set(Rr,Fi),K.changed(Rr))});return Et=xs.catch(Lo=>console.error("[editor] file write failed",Lo)),xs}function Qt(Hn,Rr){const Fi=Et.then(async()=>{const ta=await r.remove(Hn,Rr);return ta&&ft.touched(Hn,Rr),ta&&(K==null?void 0:K.id)===Hn&&K.files.delete(Rr)&&K.changed(Rr),ta});return Et=Fi.catch(ta=>console.error("[editor] file removal failed",ta)),Fi}function We(Hn){const Rr=si();if(Rr.id!==Hn)throw new Error("that scene is not the one open");return{files:()=>Rr.files,write:(Fi,ta)=>Ve(Hn,Fi,ta),remove:async Fi=>{await Qt(Hn,Fi)}}}async function Fe(Hn){var ta;const Rr=R1(await vt(Hn,"scene.json").catch(()=>{})),Fi=(((ta=Rr==null?void 0:Rr.display)==null?void 0:ta.title)??"").replace(/[\x00-\x1f\x7f]/g,"").replace(new RegExp(tVt.source,"g"),"").trim().slice(0,Qwr);return Fi===""?Hn:Fi}async function zt(Hn,Rr){const Fi=(await r.list()).find(xs=>xs.id===Hn);if(Fi===void 0)return null;const ta=await r.duplicate(Hn,`${Fi.name} ${Rr}`,ft.remoteIds());return await ot(ta.id,xs=>{var Lo;return{...xs,display:{...xs.display??{},title:`${((Lo=xs.display)==null?void 0:Lo.title)||Fi.name} ${Rr}`}}}),ta.id}const ft=yxr({store:r,session:()=>{const Hn=l();return s===null||Hn===null?null:{api:s,wallet:Hn}},account:()=>s===null?"unavailable":l()===null?"guest":"on",hash:xxe,title:Fe,duplicate:async Hn=>{const Rr=await zt(Hn,XIt(new Date));if(Rr===null)throw new Error("The scene is no longer on this device");return Rr}});let xt=!1,ht=0;async function Rt(){const Hn=++ht,Rr=l()!==null&&(await _t.shell.aiProviders()).some(Fi=>Fi.available);Hn!==ht||Rr===xt||(xt=Rr,W0())}Rt();let qt=l();const Wt=setInterval(()=>{const Hn=l();Hn!==qt&&(qt=Hn,_t.reset(),W0(),Rt(),ft.refresh(!0),de(_e).catch(Rr=>console.warn("[editor] could not clear the previews",Rr)))},Hwr),Le=()=>{document.visibilityState==="hidden"&&ft.flush()};document.addEventListener("visibilitychange",Le);const Ze=new Set;async function ot(Hn,Rr){const Fi=R1(await vt(Hn,"scene.json"));if(Fi===null)throw new Error("scene.json is missing or is not valid JSON");await Ve(Hn,"scene.json",IAt(Rr(Fi)))}async function nn(Hn,Rr){if(Rr==null||Rr==="")return null;const Fi=await vt(Hn,Rr).catch(()=>{});return Fi===void 0||Fi.length>qwr?null:NAt(Rr,Fi)}async function On(Hn,Rr=ft.status().projects){var ta,xs,Lo,fl;const Fi=R1(await vt(Hn.id,"scene.json").catch(()=>{}));return{sync:Rr[Hn.id],path:Hn.id,name:Hn.name,title:((ta=Fi==null?void 0:Fi.display)==null?void 0:ta.title)||Hn.name,world:((xs=Fi==null?void 0:Fi.worldConfiguration)==null?void 0:xs.name)||null,parcels:Array.isArray((Lo=Fi==null?void 0:Fi.scene)==null?void 0:Lo.parcels)?Fi.scene.parcels.length:0,thumbnail:await nn(Hn.id,(fl=Fi==null?void 0:Fi.display)==null?void 0:fl.navmapThumbnail),favourite:Hn.favourite,lastOpened:Hn.lastOpened,published:Hn.published,deletedAt:Hn.deletedAt??void 0}}async function fn(Hn,Rr){var ta,xs;At(),d.length=0,M({type:"sessionStarted"});const Fi=Lo=>{if(At(),Rr===Ee){A(`✖ ${Lo}`);for(const fl of T)fl(Lo)}};try{if(await ft.prepareOpen(Hn,(uf,di)=>A(`Downloading from your account… ${uf}/${di}`)),Rr!==Ee)return;if(!await r.open(Hn)){Fi("This scene is open in another tab. Close it there to edit it here.");return}const Lo=await r.readAll(Hn).then(async uf=>{for(const[di,Al]of Qvr(uf))await Ve(Hn,di,Al),uf.set(di,Al);return uf}).catch(uf=>{throw r.close(Hn),uf});if(Rr!==Ee){r.close(Hn);return}const fl=await te(Hn);if(Rr!==Ee){r.close(Hn);return}const Hd=ee.open(Hn,Lo,fl);K=Hd;const cr=ee.realmUrl(fl);if(_e=cr,A(`▶ Opening ${((xs=(ta=R1(Hd.files.get("scene.json")))==null?void 0:ta.display)==null?void 0:xs.title)||Hn}`),!await Hd.start()&&!await Hd.published()){if(Rr!==Ee)return;A("✖ The scene did not build.");for(const uf of T)uf("The scene did not build.");return}if(await r.patch(Hn,{lastOpened:Date.now()}),Rr!==Ee){At();return}const Hl=R1(Hd.files.get("scene.json"))??{};Z=GBe(Hl,cr),he=Mwr(uf=>t.engineConsole(uf),A);for(const uf of x)uf(Z)}catch(Lo){Fi(Xwr(Lo))}}function kn(Hn){Z=null;const Rr=++Ee,Fi=_t.reset(),ta=lt.then(async()=>{await Fi,await Et,Rr===Ee&&await Hn(Rr)});return lt=ta.catch(xs=>console.error("[editor] project transition failed",xs)),ta}function si(){if(K===null)throw new Error("no project is open");return K}const St={saveFile:async({path:Hn,content:Rr})=>Ve(si().id,Hn,Rr),getFile:async({path:Hn})=>{const Rr=si().files.get(Hn)??fwr(Hn);if(Rr===void 0)throw new Error(`no such file: ${Hn}`);return{content:Rr}},removeFiles:async({filePaths:Hn})=>{const Rr=si(),Fi=[],ta=[];for(const xs of Hn)(await Qt(Rr.id,xs).catch(()=>!1)?Fi:ta).push(xs);return{success:Fi,failed:ta}},getFilesSizes:async({path:Hn,ignore:Rr})=>{const Fi=Hn===""?"":`${Hn.replace(/\/+$/,"")}/`;return{files:[...si().files.keys()].filter(xs=>xs.startsWith(Fi)&&!xs.split("/").some(Lo=>Rr.includes(Lo))).sort().map(xs=>({path:xs}))}}},Mi={async find(Hn){return(await r.list()).some(Rr=>Rr.id===Hn)?!0:(await ft.refresh(!0),ft.remoteOnly().some(Rr=>Rr.id===Hn))},files:async Hn=>(K==null?void 0:K.id)===Hn?new Map(K.files):r.readAll(Hn),manifest:Hn=>ft.manifest(Hn),build:async(Hn,Rr)=>ee.build(Hn,await Mi.files(Hn),Rr),dependencies:async Hn=>Xzt(await vt(Hn,"package.json")),onImported:Hn=>(Ze.add(Hn),()=>Ze.delete(Hn))},Br=a===null?null:ixr({host:a,setWorld:async(Hn,Rr)=>{var ta,xs;((xs=(ta=R1(await vt(Hn,"scene.json")))==null?void 0:ta.worldConfiguration)==null?void 0:xs.name)!==Rr&&await ot(Hn,Lo=>({...Lo,worldConfiguration:{...Lo.worldConfiguration??{},name:Rr}}))},files:Hn=>Mi.files(Hn),build:(Hn,Rr)=>ee.build(Hn,Rr,{production:!0}),published:(Hn,Rr)=>r.patch(Hn,{published:Rr})}),go=(a==null?void 0:a.services.projects)==null?null:zwr(mxr(a.services.projects,(Hn,Rr)=>a.signedFetch(Hn,Rr)),xxe);lur(Ubr(t.editorBase)),zbr(t.editorBase),Mdr(async()=>Wwr(await Mi.files(si().id)));const _a=bwr({builtin:Dxr(t.editorBase,mB("prefabs/catalog.json"),oTe),user:()=>go!==null&&l()!==null?go.tree:null}),fc={...(a==null?void 0:a.services.projects)==null?{}:{..._t.shell,aiOffered:()=>xt,aiTranscript:()=>{const Hn=qt;if(Hn===null||K===null)return null;const Rr=K.id;return{owner:`${Rr}@${Hn.toLowerCase()}`,load:()=>r.transcript(Rr,Hn),save:Fi=>r.setTranscript(Rr,Hn,Fi)}}},pickProject:async()=>{},openProject:Hn=>kn(Rr=>fn(Hn,Rr)),relaunchProject:Hn=>kn(Rr=>fn(Hn,Rr)),closeProject:()=>kn(async()=>{At(),M({type:"sessionStarted"}),A("■ Scene closed"),await de(null).catch(Hn=>console.warn("[editor] could not clear the previews",Hn))}),getState:async()=>{const Hn=await r.list(),Rr=ft.status().projects,Fi=ft.remoteOnly().map(ta=>({path:ta.id,name:ta.name,title:ta.name,world:null,parcels:0,thumbnail:null,remoteOnly:!0}));return{recentProjects:[...Hn].sort((ta,xs)=>xs.lastOpened-ta.lastOpened).map(ta=>ta.id),projects:[...await Promise.all(Hn.map(ta=>On(ta,Rr))),...Fi],logs:[...d],bevyWebDir:"",editorSceneDir:"",webPort:0,scenePort:0,editorScenePort:0,favourites:Hn.filter(ta=>ta.favourite).map(ta=>ta.id)}},onStackLog:Hn=>{m.push(Hn)},onBuildEvent:Hn=>{_.push(Hn)},onServersReady:Hn=>{x.push(Hn)},requestReady:async()=>Z,onServersError:Hn=>{T.push(Hn)},toggleFavourite:async Hn=>{const Rr=(await r.list()).find(Fi=>Fi.id===Hn);Rr!==void 0&&await r.patch(Hn,{favourite:!Rr.favourite})},deleteProject:async Hn=>{const Rr=await r.trash(Hn);return Rr&&ft.trashed(Hn),Rr},trashedProjects:async()=>Promise.all((await r.trashed()).map(Hn=>On(Hn))),restoreProject:async Hn=>{const Rr=await r.restore(Hn);return Rr&&ft.restored(Hn),Rr},syncStatus:async()=>(ft.refresh(),ft.status()),onSyncStatus:Hn=>ft.subscribe(Hn),resolveSyncConflict:(Hn,Rr)=>ft.resolve(Hn,Rr),exportProject:async Hn=>Pxr(await Fe(Hn),await Mi.files(Hn)),importProject:async Hn=>{const Rr=await Nxr(Hn,async(Fi,ta)=>{const xs=await r.create(Fi,ta,{taken:ft.remoteIds()});return ft.touched(xs.id,"scene.json"),xs.id});if((Rr==null?void 0:Rr.ok)===!0){const{id:Fi,needsPackages:ta}=Rr.report;Object.keys(ta).length>0&&r.readAll(Fi).then(xs=>ee.install(Fi,xs)).catch(xs=>console.warn("[editor] could not install the packages of",Fi,xs));for(const xs of Ze)xs(Rr.report)}return Rr},projectPackages:async Hn=>F.get(Hn)??null,onProjectPackages:Hn=>(B.add(Hn),()=>B.delete(Hn)),...Br===null||a===null?{}:{publishScene:(Hn,Rr,Fi)=>Br.publish(Hn,Rr,Fi),publishStop:async()=>Br.stop(),publishWorlds:async()=>{const Hn=l();return Hn===null?[]:nxr(Hn,a.services.worldsContent.replace(/\/+$/,""))}},canImportFolder:Oxr(),renameProject:(Hn,Rr)=>ot(Hn,Fi=>({...Fi,display:{...Fi.display??{},title:Rr.trim()}})),duplicateProject:Hn=>zt(Hn,"copy"),sceneTemplates:async()=>cwr(),createScene:async(Hn,Rr,Fi)=>{const ta=pVt(Fi),xs=R1(ta.get("scene.json"));if(xs===null)throw new Error(`template not found: ${Fi}`);ta.set("scene.json",IAt({...xs,display:{...xs.display??{},title:Rr.trim()}}));const Lo=await r.create(Rr,ta,{taken:ft.remoteIds()});return ft.touched(Lo.id,"scene.json"),Lo.id},openExternal:async Hn=>{/^https?:$/.test(new URL(Hn).protocol)&&window.open(Hn,"_blank","noopener,noreferrer")},compositeEntityIds:async Hn=>{for(const Rr of D1r){const Fi=await vt(Hn,Rr);if(Fi!==void 0)return R1r(new TextDecoder().decode(Fi))}return[]},sceneSettings:async Hn=>{const Rr=R1(await vt(Hn,"scene.json"));if(Rr===null)throw new Error("scene.json is missing or is not valid JSON");const Fi=O1r(Rr);return{...Fi,thumbnail:await nn(Hn,Fi.thumbnailPath)}},saveSceneSettings:async(Hn,Rr)=>{const Fi=P1r(Rr);return Fi!==null?Fi:(await ot(Hn,ta=>I1r(ta,Rr)),null)},pickSceneThumbnail:async Hn=>{const Rr=await dVt(Object.values(mWe).join(","));if(Rr===null)return null;const Fi=Qzt(Rr.name);if(mWe[Fi]===void 0)throw new Error("not a supported image (png, jpg, gif, webp)");const ta=`${Jwr}/scene-thumbnail${Fi}`,xs=new Uint8Array(await Rr.arrayBuffer());return await Ve(Hn,ta,xs),{path:ta,dataUrl:NAt(ta,xs)}},appVersion:async()=>tbr,prefabLibraryList:()=>_a.list(),prefabLibraryCopyIn:async(Hn,Rr)=>_a.copyIn(Hn,We(Rr)),prefabLibraryUpdateCopy:async(Hn,Rr)=>_a.updateCopy(Hn,We(Rr)),prefabUserLibrary:()=>go===null?"unavailable":l()===null?"guest":"on",...go===null?{}:{prefabLibraryCopyOut:async(Hn,Rr)=>{if(l()===null)throw new Error(Ywr);return go.copyOut(We(Hn),Rr)},prefabLibraryDelete:async Hn=>{const Rr=mVt(Hn);return(Rr==null?void 0:Rr.scope)==="user"&&l()!==null?go.remove(Rr.name):!1}}};async function Kc(){const Hn=new Set;for(const Rr of[...await r.list(),...await r.trashed()]){const Fi=Ezt(await vt(Rr.id,A3).catch(()=>{}));for(const ta of Object.keys((Fi==null?void 0:Fi.packages)??{}))Hn.add(ta);for(const[ta,xs]of Object.entries((Fi==null?void 0:Fi.dependencies)??{}))Hn.add($j(ta,xs))}for(const Rr of await r.packages.keys())Hn.has(Rr)||await r.packages.remove(Rr)}return r.purge(Date.now()-Gwr).then(async Hn=>{const Rr=await caches.open(Txe),Fi=Hn.map(({id:xs,previewId:Lo})=>ee.realmUrl(Lo??xs));for(const xs of await Rr.keys())Fi.some(Lo=>xs.url.startsWith(Lo))&&await Rr.delete(xs);const ta=await caches.open(K0r);for(const xs of Fi)await ta.delete(`${xs}__storage`);Hn.length>0&&await Kc()}).catch(Hn=>console.warn("[editor] could not empty the trash",Hn)),{shell:fc,projects:Mi,dataLayer:St,dispose:()=>{_t.dispose(),Ee++,At(),ee.dispose(),clearInterval(Wt),document.removeEventListener("visibilitychange",Le),ft.flush().finally(()=>ft.dispose())}}};let Uj=null,mG=null,Yne=null,lOt=!1;function Kwr(){if(Uj!==null)return Uj;const t=window.__dclEditorHost;if(t===void 0||t.version!==0&&t.version!==1)return console.error("[editor] window.__dclEditorHost (contract v0 or v1) is missing: nothing to mount into"),null;console.log("[editor] web build 2026-10-14T20:28:40.691Z"),fIt(t),sIt(a=>t.engineConsole(a)),w3t(()=>t.identity()),_qn.needed=!1;const n=Zwr({host:t,sceneCompiler:$br(t.editorBase)});window.editorShell=eSr(n.shell,t),UNt(n.dataLayer??null),bGe();const r=document.createElement("link");return r.rel="stylesheet",r.href=new URL("editor.css",t.editorBase).href,r.integrity=mB("editor.css"),r.crossOrigin="anonymous",r.onerror=()=>console.error("[editor] editor.css did not load or does not match the hash this editor was published with: its fonts are not applied"),document.head.appendChild(r),jA.project=null,jA.notice=null,Uj={host:t,web:n,fonts:r},Uj}function Axe(){const t=mG;mG=null,t==null||t.unmount()}function eSr(t,n){return{...t,openProject:async r=>{const a=mG;Axe(),a==null||a.api.close(),Yne??(Yne=dFt(n.container,O.jsx(Nvr,{}))),n.setMode("edit"),jA.project=r,jA.opens++,await t.openProject(r)}}}function tSr(t,n){var m;const r=Kwr();if(r===null)return()=>{};Axe();const a=document.createElement("div");a.style.cssText="position:relative;width:100%;height:100%",YWn(a),t.appendChild(a);const s=dFt(a,O.jsx(KWn,{}),"eui-create-root"),l={api:n,unmount:()=>{s(),a.remove()}};mG=l;const d=lOt?null:((m=JA(r.host))==null?void 0:m.openProject)??null;return lOt=!0,d!==null&&r.web.projects.find(d).catch(()=>!1).then(_=>{var x;mG===l&&(_?(x=window.editorShell)==null||x.openProject(d):jA.notice=`“${d}” is not on this device or on your account. Here are your scenes.`)}),()=>{mG===l&&Axe()}}function nSr(){Axe();const t=Uj;if(t===null)return;Uj=null;const n=YA();Yne==null||Yne(),Yne=null,t.fonts.remove(),jA.project=null,delete window.editorShell,w3t(null),sIt(null),fIt(null),t.host.setMode("off"),n.finally(()=>{var r,a;(a=(r=t.web).dispose)==null||a.call(r),Uj===null&&UNt(null)})}window.__dclEditor={mountHome:tSr,unmount:nSr};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dcl-regenesislabs/web-editor",
3
- "version": "0.3.12",
3
+ "version": "0.3.13",
4
4
  "license": "Apache-2.0",
5
5
  "description": "The Decentraland scene editor for the web explorer: editor.js plus the files it loads beside it. Served by version, not installed.",
6
6
  "repository": {