illutions 0.21.6
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/LICENSE +21 -0
- package/README.md +47 -0
- package/dist/main.d.ts +2479 -0
- package/dist/main.min.cjs +8 -0
- package/dist/main.min.js +8 -0
- package/package.json +36 -0
package/dist/main.min.js
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* illutions Engine
|
|
3
|
+
* https://illutions.com
|
|
4
|
+
* @license Copyright (c) 2025-2026 illutions. All rights reserved.
|
|
5
|
+
* Commercial use is permitted only under the illutions License Agreement. Unauthorized copying, modification, distribution, resale, sublicensing, reverse engineering, deobfuscation, or bypassing of license mechanisms is prohibited.
|
|
6
|
+
* The illutions menu bar, branding, attribution, and license validation must not be removed, hidden, disabled, altered, or obscured without prior written permission.
|
|
7
|
+
*/
|
|
8
|
+
import{ACESFilmicToneMapping,AgXToneMapping,AmbientLight,AnimationAction,AnimationClip,AnimationMixer,Audio as Audio$1,AudioContext,AudioListener,AudioLoader,BasicShadowMap,Box3,BoxGeometry,Camera,CatmullRomCurve3,CineonToneMapping,Color,CustomToneMapping,DataTexture,DirectionalLight,EquirectangularReflectionMapping,Euler,Fog,Group,HemisphereLight,KeyframeTrack,Light,LinearSRGBColorSpace,LinearToneMapping,LoopOnce,LoopRepeat,MOUSE,MathUtils,Matrix4,Mesh,MeshPhysicalMaterial,MeshStandardMaterial,NeutralToneMapping,NoToneMapping,Object3D,OrthographicCamera,PCFShadowMap,PMREMGenerator,PerspectiveCamera,PointLight,PositionalAudio,Quaternion,Raycaster,ReinhardToneMapping,SRGBColorSpace,Scene,Sphere,SpotLight,TOUCH,Texture,TextureLoader,UnsignedByteType,VSMShadowMap,Vector2,Vector3,WebGLRenderer}from"three";import{gsap}from"gsap";import{createActor}from"xstate";var CfgCtrl=class{cfg;constructor(e){this.cfg=e}setAudio(e){const t=this.cfg.audio;void 0!==e.refDistance&&(t.refDistance=e.refDistance),void 0!==e.rolloffFactor&&(t.rolloffFactor=e.rolloffFactor),void 0!==e.maxDistance&&(t.maxDistance=e.maxDistance),void 0!==e.distanceModel&&(t.distanceModel=e.distanceModel),void 0!==e.coneInnerAngle&&(t.coneInnerAngle=e.coneInnerAngle),void 0!==e.coneOuterAngle&&(t.coneOuterAngle=e.coneOuterAngle),void 0!==e.coneOuterGain&&(t.coneOuterGain=e.coneOuterGain)}setRender(e){const t=this.cfg.render;void 0!==e.fpsLimiter&&(t.fpsLimiter=e.fpsLimiter),void 0!==e.deltaTimesMax&&(t.deltaTimesMax=e.deltaTimesMax)}},THREE={ACESFilmicToneMapping:ACESFilmicToneMapping,AgXToneMapping:AgXToneMapping,AmbientLight:AmbientLight,AnimationAction:AnimationAction,AnimationClip:AnimationClip,AnimationMixer:AnimationMixer,Audio:Audio$1,AudioContext:AudioContext,AudioListener:AudioListener,AudioLoader:AudioLoader,BasicShadowMap:BasicShadowMap,Box3:Box3,BoxGeometry:BoxGeometry,Camera:Camera,CatmullRomCurve3:CatmullRomCurve3,CineonToneMapping:CineonToneMapping,Color:Color,CustomToneMapping:CustomToneMapping,DataTexture:DataTexture,DirectionalLight:DirectionalLight,EquirectangularReflectionMapping:EquirectangularReflectionMapping,Euler:Euler,Fog:Fog,Group:Group,HemisphereLight:HemisphereLight,KeyframeTrack:KeyframeTrack,Light:Light,LinearSRGBColorSpace:LinearSRGBColorSpace,LinearToneMapping:LinearToneMapping,LoopOnce:LoopOnce,LoopRepeat:LoopRepeat,MathUtils:MathUtils,Matrix4:Matrix4,Mesh:Mesh,MeshPhysicalMaterial:MeshPhysicalMaterial,MeshStandardMaterial:MeshStandardMaterial,MOUSE:MOUSE,NeutralToneMapping:NeutralToneMapping,NoToneMapping:NoToneMapping,Object3D:Object3D,OrthographicCamera:OrthographicCamera,PCFShadowMap:PCFShadowMap,PMREMGenerator:PMREMGenerator,PerspectiveCamera:PerspectiveCamera,PointLight:PointLight,PositionalAudio:PositionalAudio,Quaternion:Quaternion,Raycaster:Raycaster,ReinhardToneMapping:ReinhardToneMapping,Scene:Scene,SpotLight:SpotLight,Sphere:Sphere,SRGBColorSpace:SRGBColorSpace,Texture:Texture,TextureLoader:TextureLoader,TOUCH:TOUCH,UnsignedByteType:UnsignedByteType,Vector2:Vector2,Vector3:Vector3,VSMShadowMap:VSMShadowMap,WebGLRenderer:WebGLRenderer},EventDispatcher=class{listeners=new Map;addEventListener(e,t){let s=this.listeners.get(e);return s||(s=new Set,this.listeners.set(e,s)),s.add(t),()=>this.removeEventListener(e,t)}removeEventListener(e,t){const s=this.listeners.get(e);s&&(s.delete(t),0===s.size&&this.listeners.delete(e))}emit(e){const t=this.listeners.get(e.type);if(t)for(const s of[...t])s(e)}listenerCount(e){return this.listeners.get(e)?.size??0}},Obj3D=class{canvas;cfg;cfgCtrl;events;name;obj=null;objs3D=null;raycast;renderer;scene;enableOcclusionCheck=!1;eventDispatcher=new EventDispatcher;posScreen=new THREE.Vector2;posScreenLast=null;posWorld=new THREE.Vector3;posWorldLast=null;visible=!1;visibleFrustum=!1;visibleLast=null;visibleOcclusion=!1;constructor(e,t,s,n){this.canvas=e,this.cfg=t,this.cfgCtrl=s,this.name=n}addEventListener(e,t){const s=this.eventDispatcher.addEventListener(e,t);return()=>{s(),this.resetEventStateIfNoListeners(e)}}calcScreenPos(e,t){t.updateMatrixWorld(!0);const s=new THREE.Vector3;t.getWorldPosition(s);const n=s.clone().project(e.obj),i=this.canvas.getBoundingClientRect();return this.visibleFrustum=n.x>=-1&&n.x<=1&&n.y>=-1&&n.y<=1&&n.z>=-1&&n.z<=1,new THREE.Vector2((.5*n.x+.5)*i.width,(.5*-n.y+.5)*i.height)}checkWorldAndScreenPos(e,t){if(t.getWorldPosition(this.posWorld),null!==this.posWorldLast&&this.posWorld.equals(this.posWorldLast)||(this.eventDispatcher.emit({type:"OBJ3D_POS_WORLD_CHANGED",posWorld:this.posWorld.clone()}),null===this.posWorldLast?this.posWorldLast=this.posWorld.clone():this.posWorldLast.copy(this.posWorld)),this.visibleFrustum=this.isVisibleFrustum(e,t),!this.visibleFrustum)return this.visibleOcclusion=!1,void this.posScreen.set(0,0);if(this.enableOcclusionCheck){if(this.visibleOcclusion=this.raycast.isVisibleOcclusion(t),!this.visibleOcclusion)return void this.posScreen.set(0,0)}else this.visibleOcclusion=!0;this.posScreen.copy(this.calcScreenPos(e,t)),null!=this.posScreenLast&&this.posScreen.equals(this.posScreenLast)||(this.eventDispatcher.emit({type:"OBJ3D_POS_SCREEN_CHANGED",posScreen:this.posScreen.clone()}),null===this.posScreenLast?this.posScreenLast=this.posScreen.clone():this.posScreenLast.copy(this.posScreen))}checkVisible(){this.visible=this.visibleFrustum&&this.visibleOcclusion,this.visible!==this.visibleLast&&(this.emitEvent({type:"OBJ3D_VISIBLE_CHANGED",visible:this.visible}),this.visibleLast=this.visible)}emitEvent(e){this.eventDispatcher.emit(e),this.events.send(e,this.name)}getScreenPosition(e){if(!this.obj)return null;const t=this.calcScreenPos(e,this.obj);return{x:t.x,y:t.y}}isVisibleFrustum(e,t){t.updateMatrixWorld(!0);const s=new THREE.Vector3;t.getWorldPosition(s);const n=s.clone().project(e.obj);return n.x>=-1&&n.x<=1&&n.y>=-1&&n.y<=1&&n.z>=-1&&n.z<=1}onReady(){}onStart(){}onTraverse(e){this.obj=e,this.visible=e.visible}onUpdate(e){}ready(e){this.objs3D=e,this.onReady()}removeEventListener(e,t){this.eventDispatcher.removeEventListener(e,t),0===this.eventDispatcher.listenerCount(e)&&this.resetEventStateIfNoListeners(e)}resetEventStateIfNoListeners(e){"OBJ3D_POS_WORLD_CHANGED"===e&&(this.posWorldLast=null),"OBJ3D_POS_SCREEN_CHANGED"===e&&(this.posScreenLast=null),"OBJ3D_VISIBLE_CHANGED"===e&&(this.visibleLast=null)}start(e,t){this.renderer=e,this.scene=t,this.onStart()}traverse(e){this.onTraverse(e)}update(e,t){this.obj&&(this.onUpdate(e),0==this.eventDispatcher.listenerCount("OBJ3D_POS_WORLD_CHANGED")&&0==this.eventDispatcher.listenerCount("OBJ3D_POS_SCREEN_CHANGED")||(this.checkWorldAndScreenPos(t,this.obj),0!=this.eventDispatcher.listenerCount("OBJ3D_VISIBLE_CHANGED")&&this.checkVisible()))}},Comp=class extends HTMLElement{canvas;cfg;cfgCtrl;comps=null;events;objs3D;unsubFollow=void 0;unsubVisible=void 0;follow({obj:e,enableOcclusionCheck:t=!1}){const s=this.follow.name;if(!e)return void console.warn(`${s}: Missing parameter object`);const n=e instanceof Obj3D?e:this.objs3D.get(e);n?n.obj?(this.unfollow(),n.enableOcclusionCheck=t,this.unsubFollow=n.addEventListener("OBJ3D_POS_SCREEN_CHANGED",e=>{const{x:t,y:s}=e.posScreen;this.style.left=`${t}px`,this.style.top=`${s}px`}),this.unsubVisible=n.addEventListener("OBJ3D_VISIBLE_CHANGED",e=>{this.style.display=e.visible?"block":"none"})):console.warn(`${s}: Obj3D "${e}" has no THREE.Object3D assigned.`):console.warn(`${s}: Obj3D "${e}" is not registered.`)}unfollow(){this.unsubFollow&&(this.unsubFollow(),this.unsubFollow=void 0),this.unsubVisible&&(this.unsubVisible(),this.unsubVisible=void 0)}onReady(){}onStart(){}ready(e){this.objs3D=e,this.onReady()}start(e){this.comps=e,this.onStart()}},Cam3D=class extends Obj3D{lookMode="target";obj;objGltf=null;objTarget;targetGltf=null;tmpVec=new THREE.Vector3;constructor(e,t,s,n){super(e,t,s,n),this.canvas=e;const i=e.getBoundingClientRect();"perspective"===t.cam.type?this.obj=new THREE.PerspectiveCamera(t.cam.fov,i.width/i.height,t.cam.near,t.cam.far):this.obj=new THREE.OrthographicCamera(t.cam.left,t.cam.right,t.cam.top,t.cam.bottom,t.cam.near,t.cam.far),this.objTarget=new THREE.Object3D,this.objTarget.position.copy(t.cam.lookAt),this.obj.position.copy(t.cam.position),this.obj.lookAt(this.objTarget.position)}onTraverse(e){const t=new THREE.Vector3,s=new THREE.Quaternion,n=new THREE.Vector3;e.updateMatrixWorld(!0),e.matrixWorld.decompose(t,s,n),this.obj.copy(e),this.obj.position.copy(t),this.obj.quaternion.copy(s),this.obj.scale.copy(n),this.obj instanceof THREE.PerspectiveCamera&&e instanceof THREE.PerspectiveCamera&&this.obj.updateProjectionMatrix(),this.obj.updateMatrixWorld(!0)}traverse(e){if(this.obj instanceof THREE.PerspectiveCamera&&e instanceof THREE.PerspectiveCamera||this.obj instanceof THREE.OrthographicCamera&&e instanceof THREE.OrthographicCamera){this.onTraverse(e);let t=this.canvas.getBoundingClientRect();this.updateCanvasResize(t)}else console.warn("Camera type mismatch between cfg and .gltf model.")}update(e,t){if(this.onUpdate(e),"target"===this.lookMode)this.obj.lookAt(this.objTarget.position);else{let e=this.obj.position.distanceTo(this.objTarget.position);this.objTarget.position.copy(this.obj.position).add(this.tmpVec.set(0,0,-e).applyQuaternion(this.obj.quaternion))}this.obj.updateMatrixWorld(!0),this.checkWorldAndScreenPos(t,this.obj)}updateCanvasResize(e){const t=e.width/e.height;if(this.obj instanceof THREE.PerspectiveCamera)this.obj.aspect=t,this.obj.updateProjectionMatrix();else if(this.obj instanceof THREE.OrthographicCamera){const e=this.obj.top-this.obj.bottom,s=e*t/2,n=e/2;this.obj.left=-s,this.obj.right=s,this.obj.top=n,this.obj.bottom=-n,this.obj.updateProjectionMatrix()}}},Light3D=class extends Obj3D{obj;constructor(e,t,s,n){super(e,t,s,n),this.obj=new THREE.PointLight}onTraverse(e){this.obj=e}traverse(e){this.onTraverse(e)}},Mesh3D=class extends Obj3D{obj;groundReflector=null;reflectivesSSR=[];constructor(e,t,s,n){super(e,t,s,n),this.obj=new THREE.Mesh(new THREE.BoxGeometry,new THREE.MeshPhysicalMaterial)}onTraverse(e){this.obj=e}setReflectivesSSR(e){this.reflectivesSSR=e}traverse(e){this.onTraverse(e)}},Audio=class{cfg;ctx=THREE.AudioContext.getContext();loader=new THREE.AudioLoader;engine;sounds=[];audioCfgLast;callback=null;listener=null;constructor(e,t){this.engine=t,this.cfg=e,this.audioCfgLast={...this.cfg.audio}}attachSoundTo(e,t){if(!e)return void console.warn("No name assigned.");if(!t)return void console.warn("No object to attach provided.");const s=this.engine.scene.getObjectByName(t);if(!s)return void console.warn(`Object "${t}" not found in scene.`);const n=this.sounds.find(t=>t.name===e);n?s.add(n.audio):console.warn(`Sound "${e}" not found.`)}isLoaded({name:e}){let t=this.isLoaded.name;return"running"!==this.ctx.state?(console.warn(`${t}: ctx.state is not running.`),!1):!!this.sounds.find(t=>t.name===e)}isPlaying({name:e}){let t=this.isPlaying.name;if("running"!==this.ctx.state)return console.warn(`${t}: ctx.state is not running.`),!1;const s=this.sounds.find(t=>t.name===e);return s?s.audio.isPlaying:(console.warn(`${t}: Sound not found.`),!1)}loadAndPlay({name:e,url:t,object:s,volume:n=0,fade:i=2,loop:o=!0}){let a=this.loadAndPlay.name;if(!this.listener)return void console.warn(`${a}: No audio listener set.`);const r=s?new THREE.PositionalAudio(this.listener):new THREE.Audio(this.listener);s&&!this.callback&&(this.callback=()=>this.update(),this.engine.addOnFrameUpdate(this.callback));const l=()=>{r instanceof THREE.PositionalAudio&&this.setPositionalSoundCfg(r),this.loader.load(t,t=>{r.setBuffer(t),r.setLoop(o),r.setVolume(0),this.sounds.push({name:e,audio:r,volume:n,fade:i,loop:o}),s&&this.attachSoundTo(e,s),this.play({name:e})},void 0,e=>{throw new Error(`Audio loading error for ${t}: ${e}`)})};"suspended"===this.ctx.state||"running"===this.ctx.state?this.ctx.resume().then(()=>{setTimeout(()=>{l()},this.cfg.audio.delayPlaySound)}).catch(e=>{throw new Error(`Audio API resume error: ${e}`)}):l()}play({name:e}){let t=this.play.name;if("running"!==this.ctx.state)return void console.warn(`${t}: AudioContext is not running.`);const s=this.sounds.find(t=>t.name===e);if(!s)return void console.warn(`${t}: Sound with name '${e}' not found.`);if(s.audio.isPlaying)return;s.audio.play();const n={value:0};gsap.to(n,{duration:s.fade,value:s.volume,ease:"power1.in",onUpdate:()=>{s.audio.setVolume(n.value)}})}setAttribute({name:e,attribute:t,duration:s,value:n}){if("running"!==this.ctx.state)return void console.warn("AudioContext is not running.");const i=this.sounds.find(t=>t.name===e);i?gsap.to(i.audio,{duration:s,[t]:n,ease:"power1.inOut"}):console.warn(`Sound '${e}' not found.`)}setAudioContext({state:e}){if(!this.ctx)return void console.warn("AudioContext does not exist.");const t=this.ctx.state;if(this.ctx.state!==e)switch(e){case"running":"suspended"===t&&this.ctx.resume().catch(e=>{throw new Error(`Error resuming context: ${e}`)});break;case"suspended":"running"===t&&this.ctx.suspend().catch(e=>{throw new Error(`Error suspending context: ${e}`)});break;case"closed":"closed"!==t&&this.ctx.close().catch(e=>{throw new Error(`Error closing context: ${e}`)});break;default:throw new Error(`Unknown AudioContext state: ${e}`)}}setListener({object:e}){let t=this.setListener.name;if(!e)return void console.warn(`${t}: No object listener name provided.`);const s=this.engine.scene.getObjectByName(e);if(!s)return void console.warn(`${t}: Object "${e}" not found in scene.`);const n=new THREE.AudioListener;s.add(n),this.listener=n}setAllPositionalSoundsCfg(){for(const e of this.sounds)e.audio instanceof THREE.PositionalAudio&&this.setPositionalSoundCfg(e.audio)}setPositionalSoundCfg(e){e.setRefDistance(this.cfg.audio.refDistance),e.setRolloffFactor(this.cfg.audio.rolloffFactor),e.setMaxDistance(this.cfg.audio.maxDistance),e.setDistanceModel(this.cfg.audio.distanceModel),e.setDirectionalCone(this.cfg.audio.coneInnerAngle,this.cfg.audio.coneOuterAngle,this.cfg.audio.coneOuterGain)}stop({name:e}){let t=this.stop.name;if("running"!==this.ctx.state)return void console.warn(`${t}: AudioContext is not running.`);const s=this.sounds.find(t=>t.name===e);if(!s)return void console.warn(`${t}: Sound '${e}' not found.`);const n={value:s.audio.getVolume()};gsap.to(n,{duration:s.fade,value:0,ease:"power1.inOut",onUpdate:()=>{s.audio.setVolume(n.value)},onComplete:()=>{s.audio.stop()}})}use(e){e(this)}update(){const e=this.cfg.audio,t=this.audioCfgLast;e.refDistance===t.refDistance&&e.rolloffFactor===t.rolloffFactor&&e.maxDistance===t.maxDistance&&e.distanceModel===t.distanceModel&&e.coneInnerAngle===t.coneInnerAngle&&e.coneOuterAngle===t.coneOuterAngle&&e.coneOuterGain===t.coneOuterGain||(this.audioCfgLast={...e},this.setAllPositionalSoundsCfg())}},ActionObserver=class{mixer;items=new Map;constructor(e){this.mixer=e,this.mixer.addEventListener("finished",this.onFinished)}dispose(){this.mixer.removeEventListener("finished",this.onFinished),this.items.clear()}add(e,t,s,n={}){this.items.set(e,{clipName:t,action:e,objName:s,hooks:n,started:!1,completed:!1})}has(e){return this.items.has(e)}update(){for(const e of this.items.values()){const t=e.action;!t.enabled||t.paused||t.weight<=0||(e.started||(e.started=!0,e.hooks.onStart?.()),e.hooks.onUpdate?.())}}onFinished=e=>{const t=e.action,s=this.items.get(t);s&&(s.completed||(s.completed=!0,1===e.direction?s.hooks.onComplete?.():-1===e.direction&&s.hooks.onReverseComplete?.(),this.items.delete(t)))}},progressbar_default=':host {\r\n position: absolute;\r\n display: block;\r\n top: 50%; left: 50%;\r\n width: 25%; height: 5px;\r\n transform: translate(-50%, -50%);\r\n background: #ffffff30;\r\n border-radius: 3px;\r\n pointer-events: none;\r\n z-index: 1;\r\n overflow: hidden;\r\n}\r\n\r\n#bar {\r\n position: relative;\r\n width: 0%; height: 100%;\r\n background: #F40B57;\r\n border-radius: 3px;\r\n transition: width 0.3s ease-in;\r\n overflow: hidden;\r\n}\r\n\r\n#bar::after {\r\n content: "";\r\n position: absolute;\r\n top: 0;\r\n left: -40%;\r\n width: 40%;\r\n height: 100%;\r\n\r\n background: linear-gradient(\r\n 90deg,\r\n transparent,\r\n rgba(255, 255, 255, 0.5),\r\n transparent\r\n );\r\n\r\n animation: progress-active 1s linear infinite;\r\n}\r\n\r\n@keyframes progress-active {\r\n from {\r\n transform: translateX(0);\r\n }\r\n to {\r\n transform: translateX(350%);\r\n }\r\n}',ProgressBar=class extends HTMLElement{bar;constructor(){super();const e=this.attachShadow({mode:"closed"}),t=document.createElement("div");t.id="bar";const s=document.createElement("style");s.textContent=progressbar_default,e.append(s,t),this.bar=t}setProgress(e){this.bar.style.width=e+"%",e>=100&&setTimeout(()=>{"100%"===this.bar.style.width&&(this.style.transition="opacity 0s ease 0.3s",this.style.opacity="0",setTimeout(()=>this.remove(),300))},300)}},TAG="b3d-progressbar";function loadProgressBar(){const e=document.createElement(TAG),t=document.querySelector("comp-canvas");t&&t.appendChild(e)}customElements.get(TAG)||customElements.define(TAG,ProgressBar);var stats_default=":host {\r\n z-index: 999;\r\n position: absolute;\r\n left: 8px; top: 8px;\r\n font-family: monospace;\r\n font-size: 12px;\r\n color: #ffffff;\r\n pointer-events: none;\r\n}\r\n\r\n#stats {\r\n padding: 8px;\r\n border-radius: 8px;\r\n background: hsla(230, 25%, 16%, 1.00);\r\n box-sizing: border-box;\r\n}\r\n\r\n.row {\r\n display: flex;\r\n justify-content: space-between;\r\n gap: 1em;\r\n line-height: 1.45;\r\n white-space: nowrap;\r\n}\r\n\r\n.label {\r\n opacity: 0.75;\r\n}\r\n\r\n.value {\r\n text-align: right;\r\n}\r\n\r\n.separator {\r\n height: 1px;\r\n margin: 5px 0;\r\n background: rgba(255, 255, 255, 0.18);\r\n}",Stats=class extends HTMLElement{cfg;values=new Map;timeBegin=0;timeLastFrame=0;timeFrameMs=0;timeCpuMs=0;fps=0;timeLastUpdate=0;updateInterval=100;constructor(){super();const e=this.attachShadow({mode:"closed"}),t=document.createElement("style");t.textContent=stats_default;const s=document.createElement("div");s.id="stats",this.addRow(s,"FPS","fps"),this.addRow(s,"CPU","cpu"),this.addRow(s,"Frame","frame"),this.addSeparator(s),this.addRow(s,"Calls","calls"),this.addRow(s,"Triangles","triangles"),this.addRow(s,"Lines","lines"),this.addRow(s,"Points","points"),this.addSeparator(s),this.addRow(s,"Geometries","geometries"),this.addRow(s,"Textures","textures"),this.addRow(s,"Programs","programs"),e.append(t,s)}applyCfg(){const e=this.cfg?.stats;e&&(this.setVisible("fps",e.fps),this.setVisible("cpu",e.cpu),this.setVisible("frame",e.frame),this.setVisible("calls",e.calls),this.setVisible("triangles",e.triangles),this.setVisible("lines",e.lines),this.setVisible("points",e.points),this.setVisible("geometries",e.geometries),this.setVisible("textures",e.textures),this.setVisible("programs",e.programs),this.updateInterval=1e3/Math.max(1,e.logsPerSecond))}begin(e){this.timeLastFrame>0&&(this.timeFrameMs=e-this.timeLastFrame,this.timeFrameMs>0&&(this.fps=1e3/this.timeFrameMs)),this.timeLastFrame=e,this.timeBegin=e}end(e,t){if(this.timeCpuMs=e-this.timeBegin,e-this.timeLastUpdate<this.updateInterval)return;this.timeLastUpdate=e;const s=t.info,n=Array.isArray(s.programs)?s.programs.length:s.memory.programs??0;this.setValue("fps",this.fps.toFixed(0)),this.setValue("cpu",`${this.timeCpuMs.toFixed(2)} ms`),this.setValue("frame",`${this.timeFrameMs.toFixed(2)} ms`),this.setValue("calls",String(s.render.drawCalls??s.render.calls??0)),this.setValue("triangles",this.formatNumber(s.render.triangles??0)),this.setValue("lines",this.formatNumber(s.render.lines??0)),this.setValue("points",this.formatNumber(s.render.points??0)),this.setValue("geometries",String(s.memory.geometries??0)),this.setValue("textures",String(s.memory.textures??0)),this.setValue("programs",String(n))}setUpdateInterval(e){this.updateInterval=Math.max(0,e)}addRow(e,t,s){const n=document.createElement("div");n.className="row";const i=document.createElement("span");i.className="label",i.textContent=t;const o=document.createElement("span");o.className="value",o.textContent="-",n.append(i,o),e.appendChild(n),this.values.set(s,o)}addSeparator(e){const t=document.createElement("div");t.className="separator",e.appendChild(t)}setValue(e,t){const s=this.values.get(e);s&&(s.textContent=t)}setVisible(e,t){const s=this.values.get(e);s?.parentElement&&(s.parentElement.style.display=t?"":"none")}formatNumber(e){return Math.round(e).toLocaleString("de-DE")}};function loadStats(e){const t="b3d-stats";customElements.get(t)||customElements.define(t,Stats);const s=document.createElement(t);return s.cfg=e,s.applyCfg(),document.body.appendChild(s),s}var fixedStep=1/60,Engine=class{scene;cam3D;events;modules;comps;objs3D;cfg;stats=null;actionObserver=null;gltf=null;mixer=null;composer=null;renderer;renderPipeline=null;modelReady;rendererReady=null;callbacks=[];canvas;fxaaPass=null;outputPass=null;renderPass=null;smaaPass=null;tslPass=null;ssaoPass=null;gtaoNode=null;ssrPass=null;ssrNode=null;groundReflector=null;reflectivesSSR=[];ambientLight=null;hemisphereLight=null;powerMode="Low";postAuto=!1;dTs=[];dT=0;dTFrameMax=0;gpuFps=0;timeGsap=0;timeLast=-1;timeLastFrame=0;resizeTimeout=null;resizeDelay=100;constructor(e,t,s,n,i,o,a){this.canvas=t,this.cam3D=e,this.comps=n,this.events=i,this.objs3D=a,this.modules=o,this.cfg=s,this.scene=new THREE.Scene,this.scene.backgroundBlurriness=this.cfg.envCtrls.backgroundBlurriness,this.scene.backgroundIntensity=this.cfg.envCtrls.backgroundIntensity,this.scene.environmentIntensity=this.cfg.envCtrls.environmentIntensity;const r=this.modules.webGpuRendererClass;if(r){const e=this.cfg.render.webgpu.parameters;this.renderer=new r(e),this.rendererReady=this.initWebGpuRenderer(),"none"!==this.cfg.debug.log&&console.log("WebGPU Renderer")}else this.renderer=new THREE.WebGLRenderer(this.cfg.render.webgl.parameters),this.rendererReady=Promise.resolve(),"none"!==this.cfg.debug.log&&console.log(this.renderer.getContext().getParameter(this.renderer.getContext().VERSION));const l=this.canvas.getBoundingClientRect();this.renderer.setPixelRatio(this.cfg.render.pixelRatio),this.renderer.setSize(l.width,l.height,!1),this.renderer.shadowMap.enabled=this.cfg.render.shadowMapEnabled,this.renderer.shadowMap.type=this.cfg.render.shadowMapType,this.renderer.toneMapping=this.cfg.render.toneMapping,this.renderer.toneMappingExposure=this.cfg.render.toneMappingExposure,this.renderer.outputColorSpace=this.cfg.render.outputColorSpace,this.cfg.model.file?this.modelReady=this.loadModel(this.cfg.model.file):(this.scene.add(this.cam3D.obj),this.modelReady=Promise.resolve());const c=this.renderer.domElement;c.style.display="block",c.style.width="100%",c.style.height="100%",c.style.boxSizing="border-box",this.canvas.tabIndex=0,this.canvas.addEventListener("click",e=>{this.canvas.focus(),this.events.send({type:"CANVAS_CLICK",event:e})}),this.canvas.addEventListener("pointerleave",e=>{this.events.send({type:"CANVAS_POINTER_LEAVE",event:e})}),this.canvas.addEventListener("pointerenter",e=>{this.events.send({type:"CANVAS_POINTER_ENTER",event:e})}),this.canvas.addEventListener("keydown",e=>{this.events.send({type:"CANVAS_KEY_DOWN",event:e})}),this.canvas.addEventListener("keyup",e=>{this.events.send({type:"CANVAS_KEY_UP",event:e})}),this.canvas.prepend(this.renderer.domElement);for(const e of a.values())e instanceof Mesh3D?(e.setReflectivesSSR(this.reflectivesSSR),e.start(this.renderer,this.scene),e.groundReflector&&(this.groundReflector=e.groundReflector)):e.start(this.renderer,this.scene);if(this.cfg.stats.enabled&&(loadStats(this.cfg),this.stats=document.querySelector("b3d-stats"),this.renderer.info.autoReset=!1),this.cfg.post.auto){const e=this.modules.gpuTier;"none"!==this.cfg.debug.log&&console.log(JSON.stringify(e)),this.gpuFps=e.fps,this.postAuto=this.getPostAuto(this.gpuFps)}this.dTFrameMax=1/this.cfg.render.fpsMax,this.timeLastFrame=performance.now()/1e3,this.cfg.scene.fog.enable&&this.setFog({color:this.cfg.scene.fog.color,near:this.cfg.scene.fog.near,far:this.cfg.scene.fog.far}),this.cfg.scene.ambientlight.enable&&this.setAmbientLight({color:this.cfg.scene.ambientlight.color,intensity:this.cfg.scene.ambientlight.intensity}),this.cfg.scene.hemisphere.enable&&this.setHemisphereLight({skyColor:this.cfg.scene.hemisphere.skyColor,groundColor:this.cfg.scene.hemisphere.groundColor,intensity:this.cfg.scene.hemisphere.intensity}),this.updateCanvasResize(),window.addEventListener("resize",()=>{this.resizeTimeout&&clearTimeout(this.resizeTimeout),this.resizeTimeout=setTimeout(()=>{!1===this.cfg.render.autoResize?this.events.windowResize({type:"WINDOW_RESIZE"}):this.updateCanvasResize()},this.resizeDelay)}),gsap.ticker.remove(gsap.updateRoot),gsap.ticker.lagSmoothing(0)}async init(){for(const e of this.objs3D.values())e.ready(this.objs3D);for(const e of this.comps.values())for(const t of e)t.ready(this.objs3D);this.events.send({type:"SCENE_READY"},"Scene is set up and ready."),this.postAuto&&this.isPostEnabled()?this.modules.webGpuRendererClass?(this.setPostWebGpu(this.cfg.post.aa.mode,this.cfg.post.ssao.enable,this.cfg.post.ssr.enable),this.renderPipeline?.render()):(this.setPostWebGl(),this.composer?.render()):this.renderer.render(this.scene,this.cam3D.obj),this.events.send({type:"SCENE_RENDERED"},"Scene first time rendered."),this.setAnimationLoop()}async initWebGpuRenderer(){await this.renderer.init()}isPostEnabled(){return this.cfg.post.ssao.enable||this.cfg.post.ssr.enable||"none"!==this.cfg.post.aa.mode}addOnFrameUpdate(e){this.callbacks.push(e)}animCamCurveToTarget({camTarget:e,aimTarget:t,radiusOut:s=1,duration:n=2,ease:i="power1.inOut"}){const o=this.animCamCurveToTarget.name,a=e=>{for(;e>Math.PI;)e-=2*Math.PI;for(;e<-Math.PI;)e+=2*Math.PI;return e},r=e=>{if("string"==typeof e){const t=this.scene.getObjectByName(e);return t?t.getWorldPosition(new THREE.Vector3):(console.warn(`${o}: Object with name "${e}" not found.`),null)}return e instanceof Obj3D?e.obj?e.obj.getWorldPosition(new THREE.Vector3):(console.warn(`${o}: Obj3D not found.`),null):e instanceof THREE.Vector3?e.clone():(console.warn(`${o}: Invalid target.`),null)},l=e=>{const t=Math.max(e.length(),1e-4);return{radius:t,lat:Math.asin(THREE.MathUtils.clamp(e.y/t,-1,1)),lon:Math.atan2(e.x,e.z)}};this.cam3D.lookMode="target";const c=this.cam3D.objTarget.position.clone(),d=r(e);if(!d)return void console.warn(`Camera object with name "${e}" was not found.`);const h=t?r(t):c;if(!h)return void console.warn(`Aim object with name "${t}" was not found.`);const m=this.cam3D.obj.getWorldPosition(new THREE.Vector3).clone().sub(c),p=d.clone().sub(h),u=l(m),g=l(p),b=u.lat,f=g.lat,v=a(u.lon),C=a(a(g.lon)-v),y=u.radius,w=g.radius,E=Math.max(y,w)*s,L={t:0};gsap.to(L,{t:1,duration:n,ease:i,onStart:()=>{this.events.anim({type:"ANIM_START",objName:"Camera",fct:o})},onUpdate:()=>{const e=L.t,t=c.clone().lerp(h,e),s=THREE.MathUtils.lerp(b,f,e),n=a(v+C*e),i=THREE.MathUtils.lerp(y,w,e),o=Math.sin(Math.PI*e)*E,r=((e,t,s)=>{const n=Math.cos(t);return new THREE.Vector3(e*n*Math.sin(s),e*Math.sin(t),e*n*Math.cos(s))})(Math.max(1e-4,i+o),s,n),l=t.clone().add(r);this.cam3D.obj.position.copy(l),this.cam3D.objTarget.position.copy(t)},onComplete:()=>{this.events.anim({type:"ANIM_COMPLETE",objName:"Camera",fct:o})}})}animCamToObj({target:e,duration:t=1,ease:s="power2.inOut",dist:n=1.25}){const i="animCamToObj";this.cam3D.lookMode="target";const o=(e=>{if("string"==typeof e){const t=this.scene.getObjectByName(e);return t||(console.warn(`${i}: Object with name "${e}" not found.`),null)}return e instanceof Obj3D?e.obj?e.obj:(console.warn(`${i}: Obj3D object not found.`),null):(console.warn(`${i}: Invalid target.`),null)})(e);if(!o)return;const a=((e,t)=>{const s=(new THREE.Box3).setFromObject(e,!0);if(s.isEmpty())return console.warn(`${i}: Object bounding box is empty.`),null;const n=s.getBoundingSphere(new THREE.Sphere),o=this.cam3D.obj,a=THREE.MathUtils.degToRad(o.fov),r=2*Math.atan(Math.tan(a/2)*o.aspect),l=Math.min(a,r),c=n.radius/Math.sin(l/2)*t;return{center:n.center.clone(),camDistance:c}})(o,n);if(!a)return;const r=a.center,l=this.cam3D.objTarget.position.clone(),c=this.cam3D.obj.position.clone(),d=c.clone().sub(r);0===d.lengthSq()&&d.set(0,0,1);const h=r.clone().add(d.normalize().multiplyScalar(a.camDistance)),m={t:0};gsap.to(m,{t:1,duration:t,ease:s,onStart:()=>{this.events.anim({type:"ANIM_START",objName:"Camera",fct:i})},onUpdate:()=>{const e=m.t,t=l.clone().lerp(r,e),s=c.clone().lerp(h,e);this.cam3D.obj.position.copy(s),this.cam3D.objTarget.position.copy(t)},onComplete:()=>{this.cam3D.obj.position.copy(h),this.cam3D.objTarget.position.copy(r),this.events.anim({type:"ANIM_COMPLETE",objName:"Camera",fct:i})}})}animMaterialColor({mesh:e,duration:t=0,ease:s="power1.inOut",...n}){let i=this.animMaterialColor.name;if(!e)return void console.warn(`${i}: Missing object name`);const o=this.scene.getObjectByName(e);if(!o)return void console.warn(`${i}: Object with name "${e}" not found.`);if(!("material"in o)||!o.material)return void console.warn(`${i}: Object "${e}" has no material.`);const a=o.material,r=Object.keys(n);0!==r.length?r.forEach(o=>{const r=n[o];if(!(o in a)||!a[o].isColor)return void console.warn(`${i}: Material property "${o}" is not a color.`);if(null==r)return void console.warn(`${i}: Color value for "${o}" is null or undefined.`);const l=a[o],c=new THREE.Color(r);gsap.to(l,{r:c.r,g:c.g,b:c.b,duration:t,ease:s,onStart:()=>{this.events.animFade({type:"ANIM_FADE_START",objName:e,fct:i,property:o,value:l.getHexString()})},onUpdate:()=>{a[o].copy(l),a.needsUpdate=!0},onComplete:()=>{this.events.animFade({type:"ANIM_FADE_COMPLETE",objName:e,fct:i,property:o,value:l.getHexString()})}})}):console.warn(`${i}: No color property provided to animate.`)}animMaterialNumeric({mesh:e,startValue:t=null,infinite:s=!1,duration:n=0,ease:i="power1.inOut",...o}){let a=this.animMaterialNumeric.name;if(!e)return void console.warn(`${a}: Missing object name.`);const r=this.scene.getObjectByName(e);if(!r)return void console.warn(`${a}: Object with name "${e}" not found.`);if(!("material"in r)||!r.material)return void console.warn(`${a}: Object "${e}" has no material.`);const l=r.material,c=Object.keys(o);if(0===c.length)return void console.warn(`${a}: No property provided to animate.`);const d=c[0],h=o[d];if(!(d in l))return void console.warn(`${a}: Material property "${d}" does not exist.`);const m=l[d];if("number"!=typeof m)return void console.warn(`${a}: Material property "${d}" is not a number.`);if(null==h||"number"!=typeof h)return void console.warn(`${a}: Material property "${d}" endValue is null or undefined or not a number.`);const p={[d]:null===t?m:t};gsap.to(p,{[d]:h,duration:n,delay:0,ease:i,repeat:s?-1:0,onStart:()=>{this.events.animFade({type:"ANIM_FADE_START",objName:e,fct:a,property:d,value:p[d]})},onUpdate:()=>{l[d]=p[d],l.needsUpdate=!0},onComplete:()=>{this.events.animFade({type:"ANIM_FADE_COMPLETE",objName:e,fct:a,property:d,value:p[d]})}})}calcEaseArea(e){const t=gsap.parseEase(e);return function(e=100){let s=0;for(let n=0;n<=e;n++){s+=t(n/e)}return s/e}()}async enableAaMode(e){this.modules.webGpuRendererClass?("fxaa"===e?await this.modules.importFXAANode("fxaa"):"smaa"===e&&await this.modules.importSMAANode("smaa"),this.setPostWebGpu(e,this.cfg.post.ssao.enable,this.cfg.post.ssr.enable),this.cfg.post.aa.mode=e):(this.fxaaPass||"fxaa"!==e?this.smaaPass||"smaa"!==e||await this.modules.importSMAAPass("smaa"):await this.modules.importFXAAShader("fxaa"),this.setPostWebGl())}async enableSsao(e){this.modules.webGpuRendererClass?(await this.modules.importGtaoNode(e),this.setPostWebGpu(this.cfg.post.aa.mode,e,this.cfg.post.ssr.enable),this.cfg.post.ssao.enable=e):(this.cfg.post.ssao.enable=e,this.ssaoPass||await this.modules.importSSAOPass(e),this.setPostWebGl())}async enableSsr(e){this.modules.webGpuRendererClass?(await this.modules.importSsrNode(e),this.setPostWebGpu(this.cfg.post.aa.mode,this.cfg.post.ssao.enable,e),this.cfg.post.ssr.enable=e):(this.cfg.post.ssr.enable=e,e?this.ssrPass||await this.modules.importSsrPass(e):this.groundReflector&&(this.groundReflector.visible=!1),this.setPostWebGl())}getPostAuto(e){return!(e<50)}async loadModel(e){const t=this.modules.gltfLoader;if(!t)return void console.warn("Three.js GLTFLoader could not be started.");if("ktx2"===this.cfg.model.compression.texture){const e=this.modules.ktx2Loader;e?(await this.rendererReady,e.setTranscoderPath("/ktx2/").detectSupport(this.renderer),t.setKTX2Loader(e)):console.warn("KTX2Loader not imported.")}"draco"===this.cfg.model.compression.mesh?this.modules.dracoLoader?this.cfg.model.decoderPath?(this.modules.dracoLoader.setDecoderPath(this.cfg.model.decoderPath),t.setDRACOLoader(this.modules.dracoLoader)):console.warn("Draco decoderPath is empty."):console.warn("DRACOLoader not imported."):"meshopt"===this.cfg.model.compression.mesh&&(this.modules.meshoptDecoder?t.setMeshoptDecoder(this.modules.meshoptDecoder):console.warn("MeshoptDecoder not imported."));let s=null;return this.cfg.model.progressBar&&(loadProgressBar(),s=document.querySelector("b3d-progressbar")),new Promise((n,i)=>{t.load(e,e=>{this.gltf=e,this.scene.add(e.scene),e.animations&&e.animations.length>0&&(this.mixer=new THREE.AnimationMixer(e.scene),this.actionObserver=new ActionObserver(this.mixer)),e.scene.traverse(e=>{const t=this.objs3D.get(e.name);if(t)e instanceof THREE.Mesh&&t instanceof Mesh3D?(t.traverse(e),!this.groundReflector&&t.groundReflector&&(this.groundReflector=t.groundReflector)):e instanceof THREE.Light&&t instanceof Light3D?t.traverse(e):e instanceof THREE.Camera&&t instanceof Cam3D?(this.cam3D.traverse(e),this.scene.remove(e)):e instanceof THREE.Object3D&&t instanceof Obj3D&&t.traverse(e);else if(e instanceof THREE.Mesh){const t=e;t.castShadow=this.cfg.mesh.castShadow,t.receiveShadow=this.cfg.mesh.receiveShadow,t.frustumCulled=this.cfg.mesh.frustumCulled,t.material instanceof THREE.MeshStandardMaterial&&t.material.roughness<this.cfg.post.webgl.ssr.maxRoughness&&this.reflectivesSSR.push(t)}else if(e instanceof THREE.Light){const t=e;t.castShadow=!0,(t instanceof THREE.DirectionalLight||t instanceof THREE.SpotLight||t instanceof THREE.PointLight)&&(t.shadow.mapSize.width=this.cfg.light.mapWidth,t.shadow.mapSize.height=this.cfg.light.mapHeight,t.shadow.bias=this.cfg.light.bias,t.shadow.normalBias=this.cfg.light.normalBias,(t.shadow.camera instanceof THREE.PerspectiveCamera||t.shadow.camera instanceof THREE.OrthographicCamera)&&(t.shadow.camera.near=this.cfg.light.near,t.shadow.camera.far=this.cfg.light.far))}else e instanceof THREE.Camera&&this.cam3D.traverse(e)}),s?.setProgress(100),n()},e=>{if(e.total>0){const t=e.loaded/e.total,n=Math.round(90*t);n<90&&s?.setProgress(n);const i=Math.round(100*t);this.events.modelLoading({type:"MODEL_LOADING",loading:i})}else this.events.modelLoading({type:"MODEL_LOADING",loading:0})},e=>{const t=e instanceof Error?e:new Error(String(e));this.events.modelError({type:"MODEL_ERROR",error:t}),i(e)})})}pauseObjActions(e,t){let s=this.pauseObjActions.name;if(!this.mixer)return void console.warn(`${s}: Mixer not found.`);if(!this.actionObserver)return void console.warn(`${s}: Clip Class not found.`);const n=this.mixer._actions;for(let s=n.length-1;s>=0;s--){const i=n[s];if("finished"===t&&this.actionObserver.has(i))continue;const o=i.getClip().tracks;for(const s of o)if(s.name.includes(e)){if(i.enabled=!1,"last"===t)return;break}}}playClip({obj:e,clip:t,pauseActions:s="all",reverse:n=!1,infinite:i=!1,reset:o=!1,startSpeed:a=0,endSpeed:r=1,duration:l=0,ease:c="power1.inOut"}){let d=this.playClip.name;if(!e)return void console.warn(`${d}: Missing objectname.`);if(!t)return void console.warn(`${d}: Missing clipname.`);if(!this.gltf?.animations?.length)return void console.warn(`${d}: gltf has no animations.`);const h=THREE.AnimationClip.findByName(this.gltf.animations,t);if(!h)return void console.warn(`${d}: ClipAnimation "${t}" not found`);if(!this.mixer)return void console.warn(`${d}: Mixer not found.`);const m=this.mixer.existingAction(h)||this.mixer.clipAction(h);if(m){if("none"!==s&&this.pauseObjActions(e,s),m.enabled=!0,m.paused=!1,o&&(m.reset(),m.time=n?m.getClip().duration:0),i?(m.setLoop(THREE.LoopRepeat,1/0),m.clampWhenFinished=!1):(m.setLoop(THREE.LoopOnce,0),m.clampWhenFinished=!0),l>0){m.timeScale=n?-a:a;const e={timeScale:a};gsap.to(e,{id:t,timeScale:n?-r:r,duration:l,delay:0,ease:c,onStart:()=>{this.events.clip({type:"CLIP_START",clipName:t,fct:d,action:m}),this.events.clipFade({type:"CLIP_FADE_START",clipName:t,fct:d,action:m})},onComplete:()=>{this.events.clipFade({type:"CLIP_FADE_COMPLETE",clipName:t,fct:d,action:m})},onUpdate:()=>{m.timeScale=e.timeScale},onReverseComplete:()=>{this.events.clipFade({type:"CLIP_FADE_COMPLETE",clipName:t,fct:d,action:m})}})}else m.timeScale=n?-1:1;this.actionObserver&&this.actionObserver.add(m,t,e,{onStart:()=>{0==l&&this.events.clip({type:"CLIP_START",clipName:t,fct:d,action:m})},onComplete:()=>{this.events.clip({type:"CLIP_COMPLETE",clipName:t,fct:d,action:m})},onReverseComplete:()=>{this.events.clip({type:"CLIP_COMPLETE",clipName:t,fct:d,action:m})}}),m.play(),this.mixer.update(0)}else console.warn(`${d}: Could not create or find action for clip`)}playClipCam({obj:e,clip:t,pauseActions:s="all",reverse:n=!1,infinite:i=!1,reset:o=!1,startSpeed:a=0,endSpeed:r=1,duration:l=0,ease:c="power1.inOut"}){const d=this.playClipCam.name,h=this.cam3D.targetGltf,m=this.cam3D.objGltf;if(!h)return void console.warn(`${d}: Aim object not found.`);if(!m)return void console.warn(`${d}: Gltf object not found.`);if(!t)return void console.warn(`${d}: Missing clipname.`);if(!this.gltf?.animations?.length)return void console.warn(`${d}: gltf has no animations.`);const p=THREE.AnimationClip.findByName(this.gltf.animations,t);if(!p)return void console.warn(`${d}: ClipAnimation "${t}" not found`);if(!this.mixer)return void console.warn(`${d}: Mixer not found.`);"none"!==s&&this.pauseObjActions(e,s);const u=this.mixer.existingAction(p)||this.mixer.clipAction(p);if(!u)return void console.warn(`${d}: Could not create or find action for clip`);u.enabled=!0,u.paused=!1,o&&(u.reset(),u.time=n?u.getClip().duration:0),i?(u.setLoop(THREE.LoopRepeat,1/0),u.clampWhenFinished=!1):(u.setLoop(THREE.LoopOnce,0),u.clampWhenFinished=!0),l>0?(u.timeScale=n?-a:a,gsap.to(u,{id:t,timeScale:n?-r:r,duration:l,delay:0,ease:c,onStart:()=>{this.events.clip({type:"CLIP_START",clipName:t,fct:d,action:u}),this.events.clipFade({type:"CLIP_FADE_START",clipName:t,fct:d,action:u})},onComplete:()=>{this.events.clipFade({type:"CLIP_FADE_COMPLETE",clipName:t,fct:d,action:u})},onReverseComplete:()=>{this.events.clipFade({type:"CLIP_FADE_COMPLETE",clipName:t,fct:d,action:u})}})):u.timeScale=n?-1:1,this.cam3D.lookMode="target";let g=new THREE.Vector3,b=new THREE.Vector3;this.actionObserver&&this.actionObserver.add(u,t,"Camera",{onStart:()=>{0==l&&this.events.clip({type:"CLIP_START",clipName:t,fct:d,action:u})},onUpdate:()=>{h&&m&&(this.cam3D.obj.position.copy(m.getWorldPosition(g)),this.cam3D.objTarget.position.copy(h.getWorldPosition(b)))},onComplete:()=>{this.events.clip({type:"CLIP_COMPLETE",clipName:t,fct:d,action:u})},onReverseComplete:()=>{this.events.clip({type:"CLIP_COMPLETE",clipName:t,fct:d,action:u})}}),u.play(),this.mixer.update(0)}removeAmbientLight(){this.ambientLight&&(this.scene.remove(this.ambientLight),this.ambientLight.dispose(),this.ambientLight=null)}removeFog(){this.scene.fog&&(this.scene.fog=null)}removeHemisphereLight(){this.hemisphereLight&&(this.scene.remove(this.hemisphereLight),this.hemisphereLight.dispose(),this.hemisphereLight=null)}removeOnFrameUpdate(e){this.callbacks=this.callbacks.filter(t=>t!==e)}setAmbientLight({color:e,intensity:t}){if(!this.ambientLight){if(void 0===e||void 0===t)return;return this.ambientLight=new THREE.AmbientLight(e,t),void this.scene.add(this.ambientLight)}void 0!==e&&this.ambientLight.color.set(e),void 0!==t&&(this.ambientLight.intensity=t)}setAnimationLoop(){this.renderer.setAnimationLoop(e=>this.update(e))}setFog({color:e,near:t,far:s}){if(this.scene.fog)void 0!==e&&this.scene.fog.color.set(e),this.scene.fog instanceof THREE.Fog&&(void 0!==t&&(this.scene.fog.near=t),void 0!==s&&(this.scene.fog.far=s));else{if(void 0===e||void 0===t||void 0===s)return;this.scene.fog=new THREE.Fog(e,t,s)}}setFxaaResolution(e){if(!this.fxaaPass)return;const t=this.renderer.getSize(new THREE.Vector2),s=this.renderer.getPixelRatio(),n=this.fxaaPass.material.uniforms;n.resolution.value.x=e/(t.x*s),n.resolution.value.y=e/(t.y*s)}setHemisphereLight({skyColor:e,groundColor:t,intensity:s}){if(!this.hemisphereLight){if(void 0===e||void 0===t||void 0===s)return;return this.hemisphereLight=new THREE.HemisphereLight(e,t,s),void this.scene.add(this.hemisphereLight)}void 0!==e&&this.hemisphereLight.color.set(e),void 0!==t&&this.hemisphereLight.groundColor.set(t),void 0!==s&&(this.hemisphereLight.intensity=s)}setMaterialProperties({obj:e,...t}){let s=this.setMaterialProperties.name;if(!e)return void console.warn(`${s}: Missing objName`);const n=this.scene.getObjectByName(e);if(!n)return void console.warn(`${s}: Object with name "${e}" not found.`);if(!("material"in n)||!n.material)return void console.warn(`${s}: Object "${e}" has no material.`);const i=n.material,o=Object.keys(t);if(0===o.length)return void console.warn(`${s}: No material properties provided.`);let a=null;for(const e of o){const n=t[e];if(("map"===e||"emissiveMap"===e)&&"string"==typeof n){a||(a=new THREE.TextureLoader),a.load(n,t=>{i[e]=t,i.needsUpdate=!0},void 0,t=>{console.error(`${s}: Failed to load texture "${n}" for "${e}":`,t)});continue}if(!(e in i)){console.warn(`${s}: Material property "${e}" does not exist.`);continue}const o=i[e];o instanceof THREE.Color?o.set(n):typeof o==typeof n?i[e]=n:console.warn(`${s}: Type mismatch for "${e}": expected ${typeof o}, got ${typeof n}`)}i.needsUpdate=!0}setPostWebGl(){if(!this.composer){const e=this.modules.effectComposerClass;e?this.renderer instanceof THREE.WebGLRenderer&&(this.composer=new e(this.renderer)):console.warn("EffectComposer could not be started.")}if(!this.composer)return;for(const e of this.composer.passes)e.dispose?.();this.composer.passes.length=0;const e=this.canvas.getBoundingClientRect();if(!this.renderPass){const e=this.modules.renderPassClass;e?this.renderPass=new e(this.scene,this.cam3D.obj):console.warn("Module Three.js RenderPass could not be imported.")}if(this.renderPass&&this.composer.addPass(this.renderPass),this.cfg.post.ssr.enable){if(!this.ssrPass)if(this.modules.ssrPassClass){this.groundReflector&&!this.groundReflector.parent&&this.scene.add(this.groundReflector);const t=this.cfg.post.webgl.ssr;this.ssrPass=new this.modules.ssrPassClass({renderer:this.renderer,scene:this.scene,camera:this.cam3D.obj,width:e.width,height:e.height,bouncing:t.bouncing,groundReflector:this.groundReflector,selects:t.selective?this.reflectivesSSR:null}),this.ssrPass&&(this.ssrPass.enabled=!0,this.ssrPass.clear=t.clear,this.ssrPass.selective=t.selective,this.ssrPass.fresnel=t.fresnel,this.ssrPass.distanceAttenuation=t.distanceAttenuation,this.ssrPass.infiniteThick=t.infiniteThick,this.ssrPass.maxDistance=t.maxDistance,this.ssrPass.opacity=t.opacity,this.ssrPass.thickness=t.thickness,this.ssrPass.resolutionScale=t.resolutionScale,this.ssrPass.blur=t.blur,this.ssrPass.output=t.output)}else console.warn("Module Three.js SSRPass could not be imported.");this.ssrPass&&this.composer.addPass(this.ssrPass)}this.cfg.post.ssao.enable&&(this.ssaoPass||(this.modules.ssaoPassClass?(this.ssaoPass=new this.modules.ssaoPassClass(this.scene,this.cam3D.obj,e.width,e.height),this.ssaoPass&&(this.ssaoPass.enabled=!0,this.ssaoPass.kernelRadius=this.cfg.post.webgl.ssao.kernelRadius,this.ssaoPass.minDistance=this.cfg.post.webgl.ssao.minDistance,this.ssaoPass.maxDistance=this.cfg.post.webgl.ssao.maxDistance)):console.warn("Module Three.js SSAOPass could not be imported.")),this.ssaoPass&&this.composer.addPass(this.ssaoPass));const t=this.cfg.post.aa;if("smaa"===t.mode&&(this.smaaPass||(this.modules.smaaPassClass?(this.smaaPass=new this.modules.smaaPassClass(e.width,e.height),this.smaaPass&&(this.smaaPass.enabled=!0)):console.warn("Module Three.js SMAAPass could not be imported.")),this.smaaPass&&this.composer.addPass(this.smaaPass)),!this.outputPass){const e=this.modules.outputPassClass;e?this.outputPass=new e:console.warn("Module Three.js OutputPass could not be imported.")}if(this.outputPass&&this.composer.addPass(this.outputPass),"fxaa"===t.mode){if(!this.fxaaPass){const e=this.modules.shaderPassClass;e&&this.modules.fxaaShader?(this.fxaaPass=new e(this.modules.fxaaShader),this.fxaaPass&&(this.fxaaPass.enabled=!0),this.setFxaaResolution(this.cfg.post.webgl.aa.fxaa.sharpness)):console.warn("Module Three.js FXAAShader could not be imported.")}this.fxaaPass&&this.composer.addPass(this.fxaaPass)}}setPostWebGpu(e,t,s){if(!this.renderPipeline){const e=this.modules.renderPipelineClass;if(e){const t=this.modules.webGpuRendererClass;t&&this.renderer instanceof t&&(this.renderPipeline=new e(this.renderer))}else console.warn("EffectComposer could not be started.")}if(!this.renderPipeline)return;const{tslPass:n,tslMrt:i,tslOutput:o,tslNormalView:a,tslMetalness:r,tslRoughness:l,tslSample:c,tslVec2:d,tslVec3:h,tslVec4:m,tslDirectionToColor:p,tslColorToDirection:u}=this.modules;if(!(n&&i&&o&&a&&r&&l&&c&&d&&h&&m&&p&&u))return;this.tslPass||(this.tslPass=n(this.scene,this.cam3D.obj),this.tslPass.setMRT(i({output:o,normal:p(a),metalrough:d(r,l)})),this.tslPass.getTexture("normal").type=THREE.UnsignedByteType,this.tslPass.getTexture("metalrough").type=THREE.UnsignedByteType);const g=this.tslPass,b=g.getTextureNode("output"),f=g.getTextureNode("depth"),v=g.getTextureNode("normal"),C=g.getTextureNode("metalrough"),y=c(e=>u(v.sample(e)));let w=b;if(t)if(this.modules.gtaoNodeClass){if(!this.gtaoNode){const e=this.cfg.post.webgpu.ssao,t=this.modules.gtaoNodeClass(f,y,this.cam3D.obj);this.gtaoNode=t,t.radius.value=e.radius,t.thickness.value=e.thickness,t.distanceExponent.value=e.distanceExponent,t.distanceFallOff.value=e.distanceFallOff,t.scale.value=e.scale,t.samples.value=e.samples,t.resolutionScale=e.resolutionScale}if(this.gtaoNode){const e=this.gtaoNode.getTextureNode();w=w.mul(m(h(e.r),1))}}else console.warn("Module Three.js GTAONode could not be imported.");if(s)if(this.modules.ssrNode){if(!this.ssrNode){const e=this.cfg.post.webgpu.ssr,t=this.modules.ssrNode(b,f,y,C.r,C.g,this.cam3D.obj);this.ssrNode=t,t.quality.value=e.quality,t.blurQuality.value=e.blurQuality,t.maxDistance.value=e.maxDistance,t.opacity.value=e.opacity,t.thickness.value=e.thickness,t.resolutionScale=e.resolutionScale}this.ssrNode&&(w=w.add(m(this.ssrNode.rgb,0)))}else console.warn("Module Three.js SSRNode could not be imported.");if("smaa"===e&&this.modules.smaaNode){const e=this.modules.smaaNode(w);e?w=e.getTextureNode():console.warn("Module Three.js SMAANode could not be imported.")}if("fxaa"===e&&this.modules.fxaaNode){const e=this.modules.fxaaNode(w);e?w=e:console.warn("Module Three.js FXAANode could not be imported.")}this.renderPipeline.outputNode=w,this.renderPipeline.needsUpdate=!0}stopAnimClip({clipName:e,fadeOut:t=0,ease:s="power1.inOut"}){let n=this.stopAnimClip.name;if(!e)return void console.warn(`${n}: Missing clipName.`);if(!this.gltf?.animations?.length)return void console.warn(`${n}: glb has no animations.`);const i=THREE.AnimationClip.findByName(this.gltf.animations,e);if(!i)return void console.warn(`${n}: ClipAnimation "${e}" not found.`);if(!this.mixer)return void console.warn(`${n}: Mixer not exists.`);const o=this.mixer.existingAction(i);if(o)if(t>0){const i=(e,t,s,i)=>{gsap.to(t,{id:e,timeScale:0,duration:s,ease:i,onStart:()=>{this.events.clipFade({type:"CLIP_FADEOUT_START",clipName:e,fct:n,action:o})},onUpdate:()=>{o.timeScale=t.timeScale},onComplete:()=>{this.events.clipFade({type:"CLIP_FADEOUT_COMPLETE",clipName:e,fct:n,action:o})}})};i(e,{timeScale:o.timeScale},t,s)}else o.stop();else console.warn(`${n}: "${e}" is not currently playing on object`)}toggleFullscreen(){document.fullscreenElement?document.exitFullscreen():this.canvas.requestFullscreen()}use(e){e(this)}update(e){-1===this.timeLast&&(this.timeLast=e),this.dT=fixedStep,this.timeLast=e;let t=!1,s=0;if(this.cfg.render.fpsLimiter){let n=0,i=0,o=0;if(this.dTs.push(this.dT),this.dTs.length>this.cfg.render.deltaTimesMax){this.dTs.shift();const e=[...this.dTs].sort((e,t)=>e-t);n=e[Math.floor(.5*(e.length-1))],o=e[Math.floor(.75*(e.length-1))],i=o/this.dTFrameMax}if(i<.75)if("Low"==this.powerMode){s=(e-this.timeLastFrame)/1e3;const i=s+n;(s>=this.dTFrameMax||i>=this.dTFrameMax&&i-this.dTFrameMax>this.dTFrameMax-s)&&(t=!0)}else t=!0,s=this.dT;else this.postAuto&&(this.postAuto=!1),t=!0,s=this.dT,this.dTs.length=0}else t=!0,s=this.dT;if(t){this.stats&&this.stats.begin(e),this.timeGsap+=s,gsap.updateRoot(this.timeGsap),this.mixer&&this.actionObserver&&(this.actionObserver.update(),this.mixer.update(s));for(const e of this.callbacks)e(s);for(const e of this.objs3D.values())e.update(s,this.cam3D);this.postAuto&&this.isPostEnabled()?this.modules.webGpuRendererClass?this.renderPipeline?.render():this.composer?.render():this.renderer.render(this.scene,this.cam3D.obj),this.timeLastFrame=e,this.stats&&(this.stats.end(performance.now(),this.renderer),this.renderer.info.reset())}}updateCanvasResize(){const e=this.canvas.getBoundingClientRect(),t=e.width,s=e.height;this.renderer.setSize(t,s,!1),this.modules.webGpuRendererClass?(this.tslPass?.setSize(t,s),this.gtaoNode?.setSize(t,s),this.ssrNode?.setSize(t,s),this.renderPipeline&&(this.renderPipeline.needsUpdate=!0)):(this.composer?.setSize(t,s),this.smaaPass?.setSize(t,s),this.fxaaPass&&this.setFxaaResolution(this.cfg.post.webgl.aa.fxaa.sharpness)),this.cfg.post.auto&&(this.postAuto=this.getPostAuto(this.gpuFps)),this.dTs.length=0,this.cam3D.updateCanvasResize(e),this.groundReflector&&(this.groundReflector.getRenderTarget().setSize(t,s),this.groundReflector.resolution.set(t,s))}},EnvCtrls=class{cfg;engine;modules;envReady=Promise.resolve();textureReady=Promise.resolve(null);envEnabled=!1;envInit=!1;envIntensity;bgIntensity;bgBlurriness;rotation;rotationSpeed;timeBgRot=0;callback=null;constructor(e,t,s){this.cfg=e,this.engine=t,this.modules=s,this.envIntensity=this.cfg.envCtrls.environmentIntensity,this.bgIntensity=this.cfg.envCtrls.backgroundIntensity,this.bgBlurriness=this.cfg.envCtrls.backgroundBlurriness,this.rotationSpeed=this.cfg.envCtrls.rotationSpeed,this.rotation=new THREE.Euler(THREE.MathUtils.degToRad(this.cfg.envCtrls.rotation.x),THREE.MathUtils.degToRad(this.cfg.envCtrls.rotation.y),THREE.MathUtils.degToRad(this.cfg.envCtrls.rotation.z)),this.cfg.envCtrls.enable&&(this.textureReady=this.loadTexture(this.cfg.envCtrls.type,this.cfg.envCtrls.map))}init(){this.cfg.envCtrls.enable&&(this.envEnabled||this.envInit||(this.envInit=!0,this.startEnv()))}async applyEnv(){const e=await this.textureReady;if(!e)return;const t=this.modules.webGpuRendererClass;if(t&&this.engine.renderer instanceof t)this.setEnv(e);else{const t=new THREE.PMREMGenerator(this.engine.renderer);try{t.compileEquirectangularShader();const s=t.fromEquirectangular(e).texture;this.setEnv(s)}finally{t.dispose()}}this.callback||(this.callback=e=>this.update(e),this.engine.addOnFrameUpdate(this.callback))}enable(e){if(this.envEnabled)return;const t=e?.type??this.cfg.envCtrls.type,s=e?.map??this.cfg.envCtrls.map;this.cfg.envCtrls.enable=!0,this.envEnabled=!0,this.textureReady=this.loadTexture(t,s),this.startEnv()}disable(){(this.envEnabled||this.envInit||this.isEnabled())&&(this.cfg.envCtrls.enable=!1,this.envEnabled=!1,this.envInit=!1,this.engine&&this.callback&&(this.engine.removeOnFrameUpdate(this.callback),this.callback=null),this.engine.scene.environment=null,this.engine.scene.environmentRotation.set(0,0,0),this.engine.scene.environmentIntensity=this.envIntensity,this.engine.scene.background=null,this.engine.scene.backgroundRotation.set(0,0,0),this.engine.scene.backgroundIntensity=this.bgIntensity,this.engine.scene.backgroundBlurriness=this.bgBlurriness,this.rotationSpeed=this.cfg.envCtrls.rotationSpeed,this.timeBgRot=0)}get(){return{rotationSpeed:this.rotationSpeed,environmentIntensity:this.envIntensity,backgroundIntensity:this.bgIntensity,backgroundBlurriness:this.bgBlurriness,rotation:{x:THREE.MathUtils.radToDeg(this.rotation.x),y:THREE.MathUtils.radToDeg(this.rotation.y),z:THREE.MathUtils.radToDeg(this.rotation.z)}}}isEnabled(){return null!==this.engine.scene.environment||null!==this.engine.scene.background}async loadTexture(e,t){if(!t)return console.warn("Environment map is empty."),null;try{let s;if("hdr"===e||"exr"===e){if(!this.modules.envLoader)return console.warn("Modules EXRLoader or ENVLoader could not be imported."),null;s=await this.modules.envLoader.loadAsync(t)}else s=await(new THREE.TextureLoader).loadAsync(t);return s.mapping=THREE.EquirectangularReflectionMapping,s}catch(e){return console.warn("Failed to load environment map:",t,e),null}}set(e){void 0!==e.rotationSpeed&&(this.rotationSpeed=e.rotationSpeed),void 0!==e.environmentIntensity&&(this.envIntensity=e.environmentIntensity,this.engine.scene.environmentIntensity=this.envIntensity),void 0!==e.backgroundIntensity&&(this.bgIntensity=e.backgroundIntensity,this.engine.scene.backgroundIntensity=this.bgIntensity),void 0!==e.backgroundBlurriness&&(this.bgBlurriness=e.backgroundBlurriness,this.engine.scene.backgroundBlurriness=this.bgBlurriness),void 0!==e.rotation&&(this.rotation.set(THREE.MathUtils.degToRad(e.rotation.x),THREE.MathUtils.degToRad(e.rotation.y),THREE.MathUtils.degToRad(e.rotation.z)),this.engine.scene.environmentRotation.copy(this.rotation),this.engine.scene.backgroundRotation.copy(this.rotation))}setEnv(e){this.engine.scene.environment=e,this.engine.scene.environmentRotation.copy(this.rotation),this.engine.scene.environmentIntensity=this.envIntensity,this.engine.scene.background=e,this.engine.scene.backgroundRotation.copy(this.rotation),this.engine.scene.backgroundIntensity=this.bgIntensity,this.engine.scene.backgroundBlurriness=this.bgBlurriness}startEnv(){this.envReady=this.applyEnv().catch(e=>{console.warn("Failed to apply environment:",e),this.setEnv(null)})}update(e){if(0===this.rotationSpeed)return this.engine.scene.environmentRotation.copy(this.rotation),void this.engine.scene.backgroundRotation.copy(this.rotation);this.timeBgRot+=e*this.rotationSpeed;const t=THREE.MathUtils.degToRad(this.timeBgRot);this.engine.scene.environmentRotation.set(this.rotation.x,this.rotation.y+t,this.rotation.z),this.engine.scene.backgroundRotation.copy(this.engine.scene.environmentRotation)}},Events=class{cfg;stateMachine;eventQueue=[];isProcessingEvents=!1;constructor(e,t){this.cfg=e,this.stateMachine=t}enqueue(e){if(this.eventQueue.push(e),!this.isProcessingEvents){this.isProcessingEvents=!0;try{for(;this.eventQueue.length>0;){const e=this.eventQueue.shift();e&&e()}}finally{this.isProcessingEvents=!1}}}anim(e){let t=`${e.fct} | ${e.objName}`;this.send(e,t)}animFade(e){let t=`${e.fct} | ${e.objName} | ${e.property} | ${e.value}`;this.send(e,t)}clip(e){let t=[];e.fct&&t.push(e.fct),e.clipName&&t.push(e.clipName),e.action&&t.push(`timeScale=${e.action.timeScale}`),e.action&&t.push(`time=${e.action.time}`);const s=t.join(" | ");this.send(e,s)}clipFade(e){let t=[];e.fct&&t.push(e.fct),e.clipName&&t.push(e.clipName),e.action&&t.push(`timeScale=${e.action.timeScale}`),e.action&&t.push(`time=${e.action.time}`);const s=t.join(" | ");this.send(e,s)}modelError(e){let t="";t="SyntaxError"==e.error.name?"MODEL_ERROR: Invalid GLTF file or wrong path/filename.":`${e.error.name} / ${e.error.message}`,this.send(e,t)}modelLoading(e){this.send(e,`${e.loading}% loaded model`)}send(e,t){this.enqueue(()=>{const s=this.stateMachine.sendEvent(e,t);"all"!=this.cfg.debug.log||s||console.log(`${e.type}${t?`: ${t}`:""}`)})}windowResize(e){this.send(e,"Window render size updated.")}},OrbitCtrls=class{cam3D;canvas;cfg;engine;events;modules;orbitControls=null;enableDamping;dampingFactor;minDistance;maxDistance;enableZoom;zoomSpeed;enableRotate;rotateSpeed;enablePan;panSpeed;autoRotate;autoRotateSpeed;minPolarAngle;maxPolarAngle;orbitCtrlsFirstChange=!0;callback=null;listenerPointersStart;listenerPointersEnd;touchPointerIds=new Set;constructor(e,t,s,n,i,o){this.cam3D=e,this.cfg=s,this.engine=n,this.events=i,this.modules=o,this.canvas=t,this.enableDamping=s.orbitCtrls.enableDamping,this.dampingFactor=s.orbitCtrls.dampingFactor,this.minDistance=s.orbitCtrls.minDistance,this.maxDistance=s.orbitCtrls.maxDistance,this.enableZoom=s.orbitCtrls.enableZoom,this.zoomSpeed=s.orbitCtrls.zoomSpeed,this.enableRotate=s.orbitCtrls.enableRotate,this.rotateSpeed=s.orbitCtrls.rotateSpeed,this.enablePan=s.orbitCtrls.enablePan,this.panSpeed=s.orbitCtrls.panSpeed,this.autoRotate=s.orbitCtrls.autoRotate,this.autoRotateSpeed=s.orbitCtrls.autoRotateSpeed,this.minPolarAngle=s.orbitCtrls.minPolarAngle,this.maxPolarAngle=s.orbitCtrls.maxPolarAngle,this.listenerPointersStart=e=>this.updatePointersStart(e),this.listenerPointersEnd=e=>this.updatePointersEnd(e),this.cfg.orbitCtrls.enable&&this.enable()}create(){this.orbitControls||this.modules.orbitControlsClass&&(this.orbitControls=new this.modules.orbitControlsClass(this.cam3D.obj,this.engine.renderer.domElement),this.orbitControls?(this.orbitControls.enabled=!1,this.orbitCtrlsFirstChange=!0,this.canvas.addEventListener("pointerdown",this.listenerPointersStart,!0),this.canvas.addEventListener("pointerup",this.listenerPointersEnd,!0),this.canvas.addEventListener("pointercancel",this.listenerPointersEnd,!0),this.orbitControls.addEventListener("start",()=>{this.orbitCtrlsFirstChange=!1,this.events.send({type:"ORBITCTRLS_START"})}),this.orbitControls.addEventListener("change",()=>{this.orbitCtrlsFirstChange||(this.orbitCtrlsFirstChange=!0,this.events.send({type:"ORBITCTRLS_CHANGED"}))}),this.orbitControls.addEventListener("end",()=>{this.events.send({type:"ORBITCTRLS_END"})})):console.warn("Module OrbitControls could not be imported."))}disable(){this.orbitControls&&!1!==this.orbitControls.enabled&&(this.orbitControls.enabled=!1,this.touchPointerIds.clear(),this.callback&&(this.engine.removeOnFrameUpdate(this.callback),this.callback=null),this.events.send({type:"ORBITCTRLS_DISABLED"}))}enable(){this.orbitControls||this.create(),this.orbitControls&&(this.orbitControls.enabled||(this.orbitCtrlsFirstChange=!0,this.orbitControls.enabled=!0,this.orbitControls.target.copy(this.cam3D.objTarget.position),this.orbitControls.enableDamping=this.enableDamping,this.orbitControls.dampingFactor=this.dampingFactor,this.orbitControls.minDistance=this.minDistance,this.orbitControls.maxDistance=this.maxDistance,this.orbitControls.enableZoom=this.enableZoom,this.orbitControls.zoomSpeed=this.zoomSpeed,this.orbitControls.enableRotate=this.enableRotate,this.orbitControls.rotateSpeed=this.rotateSpeed,this.orbitControls.enablePan=this.enablePan,this.orbitControls.panSpeed=this.panSpeed,this.orbitControls.autoRotate=this.autoRotate,this.orbitControls.autoRotateSpeed=this.autoRotateSpeed,this.orbitControls.minPolarAngle=THREE.MathUtils.degToRad(this.minPolarAngle),this.orbitControls.maxPolarAngle=THREE.MathUtils.degToRad(this.maxPolarAngle),this.orbitControls.mouseButtons.LEFT=THREE.MOUSE.ROTATE,this.orbitControls.mouseButtons.MIDDLE=THREE.MOUSE.DOLLY,this.orbitControls.mouseButtons.RIGHT=THREE.MOUSE.PAN,this.orbitControls.touches.ONE=THREE.TOUCH.ROTATE,this.orbitControls.touches.TWO=THREE.TOUCH.DOLLY_PAN,this.callback=e=>{this.orbitControls?.update(e)},this.engine.addOnFrameUpdate(this.callback),this.events.send({type:"ORBITCTRLS_ENABLED"})))}dispose(){this.canvas.removeEventListener("pointerdown",this.listenerPointersStart,!0),this.canvas.removeEventListener("pointerup",this.listenerPointersEnd,!0),this.canvas.removeEventListener("pointercancel",this.listenerPointersEnd,!0),this.touchPointerIds.clear(),this.callback&&(this.engine.removeOnFrameUpdate(this.callback),this.callback=null),this.orbitControls?.dispose(),this.orbitControls=null,this.events.send({type:"ORBITCTRLS_DISPOSED"})}isEnabled(){return null!==this.orbitControls&&!0===this.orbitControls?.enabled}set(e){this.orbitControls&&(void 0!==e.enableDamping&&(this.enableDamping=e.enableDamping,this.orbitControls.enableDamping=e.enableDamping),void 0!==e.dampingFactor&&(this.dampingFactor=e.dampingFactor,this.orbitControls.dampingFactor=e.dampingFactor),void 0!==e.minDistance&&(this.minDistance=e.minDistance,this.orbitControls.minDistance=e.minDistance),void 0!==e.maxDistance&&(this.maxDistance=e.maxDistance,this.orbitControls.maxDistance=e.maxDistance),void 0!==e.enableZoom&&(this.enableZoom=e.enableZoom,this.orbitControls.enableZoom=e.enableZoom),void 0!==e.zoomSpeed&&(this.zoomSpeed=e.zoomSpeed,this.orbitControls.zoomSpeed=e.zoomSpeed),void 0!==e.enableRotate&&(this.enableRotate=e.enableRotate,this.orbitControls.enableRotate=e.enableRotate),void 0!==e.rotateSpeed&&(this.rotateSpeed=e.rotateSpeed,this.orbitControls.rotateSpeed=e.rotateSpeed),void 0!==e.enablePan&&(this.enablePan=e.enablePan,this.orbitControls.enablePan=e.enablePan),void 0!==e.panSpeed&&(this.panSpeed=e.panSpeed,this.orbitControls.panSpeed=e.panSpeed),void 0!==e.autoRotate&&(this.autoRotate=e.autoRotate,this.orbitControls.autoRotate=e.autoRotate),void 0!==e.autoRotateSpeed&&(this.autoRotateSpeed=e.autoRotateSpeed,this.orbitControls.autoRotateSpeed=e.autoRotateSpeed),void 0!==e.minPolarAngle&&(this.minPolarAngle=e.minPolarAngle,this.orbitControls.minPolarAngle=THREE.MathUtils.degToRad(e.minPolarAngle)),void 0!==e.maxPolarAngle&&(this.maxPolarAngle=e.maxPolarAngle,this.orbitControls.maxPolarAngle=THREE.MathUtils.degToRad(e.maxPolarAngle)))}get(){return{enableDamping:this.enableDamping,dampingFactor:this.dampingFactor,minDistance:this.minDistance,maxDistance:this.maxDistance,enableZoom:this.enableZoom,zoomSpeed:this.zoomSpeed,enableRotate:this.enableRotate,rotateSpeed:this.rotateSpeed,enablePan:this.enablePan,panSpeed:this.panSpeed,autoRotate:this.autoRotate,autoRotateSpeed:this.autoRotateSpeed,minPolarAngle:this.minPolarAngle,maxPolarAngle:this.maxPolarAngle}}use(e){e(this)}updatePointersEnd(e){"touch"===e.pointerType&&this.touchPointerIds.delete(e.pointerId)}updatePointersStart(e){if(!this.orbitControls?.enabled)return;if("touch"===e.pointerType){if(this.touchPointerIds.add(e.pointerId),this.touchPointerIds.size<2)return;const t=this.orbitControls.touches.TWO??null;if(null===t)return;return void(t===THREE.TOUCH.PAN||t===THREE.TOUCH.DOLLY_PAN?this.cam3D.lookMode="free":t!==THREE.TOUCH.ROTATE&&t!==THREE.TOUCH.DOLLY_ROTATE||(this.cam3D.lookMode="target"))}let t=null;if(0===e.button)t=THREE.MOUSE.ROTATE;else if(1===e.button)t=THREE.MOUSE.DOLLY;else{if(2!==e.button)return;t=THREE.MOUSE.PAN}t===THREE.MOUSE.PAN?this.cam3D.lookMode="free":t===THREE.MOUSE.ROTATE&&(this.cam3D.lookMode="target")}},FpvCtrls=class{cam3D;canvas;cfg;engine;events;modules;pointerLockCtrls=null;minPolarAngle;maxPolarAngle;pointerSpeed;keyMoveForward;keyMoveLeft;keyMoveBackward;keyMoveRight;keyMoveUp;keyMoveDown;isMoveForward=!1;isMoveLeft=!1;isMoveBackward=!1;isMoveRight=!1;isMoveUp=!1;isMoveDown=!1;callback=null;onClick=()=>{this.isEnabled()&&(this.isLocked()?this.unlock():this.lock())};onKeyDown=e=>{this.isEnabled()&&(e.code===this.keyMoveForward&&(this.isMoveForward=!0),e.code===this.keyMoveLeft&&(this.isMoveLeft=!0),e.code===this.keyMoveBackward&&(this.isMoveBackward=!0),e.code===this.keyMoveRight&&(this.isMoveRight=!0),e.code===this.keyMoveUp&&(this.isMoveUp=!0),e.code===this.keyMoveDown&&(this.isMoveDown=!0))};onKeyUp=e=>{this.isEnabled()&&(e.code===this.keyMoveForward&&(this.isMoveForward=!1),e.code===this.keyMoveLeft&&(this.isMoveLeft=!1),e.code===this.keyMoveBackward&&(this.isMoveBackward=!1),e.code===this.keyMoveRight&&(this.isMoveRight=!1),e.code===this.keyMoveUp&&(this.isMoveUp=!1),e.code===this.keyMoveDown&&(this.isMoveDown=!1))};constructor(e,t,s,n,i,o){this.cam3D=e,this.canvas=t,this.cfg=s,this.engine=n,this.events=i,this.modules=o,this.minPolarAngle=s.fpvCtrls.minPolarAngle,this.maxPolarAngle=s.fpvCtrls.maxPolarAngle,this.pointerSpeed=s.fpvCtrls.pointerSpeed,this.keyMoveForward=s.fpvCtrls.keyMoveForward,this.keyMoveLeft=s.fpvCtrls.keyMoveLeft,this.keyMoveBackward=s.fpvCtrls.keyMoveBackward,this.keyMoveRight=s.fpvCtrls.keyMoveRight,this.keyMoveUp=s.fpvCtrls.keyMoveUp,this.keyMoveDown=s.fpvCtrls.keyMoveDown,this.cfg.fpvCtrls.enable&&this.enable()}create(){this.pointerLockCtrls||this.modules.pointerLockControlsClass&&(this.pointerLockCtrls=new this.modules.pointerLockControlsClass(this.cam3D.obj,this.engine.renderer.domElement),this.pointerLockCtrls?(this.pointerLockCtrls.enabled=!1,this.pointerLockCtrls.addEventListener("lock",()=>{this.events.send({type:"FPVCTRLS_LOCK"})}),this.pointerLockCtrls.addEventListener("unlock",()=>{this.events.send({type:"FPVCTRLS_UNLOCK"})}),this.canvas.addEventListener("click",this.onClick),this.canvas.addEventListener("keydown",this.onKeyDown),this.canvas.addEventListener("keyup",this.onKeyUp)):console.warn("Module PointerLockControls could not be imported."))}disable(){this.pointerLockCtrls&&0!=this.pointerLockCtrls.enabled&&(this.pointerLockCtrls.enabled=!1,this.pointerLockCtrls.isLocked&&this.pointerLockCtrls.unlock(),this.callback&&(this.engine.removeOnFrameUpdate(this.callback),this.callback=null),this.isMoveForward=!1,this.isMoveLeft=!1,this.isMoveBackward=!1,this.isMoveRight=!1,this.isMoveUp=!1,this.isMoveDown=!1,this.events.send({type:"FPVCTRLS_DISABLED"}))}enable(){this.pointerLockCtrls||this.create(),this.pointerLockCtrls&&1!=this.pointerLockCtrls.enabled&&(this.pointerLockCtrls.enabled=!0,this.pointerLockCtrls.minPolarAngle=this.minPolarAngle,this.pointerLockCtrls.maxPolarAngle=this.maxPolarAngle,this.pointerLockCtrls.pointerSpeed=this.pointerSpeed,this.callback=e=>{this.pointerLockCtrls?.isLocked&&(this.isMoveForward&&this.moveForward(e),this.isMoveBackward&&this.moveForward(-e),this.isMoveLeft&&this.moveRight(-e),this.isMoveRight&&this.moveRight(e),this.isMoveUp&&this.moveUp(e),this.isMoveDown&&this.moveUp(-e))},this.engine.addOnFrameUpdate(this.callback),this.events.send({type:"FPVCTRLS_ENABLED"}))}dispose(){this.callback&&(this.engine.removeOnFrameUpdate(this.callback),this.callback=null),this.canvas.removeEventListener("click",this.onClick),this.canvas.removeEventListener("keydown",this.onKeyDown),this.canvas.removeEventListener("keyup",this.onKeyUp),this.isMoveForward=!1,this.isMoveLeft=!1,this.isMoveBackward=!1,this.isMoveRight=!1,this.isMoveUp=!1,this.isMoveDown=!1,this.pointerLockCtrls?.isLocked&&this.pointerLockCtrls.unlock(),this.pointerLockCtrls?.dispose(),this.pointerLockCtrls=null,this.events.send({type:"FPVCTRLS_DISPOSED"})}get(){return{minPolarAngle:this.minPolarAngle,maxPolarAngle:this.maxPolarAngle,pointerSpeed:this.pointerSpeed,keyMoveForward:this.keyMoveForward,keyMoveLeft:this.keyMoveLeft,keyMoveBackward:this.keyMoveBackward,keyMoveRight:this.keyMoveRight,keyMoveUp:this.keyMoveUp,keyMoveDown:this.keyMoveDown}}isEnabled(){return!0===this.pointerLockCtrls?.enabled}isLocked(){return this.pointerLockCtrls?.isLocked??!1}lock(){this.cam3D.lookMode="free",this.pointerLockCtrls?.lock()}moveForward(e){this.pointerLockCtrls?.moveForward(e)}moveRight(e){this.pointerLockCtrls?.moveRight(e)}moveUp(e){this.cam3D.obj.position.y+=e}set(e){this.pointerLockCtrls&&(void 0!==e.minPolarAngle&&(this.minPolarAngle=e.minPolarAngle,this.pointerLockCtrls.minPolarAngle=e.minPolarAngle),void 0!==e.maxPolarAngle&&(this.maxPolarAngle=e.maxPolarAngle,this.pointerLockCtrls.maxPolarAngle=e.maxPolarAngle),void 0!==e.pointerSpeed&&(this.pointerSpeed=e.pointerSpeed,this.pointerLockCtrls.pointerSpeed=e.pointerSpeed),void 0!==e.keyMoveForward&&(this.keyMoveForward=e.keyMoveForward),void 0!==e.keyMoveLeft&&(this.keyMoveLeft=e.keyMoveLeft),void 0!==e.keyMoveBackward&&(this.keyMoveBackward=e.keyMoveBackward),void 0!==e.keyMoveRight&&(this.keyMoveRight=e.keyMoveRight),void 0!==e.keyMoveUp&&(this.keyMoveUp=e.keyMoveUp),void 0!==e.keyMoveDown&&(this.keyMoveDown=e.keyMoveDown))}unlock(){this.pointerLockCtrls?.unlock(),this.events.send({type:"FPVCTRLS_UNLOCK"})}use(e){e(this)}},Raycast=class{cam3D;canvas;cfg;engine;events;objs3D;raycasterSelect=new THREE.Raycaster;raycasterVisible=new THREE.Raycaster;objsSelectTracked=new Set;objActive=null;objCandidate=null;closestObjCounter=0;isEnabled=!1;callbackSelect=null;listenerClick;listenerDown;listenerMove;listenerUp;pointerEvent=null;posPrevPointerX=0;posPrevPointerY=0;posWorldObj=new THREE.Vector3;dirCamToObj=new THREE.Vector3;posNdcPointer=new THREE.Vector2;constructor(e,t,s,n,i,o){this.cam3D=e,this.canvas=t,this.cfg=s,this.engine=n,this.events=i,this.objs3D=o,this.listenerMove=e=>this.updatePointer(e),this.listenerClick=e=>this.onClick(e),this.listenerDown=e=>this.onPointerDown(e),this.listenerUp=e=>this.onPointerUp(e)}enable(){this.isEnabled||0!==this.objsSelectTracked.size&&(this.canvas.addEventListener("pointermove",this.listenerMove),this.canvas.addEventListener("click",this.listenerClick),this.canvas.addEventListener("pointerdown",this.listenerDown),this.canvas.addEventListener("pointerup",this.listenerUp),this.callbackSelect=()=>this.updateSelect(),this.engine.addOnFrameUpdate(this.callbackSelect),this.isEnabled=!0)}disable(){this.isEnabled&&(this.canvas.removeEventListener("pointermove",this.listenerMove),this.canvas.removeEventListener("click",this.listenerClick),this.canvas.removeEventListener("pointerdown",this.listenerDown),this.canvas.removeEventListener("pointerup",this.listenerUp),this.callbackSelect&&(this.engine.removeOnFrameUpdate(this.callbackSelect),this.callbackSelect=null),this.objActive=null,this.objCandidate=null,this.closestObjCounter=0,this.pointerEvent=null,this.isEnabled=!1)}isVisibleOcclusion(e){e.updateMatrixWorld(!0),e.getWorldPosition(this.posWorldObj),this.dirCamToObj.subVectors(this.posWorldObj,this.cam3D.obj.position);const t=this.dirCamToObj.length();return t<=0||(this.dirCamToObj.normalize(),this.raycasterVisible.set(this.cam3D.obj.position,this.dirCamToObj),this.raycasterVisible.near=0,this.raycasterVisible.far=Math.max(0,t-1e-4),0===this.raycasterVisible.intersectObjects(this.engine.scene.children,!0).filter(t=>t.object!==e).length)}onClick(e){this.objActive?.name&&this.objs3D.get(this.objActive.name)?.emitEvent({type:"OBJ3D_CLICK",event:e,objName:this.objActive.name})}onPointerDown(e){this.objActive?.name&&this.objs3D.get(this.objActive.name)?.emitEvent({type:"OBJ3D_POINTER_DOWN",event:e,objName:this.objActive.name})}onPointerEnter(e,t){const s=this.objs3D.get(e);s&&s?.emitEvent({type:"OBJ3D_POINTER_ENTER",event:t,objName:e})}onPointerLeave(e,t){const s=this.objs3D.get(e);s&&s?.emitEvent({type:"OBJ3D_POINTER_LEAVE",event:t,objName:e})}onPointerMove(e,t){this.objs3D.get(e)?.emitEvent({type:"OBJ3D_POINTER_MOVE",event:t,objName:e})}onPointerUp(e){this.objActive?.name&&this.objs3D.get(this.objActive.name)?.emitEvent({type:"OBJ3D_POINTER_UP",event:e,objName:this.objActive.name})}trackSelectable({objs3D:e}){if(Array.isArray(e)){for(const t of e)t.obj&&this.objsSelectTracked.add(t.obj);this.enable()}}use(e){e(this)}untrackSelectable({objs3D:e}){if(Array.isArray(e)){for(const t of e)t.obj&&this.objsSelectTracked.delete(t.obj);0===this.objsSelectTracked.size&&this.disable()}}updateSelect(){if(0===this.objsSelectTracked.size)return;let e=null,t=1/0;for(let s=0;s<this.cfg.raycast.circleSteps;s++){const n=s/this.cfg.raycast.circleSteps*Math.PI*2,i=this.canvas.getBoundingClientRect(),o=Math.cos(n)*this.cfg.raycast.circleRadius/i.width*2,a=Math.sin(n)*this.cfg.raycast.circleRadius/i.height*2,r=new THREE.Vector2(this.posNdcPointer.x+o,this.posNdcPointer.y+a);this.raycasterSelect.setFromCamera(r,this.cam3D.obj);const l=this.raycasterSelect.intersectObjects([...this.objsSelectTracked],!1);if(l.length>0){const s=l[0],n=s.point.clone().project(this.cam3D.obj),i=this.posNdcPointer.distanceTo(n);i<t&&(t=i,e=s.object)}}if(e!==this.objActive)e===this.objCandidate?this.closestObjCounter++:(this.objCandidate=e,this.closestObjCounter=1),this.closestObjCounter>=this.cfg.raycast.countClosestObjs&&(this.objActive?.name&&this.pointerEvent&&this.onPointerLeave(this.objActive.name,this.pointerEvent),this.objCandidate?.name&&this.pointerEvent&&this.onPointerEnter(this.objCandidate.name,this.pointerEvent),this.objActive=this.objCandidate,this.objCandidate=null,this.closestObjCounter=0);else{if(this.closestObjCounter=0,this.objCandidate=null,!this.pointerEvent)return;const e=this.pointerEvent;e.clientX===this.posPrevPointerX&&e.clientY===this.posPrevPointerY||!this.objActive?.name||this.onPointerMove(this.objActive.name,e),this.posPrevPointerX=e.clientX,this.posPrevPointerY=e.clientY}}updatePointer(e){this.pointerEvent=e;const t=this.canvas.getBoundingClientRect(),s=(e.clientX-t.left)/t.width,n=(e.clientY-t.top)/t.height;this.posNdcPointer.x=2*s-1,this.posNdcPointer.y=-(2*n-1)}},StateMachine=class{cfg;modules;actor=null;lastState="";snapshot=null;stateMachine=null;constructor(e,t){this.cfg=e,this.modules=t}sendEvent(e,t){if(!this.actor)return null;let s=!1;return(null!=this.snapshot?this.snapshot:this.actor.getSnapshot?.())?.can?.(e)&&(s=!0,"none"!=this.cfg.debug.log&&console.log(`${e.type}${t?`: ${t}`:""}`),this.actor.send(e)),s}start(e){if(this.stateMachine=e,this.stateMachine)if(this.actor)console.warn("Actor is already started.");else{if(this.cfg.stateMachine.inspector&&this.modules.createBrowserInspector){const{inspect:e}=this.modules.createBrowserInspector();this.actor=createActor(this.stateMachine,{inspect:e})}else this.actor=createActor(this.stateMachine);this.actor.subscribe(e=>{if(this.snapshot=e,"none"==this.cfg.debug.log)return;const t=e.value,s=JSON.stringify(t);if(s!==this.lastState)if(this.lastState=s,"object"==typeof t&&null!==t){const e=(t,s="")=>{if("string"==typeof t)return[s?`${s} > ${t}`:t];const n=[];for(const[i,o]of Object.entries(t)){const t=s?`${s} > ${i}`:i;n.push(...e(o,t))}return n};e(t).forEach(e=>{console.log(`STATE: ${e}`)})}else console.log(`STATE: ${t}`)}),this.actor.start()}else console.warn("State Machine not found.")}},cfg={audio:{guiOpened:!1,delayPlaySound:200,refDistance:1,rolloffFactor:5,maxDistance:1e3,distanceModel:"exponential",coneInnerAngle:360,coneOuterAngle:360,coneOuterGain:0},cam:{fov:75,near:.1,far:1e3,type:"perspective",lookAt:{x:0,y:0,z:0},position:{x:0,y:.5,z:.5}},debug:{log:"xstate"},envCtrls:{backgroundBlurriness:0,backgroundIntensity:0,enable:!1,environmentIntensity:1.8,load:!1,map:"",rotation:{x:0,y:0,z:0},rotationSpeed:0,type:"exr"},fpvCtrls:{enable:!1,load:!1,minPolarAngle:0,maxPolarAngle:Math.PI,pointerSpeed:.1,keyMoveForward:"KeyW",keyMoveLeft:"KeyA",keyMoveBackward:"KeyS",keyMoveRight:"KeyD",keyMoveUp:"KeyQ",keyMoveDown:"KeyE"},light:{mapWidth:2048,mapHeight:2048,bias:-2e-5,normalBias:.005,near:.1,far:5},menuBar:{enable:!0,backgroundColor:"#F40B5780",logo:""},mesh:{castShadow:!0,receiveShadow:!0,frustumCulled:!1},model:{compression:{mesh:"none",texture:"none"},decoderPath:"/draco/",file:null,progressBar:!0},orbitCtrls:{autoRotate:!1,autoRotateSpeed:2,dampingFactor:.1,enable:!1,enableDamping:!1,enablePan:!0,enableRotate:!0,enableZoom:!0,load:!1,maxDistance:1/0,maxPolarAngle:180,minDistance:0,minPolarAngle:0,panSpeed:1,rotateSpeed:1,zoomSpeed:1},post:{auto:!0,guiOpened:!1,aa:{guiOpened:!1,mode:"none"},ssao:{enable:!1,guiOpened:!1},ssr:{enable:!1,guiOpened:!1},webgl:{aa:{fxaa:{sharpness:.5}},ssao:{kernelRadius:8,minDistance:.005,maxDistance:.1},ssr:{bouncing:!1,distanceAttenuation:!0,fresnel:!0,infiniteThick:!1,maxDistance:180,opacity:.5,thickness:.018,blur:!0,resolutionScale:1,output:0,selective:!1,clear:!0,maxRoughness:.5}},webgpu:{ssao:{radius:.25,thickness:1,distanceExponent:1,distanceFallOff:1,scale:1,samples:16,resolutionScale:1},ssr:{distanceAttenuation:!0,fresnel:!0,maxDistance:180,opacity:.5,thickness:.018,resolutionScale:1,quality:.5,blurQuality:1}}},raycast:{circleRadius:10,circleSteps:12,countClosestObjs:5},render:{api:"auto",autoResize:!0,guiOpened:!1,fpsLimiter:!0,fpsMax:30,deltaTimesMax:10,gui:!1,outputColorSpace:THREE.SRGBColorSpace,pixelRatio:1,shadowMapEnabled:!0,shadowMapType:THREE.PCFShadowMap,toneMapping:THREE.ACESFilmicToneMapping,toneMappingExposure:1,webgl:{parameters:{antialias:!0,alpha:!1,powerPreference:"low-power"}},webgpu:{parameters:{antialias:!0,alpha:!1}}},scene:{guiOpened:!1,canvas:"comp-canvas",fog:{enable:!1,color:0,near:0,far:100},ambientlight:{enable:!1,color:16777215,intensity:1},hemisphere:{enable:!1,skyColor:16777147,groundColor:526368,intensity:1}},stateMachine:{inspector:!1},stats:{enabled:!0,fps:!0,cpu:!0,frame:!0,calls:!0,triangles:!0,lines:!0,points:!0,geometries:!0,textures:!0,programs:!0,logsPerSecond:10}},gui_default="/* nur Chrome / Edge / Safari */\r\n.illutions-pane {\r\n font-family: monospace;\r\n font-size: 12px;\r\n\r\n --tp-base-background-color: hsla(230, 20%, 11%, 1.00);\r\n --tp-base-shadow-color: hsla(0, 0%, 0%, 0.2);\r\n --tp-button-background-color: hsla(230, 10%, 80%, 1.00);\r\n --tp-button-background-color-active: hsla(230, 10%, 95%, 1.00);\r\n --tp-button-background-color-focus: hsla(230, 10%, 90%, 1.00);\r\n --tp-button-background-color-hover: hsla(230, 10%, 85%, 1.00);\r\n --tp-button-foreground-color: hsla(230, 20%, 11%, 1.00);\r\n --tp-container-background-color: hsla(230, 25%, 16%, 1.00);\r\n --tp-container-background-color-active: hsla(230, 25%, 31%, 1.00);\r\n --tp-container-background-color-focus: hsla(230, 25%, 26%, 1.00);\r\n --tp-container-background-color-hover: hsla(230, 25%, 21%, 1.00);\r\n --tp-container-foreground-color: hsla(230, 10%, 80%, 1.00);\r\n --tp-groove-foreground-color: hsla(230, 20%, 8%, 1.00);\r\n --tp-input-background-color: hsla(230, 20%, 8%, 1.00);\r\n --tp-input-background-color-active: hsla(230, 28%, 23%, 1.00);\r\n --tp-input-background-color-focus: hsla(230, 28%, 18%, 1.00);\r\n --tp-input-background-color-hover: hsla(230, 20%, 13%, 1.00);\r\n --tp-input-foreground-color: hsla(230, 10%, 80%, 1.00);\r\n --tp-label-foreground-color: hsla(230, 12%, 48%, 1.00);\r\n --tp-monitor-background-color: hsla(230, 20%, 8%, 1.00);\r\n --tp-monitor-foreground-color: hsla(230, 12%, 48%, 1.00);\r\n\r\n max-height: 95vh;\r\n overflow-y: auto;\r\n scrollbar-width: thin;\r\n scrollbar-color: #F40B5780 #1e1e1e;\r\n}\r\n\r\n/* WebKit Hover + Fallback for older Chrome / Edge / Safari */\r\n.illutions-pane::-webkit-scrollbar {\r\n width: 10px;\r\n}\r\n\r\n.illutions-pane::-webkit-scrollbar-track {\r\n background: #1e1e1e;\r\n}\r\n\r\n.illutions-pane::-webkit-scrollbar-thumb {\r\n background: #F40B5780;\r\n border-radius: 6px;\r\n}\r\n\r\n.illutions-pane::-webkit-scrollbar-thumb:hover {\r\n background: #F40B57;\r\n}\r\n",outputColorSpaceParam={SRGB:THREE.SRGBColorSpace,LinearSRGB:THREE.LinearSRGBColorSpace},shadowMapTypeParam={Basic:THREE.BasicShadowMap,PCF:THREE.PCFShadowMap,PCFSoft:THREE.PCFShadowMap,VSM:THREE.VSMShadowMap},toneMappingParam={None:THREE.NoToneMapping,Linear:THREE.LinearToneMapping,Reinhard:THREE.ReinhardToneMapping,Cineon:THREE.CineonToneMapping,ACESFilmic:THREE.ACESFilmicToneMapping,AgX:THREE.AgXToneMapping,Neutral:THREE.NeutralToneMapping,Custom:THREE.CustomToneMapping},Gui=class{engine;envCtrls;gui=null;modules;orbitCtrls;fpvCtrls;cfg;cfgCtrl;constructor(e,t,s,n,i,o,a){if(this.engine=s,this.envCtrls=n,this.modules=i,this.orbitCtrls=o,this.fpvCtrls=a,this.cfgCtrl=t,this.cfg=e,!this.modules.paneClass)return void console.warn("Module tweakpane could not be imported.");if(this.gui=new this.modules.paneClass({title:"illutions"}),!this.gui)return;const r=this.gui.element;r.style.position="fixed",r.style.top="8px",r.style.right="8px",r.style.zIndex="1000",r.classList.add("illutions-pane");const l=document.createElement("style");l.textContent=gui_default,document.head.appendChild(l);const c=this.gui.addFolder({title:"Audio",expanded:this.cfg.audio.guiOpened});c.addBinding(this.cfg.audio,"refDistance",{min:.1,max:20,step:.1}),c.addBinding(this.cfg.audio,"rolloffFactor",{min:0,max:20,step:.1}),c.addBinding(this.cfg.audio,"maxDistance",{min:1,max:5e3,step:10}),c.addBinding(this.cfg.audio,"distanceModel",{options:{linear:"linear",inverse:"inverse",exponential:"exponential"}}),c.addBinding(this.cfg.audio,"coneInnerAngle",{min:0,max:360,step:1}),c.addBinding(this.cfg.audio,"coneOuterAngle",{min:0,max:360,step:1}),c.addBinding(this.cfg.audio,"coneOuterGain",{min:0,max:1,step:.01});const d=this.gui.addFolder({title:"Navigation",expanded:!1});if(this.cfg.orbitCtrls.enable){const w=d.addFolder({title:"Orbit",expanded:!0});w.addBinding(this.cfg.orbitCtrls,"enableDamping").on("change",e=>this.orbitCtrls.set({enableDamping:e.value})),w.addBinding(this.cfg.orbitCtrls,"dampingFactor",{min:0,max:1,step:.01}).on("change",e=>this.orbitCtrls.set({dampingFactor:e.value})),w.addBinding(this.cfg.orbitCtrls,"minDistance",{min:0,max:500,step:.1}).on("change",e=>this.orbitCtrls.set({minDistance:e.value})),w.addBinding(this.cfg.orbitCtrls,"maxDistance",{min:0,max:2e3,step:.1}).on("change",e=>this.orbitCtrls.set({maxDistance:e.value})),w.addBinding(this.cfg.orbitCtrls,"minPolarAngle",{min:0,max:180,step:1,format:e=>`${e}°`,parse:e=>Number(e.replace("°",""))}).on("change",e=>this.orbitCtrls.set({minPolarAngle:e.value})),w.addBinding(this.cfg.orbitCtrls,"maxPolarAngle",{min:0,max:180,step:1,format:e=>`${e}°`,parse:e=>Number(e.replace("°",""))}).on("change",e=>this.orbitCtrls.set({maxPolarAngle:e.value})),w.addBinding(this.cfg.orbitCtrls,"enableZoom").on("change",e=>this.orbitCtrls.set({enableZoom:e.value})),w.addBinding(this.cfg.orbitCtrls,"zoomSpeed",{min:.1,max:5,step:.1}).on("change",e=>this.orbitCtrls.set({zoomSpeed:e.value})),w.addBinding(this.cfg.orbitCtrls,"enableRotate"),w.addBinding(this.cfg.orbitCtrls,"rotateSpeed",{min:.1,max:5,step:.1}).on("change",e=>this.orbitCtrls.set({rotateSpeed:e.value})),w.addBinding(this.cfg.orbitCtrls,"enablePan").on("change",e=>this.orbitCtrls.set({enablePan:e.value})),w.addBinding(this.cfg.orbitCtrls,"panSpeed",{min:.1,max:5,step:.1}).on("change",e=>this.orbitCtrls.set({panSpeed:e.value})),w.addBinding(this.cfg.orbitCtrls,"autoRotate").on("change",e=>this.orbitCtrls.set({autoRotate:e.value})),w.addBinding(this.cfg.orbitCtrls,"autoRotateSpeed",{min:.1,max:10,step:.1}).on("change",e=>this.orbitCtrls.set({autoRotateSpeed:e.value}))}if(this.cfg.fpvCtrls.enable){const E=d.addFolder({title:"FirstPerson",expanded:!0});E.addBinding(this.cfg.fpvCtrls,"minPolarAngle",{min:0,max:Math.PI,step:.01}).on("change",e=>this.fpvCtrls.set({minPolarAngle:e.value})),E.addBinding(this.cfg.fpvCtrls,"maxPolarAngle",{min:0,max:Math.PI,step:.01}).on("change",e=>this.fpvCtrls.set({maxPolarAngle:e.value})),E.addBinding(this.cfg.fpvCtrls,"pointerSpeed",{min:.01,max:1,step:.01}).on("change",e=>this.fpvCtrls.set({pointerSpeed:e.value}))}const h=this.gui.addFolder({title:"Renderer",expanded:this.cfg.render.guiOpened});h.addBinding(this.cfg.render,"fpsLimiter"),h.addBinding(this.cfg.render,"deltaTimesMax",{min:1,max:120,step:1}),h.addBinding(this.cfg.render,"pixelRatio",{min:.25,max:2,step:.05}).on("change",e=>{this.engine.renderer.setPixelRatio(e.value)});const m={outputColorSpace:Object.keys(outputColorSpaceParam).find(e=>outputColorSpaceParam[e]===this.cfg.render.outputColorSpace)},p=Object.keys(outputColorSpaceParam).reduce((e,t)=>(e[t]=t,e),{});h.addBinding(m,"outputColorSpace",{options:p}).on("change",e=>{const t=outputColorSpaceParam[e.value];this.cfg.render.outputColorSpace=t,this.engine.renderer.outputColorSpace=t});const u=h.addFolder({title:"ShadowMap",expanded:!1});u.addBinding(this.cfg.render,"shadowMapEnabled").on("change",e=>{this.engine.renderer.shadowMap.enabled=e.value});const g={shadowMapType:Object.keys(shadowMapTypeParam).find(e=>shadowMapTypeParam[e]===this.cfg.render.shadowMapType)},b=Object.keys(shadowMapTypeParam).reduce((e,t)=>(e[t]=t,e),{});u.addBinding(g,"shadowMapType",{options:b}).on("change",e=>{const t=shadowMapTypeParam[e.value];this.engine.renderer.shadowMap.type=t});const f=h.addFolder({title:"ToneMapping",expanded:!1}),v={toneMapping:Object.keys(toneMappingParam).find(e=>toneMappingParam[e]===this.cfg.render.toneMapping)},C=Object.keys(toneMappingParam).reduce((e,t)=>(e[t]=t,e),{});if(f.addBinding(v,"toneMapping",{options:C}).on("change",e=>{const t=e.value;this.engine.renderer.toneMapping=toneMappingParam[t]}),f.addBinding(this.cfg.render,"toneMappingExposure",{min:0,max:5}).on("change",e=>{this.engine.renderer.toneMappingExposure=e.value}),this.cfg.post.auto){const L=h.addFolder({title:"Postprocessing",expanded:this.cfg.post.guiOpened}),T={ssaoEnable:this.cfg.post.ssao.enable,ssrEnable:this.cfg.post.ssr.enable,aaMode:this.cfg.post.aa.mode};function M(e,t,s){for(const n of e.children)n!==t&&(n.disabled=s)}const P=this.cfg.post.ssao;if(this.modules.webGpuRendererClass){const A=this.cfg.post.webgpu.ssao,G=L.addFolder({title:"SSAO",expanded:P.guiOpened}),O=G.addBinding(T,"ssaoEnable",{label:"Enable"}).on("change",async e=>{await this.engine.enableSsao(e.value),M(G,O,!e.value)});G.addBinding(A,"radius",{min:0,max:10,step:.01,label:"Radius"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.radius.value=e.value)}),G.addBinding(A,"thickness",{min:0,max:10,step:.01,label:"Thickness"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.thickness.value=e.value)}),G.addBinding(A,"distanceExponent",{min:0,max:10,step:.01,label:"DistanceExponent"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.distanceExponent.value=e.value)}),G.addBinding(A,"distanceFallOff",{min:0,max:10,step:.01,label:"DistanceFallOff"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.distanceFallOff.value=e.value)}),G.addBinding(A,"scale",{min:0,max:5,step:.01,label:"Scale"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.scale.value=e.value)}),G.addBinding(A,"samples",{min:1,max:64,step:1,label:"Samples"}).on("change",e=>{this.engine.gtaoNode&&(this.engine.gtaoNode.samples.value=Math.round(e.value))}),M(G,O,!P.enable)}else{const B=this.cfg.post.webgl.ssao,U=L.addFolder({title:"SSAO",expanded:P.guiOpened}),j=U.addBinding(P,"enable",{label:"Enable"}).on("change",e=>{this.engine.enableSsao(e.value),M(U,j,!e.value)});U.addBinding(B,"kernelRadius",{min:0,max:32,step:1,label:"KernelRadius"}).on("change",e=>{this.engine.ssaoPass&&(this.engine.ssaoPass.kernelRadius=e.value)}),U.addBinding(B,"minDistance",{min:0,max:.5,step:.001,label:"MinDistance"}).on("change",e=>{this.engine.ssaoPass&&(this.engine.ssaoPass.minDistance=e.value)}),U.addBinding(B,"maxDistance",{min:0,max:1,step:.01,label:"MaxDistance"}).on("change",e=>{this.engine.ssaoPass&&(this.engine.ssaoPass.maxDistance=e.value)}),M(U,j,!P.enable)}const S=this.cfg.post.ssr;if(this.modules.webGpuRendererClass){const k=this.cfg.post.webgpu.ssr,I=L.addFolder({title:"SSR",expanded:S.guiOpened}),J=I.addBinding(T,"ssrEnable",{label:"Enable"}).on("change",async e=>{await this.engine.enableSsr(e.value),M(I,J,!e.value)});I.addBinding(k,"maxDistance",{min:0,max:180,step:.01,label:"MaxDistance"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.maxDistance.value=e.value)}),I.addBinding(k,"opacity",{min:0,max:1,step:.01,label:"Opacity"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.opacity.value=e.value)}),I.addBinding(k,"thickness",{min:0,max:.1,step:.001,label:"Thickness"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.thickness.value=e.value)}),I.addBinding(k,"resolutionScale",{min:0,max:1,step:.01,label:"ResolutionScale"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.resolutionScale=e.value)}),I.addBinding(k,"quality",{min:0,max:1,step:.01,label:"Quality"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.quality.value=e.value)}),I.addBinding(k,"blurQuality",{min:1,max:3,step:1,label:"BlurQuality"}).on("change",e=>{this.engine.ssrNode&&(this.engine.ssrNode.blurQuality.value=Math.round(e.value))}),M(I,J,!S.enable)}else{const N=this.cfg.post.webgl.ssr,Y=L.addFolder({title:"SSR",expanded:S.guiOpened});let Z=null;const z=()=>{if(Z)return;if(!this.modules.ssrPassClass)return;const e={Default:this.modules.ssrPassClass.OUTPUT.Default,"SSR Only":this.modules.ssrPassClass.OUTPUT.SSR,Beauty:this.modules.ssrPassClass.OUTPUT.Beauty,Depth:this.modules.ssrPassClass.OUTPUT.Depth,Normal:this.modules.ssrPassClass.OUTPUT.Normal,Metalness:this.modules.ssrPassClass.OUTPUT.Metalness};Z=Y.addBinding(N,"output",{label:"Output",options:e}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.output=e.value)})},W=Y.addBinding(S,"enable",{label:"Enable"}).on("change",async e=>{await this.engine.enableSsr(e.value),z(),M(Y,W,!e.value)});Y.addBinding(N,"fresnel",{label:"Fresnel"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.fresnel=e.value),this.engine.groundReflector&&(this.engine.groundReflector.fresnel=e.value)}),Y.addBinding(N,"distanceAttenuation",{label:"DistanceAttenuation"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.distanceAttenuation=e.value),this.engine.groundReflector&&(this.engine.groundReflector.distanceAttenuation=e.value)}),Y.addBinding(N,"maxDistance",{min:0,max:180,step:.01,label:"MaxDistance"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.maxDistance=e.value),this.engine.groundReflector&&(this.engine.groundReflector.maxDistance=e.value)}),Y.addBinding(N,"opacity",{min:0,max:1,step:.01,label:"Opacity"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.opacity=e.value),this.engine.groundReflector&&(this.engine.groundReflector.opacity=e.value)}),Y.addBinding(N,"thickness",{min:0,max:.1,step:.001,label:"Thickness"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.thickness=e.value)}),Y.addBinding(N,"infiniteThick",{label:"InfiniteThick"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.infiniteThick=e.value)}),Y.addBinding(N,"blur",{label:"Blur"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.blur=e.value)}),Y.addBinding(N,"resolutionScale",{min:0,max:1,step:.01,label:"ResolutionScale"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.resolutionScale=e.value)}),Y.addBinding(N,"bouncing",{label:"Bouncing"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.bouncing=e.value)}),Y.addBinding(N,"clear",{label:"Clear"}).on("change",e=>{this.engine.ssrPass&&(this.engine.ssrPass.clear=e.value)}),z(),M(Y,W,!S.enable)}const x=this.cfg.post.aa,D=L.addFolder({title:"AA",expanded:x.guiOpened});let R=null;D.addBinding(T,"aaMode",{label:"Mode",options:{None:"none",FXAA:"fxaa",SMAA:"smaa"}}).on("change",async e=>{x.mode=e.value,await this.engine.enableAaMode(x.mode),R&&(R.hidden="fxaa"!==x.mode)}),this.modules.webGpuRendererClass||(R=D.addBinding(this.cfg.post.webgl.aa.fxaa,"sharpness",{min:.1,max:1,step:.05,label:"Sharpness"}).on("change",e=>{"fxaa"===x.mode&&this.engine.setFxaaResolution(e.value)}),R.hidden="fxaa"!==x.mode)}const y=this.gui.addFolder({title:"Scene",expanded:this.cfg.scene.guiOpened});if(this.cfg.scene.ambientlight.enable){const F=y.addFolder({title:"Ambient Light",expanded:!0});F.addBinding(this.cfg.scene.ambientlight,"enable",{label:"Enabled"}).on("change",e=>{e.value?this.engine.setAmbientLight({color:this.cfg.scene.ambientlight.color,intensity:this.cfg.scene.ambientlight.intensity}):this.engine.removeAmbientLight()}),F.addBinding(this.cfg.scene.ambientlight,"color",{label:"Color",view:"color"}).on("change",e=>{this.engine.setAmbientLight({color:e.value})}),F.addBinding(this.cfg.scene.ambientlight,"intensity",{min:0,max:5,label:"Intensity"}).on("change",e=>{this.engine.setAmbientLight({intensity:e.value})})}if(this.cfg.scene.hemisphere.enable){const H=y.addFolder({title:"Hemisphere Light",expanded:!0});H.addBinding(this.cfg.scene.hemisphere,"enable",{label:"Enabled"}).on("change",e=>{e.value?this.engine.setHemisphereLight({skyColor:this.cfg.scene.hemisphere.skyColor,groundColor:this.cfg.scene.hemisphere.groundColor,intensity:this.cfg.scene.hemisphere.intensity}):this.engine.removeHemisphereLight()}),H.addBinding(this.cfg.scene.hemisphere,"skyColor",{label:"Sky Color",view:"color"}).on("change",e=>{this.engine.setHemisphereLight({skyColor:e.value})}),H.addBinding(this.cfg.scene.hemisphere,"groundColor",{label:"Ground Color",view:"color"}).on("change",e=>{this.engine.setHemisphereLight({groundColor:e.value})}),H.addBinding(this.cfg.scene.hemisphere,"intensity",{min:0,max:5,label:"Intensity"}).on("change",e=>{this.engine.setHemisphereLight({intensity:e.value})})}if(this.cfg.scene.fog.enable){const q=y.addFolder({title:"Fog",expanded:!0});q.addBinding(this.cfg.scene.fog,"enable",{label:"Enabled"}).on("change",e=>{e.value?this.engine.setFog({color:this.cfg.scene.fog.color,near:this.cfg.scene.fog.near,far:this.cfg.scene.fog.far}):this.engine.removeFog()}),q.addBinding(this.cfg.scene.fog,"color",{label:"Color",view:"color"}).on("change",e=>{this.engine.setFog({color:e.value})}),q.addBinding(this.cfg.scene.fog,"near",{min:0,max:50,label:"Near"}).on("change",e=>{this.engine.setFog({near:e.value})}),q.addBinding(this.cfg.scene.fog,"far",{min:0,max:100,label:"Far"}).on("change",e=>{this.engine.setFog({far:e.value})})}if(this.cfg.envCtrls.enable||this.cfg.envCtrls.load){const V=y.addBinding(this.cfg.envCtrls,"enable",{label:"Enabled"}),X=y.addFolder({title:"Background",expanded:!1}),_=y.addFolder({title:"Environment",expanded:!1});V.on("change",e=>{e.value?this.envCtrls.enable():this.envCtrls.disable(),X.disabled=!e.value,_.disabled=!e.value}),X.disabled=!this.cfg.envCtrls.enable,_.disabled=!this.cfg.envCtrls.enable,X.addBinding(this.cfg.envCtrls,"backgroundBlurriness",{min:0,max:1,label:"Blurriness"}).on("change",e=>{this.envCtrls.set({backgroundBlurriness:e.value})}),X.addBinding(this.cfg.envCtrls,"backgroundIntensity",{min:0,max:5,label:"Intensity"}).on("change",e=>{this.envCtrls.set({backgroundIntensity:e.value})}),_.addBinding(this.cfg.envCtrls,"environmentIntensity",{min:0,max:10,label:"Intensity"}).on("change",e=>{this.envCtrls.set({environmentIntensity:e.value})});const K=this.envCtrls.get().rotation;if(K){const $={x:K.x,y:K.y,z:K.z};_.addBinding($,"x",{min:0,max:360,label:"Rotate X"}).on("change",()=>{this.envCtrls.set({rotation:$})}),_.addBinding($,"y",{min:0,max:360,label:"Rotate Y"}).on("change",()=>{this.envCtrls.set({rotation:$})}),_.addBinding($,"z",{min:0,max:360,label:"Rotate Z"}).on("change",()=>{this.envCtrls.set({rotation:$})})}}}},Modules=class{gpuTier=null;fxaaNode=null;fxaaShader=null;smaaPassClass=null;smaaNode=null;ssaoPassClass=null;gtaoNodeClass=null;ssrNode=null;ssrPassClass=null;paneClass=null;createBrowserInspector=null;effectComposerClass=null;envLoader=null;dracoLoader=null;gltfLoader=null;ktx2Loader=null;meshoptDecoder=null;outputPassClass=null;renderPassClass=null;shaderPassClass=null;orbitControlsClass=null;pointerLockControlsClass=null;webGpuRendererClass=null;renderPipelineClass=null;tslPass=null;tslMrt=null;tslOutput=null;tslNormalView=null;tslMetalness=null;tslRoughness=null;tslSample=null;tslVec2=null;tslVec3=null;tslVec4=null;tslFloat=null;tslDirectionToColor=null;tslColorToDirection=null;cfg;constructor(e){this.cfg=e}consoleLog(e){"none"!==this.cfg.debug.log&&console.log(`Module ${e} successfully imported.`)}async importDracoLoader(){if(!this.dracoLoader&&"draco"===this.cfg.model.compression.mesh)try{const e=await import("three/addons/loaders/DRACOLoader.js");this.consoleLog("DRACOLoader"),this.dracoLoader=new e.DRACOLoader,this.dracoLoader.setDecoderPath("/draco/")}catch{console.warn("DRACOLoader could not be imported")}}async importEffectComposer(){if(!this.effectComposerClass)try{const e=await import("three/addons/postprocessing/EffectComposer.js");this.effectComposerClass=e.EffectComposer,this.consoleLog("EffectComposer")}catch{console.warn("EffectComposer could not be imported")}}async importENVLoader(){if(!this.envLoader&&(this.cfg.envCtrls.enable||this.cfg.envCtrls.load))if("exr"===this.cfg.envCtrls.type)try{const e=await import("three/addons/loaders/EXRLoader.js");this.consoleLog("EXRLoader"),this.envLoader=new e.EXRLoader}catch{console.warn("EXRLoader could not be imported")}else if("hdr"===this.cfg.envCtrls.type)try{const e=await import("three/addons/loaders/HDRLoader.js");this.consoleLog("HDRLoader"),this.envLoader=new e.HDRLoader}catch{console.warn("HDRLoader could not be imported")}}async importFpvCtrls(){if(this.cfg.fpvCtrls.enable||this.cfg.fpvCtrls.load)try{const e=await import("three/addons/controls/PointerLockControls.js");this.pointerLockControlsClass=e.PointerLockControls,this.consoleLog("PointerLockControls")}catch{console.warn("PointerLockControls could not be imported")}}async importFXAANode(e){if(!this.fxaaNode&&"fxaa"===e)try{const e=await import("three/addons/tsl/display/FXAANode.js");this.fxaaNode=e.fxaa,this.consoleLog("FXAANode")}catch{console.warn("FXAANode could not be imported")}}async importFXAAShader(e){if("fxaa"===e&&!this.fxaaShader){try{const e=await import("three/addons/shaders/FXAAShader.js");this.fxaaShader=e.FXAAShader,this.consoleLog("FXAAShader")}catch{console.warn("FXAAShader could not be imported")}if(!this.shaderPassClass)try{const e=await import("three/addons/postprocessing/ShaderPass.js");this.shaderPassClass=e.ShaderPass,this.consoleLog("ShaderPass")}catch{console.warn("ShaderPass could not be imported")}}}async importGLTFLoader(){if(this.cfg.model.file)try{const e=await import("three/addons/loaders/GLTFLoader.js");this.consoleLog("GLTFLoader"),this.gltfLoader=new e.GLTFLoader}catch{console.warn("GLTFLoader could not be imported")}}async importGpuDetect(){if(this.cfg.post.auto)try{const e=await import("detect-gpu");this.consoleLog("detect-gpu");const t=e.getGPUTier;this.gpuTier=await t()}catch{console.warn("detect-gpu could not be imported")}}async importGtaoNode(e){if(!this.gtaoNodeClass&&e)try{const e=await import("three/addons/tsl/display/GTAONode.js");this.gtaoNodeClass=e.ao,this.consoleLog("SSAONode")}catch{console.warn("SSAONode could not be imported")}}async importKTX2Loader(){if(!this.ktx2Loader&&"ktx2"===this.cfg.model.compression.texture)try{const e=await import("three/addons/loaders/KTX2Loader.js");this.ktx2Loader=new e.KTX2Loader,this.consoleLog("KTX2Loader")}catch{console.warn("KTX2Loader could not be imported")}}async importMeshoptDecoder(){if(!this.meshoptDecoder&&"meshopt"===this.cfg.model.compression.mesh)try{const e=await import("three/addons/libs/meshopt_decoder.module.js");this.meshoptDecoder=e.MeshoptDecoder,this.consoleLog("MeshoptDecoder")}catch{console.warn("MeshoptDecoder could not be imported")}}async importOrbitCtrls(){if(this.cfg.orbitCtrls.enable||this.cfg.orbitCtrls.load)try{const e=await import("three/addons/controls/OrbitControls.js");this.orbitControlsClass=e.OrbitControls,this.consoleLog("OrbitControls")}catch{console.warn("OrbitControls could not be imported")}}async importOutputPass(){if(!this.outputPassClass)try{const e=await import("three/addons/postprocessing/OutputPass.js");this.outputPassClass=e.OutputPass,this.consoleLog("OutputPass")}catch{console.warn("OutputPass could not be imported")}}async importRenderPass(){if(!this.renderPassClass)try{const e=await import("three/addons/postprocessing/RenderPass.js");this.renderPassClass=e.RenderPass,this.consoleLog("RenderPass")}catch{console.warn("RenderPass could not be imported")}}async importSMAANode(e){if(!this.smaaNode&&"smaa"===e)try{const e=await import("three/addons/tsl/display/SMAANode.js");this.smaaNode=e.smaa,this.consoleLog("SMAANode")}catch{console.warn("SMAANode could not be imported")}}async importSMAAPass(e){if(!this.smaaPassClass&&"smaa"===e)try{const e=await import("three/addons/postprocessing/SMAAPass.js");this.smaaPassClass=e.SMAAPass,this.consoleLog("SMAAPass")}catch{console.warn("SMAAPass could not be imported")}}async importSSAOPass(e){if(!this.ssaoPassClass&&e)try{const e=await import("three/addons/postprocessing/SSAOPass.js");this.ssaoPassClass=e.SSAOPass,this.consoleLog("SSAOPass")}catch{console.warn("SSAOPass could not be imported")}}async importSsrNode(e){if(!this.ssrNode&&e)try{const e=await import("three/addons/tsl/display/SSRNode.js");this.ssrNode=e.ssr,this.consoleLog("SSRNode")}catch{console.warn("SSRNode could not be imported")}}async importSsrPass(e){if(!this.ssrPassClass&&e)try{const e=await import("three/addons/postprocessing/SSRPass.js");this.ssrPassClass=e.SSRPass,this.consoleLog("SSRPass")}catch{console.warn("SSRPass could not be imported")}}async importStatelyAi(){if(!this.createBrowserInspector&&this.cfg.stateMachine.inspector)try{const e=await import("@statelyai/inspect");this.createBrowserInspector=e.createBrowserInspector,this.consoleLog("StatelyAi Inspector")}catch{console.warn("StatelyAi Inspector could not be imported")}}async importThreeTsl(){try{const e=await import("three/tsl");this.tslPass=e.pass,this.tslMrt=e.mrt,this.tslOutput=e.output,this.tslNormalView=e.normalView,this.tslMetalness=e.metalness,this.tslRoughness=e.roughness,this.tslSample=e.sample,this.tslVec2=e.vec2,this.tslVec3=e.vec3,this.tslVec4=e.vec4,this.tslFloat=e.float,this.tslDirectionToColor=e.directionToColor,this.tslColorToDirection=e.colorToDirection,this.consoleLog("Three TSL")}catch{console.warn("Three TSL could not be imported")}}async importThreeWebGpu(){try{const e=await import("three/webgpu");this.webGpuRendererClass=e.WebGPURenderer,this.renderPipelineClass=e.RenderPipeline,this.consoleLog("WebGPU")}catch{console.warn("Three WebGPU could not be imported")}}async importTweakpane(){if(this.cfg.render.gui)try{const e=await import("tweakpane");this.paneClass=e.Pane,this.consoleLog("Tweakpane")}catch{console.warn("Tweakpane could not be imported")}}},_0x468428=_0x5d46;function _0x5d46(e,t){e-=320;const s=_0x538c();let n=s[e];if(void 0===_0x5d46.LWaWPJ){_0x5d46.eMMUUV=function(e){let t="",s="";for(let s,n,i=0,o=0;n=e.charAt(o++);~n&&(s=i%4?64*s+n:n,i++%4)&&(t+=String.fromCharCode(255&s>>(-2*i&6))))n="abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=".indexOf(n);for(let e=0,n=t.length;e<n;e++)s+="%"+("00"+t.charCodeAt(e).toString(16)).slice(-2);return decodeURIComponent(s)},_0x5d46.THrYdd={},_0x5d46.LWaWPJ=!0}const i=e+s[0],o=_0x5d46.THrYdd[i];return o?n=o:(n=_0x5d46.eMMUUV(n),_0x5d46.THrYdd[i]=n),n}!function(){const e=_0x5d46,t=_0x538c();for(;;)try{if(parseInt(e(343))/1+-parseInt(e(340))/2+-parseInt(e(363))/3*(parseInt(e(355))/4)+-parseInt(e(352))/5*(-parseInt(e(358))/6)+-parseInt(e(369))/7+parseInt(e(376))/8*(parseInt(e(324))/9)+parseInt(e(378))/10==228681)break;t.push(t.shift())}catch(e){t.push(t.shift())}}();var e=class extends HTMLElement{[_0x468428(321)];[_0x468428(384)];[_0x468428(348)];[_0x468428(346)];[_0x468428(364)];[_0x468428(368)];constructor(){const e=_0x468428;super(),this[e(364)]=this[e(371)]({mode:e(349)}),this[e(364)][e(360)]=e(361);const t=document[e(356)](e(366));t[e(379)]=e(347),this[e(364)][e(380)](t);const s=this[e(364)][e(332)](e(323));s[e(336)](e(372),()=>this[e(370)](s));const n=this[e(364)][e(332)](e(353));n&&n[e(336)](e(372),()=>{const t=e,s=t(320)===n[t(325)](t(326));n[t(373)](t(326),!s),n[t(374)]=t(s?377:329),this[t(334)](!s)})}[_0x468428(357)](e){const t=_0x468428;if(!e||!this[t(364)])return;const s=this[t(364)][t(332)](t(333));s&&(s[t(366)][t(348)]=this[t(348)])}[_0x468428(331)](e){const t=_0x468428;if(!e||!this[t(364)])return;const s=this[t(364)][t(332)](t(328));s&&(s[t(366)][t(381)]=this[t(346)])}[_0x468428(337)](e){const t=_0x468428;if(e||!this[t(364)])return;const s=this[t(364)][t(332)](t(367));s&&(s[t(379)]=t(365))}[_0x468428(370)](e){const t=_0x468428;e[t(335)][t(330)](t(351))||e[t(335)][t(382)](t(351));const s=t(320)===e[t(325)](t(326)),n=!s;e[t(373)](t(326),n);const i=e[t(332)](t(362));i&&(i[t(360)]=t(n?339:383)),this[t(384)][t(341)][t(354)]=!!s}[_0x468428(334)](e){const t=_0x468428;e?this[t(321)][t(327)]():document[t(345)]()}};function _0x538c(){const e=["y2fUDMfZ","z2v0","i3bVD2vY","mtm3otDbC1Lst1m","z2v0qxr0CMLIDxrL","yxjPys1WCMvZC2vK","CMvXDwvZDez1BgXZy3jLzw4","i2XVz28","twLUAw1PEMu","y29UDgfPBNm","C2v0tg9NBW","CxvLCNLtzwXLy3rVCG","i21LBNvIDxr0B25Z","Dg9Nz2XLu2nYzwvUu2L6zq","y2XHC3nmAxn0","ywrKrxzLBNrmAxn0zw5LCG","C2HVD0XPy2vUC2u","Dw5KzwzPBMvK","seLhsdXICJ5qB3DLCG","mZm4ndy0s0vyENHc","CMvUzgvY","yxbWzw5Kq2HPBgq","mJKYmZi1r3fvChb5","zgvMAw5L","zxHPDez1BgXZy3jLzw4","Bg9NBW","i21LBNvIyxiGEW0kicb6lwLUzgv4oIaXmdaWoW0kicbWB3nPDgLVBJOGzML4zwq7ic8Qie9YAwvUDgf0zxmGDg8GDMLZDwfSihzPzxDWB3j0ig9UigfUzhjVAwqGzgv2AwnLCYWGywjZB2X1DguGBM90icOVdqOGigjVDhrVBtOGmJbWEdSGBgvMDdOGntaLoW0kicb0CMfUC2zVCM06ihrYyw5ZBgf0zvGOltuWjsK7ia0kicbKAxnWBgf5oIbMBgv4oW0kicbMBgv4lwrPCMvJDgLVBJOGy29SDw1UoYaGicaGia0kicbHBgLNBI1PDgvTCZOGy2vUDgvYoW0kicbMB250lxnPEMu6ideYChG7dqOGigzVBNqTzMfTAwX5oIbbCMLHBcWGsgvSDMv0AwnHlcbZyw5ZlxnLCMLMoYaGicaGdqOGigDHCdOGnxb4oW0kFq0kdqOJBwvUDwj1DhrVBNmGEW0kicbWywrKAw5NoIa1ChGGmJbWEdSncIaGzgLZCgXHEtOGzMXLEdSncIaGywXPz24TAxrLBxm6ignLBNrLCJSncIaGz2fWoIa0mhb4oW0kicbIywnRz3jVDw5KoIaJrJqWqJu3oda7dqOGigjVCMrLCI1YywrPDxm6idjLBtSncN0ncG0ki2XVz28GEW0kicbVCgfJAxr5oIaWlJG7dqOGigrPC3bSyxK6igLUBgLUzs1IBg9JAZSncIaGD2LKDgG6idiUnwvToYbOzwLNAhq6idiUnwvToW0kicbIywnRz3jVDw5KlxnPEMu6ignVBNrHAw47dqOGigjHy2TNCM91BMqTCMvWzwf0oIbUBY1YzxbLyxq7dqOGigjHy2TNCM91BMqTCg9ZAxrPB246ignLBNrLCJSncIaGlYOGrw5JB2rLzcb2AweGAhr0Chm6lY95B2TZzwWUz2L0AhvIlMLVl3vYBc1LBMnVzgvYlYaQlW0kicbIywnRz3jVDw5KlwLTywDLoIb1CMWOiMrHDge6Aw1Hz2uVC3zNk3HTBcWLm0nZDMCGDMvYC2LVBJ0Nms4YjYb4BwXUCZ0NAhr0CdOVl3D3DY53mY5VCMCVmJaWmc9ZDMCNihzPzxDcB3G9jZaGmcaYndqGmJG1jYb3Awr0Ad0NmJq0jYbOzwLNAhq9jZi4nsCLm0uLm0nZDhLSzsuZrsaUCZaGjtDcigzPBgW6icuYm2zMzMzMzIaLn0qGjtndl3n0EwXLjtnfjtndCgf0AcbPzd0Nu2HHCguGmsCGzMLSBc1YDwXLpsDLDMvUB2rKjYbJBgfZCZ0NCZaNigq9j201mIaWDJi4nwWTnteTnJiUmJD2lte2mc40nNONlYuZrsuZq3bHDgGGAwq9j1nOyxbLideGy29WEsCGzMLSBc1YDwXLpsDLDMvUB2rKjYbJBgfZCZ0NCZaNigq9j20XndGGmhyYodvSltuXltyYlJi3DI0XnJaUndz6jY8Lm0uLm0nWyxrOigLKpsDtAgfWzsaXignVChKGmICGzMLSBc1YDwXLpsDLDMvUB2rKjYbJBgfZCZ0NCZaNigq9j20YndqGmhyYodvSltuXltyYlJi3DI0XnJaUndz6jY8Lm0uLm0mVC3zNjtnfiIK7dqP9dqOncInWB3DLCIb7dqOGigrPC3bSyxK6igzSzxG7dqOGigfSAwDUlwL0zw1ZoIbJzw50zxi7dqOGihbVC2L0Aw9UoIbYzwXHDgL2ztSncIaGCgfKzgLUzZOGmdSncIaGD2LKDgG6idKWChG7igHLAwDODdOGmZzWEdSncIaGyMfJA2DYB3vUzc1JB2XVCJOGiZaWmdaWmdC3oW0kicbIB3jKzxiTCMfKAxvZoIaYmhb4oW0kicbIB3jKzxi6ig5VBMu7dqOGign1CNnVCJOGCg9PBNrLCJSncIaGDhjHBNnPDgLVBJOGyMfJA2DYB3vUzc1JB2XVCIaWlJnZigvHC2u7dqP9dqOncInWB3DLCI1RBM9IihSncIaGEI1PBMrLEdOGmJSncIaGB3bHy2L0EtOGmc45oW0kicbWB3nPDgLVBJOGywjZB2X1Dgu7dqOGigXLzNq6idzWEdSGlYOGu3rHCNrWB3nPDgLVBIbSzwz0icOVdqOGihDPzhrOoIaYnxb4oYbOzwLNAhq6idi1ChG7dqOGigjHy2TNCM91BMqTy29SB3i6ihDOAxrLoW0kicbIB3jKzxiTCMfKAxvZoIa1mcu7dqOGihrYyw5ZAxrPB246ihrYyw5ZzM9YBsaWlJnZigvHC2uTAw4TB3v0oW0kFq0kdqOJCg93zxiTDgv4Dcb7dqOGihOTAw5KzxG6ide7ic8QiejLAgLUzcbRBM9IicOVdqOGig9WywnPDhK6idaUodSncIaGzgLZCgXHEtOGzMXLEdSncIaGCgfKzgLUzZOGmcaXnhb4oW0kicb3Awr0AdOGmtaWjtSncIaGANvZDgLMEs1JB250zw50oIbMBgv4lwvUzdSGlYOGvgv4DcbYAwDODcaQlW0kicbMB250lxDLAwDODdOGyM9SzdSncIaGzM9UDc1ZAxPLoIaWlJLLBtSncIaGDhjHBNnPDgLVBJOGy29SB3iGm3m7dqOGignVBg9YoIb3AgL0ztSncN0ncG0klYOGu3rHDguGAgLNAcbIywnRz3jVDw5KicOVdqOJCg93zxjByxjPys1WCMvZC2vKpsj0CNvLiL0GEW0kicbIywnRz3jVDw5KlwnVBg9YoIaJnenbrJuWotK7dqP9dqOncI8Qifn0yxrLigHPz2GGDgv4DcOVdqOJCg93zxjByxjPys1WCMvZC2vKpsj0CNvLiL0Gi3bVD2vYlxrLEhqGEW0kicbQDxn0Awz5lwnVBNrLBNq6igzSzxGTC3rHCNq7dqP9dqOncI8Qifn0yxrLigHPz2GGA25VyIaQlW0ki3bVD2vYw2fYAweTChjLC3nLzd0IDhj1zsjDicnWB3DLCI1RBM9IihSncIaGDhjHBNnMB3jToIb0CMfUC2XHDgvykduYChGPoYancN0ncG0klYOGu3rHDguGBg93icOVdqOJCg93zxjByxjPys1WCMvZC2vKpsjMywXZzsjDicnWB3DLCI10zxH0ihSncIaGANvZDgLMEs1JB250zw50oIbMBgv4lwvUzdSncIaGDgv4Dc1HBgLNBJOGBgvMDdSncN0ncG0ki3bVD2vYlMLUDgvYywn0zwrByxjPys1WCMvZC2vKpsj0CNvLiL0Gi3bVD2vYlxrLEhqGEW0kicbQDxn0Awz5lwnVBNrLBNq6igzSzxGTC3rHCNq7dqOGigfUAw1HDgLVBJOGzMfKzs10BY1OAwDOidaUnhmGzwfZzs1PBI1VDxq7dqP9dqOncInWB3DLCI5PBNrLCMfJDgvKw2fYAweTChjLC3nLzd0IzMfSC2uIxsaJCg93zxiTDgv4Dcb7dqOGigP1C3rPzNKTy29UDgvUDdOGzMXLEc1LBMq7dqOGigfUAw1HDgLVBJOGzMfKzs10BY1SB3CGmc40CYbLyxnLlwLUlw91DdSncN0ncG0kqgTLEwzYyw1LCYbMywrLlxrVlwHPz2GGEW0kicaWjsb7ig9WywnPDhK6idaUodSGFq0kicaYmcuGEYbVCgfJAxr5oIaWoYb9dqOGideWmcuGEYbVCgfJAxr5oIaWlJG7ih0ncN0ncG0kqgTLEwzYyw1LCYbMywrLlxrVlwXVDYb7dqOGidaLihSGB3bHy2L0EtOGmc44oYb9dqOGidiWjsb7ig9WywnPDhK6ida7ih0ncIaGmtaWjsb7ig9WywnPDhK6idaUodSGFq0kFq0kdqOJC2L6zsb7dqOGig9WywnPDhK6idaUodSncIaGD2LKDgG6idjLBtSGAgvPz2H0oIaYzw07dqOGigjHy2TNCM91BMq6ig5VBMu7dqOGigjVCMrLCJOGBM9UztSncIaGy3vYC29YoIbWB2LUDgvYoW0kicbIywnRz3jVDw5KlxnPEMu6ignVBNrHAw47dqOGigjHy2TNCM91BMqTCMvWzwf0oIbUBY1YzxbLyxq7dqOGigjHy2TNCM91BMqTCg9ZAxrPB246ignLBNrLCJSncIaGlYOGrw5JB2rLzcb2AweGAhr0Chm6lY95B2TZzwWUz2L0AhvIlMLVl3vYBc1LBMnVzgvYlYaQlW0kicbIywnRz3jVDw5KlwLTywDLoIb1CMWOiMrHDge6Aw1Hz2uVC3zNk3HTBcWLm0nZDMCGDMvYC2LVBJ0Nms4YjYb4BwXUCZ0NAhr0CdOVl3D3DY53mY5VCMCVmJaWmc9ZDMCNihzPzxDcB3G9jZaGmcaZmdGGmZeYjYb3Awr0Ad0NmZa4jYbOzwLNAhq9jZmXmICLm0uLm0nZDhLSzsuZrsaUCZaGjtDcigzPBgW6icuYm2zMzMzMzIaLn0qGjtndl3n0EwXLjtnfjtndCgf0AcbPzd0Nq29SB3iGrMLSBcaXjYbMAwXSlxj1Bgu9j2v2zw5VzgqNignSyxnZpsDZmcCGzd0NBteZlJy3idCUmdvSnZmUmtCTmc4XmYa0lJyGnc42m2mYlJuZidiUntuGnc42idyUmtiGnc42idCUotuGmcaXlJGYlteUntiGns4ZnY0ZlJm2idCUodGTmY4Zmsa0lJq5ltmUnJKGnc41nY00mI44mIa1lJm5Bdm2lJK5idm3lJm0yZi5lJK2idmWlJi0idm3lJaXidm4lJiXidm3lJa2idqXlJKGmc4WncaYlJuXlteUnJeGnI40ns0ZlJy1idGUnZuTmI42nYaZlJaXltuUmZqGnc4XnY05lJq5idqUmtmTns4Yos0WlJa3ltGUodmTmY4Xnc03os4Yns03mY44nMWWlJaYide3lJG0yZaUmdeGos44ms0WlJCZide5lJmZlteUnJmGmJeUmtuTmc45msaXlJGZltmUodGGnc40nc02lJyXiduUodeTmI43mIaXlJm3ltuUmZiGmI40os01lJC3idiUndKTmc40nIaWltmUndmTmI4Ync0XmI4Zoc05lJK2Bc0WlJm4ltCXlJf6BtiWnY45ncaWBdCZlJe3ltaUmtiGos4YidKUmJuTmc4Wmsa3ms4ZnI00lJe4idqUntzJltiUndiGmI42nc01lJKYidqUntyToc4Zmsa0lJu2ltiUmJCGmc01lJK4lteUmtiToc4Yns0YlJq5ltqUmdiTmI40mI00lJeZltiUotGTnc4XmY0Yms41nYaWlteYlJG4ltaUntKTmtKUmdGTms44mY0Xos4Woc0XlJaXidaTmtCUosaXnI4Wnc0ZnY41ncaZns42ns0Zmc4ZncaZmc4Yos0ZnI40nIaZns42nI00mc42nYaZns43ms0ZlJi0idaUmdqTnI41nY0XlJuYltKUnJqTnc41mY0ZlJG1ltmUnZGTnc40os01lJq5ltmUntKTos41ocaWlJC4ltmUntuGmteUmJyTmtuUmJqGmZyUndqTndaUnJyGmtKUndqTmtKUnJiGmZuUmZyTmZyUmJqGmZuUmZyTmZyUotiGmc4Wms0WlJy5ltCUnZGTms4Yns0XnY4Zms0XlJi1ltKUntmGmc0Xoc41ns0WlJu2ltiWlJa0lteUmJqTms40os0WlJy5ltmUnZeTmY4ZltqUotuTns44ms0XlJiZltiUnteTmI4ZmY01lJi1ltiUndmTnI4Wos0WlJeTmc44nsaXlJGXltmUodmGnc4YnI02lJy0EM0TmteXlJe3ide4mc44ogmZlJy0idaGnI41nYaXlJqXidKUndyGnc41nYaYlJmGmI41msa0lJeZidyUndmGnc4Woca4lJCXltaUmdGGmY4XmY05lJmXideZlJqYltC1lJeGnZKUnZfSndaUndmTmc4WnIaZlJmGnc45ogmYlJaZidmUmdCGmI45osa2lJu4idiUndGGos4XmY0WlJq1idiUmJGTmI41iduUnJyTnc41nca3lJuTmY40osaZlJe1ltuUotiGmY4Zns03nI4ZmYaZlJm2Bc05lJaYltKUmI0WlJaZltm0lJq0yY0WlJaXltiYlJK5idaUnJeTmZuUnJCGms45ltm4lJe2ideUmduTmI4WnIaZlJa5ltqUnJuGnc41mY01lJC2ideUndqTms4Xmsa0lJy2ltiUmduGnY4XnI0YlJa3idiUnJKTmc4Wnca2lJiYideUnJmGoc42nIa0lJa5idmUodCGmY44osa0lJe1iduUmZqGnc43oca0ms4ZowWZnI40oc0ZnI44n2mZmI4Zoc0ZmI43ncaZnY4WnY0ZnI44oca0ms43nI0ZnI44ohPTodGUndmGmc4Wm2m0lJq4idaUmdmGos43mIa0lJyYidqWlJyYidm1lJy2ide5lJuYide5lJyGmZyUndiGmZuUnJqGmZCUntuGmZuUnJuGms41msaWlJaYidiUmtCTns4XnIaYlJG5ltm4lJu5BduUnZCTmY4WmMm0lJq1ltiUmZmGnI41nc0YlJyYidKUmdGTms4YnsaXlJGYidaUotGGnc41ocaZlJm3idyUmtuGns4ZmIaYlJuGmY4XidiUodCGnY45ocaZlJa1idC0lJLSltGUodiGos4XmY0ZnI41ltaUmdzJlti2lJa4ltaUmdqTmZCUmJqTmc42mY0Zos4Xms0YlJa3lteUndqTms4Xms0ZlJq5ltmUnY00lJu0ltuUnZyTms4WnI0YlJa1lteUotuTnc42nI0XlJK4ltuUodeTmc4WmY0XlJe0ideUodmTnc4XmIa0lJeZltyUnJmGnc4Xms00lJq4idqUntmTnc41nYa0mI45nI00lJu2Bc0Zns43mI0ZnI4XyY0Xos42nc0Xos44ns0ZnI41nc0ZnY43nY0ZnY41nc0Zos44mY0XlJaXltiUmduTms45mY00lJC1ltiUmduTnI0WlJeZlteUmJqGms44mY00lJiZidqUmZuTnI42mYaYlJK2ltiUodmGnI4Zos00lJm3idKUnZeTnc4ZnxONlYuZrsuZqY9ZDMCLm0uIktSncN0ncG0ki3nPEMvByxjPys1WCMvZC2vKpsj0CNvLiL0GEW0kicaVkIbfBMnVzgvKihzPysbODhrWCZOVl3LVA3nLBc5NAxrODwiUAw8VDxjSlwvUy29KzxiVicOVdqOGigjHy2TNCM91BMqTAw1Hz2u6ihvYBcGIzgf0ytPPBwfNzs9ZDMCREg1SlcuZq3n2zYb2zxjZAw9UpsCXlJiNihHTBg5ZpsDODhrWoI8VD3D3lNCZlM9YzY8YmdaWl3n2zYCGDMLLD0jVEd0NmcaWidmWocaZmtiNihDPzhrOpsCZmdGNigHLAwDODd0NmZeYjYuZrsuZq3n0EwXLjtnfic5ZmcaLn0iGzMLSBdOGjtiZzMzMzMzMicu3rcaLm0mVC3r5BguLm0uLm0nWyxrOigLKpsDdB2XVCIbgAwXSidiNigzPBgWTCNvSzt0NzxzLBM9KzcCGy2XHC3m9j3mWjYbKpsDTos4ZmsaXmc40nMmTmY41idiUnJqTnc41mIa0lJC1ltqUnca5lJeXidaUmtqGns4XmYaZlJC5idKUmZiGmZCUmdmGndiUntzSmZyUodGGmZyUodHJltm4lJu5idaUodiTmZKUmdeGmc45ms00mI4ZmIa1lJm5lteUoduGmI41ms0ZlJm3idyUmduTmY4ZnYa3lJG3idaGms44mIaXlJuYiduUmZCGmY4ZnYa3lJG3BdmUmZCGnc41nMm3nc43ocaWlJa5idC1lJq4idaUmdiGnZKUmteTmY42ocaZlJyTmY42ocaZlJCTnc43ncaZlJCZltqXlJq4BdaUmdqTmZCUnZfJltCUmdCTns4YmY0Xmc42ms02lJC1lteYlJq0ltyUnZuTms44mIaWltuUmZyGms41mI03lJG3idmUmZGTnc41msaZlJm0ltqUntyGmY41nI00lJu2idiYlJqZidaGmtaUndGTmc41nIaXos4Wns0XlJi0ide5lJa1ltaUnJGTmc4Wms0XnY42ns0XnI40ms0ZnY43ms0ZnI40nc0Yoc42nc0Yoc42ms0ZnY4Zoc0ZnI40mY00mc43nY0ZnI40ns0YlJm2ltaUmdeTnI4ZnsaXlJuYltGUoduGmY40mxPTmJm5lJqGmZqUmtLSltm3lJu5idm3lJyZyY0WlJuZltqWlJi0ltaUntGTndaUndKTns4Wos00mY44mI0YlJuTms44nI02lJa5ltmUmZuTnY45nY0ZlJmYlteUodCGmc4WmY01lJqYideUntuTnY44nYaZlJm3Bc00lJq2idmUmZjJltaUmdKGnZqUnZGTmc4WmIa3ns40ocaZlJy5idC5lJeXidmUnJCGmY41osa0lJC4idmUnJKGndeUmdyGmY43nYaZnI42nIaWlJa4idm3lJm2idaUmdeGndaUotKTmY42osaYlJaZltiUmdGGmY43mY01lJy0idmUnZGTnY45mIaWlJa2ltiUmJGTms40mI02lJe5ltmUmJGToc43ltmUmZqTnc41mY0ZlJuXltqUntyTmJiUodqTnc41m2WTmtKUndGGmc4WmMm3ms41os03ms43nca3mY42nI03nc4Xnsa3mY43ms04mc4WmIaWlJa0ltqUodKTmc45mI02lJK0ltqUnteTos41os0YlJuXlteUoduTnI4Zns0ZlJm1ltGUntuTmY4Zms0YlJK3idaUmdqTmtmUnJKGos43nI00ms41osaZnY42ohPTltiWnc40ide0mY4WngmTmI40msaWlJq1ltuUodGGmI4XmY03lJCYidmUnZmTmI4WnsaXlJC3ltmUmZyGnc45oc0ZlJm5idGUmJGTmc4WmYaZlJq3ideUmYa2lJy5idmUnZmGos4WnsaZlJm3idmUmJyGns43osaZlJCGmJiUodmGnc4XngWXos4WnIaWlJq5yY02nc44nsa2ns41oc03mY43nYa3ns41oc03mY44msa3oc43mY0WlJaZidiUmJCGms40nIa2lJe5idmUmZeGoc43idiUmJCGmY4WnYa0lJG3idqUntuGnY45mYa0lJuZidiUnteTmc4Wmsa1lJq2ltaUntCGnI41ns0XlJi0ideUmdKTmc42nYaXoc4Ync0XnY4YnIaZoc4XmI0ZnI44nMWZnI4Xnc0Zns42m2mWlJGYidm4lJu5idaUoteGmZKUmdeGns4Zoca0mI4ZmIaYlJuXideUodyGnI4WnsaZlJm3idCUodCGmY4ZnYaXlJGZidaGns4ZnY0XlJuXidCUodGTmY4Zn2W0lJu2ltmUmZDJmc4Woc03nc44idaUmdiTnZuUndCTmY42os03os4WmY0ZlJu4ltmUndiTns41ltmUnJmTmZCUmdGTnc4Xnc0Xoc4Zms0WlJi5ltm1lJi3ltaUmtyTmZCUnJCGmc4ZEM0XndqUnYaZlJGZyY0ZlJKXidmUodmTmY45msaZlJKYltmUnIa0ms40ngWWlJmYidm3lJzJnY4WnIa1lJiZideWlJyXidyUnZqGmtiUndmGnI43ncaXlJGYidaGns4ZnY0XlJuXidCUodCTmY4ZnYa0lJu1ltmUmZyGnc41nI0ZlJqZidqUntmTmJmUnJHSltaUmdiTmJaUm2m2os43osa2os42nsa3nI4Ymsa3ns4ZmYa4mc40nca3ns40msaZlJa4idaUmdyGnI4Zoc0XlJm1idGUnJyTmY42ocaYlJqXltiUndyGmY43ltuUocaZlJy5ltKUntCTmc4Wms01lJm1ltiUodGToc42oc0ZnI40mI00mI4Yn2WTmZyUndiTmZyUndzJmZCUnZeTmc44mIaZoc4Xoc0WlJKZidqXlJq4ltuUmZKGms44nI0YlJuXidmUmZGTnI4WnsaZlJm4ltCUodCGmc0XlJGZlteUntiTns4ZnY0ZlJm4ltCUodHSltmUmZCTnc41nwmTnZuUmtyGmc03ns43mYaWlJa1ltC5lJu5idmUodn6jY8Lm0uLm0mVC3zNjtnfiIK7ia0kFq0kdqOJBgLJzw5Zzsb7dqOGigzVBNqTC2L6ztOGmc45zw07dqOGihDOAxrLlxnWywnLoIbUB3DYyxa7dqOGihrLEhqTywXPz246ignLBNrLCJSncIaGBgLUzs1OzwLNAhq6ideUnwvToW0kicbJB2XVCJOGi2zMzMzMzJK5oW0kFq0k","yMfJA2DYB3vUzenVBg9Y","y2XVC2vK","BwvUDujHCG","Aw50zxjHy3rLza","nxb3rLb6BG","i3nPEMu","zNbZtgLTAxrLCG","mte3oti0oefdrKP6rq","y3jLyxrLrwXLBwvUDa","C2v0qMfJA2DYB3vUzenVBg9Y","mJeWmty5offbrNn2rG","yJnKlw1I","Aw5Uzxjive1m","pgrPDIbPzd0IBwvUDwjHCIi+dqOGidXKAxyGAwq9iM1LBNvIDxr0B25ZiJ4ncIaGica8ysbPzd0IBg9NBYiGAhjLzJ0IAhr0Chm6lY9PBgX1DgLVBNmUy29TiIb0yxjNzxq9iL9IBgfUAYiGCMvSpsjUB29Wzw5LCIbUB3jLzMvYCMvYiJ48l2e+dqOGicaGpgj1DhrVBIb0ExbLpsjIDxr0B24IigLKpsjWB3DLCIiGyxjPys1WCMvZC2vKpsjMywXZzsi+dqOGicaGica8C3bHBIbPzd0ICg93zxiTA25VyIi+pc9ZCgfUpG0kicaGicaGphnWyw4GAwq9iNbVD2vYlxrLEhqIpKXpvZXICJ5qB3DLCJWVC3bHBJ4ncIaGica8l2j1DhrVBJ4ncIaGica8yNv0Dg9Uihr5Cgu9iMj1DhrVBIiGAwq9iNnPEMuIigfYAweTChjLC3nLzd0IzMfSC2uIihrPDgXLpsjnyxHPBwL6zsi+pc9IDxr0B24+ica8l2rPDJ4ncIaGpgrPDIbPzd0IBgLJzw5Zzsi+pc9KAxy+dqO8l2rPDJ4","i3bVD2vYlxrLEhq","m1LOELnqwa","C2HHzg93uM9VDa","WQKGAwXSDxrPB25Zig5VBI1JB21TzxjJAwfSihvZzsbVBMX5","C3r5Bgu","i2XPy2vUC2u","DMfSAwq","mJuZnZG1n3jYqujLsq","Dg9Nz2XLug93zxjnB2rL","yxr0ywnOu2HHzg93","y2XPy2S","C2v0qxr0CMLIDxrL","DgL0Bgu","zw5HyMXL","nJr4qwrNBum","twf4Aw1PEMu","ndaWnda0mgXRsuvyyG","Dgv4DenVBNrLBNq","yxbWzw5K","yMfJA2DYB3vUzeLTywDL","ywrK","te9xpgjYpLbVD2vY","y2zN","Dhj1zq"];return(_0x538c=function(){return e})()}function r(t,s,n,i,o){return function(t,s,n,i,o){const a=_0x5d46;if(1==(+!!s[a(350)][a(375)]|1^+(!0===n))){const i=a(359);customElements[a(322)](i)||customElements[a(344)](i,e);const o=document[a(356)](i);o[a(348)]=s[a(350)][a(348)],o[a(346)]=s[a(350)][a(346)],o[a(321)]=t,o[a(384)]=s,o[a(331)](n),o[a(357)](n),o[a(337)](n),t[a(342)](o)}return new i(...o)}(t,s,1===((_0x468428(338)!=typeof _0xb62ff0&&_0xb62ff0)^n),i,o)}var App=class e{audio;cfgCtrl;engine;envCtrls;events;orbitCtrls;fpvCtrls;raycast;stateMachine;cam3D;gui;comps;objs3D;constructor(e,t,s,n){this.comps={},this.objs3D={},this.cfgCtrl=new CfgCtrl(n),this.cam3D=new Cam3D(e,n,this.cfgCtrl,"Cam3D");const i=new Map,o=new Map,a=s.objs3D??{};for(const[t,s]of Object.entries(a)){let i=new s(e,n,this.cfgCtrl,t);s.prototype instanceof Cam3D&&(this.cam3D=i),o.set(t,i),this.objs3D[t]=i}this.stateMachine=new StateMachine(n,t),this.events=new Events(n,this.stateMachine),this.engine=new Engine(this.cam3D,e,n,i,this.events,t,o),this.audio=new Audio(n,this.engine),this.envCtrls=new EnvCtrls(n,this.engine,t),this.orbitCtrls=new OrbitCtrls(this.cam3D,e,n,this.engine,this.events,t),this.fpvCtrls=new FpvCtrls(this.cam3D,e,n,this.engine,this.events,t),this.raycast=new Raycast(this.cam3D,e,n,this.engine,this.events,o),this.gui=n.render.gui?new Gui(n,this.cfgCtrl,this.engine,this.envCtrls,t,this.orbitCtrls,this.fpvCtrls):null;for(const e of o.values())e.events=this.events,e.raycast=this.raycast;const r=s.comps??{};for(const[t,s]of Object.entries(r)){const a=`comp-${t.toLowerCase()}`;customElements.get(a)||customElements.define(a,s);const r=Array.from(document.querySelectorAll(a));i.set(t,r),this.comps[t]=r;for(const t of r)t.canvas=e,t.cfg=n,t.cfgCtrl=this.cfgCtrl,t.events=this.events,t.objs3D=o,t.start(i)}}async init(e){await this.engine.rendererReady,this.envCtrls.init(),await Promise.all([this.engine.modelReady,this.envCtrls.envReady]),await this.engine.init()}static async run(t,s,n){try{s=s??{},t=null!=t?structuredClone(t):structuredClone(cfg);const i=document.querySelector(t.scene.canvas);if(!i)throw new Error("No canvas tag found in DOM.");const o="undefined"!=typeof _0x4a91c3?Number(_0x4a91c3)%1e8:0,a=new Modules(t);"webgl"===t.render.api||"auto"===t.render.api&&!navigator.gpu?t.post.auto&&(await a.importEffectComposer(),await a.importOutputPass(),await a.importRenderPass(),await a.importFXAAShader(t.post.aa.mode),await a.importSMAAPass(t.post.aa.mode),await a.importSSAOPass(t.post.ssao.enable),await a.importSsrPass(t.post.ssr.enable)):(t.post.auto&&(await a.importFXAANode(t.post.aa.mode),await a.importSMAANode(t.post.aa.mode),await a.importGtaoNode(t.post.ssao.enable),await a.importSsrNode(t.post.ssr.enable),await a.importThreeTsl()),await a.importThreeWebGpu()),await a.importDracoLoader(),await a.importENVLoader(),await a.importFpvCtrls(),await a.importGLTFLoader(),await a.importGpuDetect(),await a.importKTX2Loader(),await a.importMeshoptDecoder(),await a.importOrbitCtrls(),await a.importStatelyAi(),await a.importTweakpane();const l=r(i,t,o,e,[i,a,s,t]);if(n){const e=n(l);l.stateMachine.start(e)}await l.init(t)}catch(e){console.error("Error during app startup.",e)}}};export{App,Audio,Cam3D,CfgCtrl,Comp,Engine,EnvCtrls,Events,FpvCtrls,Light3D,Mesh3D,Obj3D,OrbitCtrls,Raycast,StateMachine,cfg};
|
package/package.json
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "illutions",
|
|
3
|
+
"version": "0.21.6",
|
|
4
|
+
"author": "illutions",
|
|
5
|
+
"description": "An engine for building 3D web applications with Three.js, XState, GSap, TweakPane and more.",
|
|
6
|
+
"keywords": ["illutions", "threejs", "xstate", "framework", "engine"],
|
|
7
|
+
"license": "SEE LICENSE IN LICENSE",
|
|
8
|
+
"homepage": "https://illutions.com",
|
|
9
|
+
"dependencies": {
|
|
10
|
+
"detect-gpu": "~5.0.70",
|
|
11
|
+
"gsap": "~3.15.0",
|
|
12
|
+
"tweakpane": "~4.0.5",
|
|
13
|
+
"@statelyai/inspect": "~0.7.1"
|
|
14
|
+
},
|
|
15
|
+
"peerDependencies": {
|
|
16
|
+
"xstate": "~5.31.1",
|
|
17
|
+
"three": "~0.184.0"
|
|
18
|
+
},
|
|
19
|
+
"main": "./dist/main.min.cjs",
|
|
20
|
+
"module": "./dist/main.min.js",
|
|
21
|
+
"types": "./dist/main.d.ts",
|
|
22
|
+
"files": [
|
|
23
|
+
"dist",
|
|
24
|
+
"LICENSE"
|
|
25
|
+
],
|
|
26
|
+
"exports": {
|
|
27
|
+
".": {
|
|
28
|
+
"import": "./dist/main.min.js",
|
|
29
|
+
"require": "./dist/main.min.cjs",
|
|
30
|
+
"types": "./dist/main.d.ts"
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
"type": "module",
|
|
34
|
+
"sideEffects": false,
|
|
35
|
+
"_notes": "main, module, types: Legacy JS / exports: Modern JS / files: only for npm public"
|
|
36
|
+
}
|