@polarfront-lab/ionian 1.5.0 → 1.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -109,6 +109,8 @@ export declare class ParticlesEngine {
109
109
  getObject(): THREE.Mesh;
110
110
  getMeshIDs(): string[];
111
111
  getMatcapIDs(): string[];
112
+ getMeshes(): THREE.Mesh<THREE.BufferGeometry<THREE.NormalBufferAttributes>, THREE.Material | THREE.Material[], THREE.Object3DEventMap>[];
113
+ getTextures(): THREE.Texture[];
112
114
  /**
113
115
  * Disposes the resources used by the engine.
114
116
  */
@@ -1,2 +1,2 @@
1
- var ionian=function(e,t,i){"use strict";var s=Object.defineProperty,r=(e,t,i)=>((e,t,i)=>t in e?s(e,t,{enumerable:!0,configurable:!0,writable:!0,value:i}):e[t]=i)(e,"symbol"!=typeof t?t+"":t,i);function n(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e)for(const i in e)if("default"!==i){const s=Object.getOwnPropertyDescriptor(e,i);Object.defineProperty(t,i,s.get?s:{enumerable:!0,get:()=>e[i]})}return t.default=e,Object.freeze(t)}const a=n(t),o=e=>e;class u{constructor(){var e;r(this,"emitter",{all:e=e||new Map,on:function(t,i){var s=e.get(t);s?s.push(i):e.set(t,[i])},off:function(t,i){var s=e.get(t);s&&(i?s.splice(s.indexOf(i)>>>0,1):e.set(t,[]))},emit:function(t,i){var s=e.get(t);s&&s.slice().map((function(e){e(i)})),(s=e.get("*"))&&s.slice().map((function(e){e(t,i)}))}})}emit(e,t){this.emitter.emit(e,t)}off(e,t){this.emitter.off(e,t)}on(e,t){this.emitter.on(e,t)}once(e,t){this.emitter.on(e,(i=>{this.emitter.off(e,t),t(i)}))}dispose(){this.emitter.all.clear()}}function h(e,t){const i=new a.DataTexture(e,t,t,a.RGBAFormat,a.FloatType);return i.needsUpdate=!0,i}function c(e){e.geometry.dispose(),e.material instanceof a.Material?e.material.dispose():e.material.forEach((e=>e.dispose()))}function l(e,t,i){return e=Math.min(e,i),e=Math.max(e,t)}class d{constructor(e){r(this,"serviceState","created"),r(this,"eventEmitter"),r(this,"meshes",new Map),r(this,"textures",new Map),r(this,"gltfLoader",new i.GLTFLoader),r(this,"textureLoader",new a.TextureLoader),r(this,"dracoLoader",new i.DRACOLoader),r(this,"solidColorTexture",new a.DataTexture(new Uint8Array([127,127,127,255]),1,1,a.RGBAFormat)),this.eventEmitter=e,this.dracoLoader.setDecoderPath("https://www.gstatic.com/draco/versioned/decoders/1.5.7/"),this.gltfLoader.setDRACOLoader(this.dracoLoader),this.updateServiceState("ready")}register(e,t){if(t.name=e,t instanceof a.Mesh){const i=this.meshes.get(e);i&&c(i),this.meshes.set(e,t)}else{const i=this.textures.get(e);i&&i.dispose(),this.textures.set(e,t)}this.eventEmitter.emit("assetRegistered",{id:e})}setSolidColor(e){this.changeColor(e)}getSolidColorTexture(){return this.solidColorTexture}getMesh(e){return this.meshes.get(e)??null}getMatcap(e){const t=this.textures.get(e);return t||this.eventEmitter.emit("invalidRequest",{message:`texture with id "${e}" not found. using solid color texture instead...`}),t??this.solidColorTexture}getMeshIDs(){return Array.from(this.meshes.keys())}getTextureIDs(){return Array.from(this.textures.keys())}getMeshes(){return Array.from(this.meshes.values())}getTextures(){return Array.from(this.textures.values())}hasMatcap(e){return this.textures.has(e)}async loadMeshAsync(e,t,i={}){const s=await this.gltfLoader.loadAsync(t);try{if(i.meshName){const t=s.scene.getObjectByName(i.meshName);return this.register(e,t),t}{const t=s.scene.children[0];return this.register(e,t),t}}catch(r){return this.eventEmitter.emit("invalidRequest",{message:`failed to load mesh: ${e}. ${r}`}),null}}async loadTextureAsync(e,t){try{const i=await this.textureLoader.loadAsync(t);return this.register(e,i),i}catch(i){return this.eventEmitter.emit("invalidRequest",{message:`failed to load texture: ${e}. ${i}`}),null}}dispose(){this.updateServiceState("disposed"),this.meshes.forEach((e=>c(e))),this.meshes.clear(),this.textures.forEach((e=>e.dispose())),this.textures.clear()}changeColor(e){const t=new a.Color(e);this.solidColorTexture=new a.DataTexture(new Uint8Array([t.r,t.g,t.b,255]),1,1,a.RGBAFormat),this.solidColorTexture.needsUpdate=!0}updateServiceState(e){this.serviceState=e,this.eventEmitter.emit("serviceStateUpdated",{type:"asset",state:e})}}const m=new t.Triangle,g=new t.Vector3,p=new t.Vector2,v=new t.Vector2,x=new t.Vector2;class T{constructor(e){this.geometry=e.geometry,this.randomFunction=Math.random,this.indexAttribute=this.geometry.index,this.positionAttribute=this.geometry.getAttribute("position"),this.normalAttribute=this.geometry.getAttribute("normal"),this.colorAttribute=this.geometry.getAttribute("color"),this.uvAttribute=this.geometry.getAttribute("uv"),this.weightAttribute=null,this.distribution=null}setWeightAttribute(e){return this.weightAttribute=e?this.geometry.getAttribute(e):null,this}build(){const e=this.indexAttribute,t=this.positionAttribute,i=this.weightAttribute,s=e?e.count/3:t.count/3,r=new Float32Array(s);for(let o=0;o<s;o++){let s=1,n=3*o,a=3*o+1,u=3*o+2;e&&(n=e.getX(n),a=e.getX(a),u=e.getX(u)),i&&(s=i.getX(n)+i.getX(a)+i.getX(u)),m.a.fromBufferAttribute(t,n),m.b.fromBufferAttribute(t,a),m.c.fromBufferAttribute(t,u),s*=m.getArea(),r[o]=s}const n=new Float32Array(s);let a=0;for(let o=0;o<s;o++)a+=r[o],n[o]=a;return this.distribution=n,this}setRandomGenerator(e){return this.randomFunction=e,this}sample(e,t,i,s){const r=this.sampleFaceIndex();return this.sampleFace(r,e,t,i,s)}sampleFaceIndex(){const e=this.distribution[this.distribution.length-1];return this.binarySearch(this.randomFunction()*e)}binarySearch(e){const t=this.distribution;let i=0,s=t.length-1,r=-1;for(;i<=s;){const n=Math.ceil((i+s)/2);if(0===n||t[n-1]<=e&&t[n]>e){r=n;break}e<t[n]?s=n-1:i=n+1}return r}sampleFace(e,t,i,s,r){let n=this.randomFunction(),a=this.randomFunction();n+a>1&&(n=1-n,a=1-a);const o=this.indexAttribute;let u=3*e,h=3*e+1,c=3*e+2;return o&&(u=o.getX(u),h=o.getX(h),c=o.getX(c)),m.a.fromBufferAttribute(this.positionAttribute,u),m.b.fromBufferAttribute(this.positionAttribute,h),m.c.fromBufferAttribute(this.positionAttribute,c),t.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)),void 0!==i&&(void 0!==this.normalAttribute?(m.a.fromBufferAttribute(this.normalAttribute,u),m.b.fromBufferAttribute(this.normalAttribute,h),m.c.fromBufferAttribute(this.normalAttribute,c),i.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)).normalize()):m.getNormal(i)),void 0!==s&&void 0!==this.colorAttribute&&(m.a.fromBufferAttribute(this.colorAttribute,u),m.b.fromBufferAttribute(this.colorAttribute,h),m.c.fromBufferAttribute(this.colorAttribute,c),g.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)),s.r=g.x,s.g=g.y,s.b=g.z),void 0!==r&&void 0!==this.uvAttribute&&(p.fromBufferAttribute(this.uvAttribute,u),v.fromBufferAttribute(this.uvAttribute,h),x.fromBufferAttribute(this.uvAttribute,c),r.set(0,0).addScaledVector(p,n).addScaledVector(v,a).addScaledVector(x,1-(n+a))),this}}class f{constructor(e,t){r(this,"textureSize"),r(this,"dataTextures"),r(this,"eventEmitter"),this.eventEmitter=e,this.textureSize=t,this.dataTextures=new Map,this.updateServiceState("ready")}setTextureSize(e){this.textureSize!==e&&(this.textureSize=e,this.dataTextures.forEach((e=>e.dispose())),this.dataTextures.clear())}async getDataTexture(e){const t=this.dataTextures.get(e.name);if(t)return t;var i,s;const r=function(e,t){const i=new a.BufferGeometry;i.setAttribute("position",new a.BufferAttribute(new Float32Array(e.position),3)),e.normal&&i.setAttribute("normal",new a.BufferAttribute(new Float32Array(e.normal),3));const s=new a.MeshBasicMaterial,r=new a.Mesh(i,s);r.scale.set(e.scale.x,e.scale.y,e.scale.z);const n=new T(r).build(),o=new Float32Array(t*t*4),u=new a.Vector3;for(let a=0;a<t;a++)for(let i=0;i<t;i++){const s=a*t+i;n.sample(u),o[4*s]=u.x*e.scale.x,o[4*s+1]=u.y*e.scale.y,o[4*s+2]=u.z*e.scale.z,o[4*s+3]=.01*(Math.random()-.5)}return o}({position:(i=e).geometry.attributes.position.array,normal:null==(s=i.geometry.attributes.normal)?void 0:s.array,scale:{x:i.scale.x,y:i.scale.y,z:i.scale.z}},this.textureSize),n=h(r,this.textureSize);return n.name=e.name,n}async dispose(){this.dataTextures.clear(),this.updateServiceState("disposed")}updateServiceState(e){this.eventEmitter.emit("serviceStateUpdated",{type:"data-texture",state:e})}}class y{constructor(e){r(this,"size"),r(this,"mesh"),r(this,"matcapMaterial"),r(this,"fallbackGeometry"),r(this,"uniforms"),r(this,"originColor"),r(this,"destinationColor"),r(this,"geometries"),r(this,"uvRefsCache"),r(this,"previousScale"),this.size=e,this.geometries=new Map,this.uvRefsCache=new Map,this.previousScale={x:1,y:1,z:1},this.originColor="grey",this.destinationColor="grey",this.uniforms={uTime:{value:0},uProgress:{value:0},uTexture:{value:null},uVelocity:{value:null},uOriginTexture:{value:null},uDestinationTexture:{value:null}},this.matcapMaterial=new a.ShaderMaterial({uniforms:this.uniforms,vertexShader:"\nvarying vec2 vUv;\nuniform sampler2D uTexture;\nuniform sampler2D uVelocity;\nuniform float uTime;\nvarying vec3 vNormal;\nattribute vec2 uvRef;\nvarying vec3 vViewPosition;\n\nvec3 rotate3D(vec3 v, vec3 vel) {\n vec3 pos = v;\n vec3 up = vec3(0, 1, 0);\n vec3 axis = normalize(cross(up, vel));\n float angle = acos(dot(up, normalize(vel)));\n pos = pos * cos(angle) + cross(axis, pos) * sin(angle) + axis * dot(axis, pos) * (1. - cos(angle));\n return pos;\n}\n\nvoid main() {\n vUv = uv;\n vNormal = normal;\n\n vec4 color = texture2D(uTexture, uvRef);\n vec4 velocity = texture2D(uVelocity, uvRef);\n vec3 pos = color.xyz;// apply the texture to the vertex distribution.\n\n vec3 localPosition = position.xyz;\n if (length (velocity.xyz) < 0.0001) {\n velocity.xyz = vec3(0.0, 0.0001, 0.0001);\n }\n localPosition.y *= max(1.0, length(velocity.xyz) * 1000.0);\n localPosition = rotate3D(localPosition, velocity.xyz);\n vNormal = rotate3D(normal, velocity.xyz);\n\n mat4 instanceMat = instanceMatrix;\n instanceMat[3].xyz = pos.xyz;\n\n // unlike the traditional mvMatrix * position, we need to additional multiplication with the instance matrix.\n vec4 modelViewPosition = modelViewMatrix * instanceMat * vec4(localPosition, 1.0);\n\n vViewPosition = - modelViewPosition.xyz;\n\n gl_Position = projectionMatrix * modelViewPosition;\n}\n",fragmentShader:"\nvarying vec2 vUv;\nuniform sampler2D uTexture;\n\nuniform sampler2D uOriginTexture;\nuniform sampler2D uDestinationTexture;\n\nuniform float uProgress;\nvarying vec3 vNormal;\nvarying vec3 vViewPosition;\nvoid main() {\n vec3 viewDir = normalize( vViewPosition );\n vec3 x = normalize( vec3( viewDir.z, 0.0, - viewDir.x ) );\n vec3 y = cross( viewDir, x );\n vec2 uv = vec2( dot( x, vNormal ), dot( y, vNormal ) ) * 0.495 + 0.5; // 0.495 to remove artifacts caused by undersized matcap disks\n\n vec4 sourceMatcap = texture2D( uOriginTexture, uv );\n vec4 targetMatcap = texture2D( uDestinationTexture, uv );\n\n vec4 matcap = mix(sourceMatcap, targetMatcap, uProgress);\n gl_FragColor = matcap;\n}\n"}),this.setOriginColor(this.originColor),this.setDestinationColor(this.destinationColor),this.fallbackGeometry=new a.BoxGeometry(.001,.001,.001),this.mesh=this.createInstancedMesh(e,this.fallbackGeometry,this.matcapMaterial)}getMesh(){return this.mesh}update(e){const t=this.mesh.material;(t instanceof a.ShaderMaterial||t instanceof a.RawShaderMaterial)&&(t.uniforms.uTime.value=e)}setOriginMatcap(e){this.disposeSolidColorOriginTexture(),this.matcapMaterial.uniforms.uOriginTexture.value=e}setDestinationMatcap(e){this.disposeSolidColorDestinationTexture(),this.matcapMaterial.uniforms.uDestinationTexture.value=e}setProgress(e){e=Math.max(0,e),e=Math.min(1,e),this.matcapMaterial.uniforms.uProgress.value=e}setGeometrySize(e){this.mesh.geometry.scale(1/this.previousScale.x,1/this.previousScale.y,1/this.previousScale.z),this.mesh.geometry.scale(e.x,e.y,e.z),this.previousScale=e}useMatcapMaterial(){this.mesh.material=this.matcapMaterial}useGeometry(e){const t=this.geometries.get(e);t&&(this.mesh.geometry=t)}updateVelocityTexture(e){this.matcapMaterial.uniforms.uVelocity.value=e}updatePositionTexture(e){this.matcapMaterial.uniforms.uTexture.value=e}resize(e){if(this.size===e)return{current:this.mesh,previous:this.mesh};this.size=e;const t=this.mesh;return this.mesh=this.createInstancedMesh(e,t.geometry,t.material),{current:this.mesh,previous:t}}dispose(){this.mesh.dispose(),this.geometries.forEach((e=>e.dispose())),this.disposeSolidColorOriginTexture(),this.disposeSolidColorDestinationTexture(),this.matcapMaterial.dispose(),this.uvRefsCache.clear(),this.geometries.clear()}registerGeometry(e,t){const i=this.geometries.get(e);if(i&&i===t)return;const s=this.createUVRefs(this.size);t.setAttribute("uvRef",s),this.geometries.set(e,t),this.mesh.geometry===i&&(this.mesh.geometry=t),null==i||i.dispose()}setOriginColor(e){this.disposeSolidColorOriginTexture(),this.originColor=e,this.uniforms.uOriginTexture.value=this.createSolidColorDataTexture(e)}setDestinationColor(e){this.disposeSolidColorDestinationTexture(),this.destinationColor=e,this.uniforms.uDestinationTexture.value=this.createSolidColorDataTexture(e)}createUVRefs(e){const t=this.uvRefsCache.get(e);if(t)return t;const i=new Float32Array(e*e*2);for(let r=0;r<e;r++)for(let t=0;t<e;t++){const s=r*e+t;i[2*s]=t/(e-1),i[2*s+1]=r/(e-1)}const s=new a.InstancedBufferAttribute(i,2);return this.uvRefsCache.set(e,s),s}createInstancedMesh(e,t,i){(t=t||this.fallbackGeometry).setAttribute("uvRef",this.createUVRefs(e));const s=e*e;return new a.InstancedMesh(t,i,s)}createSolidColorDataTexture(e,t=16){const i=new a.Color(e),s=t,r=t,n=new Uint8Array(s*r*4),o=Math.floor(255*i.r),u=Math.floor(255*i.g),h=Math.floor(255*i.b);for(let a=0;a<s*r;a++){const e=4*a;n[e]=o,n[e+1]=u,n[e+2]=h,n[e+3]=255}const c=new a.DataTexture(n,s,r,a.RGBAFormat);return c.type=a.UnsignedByteType,c.wrapS=a.RepeatWrapping,c.wrapT=a.RepeatWrapping,c.minFilter=a.NearestFilter,c.magFilter=a.NearestFilter,c.needsUpdate=!0,c}disposeSolidColorOriginTexture(){this.originColor&&(this.originColor=null,this.uniforms.uOriginTexture.value&&this.uniforms.uOriginTexture.value.dispose())}disposeSolidColorDestinationTexture(){this.destinationColor&&(this.destinationColor=null,this.uniforms.uDestinationTexture.value&&this.uniforms.uDestinationTexture.value.dispose())}}class M{constructor(e,t,i,s){r(this,"active",!0),r(this,"raycaster",new a.Raycaster),r(this,"mousePosition",new a.Vector2),r(this,"camera"),r(this,"originGeometry"),r(this,"destinationGeometry"),r(this,"progress",0),r(this,"intersectionMesh",new a.Mesh),r(this,"geometryNeedsUpdate"),r(this,"eventEmitter"),r(this,"blendedGeometry"),r(this,"intersection"),r(this,"lastKnownOriginMeshID"),r(this,"lastKnownDestinationMeshID"),this.camera=t,this.originGeometry=i,this.eventEmitter=e,this.destinationGeometry=s,this.geometryNeedsUpdate=!0}setActive(e){this.active=e}getIntersectionMesh(){return this.intersectionMesh}setCamera(e){this.camera=e}setOriginGeometry(e){this.lastKnownOriginMeshID!==e.uuid&&(this.originGeometry&&this.originGeometry.dispose(),this.lastKnownOriginMeshID=e.uuid,this.originGeometry=e.geometry.clone(),this.originGeometry.applyMatrix4(e.matrixWorld),this.geometryNeedsUpdate=!0)}setDestinationGeometry(e){this.lastKnownDestinationMeshID!==e.uuid&&(this.destinationGeometry&&this.destinationGeometry.dispose(),this.lastKnownDestinationMeshID=e.uuid,this.destinationGeometry=e.geometry.clone(),this.destinationGeometry.applyMatrix4(e.matrixWorld),this.geometryNeedsUpdate=!0)}setProgress(e){this.progress=e,this.geometryNeedsUpdate=!0}setPointerPosition(e){e&&this.mousePosition.copy(e)}calculate(e){if(this.active&&(this.updateIntersectionMesh(e),this.camera))return this.geometryNeedsUpdate&&(this.geometryNeedsUpdate=!1,this.blendedGeometry=this.getBlendedGeometry()),this.blendedGeometry?this.intersection=this.getFirstIntersection(this.camera,e):this.intersection=void 0,this.intersection?this.eventEmitter.emit("interactionPositionUpdated",{position:this.intersection}):this.eventEmitter.emit("interactionPositionUpdated",{position:{x:0,y:0,z:0,w:0}}),this.intersection}dispose(){var e;null==(e=this.blendedGeometry)||e.dispose(),this.intersectionMesh.geometry.dispose()}updateIntersectionMesh(e){this.blendedGeometry&&this.blendedGeometry.uuid!==this.intersectionMesh.geometry.uuid&&(this.intersectionMesh.geometry.dispose(),this.intersectionMesh.geometry=this.blendedGeometry),this.intersectionMesh.matrix.copy(e.matrixWorld),this.intersectionMesh.matrixWorld.copy(e.matrixWorld),this.intersectionMesh.matrixAutoUpdate=!1,this.intersectionMesh.updateMatrixWorld(!0)}getFirstIntersection(e,t){this.raycaster.setFromCamera(this.mousePosition,e);const i=this.raycaster.intersectObject(this.intersectionMesh,!1)[0];if(i){const e=i.point.clone(),s=t.worldToLocal(e);return new a.Vector4(s.x,s.y,s.z,1)}}getBlendedGeometry(){return 0===this.progress?this.originGeometry:1===this.progress?this.destinationGeometry:this.originGeometry&&this.destinationGeometry?this.originGeometry===this.destinationGeometry?this.originGeometry:this.blendGeometry(this.originGeometry,this.destinationGeometry,this.progress):void 0}blendGeometry(e,t,i){const s=new a.BufferGeometry,r=e.attributes.position.array,n=t.attributes.position.array,o=new Float32Array(r.length);for(let u=0;u<r.length;u+=3){const e=new a.Vector3(r[u],r[u+1],r[u+2]),t=new a.Vector3(n[u],n[u+1],n[u+2]),s=(new a.Vector3).lerpVectors(e,t,i);o[u]=s.x,o[u+1]=s.y,o[u+2]=s.z}return s.setAttribute("position",new a.BufferAttribute(o,3)),e.attributes.normal&&s.setAttribute("normal",e.attributes.normal.clone()),e.attributes.uv&&s.setAttribute("uv",e.attributes.uv.clone()),e.index&&s.setIndex(e.index.clone()),s}}const S=new t.OrthographicCamera(-1,1,1,-1,0,1);class D extends t.BufferGeometry{constructor(){super(),this.setAttribute("position",new t.Float32BufferAttribute([-1,3,0,-1,-1,0,3,-1,0],3)),this.setAttribute("uv",new t.Float32BufferAttribute([0,2,0,0,2,0],2))}}const w=new D;class P{constructor(e){this._mesh=new t.Mesh(w,e)}dispose(){this._mesh.geometry.dispose()}render(e){e.render(this._mesh,S)}get material(){return this._mesh.material}set material(e){this._mesh.material=e}}class b{constructor(e,i,s){this.variables=[],this.currentTextureIndex=0;let r=t.FloatType;const n={passThruTexture:{value:null}},a=h("uniform sampler2D passThruTexture;\n\nvoid main() {\n\n\tvec2 uv = gl_FragCoord.xy / resolution.xy;\n\n\tgl_FragColor = texture2D( passThruTexture, uv );\n\n}\n",n),o=new P(a);function u(t){t.defines.resolution="vec2( "+e.toFixed(1)+", "+i.toFixed(1)+" )"}function h(e,i){i=i||{};const s=new t.ShaderMaterial({name:"GPUComputationShader",uniforms:i,vertexShader:"void main()\t{\n\n\tgl_Position = vec4( position, 1.0 );\n\n}\n",fragmentShader:e});return u(s),s}this.setDataType=function(e){return r=e,this},this.addVariable=function(e,i,s){const r={name:e,initialValueTexture:s,material:this.createShaderMaterial(i),dependencies:null,renderTargets:[],wrapS:null,wrapT:null,minFilter:t.NearestFilter,magFilter:t.NearestFilter};return this.variables.push(r),r},this.setVariableDependencies=function(e,t){e.dependencies=t},this.init=function(){if(0===s.capabilities.maxVertexTextures)return"No support for vertex shader textures.";for(let t=0;t<this.variables.length;t++){const s=this.variables[t];s.renderTargets[0]=this.createRenderTarget(e,i,s.wrapS,s.wrapT,s.minFilter,s.magFilter),s.renderTargets[1]=this.createRenderTarget(e,i,s.wrapS,s.wrapT,s.minFilter,s.magFilter),this.renderTexture(s.initialValueTexture,s.renderTargets[0]),this.renderTexture(s.initialValueTexture,s.renderTargets[1]);const r=s.material,n=r.uniforms;if(null!==s.dependencies)for(let e=0;e<s.dependencies.length;e++){const t=s.dependencies[e];if(t.name!==s.name){let e=!1;for(let i=0;i<this.variables.length;i++)if(t.name===this.variables[i].name){e=!0;break}if(!e)return"Variable dependency not found. Variable="+s.name+", dependency="+t.name}n[t.name]={value:null},r.fragmentShader="\nuniform sampler2D "+t.name+";\n"+r.fragmentShader}}return this.currentTextureIndex=0,null},this.compute=function(){const e=this.currentTextureIndex,t=0===this.currentTextureIndex?1:0;for(let i=0,s=this.variables.length;i<s;i++){const s=this.variables[i];if(null!==s.dependencies){const t=s.material.uniforms;for(let i=0,r=s.dependencies.length;i<r;i++){const r=s.dependencies[i];t[r.name].value=r.renderTargets[e].texture}}this.doRenderTarget(s.material,s.renderTargets[t])}this.currentTextureIndex=t},this.getCurrentRenderTarget=function(e){return e.renderTargets[this.currentTextureIndex]},this.getAlternateRenderTarget=function(e){return e.renderTargets[0===this.currentTextureIndex?1:0]},this.dispose=function(){o.dispose();const e=this.variables;for(let t=0;t<e.length;t++){const i=e[t];i.initialValueTexture&&i.initialValueTexture.dispose();const s=i.renderTargets;for(let e=0;e<s.length;e++){s[e].dispose()}}},this.addResolutionDefine=u,this.createShaderMaterial=h,this.createRenderTarget=function(s,n,a,o,u,h){s=s||e,n=n||i,a=a||t.ClampToEdgeWrapping,o=o||t.ClampToEdgeWrapping,u=u||t.NearestFilter,h=h||t.NearestFilter;return new t.WebGLRenderTarget(s,n,{wrapS:a,wrapT:o,minFilter:u,magFilter:h,format:t.RGBAFormat,type:r,depthBuffer:!1})},this.createTexture=function(){const s=new Float32Array(e*i*4),r=new t.DataTexture(s,e,i,t.RGBAFormat,t.FloatType);return r.needsUpdate=!0,r},this.renderTexture=function(e,t){n.passThruTexture.value=e,this.doRenderTarget(a,t),n.passThruTexture.value=null},this.doRenderTarget=function(e,t){const i=s.getRenderTarget(),r=s.xr.enabled,n=s.shadowMap.autoUpdate;s.xr.enabled=!1,s.shadowMap.autoUpdate=!1,o.material=e,s.setRenderTarget(t),o.render(s),o.material=a,s.xr.enabled=r,s.shadowMap.autoUpdate=n,s.setRenderTarget(i)}}}class R{constructor(e,t,i){r(this,"gpuComputationRenderer"),r(this,"webGLRenderer"),r(this,"positionDataTexture"),r(this,"velocityDataTexture"),r(this,"mixPositionsVar"),r(this,"velocityVar"),r(this,"positionVar"),r(this,"interactionPosition"),r(this,"lastKnownPositionDataTexture"),r(this,"lastKnownVelocityDataTexture"),r(this,"lastKnownMixProgress"),r(this,"initialDataTexture"),this.initialDataTexture=i??function(e){const t=new Float32Array(e*e*4);for(let i=0;i<e;i++)for(let s=0;s<e;s++){const r=i*e+s;let n=Math.random()*Math.PI*2,a=Math.acos(2*Math.random()-1),o=Math.sin(a)*Math.cos(n),u=Math.sin(a)*Math.sin(n),h=Math.cos(a);t[4*r]=o,t[4*r+1]=u,t[4*r+2]=h,t[4*r+3]=.01*(Math.random()-.5)}return h(t,e)}(e),this.positionDataTexture=this.initialDataTexture,this.webGLRenderer=t,this.gpuComputationRenderer=new b(e,e,this.webGLRenderer),this.lastKnownMixProgress=0,t.capabilities.isWebGL2||this.gpuComputationRenderer.setDataType(a.HalfFloatType),this.velocityDataTexture=function(e){return h(new Float32Array(4*e*e),e)}(e),this.interactionPosition=new a.Vector4(0,0,0,0),this.mixPositionsVar=this.gpuComputationRenderer.addVariable("uMixedPosition","\nuniform sampler2D uPositionA;\nuniform sampler2D uPositionB;\nuniform float uProgress;\n\nvoid main() {\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n vec3 positionA = texture2D(uPositionA, uv).xyz;\n vec3 positionB = texture2D(uPositionB, uv).xyz;\n vec3 mixedPosition = mix(positionA, positionB, uProgress);\n gl_FragColor = vec4(mixedPosition, 1.0);\n}\n",this.positionDataTexture),this.velocityVar=this.gpuComputationRenderer.addVariable("uCurrentVelocity","\nuniform float uProgress;\nuniform vec4 uInteractionPosition;\nuniform float uTime;\nuniform float uTractionForce;\nuniform float uMaxRepelDistance;\n\nfloat rand(vec2 co) {\n return fract(sin(dot(co, vec2(12.9898, 78.233))) * 43758.5453);\n}\n\nvoid main() {\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n float offset = rand(uv);\n\n vec3 position = texture2D(uCurrentPosition, uv).xyz;\n vec3 velocity = texture2D(uCurrentVelocity, uv).xyz;\n vec3 mixedPosition = texture2D(uMixedPosition, uv).xyz;\n\n velocity *= 0.9;\n\n // particle traction\n vec3 direction = normalize(mixedPosition - position); // direction vector\n float dist = length ( mixedPosition - position ); // distance from where it was supposed to be, and currently are.\n if (dist > 0.01) {\n position += direction * 0.1 * uTractionForce; // uTractionForce defaults to 0.1\n }\n\n // mouse repel force\n float pointerDistance = distance(position, uInteractionPosition.xyz);\n float mouseRepelModifier = clamp(uMaxRepelDistance - pointerDistance, 0.0, 1.0);\n float normalizedDistance = pointerDistance / uMaxRepelDistance;\n float repulsionStrength = (1.0 - normalizedDistance) * uInteractionPosition.w;\n direction = normalize(position - uInteractionPosition.xyz);\n velocity += (direction * 0.01 * repulsionStrength) * mouseRepelModifier;\n\n float lifespan = 20.0;\n float age = mod(uTime + lifespan * offset, lifespan);\n\n if (age < 0.1) {\n position.xyz = mixedPosition;\n }\n\n gl_FragColor = vec4(velocity, 1.0);\n}\n",this.velocityDataTexture),this.positionVar=this.gpuComputationRenderer.addVariable("uCurrentPosition","\nuniform float uProgress;\nuniform vec4 uInteractionPosition;\nuniform float uTime;\nuniform float uTractionForce;\n\nfloat rand(vec2 co) {\n return fract(sin(dot(co, vec2(12.9898, 78.233))) * 43758.5453);\n}\n\nvoid main() {\n\n // in GPGPU, we calculate the uv on each fragment shader, not using the static varying passed over from the v shader.\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n float offset = rand(uv);\n\n vec3 position = texture2D(uCurrentPosition, uv).xyz;\n vec3 velocity = texture2D(uCurrentVelocity, uv).xyz;\n vec3 mixedPosition = texture2D(uMixedPosition, uv).xyz;\n\n // particle attraction to original position.\n vec3 direction = normalize(mixedPosition - position); // direction vector\n float dist = length ( mixedPosition - position ); // distance from where it was supposed to be, and currently are.\n\n if (dist > 0.01) {\n position = mix(position, mixedPosition, 0.1 * uTractionForce); // 0.1 ~ 0.001 (faster, slower)\n }\n\n position += velocity;\n gl_FragColor = vec4(position, 1.0);\n}\n",this.positionDataTexture),this.mixPositionsVar.material.uniforms.uProgress={value:0},this.mixPositionsVar.material.uniforms.uPositionA={value:this.initialDataTexture},this.mixPositionsVar.material.uniforms.uPositionB={value:this.initialDataTexture},this.velocityVar.material.uniforms.uTime={value:0},this.velocityVar.material.uniforms.uInteractionPosition={value:this.interactionPosition},this.velocityVar.material.uniforms.uCurrentPosition={value:this.positionDataTexture},this.velocityVar.material.uniforms.uTractionForce={value:.1},this.velocityVar.material.uniforms.uMaxRepelDistance={value:.3},this.positionVar.material.uniforms.uTime={value:0},this.positionVar.material.uniforms.uProgress={value:0},this.positionVar.material.uniforms.uTractionForce={value:.1},this.positionVar.material.uniforms.uInteractionPosition={value:this.interactionPosition},this.positionVar.material.uniforms.uCurrentPosition={value:this.positionDataTexture},this.gpuComputationRenderer.setVariableDependencies(this.positionVar,[this.velocityVar,this.positionVar,this.mixPositionsVar]),this.gpuComputationRenderer.setVariableDependencies(this.velocityVar,[this.velocityVar,this.positionVar,this.mixPositionsVar]);const s=this.gpuComputationRenderer.init();if(s)throw new Error("failed to initialize SimulationRenderer: "+s);this.lastKnownVelocityDataTexture=this.getVelocityTexture(),this.lastKnownPositionDataTexture=this.getPositionTexture()}setMorphSourceDataTexture(e){this.mixPositionsVar.material.uniforms.uPositionA.value=e}setMorphDestinationDataTexture(e){this.mixPositionsVar.material.uniforms.uPositionB.value=e}setMaxRepelDistance(e){this.velocityVar.material.uniforms.uMaxRepelDistance.value=e}setProgress(e){this.lastKnownMixProgress=l(e,0,1),this.mixPositionsVar.material.uniforms.uProgress.value=this.lastKnownMixProgress}setVelocityTractionForce(e){this.velocityVar.material.uniforms.uTractionForce.value=e}setPositionalTractionForce(e){this.positionVar.material.uniforms.uTractionForce.value=e}setInteractionPosition(e){this.interactionPosition.copy(e)}dispose(){this.mixPositionsVar.renderTargets.forEach((e=>e.dispose())),this.positionVar.renderTargets.forEach((e=>e.dispose())),this.velocityVar.renderTargets.forEach((e=>e.dispose())),this.positionDataTexture.dispose(),this.velocityDataTexture.dispose(),this.gpuComputationRenderer.dispose()}compute(e){this.velocityVar.material.uniforms.uTime.value=e,this.positionVar.material.uniforms.uTime.value=e,this.gpuComputationRenderer.compute()}getVelocityTexture(){return this.lastKnownVelocityDataTexture=this.gpuComputationRenderer.getCurrentRenderTarget(this.velocityVar).texture,this.lastKnownVelocityDataTexture}getPositionTexture(){return this.lastKnownPositionDataTexture=this.gpuComputationRenderer.getCurrentRenderTarget(this.positionVar).texture,this.lastKnownPositionDataTexture}}class V{constructor(e,t,i){r(this,"state"),r(this,"textureSize"),r(this,"dataTextureTransitionProgress"),r(this,"velocityTractionForce"),r(this,"positionalTractionForce"),r(this,"simulationRenderer"),r(this,"webGLRenderer"),r(this,"eventEmitter"),r(this,"lastKnownVelocityDataTexture"),r(this,"lastKnownPositionDataTexture"),this.eventEmitter=e,this.webGLRenderer=i,this.textureSize=t,this.dataTextureTransitionProgress=0,this.velocityTractionForce=.1,this.positionalTractionForce=.1,this.updateServiceState("initializing"),this.simulationRenderer=new R(this.textureSize,this.webGLRenderer),this.lastKnownVelocityDataTexture=this.simulationRenderer.getVelocityTexture(),this.lastKnownPositionDataTexture=this.simulationRenderer.getPositionTexture(),this.updateServiceState("ready")}setTextureSize(e){this.updateServiceState("initializing"),this.simulationRenderer.dispose(),this.textureSize=e,this.simulationRenderer=new R(e,this.webGLRenderer),this.updateServiceState("ready")}setOriginDataTexture(e){this.textureSize!==e.textureSize?this.eventEmitter.emit("invalidRequest",{message:`Texture size mismatch: ${e.textureSize} vs ${this.textureSize}`}):this.simulationRenderer.setMorphSourceDataTexture(e.dataTexture)}setDestinationDataTexture(e){this.textureSize!==e.textureSize?this.eventEmitter.emit("invalidRequest",{message:`Texture size mismatch: ${e.textureSize} vs ${this.textureSize}`}):this.simulationRenderer.setMorphDestinationDataTexture(e.dataTexture)}setDataTextureTransitionProgress(e){this.dataTextureTransitionProgress=e,this.simulationRenderer.setProgress(this.dataTextureTransitionProgress)}setVelocityTractionForce(e){this.velocityTractionForce=e,this.simulationRenderer.setVelocityTractionForce(this.velocityTractionForce)}setPositionalTractionForce(e){this.positionalTractionForce=e,this.simulationRenderer.setPositionalTractionForce(this.positionalTractionForce)}compute(e){this.simulationRenderer.compute(e)}getVelocityTexture(){return"ready"===this.state&&(this.lastKnownVelocityDataTexture=this.simulationRenderer.getVelocityTexture()),this.lastKnownVelocityDataTexture}getPositionTexture(){return"ready"===this.state&&(this.lastKnownPositionDataTexture=this.simulationRenderer.getPositionTexture()),this.lastKnownPositionDataTexture}dispose(){this.updateServiceState("disposed"),this.simulationRenderer.dispose(),this.lastKnownVelocityDataTexture.dispose(),this.lastKnownPositionDataTexture.dispose()}updateServiceState(e){this.state=e,this.eventEmitter.emit("serviceStateUpdated",{type:"simulation",state:e})}setInteractionPosition(e){this.simulationRenderer.setInteractionPosition(e)}setMaxRepelDistance(e){this.simulationRenderer.setMaxRepelDistance(e)}}class A{constructor(){r(this,"execStatus",new Map)}get(e){const t=this.execStatus.get(e);return t||(this.execStatus.set(e,"idle"),"idle")}set(e,t){this.execStatus.set(e,t)}}class C{constructor(e){r(this,"eventEmitter"),r(this,"transitions",new Map),r(this,"execStatus"),r(this,"ongoingTransitions",new Map),this.eventEmitter=e,this.execStatus=new A,this.eventEmitter.on("transitionCancelled",this.handleTransitionCancelledEvent.bind(this))}enqueue(e,t,i={}){const s={...t,...i,cancelled:!1,duration:.001*t.duration};this.getQueue(e).push(s)}compute(e){this.transitions.forEach(((t,i)=>{var s;if(t.length&&!this.ongoingTransitions.has(i)){const r=t.shift();r&&(this.ongoingTransitions.set(i,{...r,startTime:e}),null==(s=r.onTransitionBegin)||s.call(r))}})),this.ongoingTransitions.forEach(((t,i)=>{var s,r,n;if(t.cancelled)return null==(s=t.onTransitionCancelled)||s.call(t),void this.ongoingTransitions.delete(i);const{startTime:a,duration:o,easing:u}=t,h=e-a,c=l(u(Math.min(1,h/o)),0,1);this.emitTransitionProgress(i,c),null==(r=t.onTransitionProgress)||r.call(t,c),c>=1&&(this.emitTransitionFinished(i),null==(n=t.onTransitionFinished)||n.call(t),this.ongoingTransitions.delete(i))}))}getQueue(e){const t=this.transitions.get(e);return t||(this.transitions.set(e,[]),this.transitions.get(e)??[])}handleTransitionCancelledEvent({type:e}){var t;const i=this.getQueue(e);for(;i.length;)i.pop();const s=this.ongoingTransitions.get(e);s&&(s.cancelled=!0,null==(t=s.onTransitionCancelled)||t.call(s))}emitTransitionProgress(e,t){this.eventEmitter.emit("transitionProgressed",{type:e,progress:t})}emitTransitionFinished(e){this.eventEmitter.emit("transitionFinished",{type:e})}}return e.ParticlesEngine=class{constructor(e){r(this,"simulationRendererService"),r(this,"eventEmitter"),r(this,"renderer"),r(this,"scene"),r(this,"serviceStates"),r(this,"assetService"),r(this,"dataTextureManager"),r(this,"instancedMeshManager"),r(this,"transitionService"),r(this,"engineState"),r(this,"intersectionService");const{scene:t,renderer:i,camera:s,textureSize:n,useIntersection:a=!0}=e;this.eventEmitter=new u,this.serviceStates=this.getInitialServiceStates(),this.eventEmitter.on("serviceStateUpdated",this.handleServiceStateUpdated.bind(this)),this.scene=t,this.renderer=i,this.engineState=this.initialEngineState(e),this.assetService=new d(this.eventEmitter),this.transitionService=new C(this.eventEmitter),this.dataTextureManager=new f(this.eventEmitter,n),this.simulationRendererService=new V(this.eventEmitter,n,this.renderer),this.instancedMeshManager=new y(n),this.instancedMeshManager.useMatcapMaterial(),this.scene.add(this.instancedMeshManager.getMesh()),this.intersectionService=new M(this.eventEmitter,s),a||this.intersectionService.setActive(!1),this.eventEmitter.on("transitionProgressed",this.handleTransitionProgress.bind(this)),this.eventEmitter.on("interactionPositionUpdated",this.handleInteractionPositionUpdated.bind(this))}render(e){this.intersectionService.calculate(this.instancedMeshManager.getMesh()),this.transitionService.compute(e),this.simulationRendererService.compute(e),this.instancedMeshManager.update(e),this.instancedMeshManager.updateVelocityTexture(this.simulationRendererService.getVelocityTexture()),this.instancedMeshManager.updatePositionTexture(this.simulationRendererService.getPositionTexture())}setOriginDataTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"});const i=this.assetService.getMesh(e);i?this.dataTextureManager.getDataTexture(i).then((t=>{this.engineState.originMeshID=e,this.simulationRendererService.setOriginDataTexture({dataTexture:t,textureSize:this.engineState.textureSize}),this.intersectionService.setOriginGeometry(i)})):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${e}" does not exist`})}setDestinationDataTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"});const i=this.assetService.getMesh(e);i?this.dataTextureManager.getDataTexture(i).then((t=>{this.engineState.destinationMeshID=e,this.simulationRendererService.setDestinationDataTexture({dataTexture:t,textureSize:this.engineState.textureSize}),this.intersectionService.setDestinationGeometry(i)})):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${e}" does not exist`})}setDataTextureTransitionProgress(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"}),this.engineState.dataTextureTransitionProgress=e,this.simulationRendererService.setDataTextureTransitionProgress(e),this.intersectionService.setProgress(e)}setOriginMatcap(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.originMatcapID=e,this.instancedMeshManager.setOriginMatcap(this.assetService.getMatcap(e))}setDestinationMatcap(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.destinationMatcapID=e,this.instancedMeshManager.setDestinationMatcap(this.assetService.getMatcap(e))}setOriginColor(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.instancedMeshManager.setOriginColor(e)}setDestinationColor(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.instancedMeshManager.setDestinationColor(e)}setOriginTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),"string"==typeof e&&this.assetService.hasMatcap(e)?this.setOriginMatcap(e):this.setOriginColor(e)}setDestinationTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),"string"==typeof e&&this.assetService.hasMatcap(e)?this.setDestinationMatcap(e):this.setDestinationColor(e)}setMatcapProgress(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.matcapTransitionProgress=e,this.instancedMeshManager.setProgress(e)}async setTextureSize(e){this.engineState.textureSize=e,this.dataTextureManager.setTextureSize(e),this.simulationRendererService.setTextureSize(e),this.instancedMeshManager.resize(e);const t=this.assetService.getMesh(this.engineState.originMeshID);if(!t)return void this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${this.engineState.originMeshID}" does not exist`});const i=this.assetService.getMesh(this.engineState.destinationMeshID);i?(this.dataTextureManager.getDataTexture(t).then((t=>this.simulationRendererService.setOriginDataTexture({dataTexture:t,textureSize:e}))),this.dataTextureManager.getDataTexture(i).then((t=>this.simulationRendererService.setDestinationDataTexture({dataTexture:t,textureSize:e}))),this.simulationRendererService.setDataTextureTransitionProgress(this.engineState.dataTextureTransitionProgress),this.simulationRendererService.setVelocityTractionForce(this.engineState.velocityTractionForce),this.simulationRendererService.setPositionalTractionForce(this.engineState.positionalTractionForce),this.instancedMeshManager.setOriginMatcap(this.assetService.getMatcap(this.engineState.originMatcapID)),this.instancedMeshManager.setDestinationMatcap(this.assetService.getMatcap(this.engineState.destinationMatcapID)),this.instancedMeshManager.setProgress(this.engineState.matcapTransitionProgress),this.instancedMeshManager.setGeometrySize(this.engineState.instanceGeometryScale)):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${this.engineState.destinationMeshID}" does not exist`})}registerMesh(e,t){this.assetService.register(e,t)}registerMatcap(e,t){this.assetService.register(e,t)}async fetchAndRegisterMesh(e,t){return await this.assetService.loadMeshAsync(e,t)}async fetchAndRegisterMatcap(e,t){return await this.assetService.loadTextureAsync(e,t)}useIntersect(e){this.intersectionService.setActive(e),this.engineState.useIntersect=e,e||(this.engineState.pointerPosition={x:-99999999,y:-99999999},this.intersectionService.setPointerPosition(this.engineState.pointerPosition))}setPointerPosition(e){this.engineState.useIntersect&&(this.engineState.pointerPosition=e,this.intersectionService.setPointerPosition(e))}setGeometrySize(e){this.engineState.instanceGeometryScale=e,this.instancedMeshManager.setGeometrySize(e)}setVelocityTractionForce(e){this.engineState.velocityTractionForce=e,this.simulationRendererService.setVelocityTractionForce(e)}setPositionalTractionForce(e){this.engineState.positionalTractionForce=e,this.simulationRendererService.setPositionalTractionForce(e)}setMaxRepelDistance(e){this.engineState.maxRepelDistance=e,this.simulationRendererService.setMaxRepelDistance(e)}scheduleMeshTransition(e,t,i=o,s=1e3,r=!1){this.transitionService.enqueue("data-texture",{easing:i,duration:s},{onTransitionBegin:()=>{this.setOriginDataTexture(e,r),this.setDestinationDataTexture(t,r),this.setDataTextureTransitionProgress(0)}})}scheduleMatcapTransition(e,t,i=o,s=1e3,r=!1){this.transitionService.enqueue("matcap",{easing:i,duration:s},{onTransitionBegin:()=>{this.setOriginMatcap(e,r),this.setDestinationMatcap(t,r),this.setMatcapProgress(0)}})}scheduleTextureTransition(e,t,i){const s=(null==i?void 0:i.easing)??o,r=(null==i?void 0:i.duration)??1e3;(null==i?void 0:i.override)&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.transitionService.enqueue("matcap",{easing:s,duration:r},{onTransitionBegin:()=>{this.setOriginTexture(e),this.setDestinationTexture(t),this.setMatcapProgress(0)}})}handleServiceStateUpdated({type:e,state:t}){this.serviceStates[e]=t}getObject(){return this.instancedMeshManager.getMesh()}getMeshIDs(){return this.assetService.getMeshIDs()}getMatcapIDs(){return this.assetService.getTextureIDs()}dispose(){this.scene.remove(this.instancedMeshManager.getMesh()),this.simulationRendererService.dispose(),this.instancedMeshManager.dispose(),this.intersectionService.dispose(),this.assetService.dispose(),this.dataTextureManager.dispose()}initialEngineState(e){return{textureSize:e.textureSize,originMeshID:"",destinationMeshID:"",dataTextureTransitionProgress:0,originMatcapID:"",destinationMatcapID:"",matcapTransitionProgress:0,velocityTractionForce:.1,positionalTractionForce:.1,maxRepelDistance:.3,pointerPosition:{x:0,y:0},instanceGeometryScale:{x:1,y:1,z:1},useIntersect:e.useIntersection??!0}}getInitialServiceStates(){return{"data-texture":"created","instanced-mesh":"created",matcap:"created",simulation:"created",asset:"created"}}handleTransitionProgress({type:e,progress:t}){switch(e){case"data-texture":this.setDataTextureTransitionProgress(t);break;case"matcap":this.setMatcapProgress(t)}}handleInteractionPositionUpdated({position:e}){this.simulationRendererService.setInteractionPosition(e)}},Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),e}({},THREE,three-stdlib);
1
+ var ionian=function(e,t,i){"use strict";var s=Object.defineProperty,r=(e,t,i)=>((e,t,i)=>t in e?s(e,t,{enumerable:!0,configurable:!0,writable:!0,value:i}):e[t]=i)(e,"symbol"!=typeof t?t+"":t,i);function n(e){const t=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(e)for(const i in e)if("default"!==i){const s=Object.getOwnPropertyDescriptor(e,i);Object.defineProperty(t,i,s.get?s:{enumerable:!0,get:()=>e[i]})}return t.default=e,Object.freeze(t)}const a=n(t),o=e=>e;class u{constructor(){var e;r(this,"emitter",{all:e=e||new Map,on:function(t,i){var s=e.get(t);s?s.push(i):e.set(t,[i])},off:function(t,i){var s=e.get(t);s&&(i?s.splice(s.indexOf(i)>>>0,1):e.set(t,[]))},emit:function(t,i){var s=e.get(t);s&&s.slice().map((function(e){e(i)})),(s=e.get("*"))&&s.slice().map((function(e){e(t,i)}))}})}emit(e,t){this.emitter.emit(e,t)}off(e,t){this.emitter.off(e,t)}on(e,t){this.emitter.on(e,t)}once(e,t){this.emitter.on(e,(i=>{this.emitter.off(e,t),t(i)}))}dispose(){this.emitter.all.clear()}}function h(e,t){const i=new a.DataTexture(e,t,t,a.RGBAFormat,a.FloatType);return i.needsUpdate=!0,i}function c(e){e.geometry.dispose(),e.material instanceof a.Material?e.material.dispose():e.material.forEach((e=>e.dispose()))}function l(e,t,i){return e=Math.min(e,i),e=Math.max(e,t)}class d{constructor(e){r(this,"serviceState","created"),r(this,"eventEmitter"),r(this,"meshes",new Map),r(this,"textures",new Map),r(this,"gltfLoader",new i.GLTFLoader),r(this,"textureLoader",new a.TextureLoader),r(this,"dracoLoader",new i.DRACOLoader),r(this,"solidColorTexture",new a.DataTexture(new Uint8Array([127,127,127,255]),1,1,a.RGBAFormat)),this.eventEmitter=e,this.dracoLoader.setDecoderPath("https://www.gstatic.com/draco/versioned/decoders/1.5.7/"),this.gltfLoader.setDRACOLoader(this.dracoLoader),this.updateServiceState("ready")}register(e,t){if(t.name=e,t instanceof a.Mesh){const i=this.meshes.get(e);i&&c(i),this.meshes.set(e,t)}else{const i=this.textures.get(e);i&&i.dispose(),this.textures.set(e,t)}this.eventEmitter.emit("assetRegistered",{id:e})}setSolidColor(e){this.changeColor(e)}getSolidColorTexture(){return this.solidColorTexture}getMesh(e){return this.meshes.get(e)??null}getMatcap(e){const t=this.textures.get(e);return t||this.eventEmitter.emit("invalidRequest",{message:`texture with id "${e}" not found. using solid color texture instead...`}),t??this.solidColorTexture}getMeshIDs(){return Array.from(this.meshes.keys())}getTextureIDs(){return Array.from(this.textures.keys())}getMeshes(){return Array.from(this.meshes.values())}getTextures(){return Array.from(this.textures.values())}hasMatcap(e){return this.textures.has(e)}async loadMeshAsync(e,t,i={}){const s=await this.gltfLoader.loadAsync(t);try{if(i.meshName){const t=s.scene.getObjectByName(i.meshName);return this.register(e,t),t}{const t=s.scene.children[0];return this.register(e,t),t}}catch(r){return this.eventEmitter.emit("invalidRequest",{message:`failed to load mesh: ${e}. ${r}`}),null}}async loadTextureAsync(e,t){try{const i=await this.textureLoader.loadAsync(t);return this.register(e,i),i}catch(i){return this.eventEmitter.emit("invalidRequest",{message:`failed to load texture: ${e}. ${i}`}),null}}dispose(){this.updateServiceState("disposed"),this.meshes.forEach((e=>c(e))),this.meshes.clear(),this.textures.forEach((e=>e.dispose())),this.textures.clear()}changeColor(e){const t=new a.Color(e);this.solidColorTexture=new a.DataTexture(new Uint8Array([t.r,t.g,t.b,255]),1,1,a.RGBAFormat),this.solidColorTexture.needsUpdate=!0}updateServiceState(e){this.serviceState=e,this.eventEmitter.emit("serviceStateUpdated",{type:"asset",state:e})}}const m=new t.Triangle,g=new t.Vector3,p=new t.Vector2,v=new t.Vector2,x=new t.Vector2;class T{constructor(e){this.geometry=e.geometry,this.randomFunction=Math.random,this.indexAttribute=this.geometry.index,this.positionAttribute=this.geometry.getAttribute("position"),this.normalAttribute=this.geometry.getAttribute("normal"),this.colorAttribute=this.geometry.getAttribute("color"),this.uvAttribute=this.geometry.getAttribute("uv"),this.weightAttribute=null,this.distribution=null}setWeightAttribute(e){return this.weightAttribute=e?this.geometry.getAttribute(e):null,this}build(){const e=this.indexAttribute,t=this.positionAttribute,i=this.weightAttribute,s=e?e.count/3:t.count/3,r=new Float32Array(s);for(let o=0;o<s;o++){let s=1,n=3*o,a=3*o+1,u=3*o+2;e&&(n=e.getX(n),a=e.getX(a),u=e.getX(u)),i&&(s=i.getX(n)+i.getX(a)+i.getX(u)),m.a.fromBufferAttribute(t,n),m.b.fromBufferAttribute(t,a),m.c.fromBufferAttribute(t,u),s*=m.getArea(),r[o]=s}const n=new Float32Array(s);let a=0;for(let o=0;o<s;o++)a+=r[o],n[o]=a;return this.distribution=n,this}setRandomGenerator(e){return this.randomFunction=e,this}sample(e,t,i,s){const r=this.sampleFaceIndex();return this.sampleFace(r,e,t,i,s)}sampleFaceIndex(){const e=this.distribution[this.distribution.length-1];return this.binarySearch(this.randomFunction()*e)}binarySearch(e){const t=this.distribution;let i=0,s=t.length-1,r=-1;for(;i<=s;){const n=Math.ceil((i+s)/2);if(0===n||t[n-1]<=e&&t[n]>e){r=n;break}e<t[n]?s=n-1:i=n+1}return r}sampleFace(e,t,i,s,r){let n=this.randomFunction(),a=this.randomFunction();n+a>1&&(n=1-n,a=1-a);const o=this.indexAttribute;let u=3*e,h=3*e+1,c=3*e+2;return o&&(u=o.getX(u),h=o.getX(h),c=o.getX(c)),m.a.fromBufferAttribute(this.positionAttribute,u),m.b.fromBufferAttribute(this.positionAttribute,h),m.c.fromBufferAttribute(this.positionAttribute,c),t.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)),void 0!==i&&(void 0!==this.normalAttribute?(m.a.fromBufferAttribute(this.normalAttribute,u),m.b.fromBufferAttribute(this.normalAttribute,h),m.c.fromBufferAttribute(this.normalAttribute,c),i.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)).normalize()):m.getNormal(i)),void 0!==s&&void 0!==this.colorAttribute&&(m.a.fromBufferAttribute(this.colorAttribute,u),m.b.fromBufferAttribute(this.colorAttribute,h),m.c.fromBufferAttribute(this.colorAttribute,c),g.set(0,0,0).addScaledVector(m.a,n).addScaledVector(m.b,a).addScaledVector(m.c,1-(n+a)),s.r=g.x,s.g=g.y,s.b=g.z),void 0!==r&&void 0!==this.uvAttribute&&(p.fromBufferAttribute(this.uvAttribute,u),v.fromBufferAttribute(this.uvAttribute,h),x.fromBufferAttribute(this.uvAttribute,c),r.set(0,0).addScaledVector(p,n).addScaledVector(v,a).addScaledVector(x,1-(n+a))),this}}class f{constructor(e,t){r(this,"textureSize"),r(this,"dataTextures"),r(this,"eventEmitter"),this.eventEmitter=e,this.textureSize=t,this.dataTextures=new Map,this.updateServiceState("ready")}setTextureSize(e){this.textureSize!==e&&(this.textureSize=e,this.dataTextures.forEach((e=>e.dispose())),this.dataTextures.clear())}async getDataTexture(e){const t=this.dataTextures.get(e.name);if(t)return t;var i,s;const r=function(e,t){const i=new a.BufferGeometry;i.setAttribute("position",new a.BufferAttribute(new Float32Array(e.position),3)),e.normal&&i.setAttribute("normal",new a.BufferAttribute(new Float32Array(e.normal),3));const s=new a.MeshBasicMaterial,r=new a.Mesh(i,s);r.scale.set(e.scale.x,e.scale.y,e.scale.z);const n=new T(r).build(),o=new Float32Array(t*t*4),u=new a.Vector3;for(let a=0;a<t;a++)for(let i=0;i<t;i++){const s=a*t+i;n.sample(u),o[4*s]=u.x*e.scale.x,o[4*s+1]=u.y*e.scale.y,o[4*s+2]=u.z*e.scale.z,o[4*s+3]=.01*(Math.random()-.5)}return o}({position:(i=e).geometry.attributes.position.array,normal:null==(s=i.geometry.attributes.normal)?void 0:s.array,scale:{x:i.scale.x,y:i.scale.y,z:i.scale.z}},this.textureSize),n=h(r,this.textureSize);return n.name=e.name,n}async dispose(){this.dataTextures.clear(),this.updateServiceState("disposed")}updateServiceState(e){this.eventEmitter.emit("serviceStateUpdated",{type:"data-texture",state:e})}}class y{constructor(e){r(this,"size"),r(this,"mesh"),r(this,"matcapMaterial"),r(this,"fallbackGeometry"),r(this,"uniforms"),r(this,"originColor"),r(this,"destinationColor"),r(this,"geometries"),r(this,"uvRefsCache"),r(this,"previousScale"),this.size=e,this.geometries=new Map,this.uvRefsCache=new Map,this.previousScale={x:1,y:1,z:1},this.originColor="grey",this.destinationColor="grey",this.uniforms={uTime:{value:0},uProgress:{value:0},uTexture:{value:null},uVelocity:{value:null},uOriginTexture:{value:null},uDestinationTexture:{value:null}},this.matcapMaterial=new a.ShaderMaterial({uniforms:this.uniforms,vertexShader:"\nvarying vec2 vUv;\nuniform sampler2D uTexture;\nuniform sampler2D uVelocity;\nuniform float uTime;\nvarying vec3 vNormal;\nattribute vec2 uvRef;\nvarying vec3 vViewPosition;\n\nvec3 rotate3D(vec3 v, vec3 vel) {\n vec3 pos = v;\n vec3 up = vec3(0, 1, 0);\n vec3 axis = normalize(cross(up, vel));\n float angle = acos(dot(up, normalize(vel)));\n pos = pos * cos(angle) + cross(axis, pos) * sin(angle) + axis * dot(axis, pos) * (1. - cos(angle));\n return pos;\n}\n\nvoid main() {\n vUv = uv;\n vNormal = normal;\n\n vec4 color = texture2D(uTexture, uvRef);\n vec4 velocity = texture2D(uVelocity, uvRef);\n vec3 pos = color.xyz;// apply the texture to the vertex distribution.\n\n vec3 localPosition = position.xyz;\n if (length (velocity.xyz) < 0.0001) {\n velocity.xyz = vec3(0.0, 0.0001, 0.0001);\n }\n localPosition.y *= max(1.0, length(velocity.xyz) * 1000.0);\n localPosition = rotate3D(localPosition, velocity.xyz);\n vNormal = rotate3D(normal, velocity.xyz);\n\n mat4 instanceMat = instanceMatrix;\n instanceMat[3].xyz = pos.xyz;\n\n // unlike the traditional mvMatrix * position, we need to additional multiplication with the instance matrix.\n vec4 modelViewPosition = modelViewMatrix * instanceMat * vec4(localPosition, 1.0);\n\n vViewPosition = - modelViewPosition.xyz;\n\n gl_Position = projectionMatrix * modelViewPosition;\n}\n",fragmentShader:"\nvarying vec2 vUv;\nuniform sampler2D uTexture;\n\nuniform sampler2D uOriginTexture;\nuniform sampler2D uDestinationTexture;\n\nuniform float uProgress;\nvarying vec3 vNormal;\nvarying vec3 vViewPosition;\nvoid main() {\n vec3 viewDir = normalize( vViewPosition );\n vec3 x = normalize( vec3( viewDir.z, 0.0, - viewDir.x ) );\n vec3 y = cross( viewDir, x );\n vec2 uv = vec2( dot( x, vNormal ), dot( y, vNormal ) ) * 0.495 + 0.5; // 0.495 to remove artifacts caused by undersized matcap disks\n\n vec4 sourceMatcap = texture2D( uOriginTexture, uv );\n vec4 targetMatcap = texture2D( uDestinationTexture, uv );\n\n vec4 matcap = mix(sourceMatcap, targetMatcap, uProgress);\n gl_FragColor = matcap;\n}\n"}),this.setOriginColor(this.originColor),this.setDestinationColor(this.destinationColor),this.fallbackGeometry=new a.BoxGeometry(.001,.001,.001),this.mesh=this.createInstancedMesh(e,this.fallbackGeometry,this.matcapMaterial)}getMesh(){return this.mesh}update(e){const t=this.mesh.material;(t instanceof a.ShaderMaterial||t instanceof a.RawShaderMaterial)&&(t.uniforms.uTime.value=e)}setOriginMatcap(e){this.disposeSolidColorOriginTexture(),this.matcapMaterial.uniforms.uOriginTexture.value=e}setDestinationMatcap(e){this.disposeSolidColorDestinationTexture(),this.matcapMaterial.uniforms.uDestinationTexture.value=e}setProgress(e){e=Math.max(0,e),e=Math.min(1,e),this.matcapMaterial.uniforms.uProgress.value=e}setGeometrySize(e){this.mesh.geometry.scale(1/this.previousScale.x,1/this.previousScale.y,1/this.previousScale.z),this.mesh.geometry.scale(e.x,e.y,e.z),this.previousScale=e}useMatcapMaterial(){this.mesh.material=this.matcapMaterial}useGeometry(e){const t=this.geometries.get(e);t&&(this.mesh.geometry=t)}updateVelocityTexture(e){this.matcapMaterial.uniforms.uVelocity.value=e}updatePositionTexture(e){this.matcapMaterial.uniforms.uTexture.value=e}resize(e){if(this.size===e)return{current:this.mesh,previous:this.mesh};this.size=e;const t=this.mesh;return this.mesh=this.createInstancedMesh(e,t.geometry,t.material),{current:this.mesh,previous:t}}dispose(){this.mesh.dispose(),this.geometries.forEach((e=>e.dispose())),this.disposeSolidColorOriginTexture(),this.disposeSolidColorDestinationTexture(),this.matcapMaterial.dispose(),this.uvRefsCache.clear(),this.geometries.clear()}registerGeometry(e,t){const i=this.geometries.get(e);if(i&&i===t)return;const s=this.createUVRefs(this.size);t.setAttribute("uvRef",s),this.geometries.set(e,t),this.mesh.geometry===i&&(this.mesh.geometry=t),null==i||i.dispose()}setOriginColor(e){this.disposeSolidColorOriginTexture(),this.originColor=e,this.uniforms.uOriginTexture.value=this.createSolidColorDataTexture(e)}setDestinationColor(e){this.disposeSolidColorDestinationTexture(),this.destinationColor=e,this.uniforms.uDestinationTexture.value=this.createSolidColorDataTexture(e)}createUVRefs(e){const t=this.uvRefsCache.get(e);if(t)return t;const i=new Float32Array(e*e*2);for(let r=0;r<e;r++)for(let t=0;t<e;t++){const s=r*e+t;i[2*s]=t/(e-1),i[2*s+1]=r/(e-1)}const s=new a.InstancedBufferAttribute(i,2);return this.uvRefsCache.set(e,s),s}createInstancedMesh(e,t,i){(t=t||this.fallbackGeometry).setAttribute("uvRef",this.createUVRefs(e));const s=e*e;return new a.InstancedMesh(t,i,s)}createSolidColorDataTexture(e,t=16){const i=new a.Color(e),s=t,r=t,n=new Uint8Array(s*r*4),o=Math.floor(255*i.r),u=Math.floor(255*i.g),h=Math.floor(255*i.b);for(let a=0;a<s*r;a++){const e=4*a;n[e]=o,n[e+1]=u,n[e+2]=h,n[e+3]=255}const c=new a.DataTexture(n,s,r,a.RGBAFormat);return c.type=a.UnsignedByteType,c.wrapS=a.RepeatWrapping,c.wrapT=a.RepeatWrapping,c.minFilter=a.NearestFilter,c.magFilter=a.NearestFilter,c.needsUpdate=!0,c}disposeSolidColorOriginTexture(){this.originColor&&(this.originColor=null,this.uniforms.uOriginTexture.value&&this.uniforms.uOriginTexture.value.dispose())}disposeSolidColorDestinationTexture(){this.destinationColor&&(this.destinationColor=null,this.uniforms.uDestinationTexture.value&&this.uniforms.uDestinationTexture.value.dispose())}}class M{constructor(e,t,i,s){r(this,"active",!0),r(this,"raycaster",new a.Raycaster),r(this,"mousePosition",new a.Vector2),r(this,"camera"),r(this,"originGeometry"),r(this,"destinationGeometry"),r(this,"progress",0),r(this,"intersectionMesh",new a.Mesh),r(this,"geometryNeedsUpdate"),r(this,"eventEmitter"),r(this,"blendedGeometry"),r(this,"intersection"),r(this,"lastKnownOriginMeshID"),r(this,"lastKnownDestinationMeshID"),this.camera=t,this.originGeometry=i,this.eventEmitter=e,this.destinationGeometry=s,this.geometryNeedsUpdate=!0}setActive(e){this.active=e}getIntersectionMesh(){return this.intersectionMesh}setCamera(e){this.camera=e}setOriginGeometry(e){this.lastKnownOriginMeshID!==e.uuid&&(this.originGeometry&&this.originGeometry.dispose(),this.lastKnownOriginMeshID=e.uuid,this.originGeometry=e.geometry.clone(),this.originGeometry.applyMatrix4(e.matrixWorld),this.geometryNeedsUpdate=!0)}setDestinationGeometry(e){this.lastKnownDestinationMeshID!==e.uuid&&(this.destinationGeometry&&this.destinationGeometry.dispose(),this.lastKnownDestinationMeshID=e.uuid,this.destinationGeometry=e.geometry.clone(),this.destinationGeometry.applyMatrix4(e.matrixWorld),this.geometryNeedsUpdate=!0)}setProgress(e){this.progress=e,this.geometryNeedsUpdate=!0}setPointerPosition(e){e&&this.mousePosition.copy(e)}calculate(e){if(this.active&&(this.updateIntersectionMesh(e),this.camera))return this.geometryNeedsUpdate&&(this.geometryNeedsUpdate=!1,this.blendedGeometry=this.getBlendedGeometry()),this.blendedGeometry?this.intersection=this.getFirstIntersection(this.camera,e):this.intersection=void 0,this.intersection?this.eventEmitter.emit("interactionPositionUpdated",{position:this.intersection}):this.eventEmitter.emit("interactionPositionUpdated",{position:{x:0,y:0,z:0,w:0}}),this.intersection}dispose(){var e;null==(e=this.blendedGeometry)||e.dispose(),this.intersectionMesh.geometry.dispose()}updateIntersectionMesh(e){this.blendedGeometry&&this.blendedGeometry.uuid!==this.intersectionMesh.geometry.uuid&&(this.intersectionMesh.geometry.dispose(),this.intersectionMesh.geometry=this.blendedGeometry),this.intersectionMesh.matrix.copy(e.matrixWorld),this.intersectionMesh.matrixWorld.copy(e.matrixWorld),this.intersectionMesh.matrixAutoUpdate=!1,this.intersectionMesh.updateMatrixWorld(!0)}getFirstIntersection(e,t){this.raycaster.setFromCamera(this.mousePosition,e);const i=this.raycaster.intersectObject(this.intersectionMesh,!1)[0];if(i){const e=i.point.clone(),s=t.worldToLocal(e);return new a.Vector4(s.x,s.y,s.z,1)}}getBlendedGeometry(){return 0===this.progress?this.originGeometry:1===this.progress?this.destinationGeometry:this.originGeometry&&this.destinationGeometry?this.originGeometry===this.destinationGeometry?this.originGeometry:this.blendGeometry(this.originGeometry,this.destinationGeometry,this.progress):void 0}blendGeometry(e,t,i){const s=new a.BufferGeometry,r=e.attributes.position.array,n=t.attributes.position.array,o=new Float32Array(r.length);for(let u=0;u<r.length;u+=3){const e=new a.Vector3(r[u],r[u+1],r[u+2]),t=new a.Vector3(n[u],n[u+1],n[u+2]),s=(new a.Vector3).lerpVectors(e,t,i);o[u]=s.x,o[u+1]=s.y,o[u+2]=s.z}return s.setAttribute("position",new a.BufferAttribute(o,3)),e.attributes.normal&&s.setAttribute("normal",e.attributes.normal.clone()),e.attributes.uv&&s.setAttribute("uv",e.attributes.uv.clone()),e.index&&s.setIndex(e.index.clone()),s}}const S=new t.OrthographicCamera(-1,1,1,-1,0,1);class D extends t.BufferGeometry{constructor(){super(),this.setAttribute("position",new t.Float32BufferAttribute([-1,3,0,-1,-1,0,3,-1,0],3)),this.setAttribute("uv",new t.Float32BufferAttribute([0,2,0,0,2,0],2))}}const w=new D;class P{constructor(e){this._mesh=new t.Mesh(w,e)}dispose(){this._mesh.geometry.dispose()}render(e){e.render(this._mesh,S)}get material(){return this._mesh.material}set material(e){this._mesh.material=e}}class b{constructor(e,i,s){this.variables=[],this.currentTextureIndex=0;let r=t.FloatType;const n={passThruTexture:{value:null}},a=h("uniform sampler2D passThruTexture;\n\nvoid main() {\n\n\tvec2 uv = gl_FragCoord.xy / resolution.xy;\n\n\tgl_FragColor = texture2D( passThruTexture, uv );\n\n}\n",n),o=new P(a);function u(t){t.defines.resolution="vec2( "+e.toFixed(1)+", "+i.toFixed(1)+" )"}function h(e,i){i=i||{};const s=new t.ShaderMaterial({name:"GPUComputationShader",uniforms:i,vertexShader:"void main()\t{\n\n\tgl_Position = vec4( position, 1.0 );\n\n}\n",fragmentShader:e});return u(s),s}this.setDataType=function(e){return r=e,this},this.addVariable=function(e,i,s){const r={name:e,initialValueTexture:s,material:this.createShaderMaterial(i),dependencies:null,renderTargets:[],wrapS:null,wrapT:null,minFilter:t.NearestFilter,magFilter:t.NearestFilter};return this.variables.push(r),r},this.setVariableDependencies=function(e,t){e.dependencies=t},this.init=function(){if(0===s.capabilities.maxVertexTextures)return"No support for vertex shader textures.";for(let t=0;t<this.variables.length;t++){const s=this.variables[t];s.renderTargets[0]=this.createRenderTarget(e,i,s.wrapS,s.wrapT,s.minFilter,s.magFilter),s.renderTargets[1]=this.createRenderTarget(e,i,s.wrapS,s.wrapT,s.minFilter,s.magFilter),this.renderTexture(s.initialValueTexture,s.renderTargets[0]),this.renderTexture(s.initialValueTexture,s.renderTargets[1]);const r=s.material,n=r.uniforms;if(null!==s.dependencies)for(let e=0;e<s.dependencies.length;e++){const t=s.dependencies[e];if(t.name!==s.name){let e=!1;for(let i=0;i<this.variables.length;i++)if(t.name===this.variables[i].name){e=!0;break}if(!e)return"Variable dependency not found. Variable="+s.name+", dependency="+t.name}n[t.name]={value:null},r.fragmentShader="\nuniform sampler2D "+t.name+";\n"+r.fragmentShader}}return this.currentTextureIndex=0,null},this.compute=function(){const e=this.currentTextureIndex,t=0===this.currentTextureIndex?1:0;for(let i=0,s=this.variables.length;i<s;i++){const s=this.variables[i];if(null!==s.dependencies){const t=s.material.uniforms;for(let i=0,r=s.dependencies.length;i<r;i++){const r=s.dependencies[i];t[r.name].value=r.renderTargets[e].texture}}this.doRenderTarget(s.material,s.renderTargets[t])}this.currentTextureIndex=t},this.getCurrentRenderTarget=function(e){return e.renderTargets[this.currentTextureIndex]},this.getAlternateRenderTarget=function(e){return e.renderTargets[0===this.currentTextureIndex?1:0]},this.dispose=function(){o.dispose();const e=this.variables;for(let t=0;t<e.length;t++){const i=e[t];i.initialValueTexture&&i.initialValueTexture.dispose();const s=i.renderTargets;for(let e=0;e<s.length;e++){s[e].dispose()}}},this.addResolutionDefine=u,this.createShaderMaterial=h,this.createRenderTarget=function(s,n,a,o,u,h){s=s||e,n=n||i,a=a||t.ClampToEdgeWrapping,o=o||t.ClampToEdgeWrapping,u=u||t.NearestFilter,h=h||t.NearestFilter;return new t.WebGLRenderTarget(s,n,{wrapS:a,wrapT:o,minFilter:u,magFilter:h,format:t.RGBAFormat,type:r,depthBuffer:!1})},this.createTexture=function(){const s=new Float32Array(e*i*4),r=new t.DataTexture(s,e,i,t.RGBAFormat,t.FloatType);return r.needsUpdate=!0,r},this.renderTexture=function(e,t){n.passThruTexture.value=e,this.doRenderTarget(a,t),n.passThruTexture.value=null},this.doRenderTarget=function(e,t){const i=s.getRenderTarget(),r=s.xr.enabled,n=s.shadowMap.autoUpdate;s.xr.enabled=!1,s.shadowMap.autoUpdate=!1,o.material=e,s.setRenderTarget(t),o.render(s),o.material=a,s.xr.enabled=r,s.shadowMap.autoUpdate=n,s.setRenderTarget(i)}}}class R{constructor(e,t,i){r(this,"gpuComputationRenderer"),r(this,"webGLRenderer"),r(this,"positionDataTexture"),r(this,"velocityDataTexture"),r(this,"mixPositionsVar"),r(this,"velocityVar"),r(this,"positionVar"),r(this,"interactionPosition"),r(this,"lastKnownPositionDataTexture"),r(this,"lastKnownVelocityDataTexture"),r(this,"lastKnownMixProgress"),r(this,"initialDataTexture"),this.initialDataTexture=i??function(e){const t=new Float32Array(e*e*4);for(let i=0;i<e;i++)for(let s=0;s<e;s++){const r=i*e+s;let n=Math.random()*Math.PI*2,a=Math.acos(2*Math.random()-1),o=Math.sin(a)*Math.cos(n),u=Math.sin(a)*Math.sin(n),h=Math.cos(a);t[4*r]=o,t[4*r+1]=u,t[4*r+2]=h,t[4*r+3]=.01*(Math.random()-.5)}return h(t,e)}(e),this.positionDataTexture=this.initialDataTexture,this.webGLRenderer=t,this.gpuComputationRenderer=new b(e,e,this.webGLRenderer),this.lastKnownMixProgress=0,t.capabilities.isWebGL2||this.gpuComputationRenderer.setDataType(a.HalfFloatType),this.velocityDataTexture=function(e){return h(new Float32Array(4*e*e),e)}(e),this.interactionPosition=new a.Vector4(0,0,0,0),this.mixPositionsVar=this.gpuComputationRenderer.addVariable("uMixedPosition","\nuniform sampler2D uPositionA;\nuniform sampler2D uPositionB;\nuniform float uProgress;\n\nvoid main() {\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n vec3 positionA = texture2D(uPositionA, uv).xyz;\n vec3 positionB = texture2D(uPositionB, uv).xyz;\n vec3 mixedPosition = mix(positionA, positionB, uProgress);\n gl_FragColor = vec4(mixedPosition, 1.0);\n}\n",this.positionDataTexture),this.velocityVar=this.gpuComputationRenderer.addVariable("uCurrentVelocity","\nuniform float uProgress;\nuniform vec4 uInteractionPosition;\nuniform float uTime;\nuniform float uTractionForce;\nuniform float uMaxRepelDistance;\n\nfloat rand(vec2 co) {\n return fract(sin(dot(co, vec2(12.9898, 78.233))) * 43758.5453);\n}\n\nvoid main() {\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n float offset = rand(uv);\n\n vec3 position = texture2D(uCurrentPosition, uv).xyz;\n vec3 velocity = texture2D(uCurrentVelocity, uv).xyz;\n vec3 mixedPosition = texture2D(uMixedPosition, uv).xyz;\n\n velocity *= 0.9;\n\n // particle traction\n vec3 direction = normalize(mixedPosition - position); // direction vector\n float dist = length ( mixedPosition - position ); // distance from where it was supposed to be, and currently are.\n if (dist > 0.01) {\n position += direction * 0.1 * uTractionForce; // uTractionForce defaults to 0.1\n }\n\n // mouse repel force\n float pointerDistance = distance(position, uInteractionPosition.xyz);\n float mouseRepelModifier = clamp(uMaxRepelDistance - pointerDistance, 0.0, 1.0);\n float normalizedDistance = pointerDistance / uMaxRepelDistance;\n float repulsionStrength = (1.0 - normalizedDistance) * uInteractionPosition.w;\n direction = normalize(position - uInteractionPosition.xyz);\n velocity += (direction * 0.01 * repulsionStrength) * mouseRepelModifier;\n\n float lifespan = 20.0;\n float age = mod(uTime + lifespan * offset, lifespan);\n\n if (age < 0.1) {\n position.xyz = mixedPosition;\n }\n\n gl_FragColor = vec4(velocity, 1.0);\n}\n",this.velocityDataTexture),this.positionVar=this.gpuComputationRenderer.addVariable("uCurrentPosition","\nuniform float uProgress;\nuniform vec4 uInteractionPosition;\nuniform float uTime;\nuniform float uTractionForce;\n\nfloat rand(vec2 co) {\n return fract(sin(dot(co, vec2(12.9898, 78.233))) * 43758.5453);\n}\n\nvoid main() {\n\n // in GPGPU, we calculate the uv on each fragment shader, not using the static varying passed over from the v shader.\n vec2 uv = gl_FragCoord.xy / resolution.xy;\n float offset = rand(uv);\n\n vec3 position = texture2D(uCurrentPosition, uv).xyz;\n vec3 velocity = texture2D(uCurrentVelocity, uv).xyz;\n vec3 mixedPosition = texture2D(uMixedPosition, uv).xyz;\n\n // particle attraction to original position.\n vec3 direction = normalize(mixedPosition - position); // direction vector\n float dist = length ( mixedPosition - position ); // distance from where it was supposed to be, and currently are.\n\n if (dist > 0.01) {\n position = mix(position, mixedPosition, 0.1 * uTractionForce); // 0.1 ~ 0.001 (faster, slower)\n }\n\n position += velocity;\n gl_FragColor = vec4(position, 1.0);\n}\n",this.positionDataTexture),this.mixPositionsVar.material.uniforms.uProgress={value:0},this.mixPositionsVar.material.uniforms.uPositionA={value:this.initialDataTexture},this.mixPositionsVar.material.uniforms.uPositionB={value:this.initialDataTexture},this.velocityVar.material.uniforms.uTime={value:0},this.velocityVar.material.uniforms.uInteractionPosition={value:this.interactionPosition},this.velocityVar.material.uniforms.uCurrentPosition={value:this.positionDataTexture},this.velocityVar.material.uniforms.uTractionForce={value:.1},this.velocityVar.material.uniforms.uMaxRepelDistance={value:.3},this.positionVar.material.uniforms.uTime={value:0},this.positionVar.material.uniforms.uProgress={value:0},this.positionVar.material.uniforms.uTractionForce={value:.1},this.positionVar.material.uniforms.uInteractionPosition={value:this.interactionPosition},this.positionVar.material.uniforms.uCurrentPosition={value:this.positionDataTexture},this.gpuComputationRenderer.setVariableDependencies(this.positionVar,[this.velocityVar,this.positionVar,this.mixPositionsVar]),this.gpuComputationRenderer.setVariableDependencies(this.velocityVar,[this.velocityVar,this.positionVar,this.mixPositionsVar]);const s=this.gpuComputationRenderer.init();if(s)throw new Error("failed to initialize SimulationRenderer: "+s);this.lastKnownVelocityDataTexture=this.getVelocityTexture(),this.lastKnownPositionDataTexture=this.getPositionTexture()}setMorphSourceDataTexture(e){this.mixPositionsVar.material.uniforms.uPositionA.value=e}setMorphDestinationDataTexture(e){this.mixPositionsVar.material.uniforms.uPositionB.value=e}setMaxRepelDistance(e){this.velocityVar.material.uniforms.uMaxRepelDistance.value=e}setProgress(e){this.lastKnownMixProgress=l(e,0,1),this.mixPositionsVar.material.uniforms.uProgress.value=this.lastKnownMixProgress}setVelocityTractionForce(e){this.velocityVar.material.uniforms.uTractionForce.value=e}setPositionalTractionForce(e){this.positionVar.material.uniforms.uTractionForce.value=e}setInteractionPosition(e){this.interactionPosition.copy(e)}dispose(){this.mixPositionsVar.renderTargets.forEach((e=>e.dispose())),this.positionVar.renderTargets.forEach((e=>e.dispose())),this.velocityVar.renderTargets.forEach((e=>e.dispose())),this.positionDataTexture.dispose(),this.velocityDataTexture.dispose(),this.gpuComputationRenderer.dispose()}compute(e){this.velocityVar.material.uniforms.uTime.value=e,this.positionVar.material.uniforms.uTime.value=e,this.gpuComputationRenderer.compute()}getVelocityTexture(){return this.lastKnownVelocityDataTexture=this.gpuComputationRenderer.getCurrentRenderTarget(this.velocityVar).texture,this.lastKnownVelocityDataTexture}getPositionTexture(){return this.lastKnownPositionDataTexture=this.gpuComputationRenderer.getCurrentRenderTarget(this.positionVar).texture,this.lastKnownPositionDataTexture}}class V{constructor(e,t,i){r(this,"state"),r(this,"textureSize"),r(this,"dataTextureTransitionProgress"),r(this,"velocityTractionForce"),r(this,"positionalTractionForce"),r(this,"simulationRenderer"),r(this,"webGLRenderer"),r(this,"eventEmitter"),r(this,"lastKnownVelocityDataTexture"),r(this,"lastKnownPositionDataTexture"),this.eventEmitter=e,this.webGLRenderer=i,this.textureSize=t,this.dataTextureTransitionProgress=0,this.velocityTractionForce=.1,this.positionalTractionForce=.1,this.updateServiceState("initializing"),this.simulationRenderer=new R(this.textureSize,this.webGLRenderer),this.lastKnownVelocityDataTexture=this.simulationRenderer.getVelocityTexture(),this.lastKnownPositionDataTexture=this.simulationRenderer.getPositionTexture(),this.updateServiceState("ready")}setTextureSize(e){this.updateServiceState("initializing"),this.simulationRenderer.dispose(),this.textureSize=e,this.simulationRenderer=new R(e,this.webGLRenderer),this.updateServiceState("ready")}setOriginDataTexture(e){this.textureSize!==e.textureSize?this.eventEmitter.emit("invalidRequest",{message:`Texture size mismatch: ${e.textureSize} vs ${this.textureSize}`}):this.simulationRenderer.setMorphSourceDataTexture(e.dataTexture)}setDestinationDataTexture(e){this.textureSize!==e.textureSize?this.eventEmitter.emit("invalidRequest",{message:`Texture size mismatch: ${e.textureSize} vs ${this.textureSize}`}):this.simulationRenderer.setMorphDestinationDataTexture(e.dataTexture)}setDataTextureTransitionProgress(e){this.dataTextureTransitionProgress=e,this.simulationRenderer.setProgress(this.dataTextureTransitionProgress)}setVelocityTractionForce(e){this.velocityTractionForce=e,this.simulationRenderer.setVelocityTractionForce(this.velocityTractionForce)}setPositionalTractionForce(e){this.positionalTractionForce=e,this.simulationRenderer.setPositionalTractionForce(this.positionalTractionForce)}compute(e){this.simulationRenderer.compute(e)}getVelocityTexture(){return"ready"===this.state&&(this.lastKnownVelocityDataTexture=this.simulationRenderer.getVelocityTexture()),this.lastKnownVelocityDataTexture}getPositionTexture(){return"ready"===this.state&&(this.lastKnownPositionDataTexture=this.simulationRenderer.getPositionTexture()),this.lastKnownPositionDataTexture}dispose(){this.updateServiceState("disposed"),this.simulationRenderer.dispose(),this.lastKnownVelocityDataTexture.dispose(),this.lastKnownPositionDataTexture.dispose()}updateServiceState(e){this.state=e,this.eventEmitter.emit("serviceStateUpdated",{type:"simulation",state:e})}setInteractionPosition(e){this.simulationRenderer.setInteractionPosition(e)}setMaxRepelDistance(e){this.simulationRenderer.setMaxRepelDistance(e)}}class A{constructor(){r(this,"execStatus",new Map)}get(e){const t=this.execStatus.get(e);return t||(this.execStatus.set(e,"idle"),"idle")}set(e,t){this.execStatus.set(e,t)}}class C{constructor(e){r(this,"eventEmitter"),r(this,"transitions",new Map),r(this,"execStatus"),r(this,"ongoingTransitions",new Map),this.eventEmitter=e,this.execStatus=new A,this.eventEmitter.on("transitionCancelled",this.handleTransitionCancelledEvent.bind(this))}enqueue(e,t,i={}){const s={...t,...i,cancelled:!1,duration:.001*t.duration};this.getQueue(e).push(s)}compute(e){this.transitions.forEach(((t,i)=>{var s;if(t.length&&!this.ongoingTransitions.has(i)){const r=t.shift();r&&(this.ongoingTransitions.set(i,{...r,startTime:e}),null==(s=r.onTransitionBegin)||s.call(r))}})),this.ongoingTransitions.forEach(((t,i)=>{var s,r,n;if(t.cancelled)return null==(s=t.onTransitionCancelled)||s.call(t),void this.ongoingTransitions.delete(i);const{startTime:a,duration:o,easing:u}=t,h=e-a,c=l(u(Math.min(1,h/o)),0,1);this.emitTransitionProgress(i,c),null==(r=t.onTransitionProgress)||r.call(t,c),c>=1&&(this.emitTransitionFinished(i),null==(n=t.onTransitionFinished)||n.call(t),this.ongoingTransitions.delete(i))}))}getQueue(e){const t=this.transitions.get(e);return t||(this.transitions.set(e,[]),this.transitions.get(e)??[])}handleTransitionCancelledEvent({type:e}){var t;const i=this.getQueue(e);for(;i.length;)i.pop();const s=this.ongoingTransitions.get(e);s&&(s.cancelled=!0,null==(t=s.onTransitionCancelled)||t.call(s))}emitTransitionProgress(e,t){this.eventEmitter.emit("transitionProgressed",{type:e,progress:t})}emitTransitionFinished(e){this.eventEmitter.emit("transitionFinished",{type:e})}}return e.ParticlesEngine=class{constructor(e){r(this,"simulationRendererService"),r(this,"eventEmitter"),r(this,"renderer"),r(this,"scene"),r(this,"serviceStates"),r(this,"assetService"),r(this,"dataTextureManager"),r(this,"instancedMeshManager"),r(this,"transitionService"),r(this,"engineState"),r(this,"intersectionService");const{scene:t,renderer:i,camera:s,textureSize:n,useIntersection:a=!0}=e;this.eventEmitter=new u,this.serviceStates=this.getInitialServiceStates(),this.eventEmitter.on("serviceStateUpdated",this.handleServiceStateUpdated.bind(this)),this.scene=t,this.renderer=i,this.engineState=this.initialEngineState(e),this.assetService=new d(this.eventEmitter),this.transitionService=new C(this.eventEmitter),this.dataTextureManager=new f(this.eventEmitter,n),this.simulationRendererService=new V(this.eventEmitter,n,this.renderer),this.instancedMeshManager=new y(n),this.instancedMeshManager.useMatcapMaterial(),this.scene.add(this.instancedMeshManager.getMesh()),this.intersectionService=new M(this.eventEmitter,s),a||this.intersectionService.setActive(!1),this.eventEmitter.on("transitionProgressed",this.handleTransitionProgress.bind(this)),this.eventEmitter.on("interactionPositionUpdated",this.handleInteractionPositionUpdated.bind(this))}render(e){this.intersectionService.calculate(this.instancedMeshManager.getMesh()),this.transitionService.compute(e),this.simulationRendererService.compute(e),this.instancedMeshManager.update(e),this.instancedMeshManager.updateVelocityTexture(this.simulationRendererService.getVelocityTexture()),this.instancedMeshManager.updatePositionTexture(this.simulationRendererService.getPositionTexture())}setOriginDataTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"});const i=this.assetService.getMesh(e);i?this.dataTextureManager.getDataTexture(i).then((t=>{this.engineState.originMeshID=e,this.simulationRendererService.setOriginDataTexture({dataTexture:t,textureSize:this.engineState.textureSize}),this.intersectionService.setOriginGeometry(i)})):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${e}" does not exist`})}setDestinationDataTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"});const i=this.assetService.getMesh(e);i?this.dataTextureManager.getDataTexture(i).then((t=>{this.engineState.destinationMeshID=e,this.simulationRendererService.setDestinationDataTexture({dataTexture:t,textureSize:this.engineState.textureSize}),this.intersectionService.setDestinationGeometry(i)})):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${e}" does not exist`})}setDataTextureTransitionProgress(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"data-texture"}),this.engineState.dataTextureTransitionProgress=e,this.simulationRendererService.setDataTextureTransitionProgress(e),this.intersectionService.setProgress(e)}setOriginMatcap(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.originMatcapID=e,this.instancedMeshManager.setOriginMatcap(this.assetService.getMatcap(e))}setDestinationMatcap(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.destinationMatcapID=e,this.instancedMeshManager.setDestinationMatcap(this.assetService.getMatcap(e))}setOriginColor(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.instancedMeshManager.setOriginColor(e)}setDestinationColor(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.instancedMeshManager.setDestinationColor(e)}setOriginTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),"string"==typeof e&&this.assetService.hasMatcap(e)?this.setOriginMatcap(e):this.setOriginColor(e)}setDestinationTexture(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),"string"==typeof e&&this.assetService.hasMatcap(e)?this.setDestinationMatcap(e):this.setDestinationColor(e)}setMatcapProgress(e,t=!1){t&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.engineState.matcapTransitionProgress=e,this.instancedMeshManager.setProgress(e)}async setTextureSize(e){this.engineState.textureSize=e,this.dataTextureManager.setTextureSize(e),this.simulationRendererService.setTextureSize(e),this.instancedMeshManager.resize(e);const t=this.assetService.getMesh(this.engineState.originMeshID);if(!t)return void this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${this.engineState.originMeshID}" does not exist`});const i=this.assetService.getMesh(this.engineState.destinationMeshID);i?(this.dataTextureManager.getDataTexture(t).then((t=>this.simulationRendererService.setOriginDataTexture({dataTexture:t,textureSize:e}))),this.dataTextureManager.getDataTexture(i).then((t=>this.simulationRendererService.setDestinationDataTexture({dataTexture:t,textureSize:e}))),this.simulationRendererService.setDataTextureTransitionProgress(this.engineState.dataTextureTransitionProgress),this.simulationRendererService.setVelocityTractionForce(this.engineState.velocityTractionForce),this.simulationRendererService.setPositionalTractionForce(this.engineState.positionalTractionForce),this.instancedMeshManager.setOriginMatcap(this.assetService.getMatcap(this.engineState.originMatcapID)),this.instancedMeshManager.setDestinationMatcap(this.assetService.getMatcap(this.engineState.destinationMatcapID)),this.instancedMeshManager.setProgress(this.engineState.matcapTransitionProgress),this.instancedMeshManager.setGeometrySize(this.engineState.instanceGeometryScale)):this.eventEmitter.emit("invalidRequest",{message:`Mesh with id "${this.engineState.destinationMeshID}" does not exist`})}registerMesh(e,t){this.assetService.register(e,t)}registerMatcap(e,t){this.assetService.register(e,t)}async fetchAndRegisterMesh(e,t){return await this.assetService.loadMeshAsync(e,t)}async fetchAndRegisterMatcap(e,t){return await this.assetService.loadTextureAsync(e,t)}useIntersect(e){this.intersectionService.setActive(e),this.engineState.useIntersect=e,e||(this.engineState.pointerPosition={x:-99999999,y:-99999999},this.intersectionService.setPointerPosition(this.engineState.pointerPosition))}setPointerPosition(e){this.engineState.useIntersect&&(this.engineState.pointerPosition=e,this.intersectionService.setPointerPosition(e))}setGeometrySize(e){this.engineState.instanceGeometryScale=e,this.instancedMeshManager.setGeometrySize(e)}setVelocityTractionForce(e){this.engineState.velocityTractionForce=e,this.simulationRendererService.setVelocityTractionForce(e)}setPositionalTractionForce(e){this.engineState.positionalTractionForce=e,this.simulationRendererService.setPositionalTractionForce(e)}setMaxRepelDistance(e){this.engineState.maxRepelDistance=e,this.simulationRendererService.setMaxRepelDistance(e)}scheduleMeshTransition(e,t,i=o,s=1e3,r=!1){this.transitionService.enqueue("data-texture",{easing:i,duration:s},{onTransitionBegin:()=>{this.setOriginDataTexture(e,r),this.setDestinationDataTexture(t,r),this.setDataTextureTransitionProgress(0)}})}scheduleMatcapTransition(e,t,i=o,s=1e3,r=!1){this.transitionService.enqueue("matcap",{easing:i,duration:s},{onTransitionBegin:()=>{this.setOriginMatcap(e,r),this.setDestinationMatcap(t,r),this.setMatcapProgress(0)}})}scheduleTextureTransition(e,t,i){const s=(null==i?void 0:i.easing)??o,r=(null==i?void 0:i.duration)??1e3;(null==i?void 0:i.override)&&this.eventEmitter.emit("transitionCancelled",{type:"matcap"}),this.transitionService.enqueue("matcap",{easing:s,duration:r},{onTransitionBegin:()=>{this.setOriginTexture(e),this.setDestinationTexture(t),this.setMatcapProgress(0)}})}handleServiceStateUpdated({type:e,state:t}){this.serviceStates[e]=t}getObject(){return this.instancedMeshManager.getMesh()}getMeshIDs(){return this.assetService.getMeshIDs()}getMatcapIDs(){return this.assetService.getTextureIDs()}getMeshes(){return this.assetService.getMeshes()}getTextures(){return this.assetService.getTextures()}dispose(){this.scene.remove(this.instancedMeshManager.getMesh()),this.simulationRendererService.dispose(),this.instancedMeshManager.dispose(),this.intersectionService.dispose(),this.assetService.dispose(),this.dataTextureManager.dispose()}initialEngineState(e){return{textureSize:e.textureSize,originMeshID:"",destinationMeshID:"",dataTextureTransitionProgress:0,originMatcapID:"",destinationMatcapID:"",matcapTransitionProgress:0,velocityTractionForce:.1,positionalTractionForce:.1,maxRepelDistance:.3,pointerPosition:{x:0,y:0},instanceGeometryScale:{x:1,y:1,z:1},useIntersect:e.useIntersection??!0}}getInitialServiceStates(){return{"data-texture":"created","instanced-mesh":"created",matcap:"created",simulation:"created",asset:"created"}}handleTransitionProgress({type:e,progress:t}){switch(e){case"data-texture":this.setDataTextureTransitionProgress(t);break;case"matcap":this.setMatcapProgress(t)}}handleInteractionPositionUpdated({position:e}){this.simulationRendererService.setInteractionPosition(e)}},Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),e}({},THREE,three-stdlib);
2
2
  //# sourceMappingURL=ionian.iife.js.map