string-tune-3d 0.0.11 → 0.0.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/modules/String3D.ts","../src/core/String3DCamera.ts","../src/core/filters/String3DCustomFilter.ts","../src/core/filters/String3DFilterPipeline.ts","../src/core/String3DRenderer.ts","../src/core/String3DObject.ts","../src/modules/string3d/styleUtils.ts","../src/core/materials/String3DCustomMaterial.ts","../src/core/materials/MaterialFactory.ts","../src/core/String3DScene.ts","../src/core/synchronizer/StyleBundleCache.ts","../src/core/synchronizer/GroupSynchronizer.ts","../src/core/synchronizer/LightSynchronizer.ts","../src/core/synchronizer/MeshSynchronizer.ts","../src/core/synchronizer/ParticlesSynchronizer.ts","../src/core/text/String3DFontRegistry.ts","../src/core/text/FontConverter.ts","../src/core/synchronizer/TextSynchronizer.ts","../src/core/synchronizer/String3DSynchronizer.ts","../src/modules/string3d/DirtySyncManager.ts","../src/modules/string3d/FilterController.ts","../src/adapters/ThreeJSMaterialFactory.ts","../src/adapters/ThreeJSProvider.ts"],"sourcesContent":["import { StringModule } from \"@fiddle-digital/string-tune\";\r\nimport { StringObject } from \"@fiddle-digital/string-tune\";\r\nimport { StringData } from \"@fiddle-digital/string-tune\";\r\nimport { StringContext } from \"@fiddle-digital/string-tune\";\r\nimport { String3DCamera } from \"../core/String3DCamera\";\r\nimport { String3DRenderer } from \"../core/String3DRenderer\";\r\nimport { String3DScene } from \"../core/String3DScene\";\r\nimport { String3DSynchronizer } from \"../core/synchronizer/String3DSynchronizer\";\r\nimport { I3DEngineProvider } from \"../core/abstractions/I3DEngineProvider\";\r\nimport { I3DEngine, I3DModelLoader } from \"../core/abstractions/I3DEngine\";\r\nimport { String3DObject } from \"../core/String3DObject\";\r\nimport { DirtySyncManager } from \"./string3d/DirtySyncManager\";\r\nimport { FilterController } from \"./string3d/FilterController\";\r\nimport { StyleReader } from \"./string3d/styleUtils\";\r\nimport { String3DFontRegistry } from \"../core/text\";\r\n\r\nexport interface String3DOptions {\r\n hideHTML?: boolean;\r\n container?: string | HTMLElement;\r\n zIndex?: number;\r\n modelLoaderType?: string;\r\n modelLoader?: I3DModelLoader;\r\n modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n useDirtySync?: boolean;\r\n styleReadIntervalMs?: number;\r\n layoutReadIntervalMs?: number;\r\n}\r\n\r\nexport class String3D extends StringModule {\r\n private static provider: I3DEngineProvider | null = null;\r\n private static _instance: String3D | null = null;\r\n\r\n private renderer: String3DRenderer | null = null;\r\n private camera: String3DCamera | null = null;\r\n private _scene: String3DScene | null = null;\r\n private synchronizer: String3DSynchronizer | null = null;\r\n private engine: I3DEngine | null = null;\r\n private canvasContainer: HTMLElement | null = null;\r\n private isLoading: Map<string, boolean> = new Map();\r\n private options: String3DOptions;\r\n private useDirtySync = false;\r\n private dirtySyncManager: DirtySyncManager;\r\n private lastSyncData: WeakMap<String3DObject, { scale: number }> = new WeakMap();\r\n private filterController: FilterController;\r\n private needsInitialResize = true;\r\n\r\n public static getInstance(): String3D | null {\r\n return String3D._instance;\r\n }\r\n\r\n public get scene(): String3DScene | null {\r\n return this._scene;\r\n }\r\n\r\n public static setProvider(provider: I3DEngineProvider): void {\r\n String3D.provider = provider;\r\n }\r\n\r\n public static registerFont(name: string, url: string, options: { default?: boolean } = {}): void {\r\n String3DFontRegistry.register(name, url);\r\n if (options.default) {\r\n String3DFontRegistry.setDefault(name);\r\n }\r\n }\r\n\r\n public static setDefaultFont(name: string): void {\r\n String3DFontRegistry.setDefault(name);\r\n }\r\n\r\n constructor(context: StringContext) {\r\n super(context);\r\n this.htmlKey = \"3d\";\r\n this.options = this.buildOptionsFromSettings();\r\n this.dirtySyncManager = new DirtySyncManager([\r\n \"style\",\r\n \"class\",\r\n \"string-3d\",\r\n \"string-3d-model-fit\",\r\n \"string-3d-model-scale\",\r\n ]);\r\n this.filterController = new FilterController((value) =>\r\n this.tools.easingFunction.process({ easing: value })\r\n );\r\n\r\n this.attributesToMap = [\r\n ...this.attributesToMap,\r\n { key: \"3d\", type: \"string\", fallback: \"box\" },\r\n { key: \"3d-model\", type: \"string\", fallback: \"\" },\r\n { key: \"3d-segments\", type: \"number\", fallback: 32 },\r\n { key: \"3d-segments-width\", type: \"number\", fallback: 32 },\r\n { key: \"3d-segments-height\", type: \"number\", fallback: 32 },\r\n { key: \"3d-model-loader\", type: \"string\", fallback: \"\" },\r\n { key: \"3d-model-scale\", type: \"number\", fallback: 1 },\r\n { key: \"3d-model-center\", type: \"boolean\", fallback: false },\r\n { key: \"3d-model-fit\", type: \"string\", fallback: \"contain\" },\r\n ];\r\n\r\n String3D._instance = this;\r\n }\r\n\r\n override canConnect(object: StringObject): boolean {\r\n return super.canConnect(object);\r\n }\r\n\r\n override initializeObject(\r\n globalId: number,\r\n object: StringObject,\r\n element: HTMLElement,\r\n attributes: Record<string, any>\r\n ): void {\r\n super.initializeObject(globalId, object, element, attributes);\r\n\r\n object.setProperty(\"parentId\", null);\r\n const parentElement = element.parentElement?.closest(\r\n '[string-3d=\"group\"]'\r\n ) as HTMLElement | null;\r\n if (parentElement) {\r\n const parentId = parentElement.getAttribute(\"string-id\");\r\n if (parentId) {\r\n object.setProperty(\"parentId\", parentId);\r\n object.setProperty(\"parent\", parentElement);\r\n }\r\n }\r\n }\r\n\r\n override onResize(): void {\r\n if (this.renderer && this.camera && this.synchronizer) {\r\n this.renderer.resize(this.camera);\r\n this.synchronizer.updateViewportSize(this.renderer.width, this.renderer.height);\r\n this.camera.clearScaleCache();\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.markAllDirty();\r\n }\r\n }\r\n }\r\n\r\n override onInit(): void {\r\n this.options = this.buildOptionsFromSettings();\r\n if (!String3D.provider) {\r\n return;\r\n }\r\n\r\n this.engine = String3D.provider.getEngine();\r\n this.canvasContainer = this.createOrGetContainer();\r\n this.registerTypedProperties();\r\n this.injectCSS();\r\n this.useDirtySync = !!this.options.useDirtySync;\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.enable();\r\n }\r\n\r\n this.renderer = new String3DRenderer(this.canvasContainer, this.engine);\r\n this.renderer.attach();\r\n\r\n this.camera = new String3DCamera(this.engine, \"orthographic\");\r\n this.camera.setPosition(0, 0, 1000);\r\n this.camera.resize(this.renderer.width, this.renderer.height);\r\n\r\n const modelLoader = this.resolveModelLoader();\r\n const modelLoaderFactory = this.resolveModelLoaderFactory();\r\n this._scene = new String3DScene(this.engine, {\r\n modelLoader,\r\n modelLoaderFactory,\r\n });\r\n this._scene.getScene().add(this.camera.camera);\r\n\r\n this.synchronizer = new String3DSynchronizer(\r\n this.camera,\r\n this.renderer.width,\r\n this.renderer.height,\r\n this.engine\r\n );\r\n this.synchronizer.setSyncOptions({\r\n styleReadIntervalMs: this.options.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.options.layoutReadIntervalMs,\r\n });\r\n\r\n this._scene.setSynchronizer(this.synchronizer);\r\n }\r\n\r\n override onSettingsChange(): void {\r\n this.options = this.buildOptionsFromSettings();\r\n const shouldUseDirtySync = !!this.options.useDirtySync;\r\n if (shouldUseDirtySync && !this.useDirtySync) {\r\n this.useDirtySync = true;\r\n this.dirtySyncManager.enable();\r\n if (this._scene) {\r\n this.dirtySyncManager.observeScene(this._scene.rootObjects);\r\n }\r\n this.dirtySyncManager.markAllDirty();\r\n } else if (!shouldUseDirtySync && this.useDirtySync) {\r\n this.useDirtySync = false;\r\n this.dirtySyncManager.disable();\r\n }\r\n\r\n this.synchronizer?.setSyncOptions({\r\n styleReadIntervalMs: this.options.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.options.layoutReadIntervalMs,\r\n });\r\n }\r\n\r\n private buildOptionsFromSettings(): String3DOptions {\r\n return {\r\n hideHTML: this.getSettingValue(\"hideHTML\", false),\r\n container: this.getSettingValue(\"container\", undefined),\r\n zIndex: this.getSettingValue(\"zIndex\", 1),\r\n modelLoaderType: this.getSettingValue(\"modelLoaderType\", undefined),\r\n modelLoader: this.getSettingValue(\"modelLoader\", undefined),\r\n modelLoaderFactory: this.getSettingValue(\"modelLoaderFactory\", undefined),\r\n useDirtySync: this.getSettingValue(\"useDirtySync\", false),\r\n styleReadIntervalMs: this.getSettingValue(\"styleReadIntervalMs\", 0),\r\n layoutReadIntervalMs: this.getSettingValue(\"layoutReadIntervalMs\", 0),\r\n };\r\n }\r\n\r\n private getSettingValue<T>(key: string, fallback: T): T {\r\n if (!this.settings || !(key in this.settings)) return fallback;\r\n return this.settings[key] as T;\r\n }\r\n\r\n private resolveModelLoader(): I3DModelLoader | undefined {\r\n if (!this.engine) return undefined;\r\n if (this.options.modelLoader) return this.options.modelLoader;\r\n if (this.options.modelLoaderFactory) return undefined;\r\n if (this.options.modelLoaderType) {\r\n try {\r\n return this.engine.createModelLoader(this.options.modelLoaderType);\r\n } catch (error) {}\r\n }\r\n return undefined;\r\n }\r\n\r\n private resolveModelLoaderFactory():\r\n | ((engine: I3DEngine, type?: string) => I3DModelLoader)\r\n | undefined {\r\n if (!this.engine) return undefined;\r\n if (this.options.modelLoaderFactory) return this.options.modelLoaderFactory;\r\n if (this.options.modelLoaderType) {\r\n return (engine: I3DEngine, type?: string) => {\r\n const loaderType = type || this.options.modelLoaderType;\r\n if (!loaderType) {\r\n throw new Error(\"[String3D] Model loader type not provided\");\r\n }\r\n return engine.createModelLoader(loaderType);\r\n };\r\n }\r\n return undefined;\r\n }\r\n\r\n private createOrGetContainer(): HTMLElement {\r\n if (this.options.container instanceof HTMLElement) {\r\n this.applyContainerStyles(this.options.container);\r\n return this.options.container;\r\n }\r\n\r\n if (typeof this.options.container === \"string\") {\r\n const existing = document.getElementById(this.options.container);\r\n if (existing) {\r\n this.applyContainerStyles(existing);\r\n return existing;\r\n }\r\n }\r\n\r\n const container = document.createElement(\"div\");\r\n container.id = \"string-3d-canvas\";\r\n this.applyContainerStyles(container);\r\n document.body.insertBefore(container, document.body.firstChild);\r\n return container;\r\n }\r\n\r\n private applyContainerStyles(el: HTMLElement): void {\r\n Object.assign(el.style, {\r\n position: \"fixed\",\r\n left: \"0\",\r\n top: \"0\",\r\n width: \"100vw\",\r\n height: \"100lvh\",\r\n zIndex: String(this.options.zIndex),\r\n pointerEvents: \"none\",\r\n });\r\n }\r\n\r\n override onObjectConnected(object: StringObject): void {\r\n if (this.isLoading.has(object.id) || !this._scene) {\r\n return;\r\n }\r\n this.isLoading.set(object.id, true);\r\n\r\n this._scene.createFromElement(object);\r\n\r\n if (this.useDirtySync && object.htmlElement) {\r\n this.dirtySyncManager.observeElement(object.htmlElement);\r\n this.dirtySyncManager.markDirty(object.htmlElement);\r\n }\r\n\r\n if (this.options.hideHTML && object.htmlElement) {\r\n object.htmlElement.style.opacity = \"0\";\r\n object.htmlElement.style.pointerEvents = \"none\";\r\n }\r\n }\r\n\r\n override onFrame(data: StringData): void {\r\n if (!this.renderer || !this._scene || !this.camera || !this.synchronizer) return;\r\n\r\n if (this.needsInitialResize) {\r\n this.needsInitialResize = false;\r\n this.renderer.resize(this.camera);\r\n this.synchronizer.updateViewportSize(this.renderer.width, this.renderer.height);\r\n }\r\n\r\n const dirtySet = this.useDirtySync ? this.dirtySyncManager.getDirtySet() : null;\r\n const forceSync = !dirtySet || dirtySet.size === 0;\r\n\r\n this.batchReadLayouts(this._scene.rootObjects, forceSync, dirtySet);\r\n\r\n this._scene.rootObjects.forEach((obj) => {\r\n this.syncRecursive(obj.el, obj, { scale: 1 }, forceSync, dirtySet);\r\n });\r\n\r\n const filterTargets = this.filterController.collectTargets(\r\n this._scene.rootObjects,\r\n performance.now(),\r\n this.useDirtySync,\r\n dirtySet\r\n );\r\n this.renderer!.render(this._scene!, this.camera!, filterTargets);\r\n\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.clearDirty();\r\n }\r\n }\r\n\r\n private batchReadLayouts(\r\n rootObjects: String3DObject[],\r\n forceSync: boolean,\r\n dirtySet: Set<HTMLElement> | null\r\n ): void {\r\n const walk = (obj: String3DObject): void => {\r\n if (obj.el) {\r\n const shouldSync = forceSync || !dirtySet || dirtySet.has(obj.el);\r\n if (shouldSync) {\r\n const rect = obj.el.getBoundingClientRect();\r\n const width = obj.el.offsetWidth || rect.width;\r\n const height = obj.el.offsetHeight || rect.height;\r\n (obj.el as any).__layoutCache = { rect, width, height };\r\n }\r\n }\r\n obj.children.forEach(walk);\r\n };\r\n rootObjects.forEach(walk);\r\n }\r\n\r\n private syncRecursive(\r\n el: HTMLElement | undefined,\r\n object: String3DObject,\r\n parentData: any,\r\n forceSync: boolean,\r\n dirtySet: Set<HTMLElement> | null\r\n ): void {\r\n if (!this.synchronizer || !el) return;\r\n const shouldSync =\r\n object.type === \"particles\" ||\r\n object.type === \"text\" ||\r\n forceSync ||\r\n !dirtySet ||\r\n dirtySet.has(el);\r\n let nextParentData = parentData;\r\n\r\n if (shouldSync) {\r\n const data = this.synchronizer.syncElement(el, object, parentData, {\r\n dirtySet,\r\n forceSync,\r\n });\r\n if (data && typeof data.scale === \"number\") {\r\n this.lastSyncData.set(object, data);\r\n nextParentData = data;\r\n }\r\n } else {\r\n const cached = this.lastSyncData.get(object);\r\n if (cached) {\r\n nextParentData = cached;\r\n }\r\n }\r\n\r\n const forceChildren = forceSync || shouldSync;\r\n object.children.forEach((child) =>\r\n this.syncRecursive(child.el, child, nextParentData, forceChildren, dirtySet)\r\n );\r\n }\r\n\r\n private injectCSS(): void {\r\n if (document.getElementById(\"string-3d-styles\")) return;\r\n\r\n const style = document.createElement(\"style\");\r\n style.id = \"string-3d-styles\";\r\n style.textContent = `\r\n @property --translate-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --translate-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --translate-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --scale { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-x { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-y { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-z { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --opacity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --filter { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --light-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --light-intensity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --light-distance { syntax: \"<number>\"; inherits: false; initial-value: 1000; }\r\n @property --light-decay { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --light-angle { syntax: \"<number>\"; inherits: false; initial-value: 1.0472; }\r\n @property --light-penumbra { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --light-ground-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --light-target { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --shadow-cast { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-receive { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-bias { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-map-size { syntax: \"<number>\"; inherits: false; initial-value: 512; }\r\n @property --texture-flip-y { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --texture-color-space { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-mode { syntax: \"*\"; inherits: false; initial-value: emitter; }\r\n @property --particles-count { syntax: \"<number>\"; inherits: false; initial-value: 300; }\r\n @property --particles-size { syntax: \"<number>\"; inherits: false; initial-value: 2; }\r\n @property --particles-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --particles-opacity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --particles-spread { syntax: \"<number>\"; inherits: false; initial-value: 120; }\r\n @property --particles-seed { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --particles-shape { syntax: \"*\"; inherits: false; initial-value: sphere; }\r\n @property --particles-fit { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --particles-model { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-model-loader { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-model-node { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model-loader { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model-node { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --emit-rate { syntax: \"<number>\"; inherits: false; initial-value: 30; }\r\n @property --emit-burst { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --particle-life { syntax: \"<number>\"; inherits: false; initial-value: 2.5; }\r\n @property --particle-speed { syntax: \"<number>\"; inherits: false; initial-value: 40; }\r\n @property --particle-direction { syntax: \"*\"; inherits: false; initial-value: 0 1 0; }\r\n @property --particle-gravity { syntax: \"*\"; inherits: false; initial-value: 0 -30 0; }\r\n @property --particle-drag { syntax: \"<number>\"; inherits: false; initial-value: 0.1; }\r\n @property --particle-size-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.6; }\r\n @property --particle-color-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.2; }\r\n @property --instance-shape { syntax: \"*\"; inherits: false; initial-value: sphere; }\r\n @property --instance-scale { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --instance-scale-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.5; }\r\n @property --instance-rotation-speed { syntax: \"<number>\"; inherits: false; initial-value: 0.4; }\r\n @property --instance-jitter { syntax: \"<number>\"; inherits: false; initial-value: 0.2; }\r\n @property --instance-flow { syntax: \"<number>\"; inherits: false; initial-value: 0.3; }\r\n @property --instance-disperse { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-depth { syntax: \"<number>\"; inherits: false; initial-value: 8; }\r\n @property --text-curve-segments { syntax: \"<number>\"; inherits: false; initial-value: 8; }\r\n @property --text-bevel-size { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-thickness { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-offset { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-steps { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-fit { syntax: \"*\"; inherits: false; initial-value: contain; }\r\n\r\n :where([string-3d]) {\r\n --translate-x: 0; --translate-y: 0; --translate-z: 0;\r\n --rotate-x: 0; --rotate-y: 0; --rotate-z: 0;\r\n --scale: 1; --scale-x: 1; --scale-y: 1; --scale-z: 1; --opacity: 1; --filter: none;\r\n --light-color: #ffffff; --light-intensity: 1; --light-distance: 1000; --light-decay: 0;\r\n --light-angle: 1.0472; --light-penumbra: 0; --light-ground-color: #ffffff; --light-target: none;\r\n --shadow-cast: 0; --shadow-receive: 0; --shadow-bias: 0; --shadow-map-size: 512;\r\n --texture-flip-y: 1; --texture-color-space: none;\r\n --particles-mode: emitter; --particles-count: 300; --particles-size: 2; --particles-color: #ffffff;\r\n --particles-opacity: 1; --particles-spread: 120; --particles-seed: 1; --particles-shape: sphere;\r\n --particles-fit: 0;\r\n --particles-model: none; --particles-model-loader: none; --particles-model-node: none;\r\n --instance-model: none; --instance-model-loader: none; --instance-model-node: none;\r\n --emit-rate: 30; --emit-burst: 0; --particle-life: 2.5; --particle-speed: 40;\r\n --particle-direction: 0 1 0; --particle-gravity: 0 -30 0; --particle-drag: 0.1;\r\n --particle-size-variation: 0.6; --particle-color-variation: 0.2;\r\n --instance-shape: sphere; --instance-scale: 1; --instance-scale-variation: 0.5;\r\n --instance-rotation-speed: 0.4; --instance-jitter: 0.2; --instance-flow: 0.3;\r\n --instance-disperse: 0;\r\n --instance-scatter: 0;\r\n --instance-scatter-x: 0; --instance-scatter-y: 0; --instance-scatter-z: 0;\r\n --text-depth: 8; --text-curve-segments: 8; --text-bevel-size: 0; --text-bevel-thickness: 0;\r\n --text-bevel-offset: 0; --text-bevel-steps: 0; --text-fit: contain;\r\n transform-style: preserve-3d;\r\n }\r\n\r\n [string-3d-visual=\"true\"] {\r\n transform:\r\n translate3d(calc(var(--translate-x) * 1px), calc(var(--translate-y) * 1px), calc(var(--translate-z) * 1px))\r\n rotateX(calc(var(--rotate-x) * 1deg))\r\n rotateY(calc(var(--rotate-y) * 1deg))\r\n rotateZ(calc(var(--rotate-z) * 1deg))\r\n scale3d(calc(var(--scale) * var(--scale-x)), calc(var(--scale) * var(--scale-y)), calc(var(--scale) * var(--scale-z)));\r\n }\r\n `;\r\n document.head.appendChild(style);\r\n }\r\n\r\n private registerTypedProperties(): void {\r\n const css = (globalThis as any).CSS;\r\n if (!css?.registerProperty) return;\r\n\r\n const props: Array<{ name: string; initialValue: string }> = [\r\n { name: \"--translate-x\", initialValue: \"0\" },\r\n { name: \"--translate-y\", initialValue: \"0\" },\r\n { name: \"--translate-z\", initialValue: \"0\" },\r\n { name: \"--rotate-x\", initialValue: \"0\" },\r\n { name: \"--rotate-y\", initialValue: \"0\" },\r\n { name: \"--rotate-z\", initialValue: \"0\" },\r\n { name: \"--scale\", initialValue: \"1\" },\r\n { name: \"--scale-x\", initialValue: \"1\" },\r\n { name: \"--scale-y\", initialValue: \"1\" },\r\n { name: \"--scale-z\", initialValue: \"1\" },\r\n { name: \"--opacity\", initialValue: \"1\" },\r\n { name: \"--filter\", initialValue: \"none\" },\r\n { name: \"--material-type\", initialValue: \"basic\" },\r\n { name: \"--material-color\", initialValue: \"#ffffff\" },\r\n { name: \"--material-metalness\", initialValue: \"0\" },\r\n { name: \"--material-roughness\", initialValue: \"1\" },\r\n { name: \"--material-emissive\", initialValue: \"#000000\" },\r\n { name: \"--rim-color\", initialValue: \"#00c8ff\" },\r\n { name: \"--rim-power\", initialValue: \"1.5\" },\r\n { name: \"--rim-strength\", initialValue: \"1\" },\r\n { name: \"--uv-strength\", initialValue: \"0.7\" },\r\n { name: \"--texture-map\", initialValue: \"none\" },\r\n { name: \"--texture-normal\", initialValue: \"none\" },\r\n { name: \"--texture-roughness\", initialValue: \"none\" },\r\n { name: \"--texture-metalness\", initialValue: \"none\" },\r\n { name: \"--texture-ao\", initialValue: \"none\" },\r\n { name: \"--light-color\", initialValue: \"#ffffff\" },\r\n { name: \"--light-intensity\", initialValue: \"1\" },\r\n { name: \"--light-distance\", initialValue: \"1000\" },\r\n { name: \"--light-decay\", initialValue: \"0\" },\r\n { name: \"--light-angle\", initialValue: \"1.0472\" },\r\n { name: \"--light-penumbra\", initialValue: \"0\" },\r\n { name: \"--light-ground-color\", initialValue: \"#ffffff\" },\r\n { name: \"--light-target\", initialValue: \"none\" },\r\n { name: \"--shadow-cast\", initialValue: \"0\" },\r\n { name: \"--shadow-receive\", initialValue: \"0\" },\r\n { name: \"--shadow-bias\", initialValue: \"0\" },\r\n { name: \"--shadow-map-size\", initialValue: \"512\" },\r\n { name: \"--texture-flip-y\", initialValue: \"1\" },\r\n { name: \"--texture-color-space\", initialValue: \"none\" },\r\n { name: \"--particles-mode\", initialValue: \"emitter\" },\r\n { name: \"--particles-count\", initialValue: \"300\" },\r\n { name: \"--particles-size\", initialValue: \"2\" },\r\n { name: \"--particles-color\", initialValue: \"#ffffff\" },\r\n { name: \"--particles-opacity\", initialValue: \"1\" },\r\n { name: \"--particles-spread\", initialValue: \"120\" },\r\n { name: \"--particles-seed\", initialValue: \"1\" },\r\n { name: \"--particles-shape\", initialValue: \"sphere\" },\r\n { name: \"--particles-fit\", initialValue: \"0\" },\r\n { name: \"--particles-model\", initialValue: \"none\" },\r\n { name: \"--particles-model-loader\", initialValue: \"none\" },\r\n { name: \"--particles-model-node\", initialValue: \"none\" },\r\n { name: \"--instance-model\", initialValue: \"none\" },\r\n { name: \"--instance-model-loader\", initialValue: \"none\" },\r\n { name: \"--instance-model-node\", initialValue: \"none\" },\r\n { name: \"--emit-rate\", initialValue: \"30\" },\r\n { name: \"--emit-burst\", initialValue: \"0\" },\r\n { name: \"--particle-life\", initialValue: \"2.5\" },\r\n { name: \"--particle-speed\", initialValue: \"40\" },\r\n { name: \"--particle-direction\", initialValue: \"0 1 0\" },\r\n { name: \"--particle-gravity\", initialValue: \"0 -30 0\" },\r\n { name: \"--particle-drag\", initialValue: \"0.1\" },\r\n { name: \"--particle-size-variation\", initialValue: \"0.6\" },\r\n { name: \"--particle-color-variation\", initialValue: \"0.2\" },\r\n { name: \"--instance-shape\", initialValue: \"sphere\" },\r\n { name: \"--instance-scale\", initialValue: \"1\" },\r\n { name: \"--instance-scale-variation\", initialValue: \"0.5\" },\r\n { name: \"--instance-rotation-speed\", initialValue: \"0.4\" },\r\n { name: \"--instance-jitter\", initialValue: \"0.2\" },\r\n { name: \"--instance-flow\", initialValue: \"0.3\" },\r\n { name: \"--instance-disperse\", initialValue: \"0\" },\r\n { name: \"--instance-scatter\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-x\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-y\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-z\", initialValue: \"0\" },\r\n { name: \"--text-depth\", initialValue: \"8\" },\r\n { name: \"--text-curve-segments\", initialValue: \"8\" },\r\n { name: \"--text-bevel-size\", initialValue: \"0\" },\r\n { name: \"--text-bevel-thickness\", initialValue: \"0\" },\r\n { name: \"--text-bevel-offset\", initialValue: \"0\" },\r\n { name: \"--text-bevel-steps\", initialValue: \"0\" },\r\n { name: \"--text-fit\", initialValue: \"contain\" },\r\n ];\r\n\r\n props.forEach(({ name, initialValue }) => {\r\n try {\r\n css.registerProperty({\r\n name,\r\n syntax:\r\n name === \"--filter\" ||\r\n name === \"--light-target\" ||\r\n name.startsWith(\"--texture-\") ||\r\n name === \"--material-type\" ||\r\n name === \"--particles-mode\" ||\r\n name === \"--particles-shape\" ||\r\n name === \"--particles-model\" ||\r\n name === \"--particles-model-loader\" ||\r\n name === \"--particles-model-node\" ||\r\n name === \"--instance-model\" ||\r\n name === \"--instance-model-loader\" ||\r\n name === \"--instance-model-node\" ||\r\n name === \"--particle-direction\" ||\r\n name === \"--particle-gravity\" ||\r\n name === \"--instance-shape\" ||\r\n name === \"--text-fit\"\r\n ? \"*\"\r\n : name.includes(\"color\") || name.includes(\"emissive\")\r\n ? \"<color>\"\r\n : \"<number>\",\r\n inherits: false,\r\n initialValue,\r\n });\r\n } catch {}\r\n });\r\n }\r\n\r\n override destroy(): void {\r\n this.renderer?.destroy();\r\n this._scene?.destroy();\r\n this.isLoading.clear();\r\n this.dirtySyncManager.disable();\r\n this.filterController.clear();\r\n this.lastSyncData = new WeakMap();\r\n\r\n const styleEl = document.getElementById(\"string-3d-styles\");\r\n styleEl?.remove();\r\n\r\n if (this.canvasContainer?.id === \"string-3d-canvas\") {\r\n this.canvasContainer.remove();\r\n }\r\n\r\n super.destroy();\r\n }\r\n}\r\n","import { I3DEngine, I3DVector3, I3DCamera } from \"./abstractions/I3DEngine\";\r\n\r\nexport type CameraMode = \"orthographic\" | \"perspective\";\r\n\r\nexport class String3DCamera {\r\n private scaleCache = new Map<number, number>();\r\n private _camera: I3DCamera;\r\n private _position: I3DVector3;\r\n private _width = 1;\r\n private _height = 1;\r\n private engine: I3DEngine;\r\n private mode: CameraMode;\r\n private perspectiveFov: number;\r\n\r\n constructor(\r\n engine: I3DEngine,\r\n mode: CameraMode = \"perspective\",\r\n fov = 50,\r\n near = 0.1,\r\n far = 10000\r\n ) {\r\n this.engine = engine;\r\n this.mode = mode;\r\n this.perspectiveFov = fov;\r\n\r\n if (mode === \"orthographic\") {\r\n this._camera = engine.createOrthographicCamera(-1, 1, 1, -1, near, far);\r\n } else {\r\n this._camera = engine.createPerspectiveCamera(fov, 1, near, far);\r\n }\r\n\r\n this._position = engine.createVector3(0, 0, 1000);\r\n this.update();\r\n }\r\n\r\n public get camera(): I3DCamera {\r\n return this._camera;\r\n }\r\n\r\n public resize(width: number, height: number): void {\r\n this._width = width;\r\n this._height = height;\r\n\r\n if (this.mode === \"orthographic\") {\r\n const ortho = this._camera as any;\r\n ortho.left = -width / 2;\r\n ortho.right = width / 2;\r\n ortho.top = height / 2;\r\n ortho.bottom = -height / 2;\r\n } else {\r\n this._camera.aspect = width / height;\r\n }\r\n\r\n this.update();\r\n }\r\n\r\n public setPosition(x: number, y: number, z: number): void {\r\n this._position.set(x, y, z);\r\n this._camera.position.copy(this._position);\r\n this.update();\r\n }\r\n\r\n public lookAt(x: number, y: number, z: number): void {\r\n this._camera.lookAt(x, y, z);\r\n this.update();\r\n }\r\n\r\n public update(): void {\r\n this._camera.updateProjectionMatrix();\r\n (this._camera as any).updateMatrixWorld?.();\r\n }\r\n\r\n public screenToWorld(screenX: number, screenY: number, z = 0): I3DVector3 {\r\n if (this.mode === \"orthographic\") {\r\n const x = screenX - this._width / 2;\r\n const y = -(screenY - this._height / 2);\r\n return this.engine.createVector3(x, y, z);\r\n } else {\r\n const { width, height } = this.getFrustumSizeAt(z);\r\n const normalizedX = screenX / this._width;\r\n const normalizedY = screenY / this._height;\r\n const x = (normalizedX - 0.5) * width;\r\n const y = -(normalizedY - 0.5) * height;\r\n return this.engine.createVector3(x, y, z);\r\n }\r\n }\r\n\r\n public getFrustumSizeAt(z: number): { width: number; height: number } {\r\n if (this.mode === \"orthographic\") {\r\n return { width: this._width, height: this._height };\r\n }\r\n\r\n const fov = this.engine.degToRad(this.perspectiveFov);\r\n const distance = Math.abs(z - this._camera.position.z);\r\n const height = 2 * Math.tan(fov / 2) * distance;\r\n const width = height * this._camera.aspect;\r\n return { width, height };\r\n }\r\n\r\n public getScaleAtZ(z: number, viewportHeight: number): number {\r\n if (this.mode === \"orthographic\") {\r\n return 1;\r\n }\r\n\r\n const roundedZ = Math.round(z * 1000) / 1000;\r\n if (this.scaleCache.has(roundedZ)) {\r\n return this.scaleCache.get(roundedZ)!;\r\n }\r\n\r\n const { height } = this.getFrustumSizeAt(z);\r\n const scale = height / viewportHeight;\r\n this.scaleCache.set(roundedZ, scale);\r\n return scale;\r\n }\r\n\r\n public clearScaleCache(): void {\r\n this.scaleCache.clear();\r\n }\r\n\r\n public getMode(): CameraMode {\r\n return this.mode;\r\n }\r\n\r\n public getPerspectiveFov(): number {\r\n return this.perspectiveFov;\r\n }\r\n\r\n public getPositionZ(): number {\r\n return this._position.z;\r\n }\r\n}\r\n","export type String3DCustomFilterDefinition = {\n name: string;\n fragmentShader: string;\n uniforms?: Record<string, any>;\n parse?: (args: string) => Record<string, any> | null;\n};\n\nexport class String3DCustomFilterRegistry {\n private static filters: Map<string, String3DCustomFilterDefinition> = new Map();\n\n static register(definition: String3DCustomFilterDefinition): void {\n const name = definition.name.trim().toLowerCase();\n if (!name) {\n throw new Error(\"[String3D] Custom filter name is required.\");\n }\n this.filters.set(name, { ...definition, name });\n }\n\n static get(name: string): String3DCustomFilterDefinition | undefined {\n return this.filters.get(name.trim().toLowerCase());\n }\n\n static has(name: string): boolean {\n return this.filters.has(name.trim().toLowerCase());\n }\n\n static list(): String3DCustomFilterDefinition[] {\n return Array.from(this.filters.values());\n }\n}\n","import {\n I3DEngine,\n I3DRenderer,\n I3DRenderTarget,\n I3DScene,\n I3DCamera,\n I3DMaterial,\n I3DObject,\n} from \"../abstractions/I3DEngine\";\nimport type { String3DFilterChain } from \"./String3DFilterTypes\";\nimport { String3DCustomFilterRegistry } from \"./String3DCustomFilter\";\n\ntype RenderTargetFactory = (width: number, height: number) => I3DRenderTarget;\n\nclass RenderTargetPool {\n private pool: I3DRenderTarget[] = [];\n private create: RenderTargetFactory;\n\n constructor(create: RenderTargetFactory) {\n this.create = create;\n }\n\n acquire(width: number, height: number): I3DRenderTarget {\n const target = this.pool.pop() || this.create(width, height);\n if (target.width !== width || target.height !== height) {\n target.setSize(width, height);\n }\n return target;\n }\n\n release(target: I3DRenderTarget): void {\n this.pool.push(target);\n }\n\n dispose(): void {\n this.pool.forEach((target) => target.dispose());\n this.pool = [];\n }\n}\n\nexport class String3DFilterPipeline {\n private engine: I3DEngine;\n private renderer: I3DRenderer;\n private width: number;\n private height: number;\n private scale = 1;\n private scene: I3DScene;\n private camera: I3DCamera;\n private quad: I3DObject;\n private copyMaterial: I3DMaterial;\n private blurMaterial: I3DMaterial;\n private pixelMaterial: I3DMaterial;\n private bloomExtractMaterial: I3DMaterial;\n private bloomAddMaterial: I3DMaterial;\n private colorMaterial: I3DMaterial;\n private customMaterials: Map<string, I3DMaterial> = new Map();\n private pool: RenderTargetPool;\n\n constructor(engine: I3DEngine, renderer: I3DRenderer, width: number, height: number) {\n this.engine = engine;\n this.renderer = renderer;\n this.width = width;\n this.height = height;\n\n this.scene = engine.createScene();\n this.camera = engine.createOrthographicCamera(-1, 1, 1, -1, 0, 1);\n\n const geometry = engine.createPlaneGeometry(2, 2);\n this.copyMaterial = this.createCopyMaterial();\n this.blurMaterial = this.createBlurMaterial();\n this.pixelMaterial = this.createPixelMaterial();\n this.bloomExtractMaterial = this.createBloomExtractMaterial();\n this.bloomAddMaterial = this.createBloomAddMaterial();\n this.colorMaterial = this.createColorMaterial();\n\n this.quad = engine.createMesh(geometry, this.copyMaterial);\n this.scene.add(this.quad);\n\n const create = (w: number, h: number) => {\n if (!this.engine.createRenderTarget) {\n throw new Error(\"[String3DFilterPipeline] Render target support missing.\");\n }\n return this.engine.createRenderTarget(w, h);\n };\n this.pool = new RenderTargetPool(create);\n }\n\n public isSupported(): boolean {\n return (\n !!this.engine.createRenderTarget &&\n !!this.engine.createShaderMaterial &&\n !!this.renderer.setRenderTarget\n );\n }\n\n public resize(width: number, height: number): void {\n this.width = width;\n this.height = height;\n }\n\n public setScale(scale: number): void {\n const next = Math.max(0.75, Math.min(1, scale));\n this.scale = next;\n }\n\n public applyFilters(\n input: I3DRenderTarget,\n effects: String3DFilterChain,\n quality = 1\n ): I3DRenderTarget {\n let current = input;\n const locals: I3DRenderTarget[] = [];\n\n const releaseLocal = (target: I3DRenderTarget): void => {\n const idx = locals.indexOf(target);\n if (idx >= 0) {\n locals.splice(idx, 1);\n this.pool.release(target);\n }\n };\n\n const acquire = (): I3DRenderTarget => {\n const { width, height } = this.getScaledSize();\n const target = this.pool.acquire(width, height);\n locals.push(target);\n return target;\n };\n\n effects.forEach((effect) => {\n if (effect.type === \"blur\") {\n const radius = effect.amount * quality;\n if (radius <= 0.0001) return;\n const first = acquire();\n this.renderPass(this.blurMaterial, current, first, {\n uDirection: [1, 0],\n uRadius: radius,\n });\n const second = acquire();\n this.renderPass(this.blurMaterial, first, second, {\n uDirection: [0, 1],\n uRadius: radius,\n });\n releaseLocal(first);\n if (current !== input) {\n releaseLocal(current);\n }\n current = second;\n } else if (effect.type === \"pixel\") {\n if (effect.size <= 0.5) return;\n const output = acquire();\n this.renderPass(this.pixelMaterial, current, output, {\n uPixelSize: effect.size,\n });\n if (current !== input) {\n releaseLocal(current);\n }\n current = output;\n } else if (effect.type === \"bloom\") {\n const intensity = effect.intensity;\n if (intensity <= 0.0001) return;\n if (effect.threshold >= 0.99) return;\n const blurRadius = Math.max(1, 4 * quality);\n const extracted = acquire();\n this.renderPass(this.bloomExtractMaterial, current, extracted, {\n uThreshold: effect.threshold,\n });\n\n const blur1 = acquire();\n this.renderPass(this.blurMaterial, extracted, blur1, {\n uDirection: [1, 0],\n uRadius: blurRadius,\n });\n const blur2 = acquire();\n this.renderPass(this.blurMaterial, blur1, blur2, {\n uDirection: [0, 1],\n uRadius: blurRadius,\n });\n\n releaseLocal(extracted);\n releaseLocal(blur1);\n\n const combined = acquire();\n this.renderAddPass(current, blur2, combined, intensity);\n releaseLocal(blur2);\n\n if (current !== input) {\n releaseLocal(current);\n }\n current = combined;\n } else if (\n effect.type === \"brightness\" ||\n effect.type === \"contrast\" ||\n effect.type === \"saturate\" ||\n effect.type === \"grayscale\" ||\n effect.type === \"sepia\" ||\n effect.type === \"invert\" ||\n effect.type === \"hue-rotate\"\n ) {\n const output = acquire();\n const mode = this.getColorMode(effect.type);\n const amount = effect.type === \"hue-rotate\" ? effect.angle : effect.amount;\n this.renderPass(this.colorMaterial, current, output, {\n uMode: mode,\n uAmount: amount,\n });\n if (current !== input) {\n releaseLocal(current);\n }\n current = output;\n } else if (effect.type === \"custom\") {\n const output = acquire();\n const material = this.getCustomMaterial(effect.name);\n if (material) {\n this.renderPass(material, current, output, effect.uniforms);\n if (current !== input) {\n releaseLocal(current);\n }\n current = output;\n } else {\n releaseLocal(output);\n }\n }\n });\n\n locals.forEach((target) => {\n if (target !== current) {\n this.pool.release(target);\n }\n });\n\n return current;\n }\n\n public acquireTarget(): I3DRenderTarget {\n const { width, height } = this.getScaledSize();\n return this.pool.acquire(width, height);\n }\n\n public releaseTarget(target: I3DRenderTarget): void {\n this.pool.release(target);\n }\n\n public renderToScreen(input: I3DRenderTarget): void {\n this.renderPass(this.copyMaterial, input, null, {}, false);\n }\n\n public dispose(): void {\n this.pool.dispose();\n this.customMaterials.forEach((material) => material.dispose());\n this.customMaterials.clear();\n }\n\n private renderPass(\n material: I3DMaterial,\n input: I3DRenderTarget,\n output: I3DRenderTarget | null,\n uniforms: Record<string, any> = {},\n clear = true\n ): void {\n const renderer = this.renderer as any;\n if (renderer.setRenderTarget) {\n renderer.setRenderTarget(output);\n }\n\n this.setMaterial(this.quad, material);\n this.setUniform(material, \"tDiffuse\", input.texture);\n const { width, height } = this.getScaledSize();\n this.setUniform(material, \"uResolution\", [width, height]);\n this.setUniform(material, \"uTexel\", [1 / width, 1 / height]);\n Object.entries(uniforms).forEach(([key, value]) => this.setUniform(material, key, value));\n\n if (clear && renderer.clear) {\n renderer.clear(true, true, true);\n }\n this.renderer.render(this.scene, this.camera);\n }\n\n private renderAddPass(\n base: I3DRenderTarget,\n bloom: I3DRenderTarget,\n output: I3DRenderTarget,\n intensity: number\n ): void {\n const renderer = this.renderer as any;\n if (renderer.setRenderTarget) {\n renderer.setRenderTarget(output);\n }\n\n this.setMaterial(this.quad, this.bloomAddMaterial);\n this.setUniform(this.bloomAddMaterial, \"tBase\", base.texture);\n this.setUniform(this.bloomAddMaterial, \"tBloom\", bloom.texture);\n this.setUniform(this.bloomAddMaterial, \"uIntensity\", intensity);\n const { width, height } = this.getScaledSize();\n this.setUniform(this.bloomAddMaterial, \"uResolution\", [width, height]);\n\n if (renderer.clear) {\n renderer.clear(true, true, true);\n }\n this.renderer.render(this.scene, this.camera);\n }\n\n private setMaterial(object: I3DObject, material: I3DMaterial): void {\n const anyObj = object as any;\n if (anyObj.material !== material) {\n anyObj.material = material as any;\n }\n }\n\n private setUniform(material: I3DMaterial, name: string, value: any): void {\n const uniforms = (material as any).uniforms;\n if (!uniforms) return;\n if (!uniforms[name]) {\n uniforms[name] = { value };\n } else {\n uniforms[name].value = value;\n }\n }\n\n private createCopyMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: { tDiffuse: { value: null } },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tDiffuse;\n void main() {\n gl_FragColor = texture2D(tDiffuse, vUv);\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private createPixelMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: {\n tDiffuse: { value: null },\n uResolution: { value: [this.width, this.height] },\n uPixelSize: { value: 1 },\n },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tDiffuse;\n uniform vec2 uResolution;\n uniform float uPixelSize;\n void main() {\n vec2 pixel = uPixelSize / uResolution;\n vec2 coord = floor(vUv / pixel) * pixel + pixel * 0.5;\n gl_FragColor = texture2D(tDiffuse, coord);\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private createBlurMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: {\n tDiffuse: { value: null },\n uTexel: { value: [1 / this.width, 1 / this.height] },\n uDirection: { value: [1, 0] },\n uRadius: { value: 2 },\n },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tDiffuse;\n uniform vec2 uTexel;\n uniform vec2 uDirection;\n uniform float uRadius;\n void main() {\n vec2 off1 = uDirection * uTexel * uRadius;\n vec2 off2 = uDirection * uTexel * uRadius * 2.0;\n vec2 off3 = uDirection * uTexel * uRadius * 3.0;\n vec2 off4 = uDirection * uTexel * uRadius * 4.0;\n vec4 color = texture2D(tDiffuse, vUv) * 0.227027;\n color += texture2D(tDiffuse, vUv + off1) * 0.1945946;\n color += texture2D(tDiffuse, vUv - off1) * 0.1945946;\n color += texture2D(tDiffuse, vUv + off2) * 0.1216216;\n color += texture2D(tDiffuse, vUv - off2) * 0.1216216;\n color += texture2D(tDiffuse, vUv + off3) * 0.054054;\n color += texture2D(tDiffuse, vUv - off3) * 0.054054;\n color += texture2D(tDiffuse, vUv + off4) * 0.016216;\n color += texture2D(tDiffuse, vUv - off4) * 0.016216;\n gl_FragColor = color;\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private createBloomExtractMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: {\n tDiffuse: { value: null },\n uThreshold: { value: 0.8 },\n },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tDiffuse;\n uniform float uThreshold;\n void main() {\n vec4 color = texture2D(tDiffuse, vUv);\n float brightness = max(max(color.r, color.g), color.b);\n gl_FragColor = brightness > uThreshold ? color : vec4(0.0);\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private createBloomAddMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: {\n tBase: { value: null },\n tBloom: { value: null },\n uIntensity: { value: 1 },\n uResolution: { value: [this.width, this.height] },\n },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tBase;\n uniform sampler2D tBloom;\n uniform float uIntensity;\n void main() {\n vec4 base = texture2D(tBase, vUv);\n vec4 bloom = texture2D(tBloom, vUv);\n gl_FragColor = vec4(base.rgb + bloom.rgb * uIntensity, base.a);\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private createColorMaterial(): I3DMaterial {\n return this.createShaderMaterial({\n uniforms: {\n tDiffuse: { value: null },\n uMode: { value: 0 },\n uAmount: { value: 1 },\n },\n vertexShader: this.getVertexShader(),\n fragmentShader: `\n varying vec2 vUv;\n uniform sampler2D tDiffuse;\n uniform int uMode;\n uniform float uAmount;\n\n vec3 applyHueRotate(vec3 color, float angle) {\n float cosA = cos(angle);\n float sinA = sin(angle);\n mat3 m = mat3(\n 0.213 + cosA * 0.787 - sinA * 0.213,\n 0.715 - cosA * 0.715 - sinA * 0.715,\n 0.072 - cosA * 0.072 + sinA * 0.928,\n 0.213 - cosA * 0.213 + sinA * 0.143,\n 0.715 + cosA * 0.285 + sinA * 0.140,\n 0.072 - cosA * 0.072 - sinA * 0.283,\n 0.213 - cosA * 0.213 - sinA * 0.787,\n 0.715 - cosA * 0.715 + sinA * 0.715,\n 0.072 + cosA * 0.928 + sinA * 0.072\n );\n return clamp(m * color, 0.0, 1.0);\n }\n\n void main() {\n vec4 color = texture2D(tDiffuse, vUv);\n float luma = dot(color.rgb, vec3(0.299, 0.587, 0.114));\n\n if (uMode == 1) {\n color.rgb *= uAmount;\n } else if (uMode == 2) {\n color.rgb = (color.rgb - 0.5) * uAmount + 0.5;\n } else if (uMode == 3) {\n color.rgb = mix(vec3(luma), color.rgb, uAmount);\n } else if (uMode == 4) {\n color.rgb = mix(color.rgb, vec3(luma), uAmount);\n } else if (uMode == 5) {\n vec3 sepia = vec3(\n dot(color.rgb, vec3(0.393, 0.769, 0.189)),\n dot(color.rgb, vec3(0.349, 0.686, 0.168)),\n dot(color.rgb, vec3(0.272, 0.534, 0.131))\n );\n color.rgb = mix(color.rgb, sepia, uAmount);\n } else if (uMode == 6) {\n color.rgb = mix(color.rgb, vec3(1.0) - color.rgb, uAmount);\n } else if (uMode == 7) {\n color.rgb = applyHueRotate(color.rgb, uAmount);\n }\n\n gl_FragColor = color;\n }\n `,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n }\n\n private getColorMode(type: string): number {\n switch (type) {\n case \"brightness\":\n return 1;\n case \"contrast\":\n return 2;\n case \"saturate\":\n return 3;\n case \"grayscale\":\n return 4;\n case \"sepia\":\n return 5;\n case \"invert\":\n return 6;\n case \"hue-rotate\":\n return 7;\n default:\n return 0;\n }\n }\n\n private createShaderMaterial(params: any): I3DMaterial {\n if (!this.engine.createShaderMaterial) {\n throw new Error(\"[String3DFilterPipeline] Shader material support missing.\");\n }\n return this.engine.createShaderMaterial(params);\n }\n\n private getCustomMaterial(name: string): I3DMaterial | null {\n const normalized = name.trim().toLowerCase();\n if (!normalized) return null;\n if (this.customMaterials.has(normalized)) {\n return this.customMaterials.get(normalized)!;\n }\n const def = String3DCustomFilterRegistry.get(normalized);\n if (!def) return null;\n\n const uniforms: Record<string, any> = { tDiffuse: { value: null } };\n const { width, height } = this.getScaledSize();\n uniforms.uResolution = { value: [width, height] };\n uniforms.uTexel = { value: [1 / width, 1 / height] };\n Object.entries(def.uniforms || {}).forEach(([key, value]) => {\n uniforms[key] = { value };\n });\n\n const material = this.createShaderMaterial({\n uniforms,\n vertexShader: this.getVertexShader(),\n fragmentShader: def.fragmentShader,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\n\n this.customMaterials.set(normalized, material);\n return material;\n }\n\n private getScaledSize(): { width: number; height: number } {\n const width = Math.max(1, Math.round(this.width * this.scale));\n const height = Math.max(1, Math.round(this.height * this.scale));\n return { width, height };\n }\n\n private getVertexShader(): string {\n return `\n varying vec2 vUv;\n void main() {\n vUv = uv;\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\n }\n `;\n }\n}\n","import { I3DEngine, I3DRenderer, I3DObject, I3DRenderTarget } from \"./abstractions/I3DEngine\";\nimport { String3DCamera } from \"./String3DCamera\";\nimport { String3DScene } from \"./String3DScene\";\nimport { String3DFilterPipeline } from \"./filters/String3DFilterPipeline\";\nimport type { String3DFilterTarget } from \"./filters/String3DFilterTypes\";\nimport type { String3DFilterEffect } from \"./filters/String3DFilterTypes\";\n\ntype FilterCacheEntry = {\n target: I3DRenderTarget;\n effectsKey: string;\n lastUsedFrame: number;\n qualityScale: number;\n};\n\nexport class String3DRenderer {\n private _container: HTMLElement;\n private _renderer: I3DRenderer;\n private _width: number;\n private _height: number;\n private engine: I3DEngine;\n private filterPipeline: String3DFilterPipeline | null = null;\n private filterCache: Map<string, FilterCacheEntry> = new Map();\n private frameId = 0;\n private lastFrameTime = performance.now();\n private avgFrameMs = 16.7;\n private qualityScale = 1;\n private lastQualityChange = 0;\n private filterLayer = 1;\n\n constructor(container: HTMLElement, engine: I3DEngine) {\n this.engine = engine;\n this._container = container;\n const { width, height } = container.getBoundingClientRect();\n this._width = width;\n this._height = height;\n\n this._renderer = engine.createRenderer({\n antialias: true,\n alpha: true,\n logarithmicDepthBuffer: true,\n });\n const rendererAny = this._renderer as any;\n if (typeof rendererAny.setClearColor === \"function\") {\n rendererAny.setClearColor(0x000000, 0);\n }\n this._renderer.setPixelRatio(window.devicePixelRatio);\n this._renderer.setSize(width, height);\n\n if (this._renderer.shadowMap) {\n this._renderer.shadowMap.enabled = true;\n }\n }\n\n public attach(): void {\n this._container.appendChild(this._renderer.domElement);\n }\n\n public render(\n scene: String3DScene,\n camera: String3DCamera,\n filterTargets: String3DFilterTarget[] = []\n ): void {\n if (filterTargets.length === 0) {\n this._renderer.render(scene.getScene(), camera.camera);\n return;\n }\n\n const pipeline = this.ensureFilterPipeline();\n if (!pipeline?.isSupported()) {\n this._renderer.render(scene.getScene(), camera.camera);\n return;\n }\n\n this.frameId += 1;\n this.updateQuality(filterTargets.length, pipeline);\n\n const allObjects = scene.getAllObjects();\n const visibility = new Map<I3DObject, boolean | undefined>();\n allObjects.forEach((obj) => {\n const anyObj = obj.object as any;\n if (\"visible\" in anyObj) {\n visibility.set(obj.object, anyObj.visible);\n }\n });\n\n const filteredSet = new Set<I3DObject>();\n filterTargets.forEach((target) => {\n this.collectSubtreeObjects(target.object, filteredSet);\n });\n\n allObjects.forEach((obj) => {\n if (filteredSet.has(obj.object)) {\n this.setVisible(obj.object, false);\n }\n });\n\n const rendererAny = this._renderer as any;\n const prevAutoClear = rendererAny.autoClear;\n rendererAny.autoClear = true;\n if (rendererAny.setRenderTarget) {\n rendererAny.setRenderTarget(null);\n }\n if (rendererAny.clear) {\n rendererAny.clear(true, true, true);\n }\n this._renderer.render(scene.getScene(), camera.camera);\n\n rendererAny.autoClear = false;\n\n allObjects.forEach((obj) => {\n const originalVisible = visibility.get(obj.object);\n if (typeof originalVisible !== \"undefined\") {\n this.setVisible(obj.object, originalVisible);\n }\n });\n\n const lights = allObjects.filter((obj) => obj.type.endsWith(\"Light\"));\n const supportsLayers = this.supportsLayers(camera.camera, allObjects);\n\n filterTargets.forEach((target) => {\n const cache = this.filterCache.get(target.object.id);\n const canUseCache =\n !target.dirty &&\n cache &&\n cache.effectsKey === target.effectsKey &&\n cache.qualityScale === this.qualityScale;\n\n if (canUseCache) {\n cache.lastUsedFrame = this.frameId;\n pipeline.renderToScreen(cache.target);\n return;\n }\n\n const effects = this.injectEffectContext(\n target.object.el as HTMLElement | undefined,\n target.effects\n );\n\n const allowed = new Set<I3DObject>();\n this.collectSubtreeObjects(target.object, allowed);\n\n let restoreLayers: Array<{ object: I3DObject; mask: number }> = [];\n let restoreCameraMask: number | null = null;\n\n if (supportsLayers) {\n const subtree = target.object.getSubtreeObjects();\n restoreLayers = this.applyLayerMask(subtree, lights, this.filterLayer);\n restoreCameraMask = this.setCameraLayer(camera.camera, this.filterLayer);\n } else {\n allObjects.forEach((obj) => {\n const originalVisible = visibility.get(obj.object);\n if (originalVisible === false) {\n this.setVisible(obj.object, false);\n return;\n }\n\n if (obj.type.endsWith(\"Light\")) {\n this.setVisible(obj.object, true);\n return;\n }\n\n this.setVisible(obj.object, allowed.has(obj.object));\n });\n }\n\n const input = pipeline.acquireTarget();\n if (rendererAny.setRenderTarget) {\n rendererAny.setRenderTarget(input);\n }\n if (rendererAny.clear) {\n rendererAny.clear(true, true, true);\n }\n this._renderer.render(scene.getScene(), camera.camera);\n\n const output = pipeline.applyFilters(input, effects, this.qualityScale);\n if (rendererAny.setRenderTarget) {\n rendererAny.setRenderTarget(null);\n }\n pipeline.renderToScreen(output);\n\n if (supportsLayers) {\n this.restoreLayerMask(restoreLayers);\n if (restoreCameraMask !== null) {\n this.restoreCameraLayer(camera.camera, restoreCameraMask);\n }\n }\n\n if (output !== input) {\n pipeline.releaseTarget(input);\n }\n\n const entry: FilterCacheEntry = {\n target: output,\n effectsKey: target.effectsKey,\n lastUsedFrame: this.frameId,\n qualityScale: this.qualityScale,\n };\n const existing = this.filterCache.get(target.object.id);\n if (existing && existing.target !== output) {\n pipeline.releaseTarget(existing.target);\n }\n this.filterCache.set(target.object.id, entry);\n });\n\n if (!supportsLayers) {\n allObjects.forEach((obj) => {\n const originalVisible = visibility.get(obj.object);\n if (typeof originalVisible !== \"undefined\") {\n this.setVisible(obj.object, originalVisible);\n }\n });\n }\n\n rendererAny.autoClear = prevAutoClear;\n\n this.evictCache();\n }\n\n public resize(camera: String3DCamera): void {\n const { width, height } = this._container.getBoundingClientRect();\n this._width = width;\n this._height = height;\n this._renderer.setSize(width, height);\n camera.resize(width, height);\n this.filterPipeline?.resize(width, height);\n this.invalidateFilterCache();\n }\n\n public get width(): number {\n return this._width;\n }\n\n public get height(): number {\n return this._height;\n }\n\n public get renderer(): I3DRenderer {\n return this._renderer;\n }\n\n public destroy(): void {\n this._renderer.dispose();\n this.filterPipeline?.dispose();\n this.filterCache.clear();\n }\n\n private ensureFilterPipeline(): String3DFilterPipeline | null {\n if (!this.canCreateFilterPipeline()) {\n return null;\n }\n if (!this.filterPipeline) {\n this.filterPipeline = new String3DFilterPipeline(\n this.engine,\n this._renderer,\n this._width,\n this._height\n );\n this.filterPipeline.setScale(this.qualityScale);\n }\n return this.filterPipeline;\n }\n\n private canCreateFilterPipeline(): boolean {\n return (\n typeof this.engine.createRenderTarget === \"function\" &&\n typeof this.engine.createShaderMaterial === \"function\" &&\n typeof (this._renderer as any).setRenderTarget === \"function\"\n );\n }\n\n private collectSubtreeObjects(\n object: import(\"./String3DObject\").String3DObject,\n set: Set<I3DObject>\n ): void {\n set.add(object.object);\n object.children.forEach((child) => this.collectSubtreeObjects(child, set));\n }\n\n private setVisible(object: I3DObject, visible: boolean): void {\n const anyObj = object as any;\n if (\"visible\" in anyObj) {\n anyObj.visible = visible;\n }\n }\n\n private getFilterCenter(el: HTMLElement | undefined): [number, number] {\n if (!el || !this._width || !this._height) return [0.5, 0.5];\n const cached = (el as any).__layoutCache;\n const rect = cached ? cached.rect : el.getBoundingClientRect();\n const cx = (rect.left + rect.width / 2) / this._width;\n const cy = 1 - (rect.top + rect.height / 2) / this._height;\n const clamp = (value: number) => Math.max(0, Math.min(1, value));\n return [clamp(cx), clamp(cy)];\n }\n\n private injectEffectContext(\n el: HTMLElement | undefined,\n effects: String3DFilterEffect[]\n ): String3DFilterEffect[] {\n if (!effects.some((effect) => effect.type === \"custom\")) {\n return effects;\n }\n const center = this.getFilterCenter(el);\n let changed = false;\n const next = effects.map((effect) => {\n if (effect.type !== \"custom\") return effect;\n if (effect.uniforms && \"uCenter\" in effect.uniforms) return effect;\n const uniforms = { ...(effect.uniforms || {}), uCenter: center };\n changed = true;\n return { ...effect, uniforms };\n });\n return changed ? next : effects;\n }\n\n private updateQuality(filterCount: number, pipeline: String3DFilterPipeline): void {\n const now = performance.now();\n const dt = Math.max(0.1, now - this.lastFrameTime);\n this.lastFrameTime = now;\n this.avgFrameMs = this.avgFrameMs * 0.9 + dt * 0.1;\n\n const fps = 1000 / this.avgFrameMs;\n const countScale = Math.max(0.75, 1 - Math.min(0.4, filterCount * 0.03));\n let targetScale = countScale;\n\n if (fps < 48) targetScale = Math.max(0.75, countScale - 0.1);\n if (fps < 40) targetScale = Math.max(0.75, countScale - 0.2);\n if (fps > 58) targetScale = Math.min(1, countScale + 0.05);\n\n if (Math.abs(targetScale - this.qualityScale) >= 0.05 && now - this.lastQualityChange > 300) {\n this.qualityScale = targetScale;\n this.lastQualityChange = now;\n pipeline.setScale(this.qualityScale);\n this.invalidateFilterCache();\n }\n }\n\n private invalidateFilterCache(): void {\n if (!this.filterPipeline) return;\n this.filterCache.forEach((entry) => {\n this.filterPipeline?.releaseTarget(entry.target);\n });\n this.filterCache.clear();\n }\n\n private evictCache(): void {\n if (!this.filterPipeline) return;\n const maxAge = 120;\n this.filterCache.forEach((entry, key) => {\n if (this.frameId - entry.lastUsedFrame > maxAge) {\n this.filterPipeline?.releaseTarget(entry.target);\n this.filterCache.delete(key);\n }\n });\n }\n\n private supportsLayers(camera: any, objects: Array<{ object: I3DObject }>): boolean {\n if (!camera?.layers || typeof camera.layers.set !== \"function\") return false;\n return objects.some((obj) => this.hasLayers(obj.object));\n }\n\n private hasLayers(object: any): boolean {\n return object?.layers && typeof object.layers.set === \"function\";\n }\n\n private applyLayerMask(\n objects: I3DObject[],\n lights: Array<{ object: I3DObject }>,\n layer: number\n ): Array<{ object: I3DObject; mask: number }> {\n const restoredMap = new Map<I3DObject, number>();\n const apply = (obj: I3DObject, setMode: \"set\" | \"enable\") => {\n const anyObj = obj as any;\n if (!this.hasLayers(anyObj)) return;\n if (!restoredMap.has(obj)) {\n restoredMap.set(obj, anyObj.layers.mask);\n }\n if (setMode === \"set\") {\n anyObj.layers.set(layer);\n } else {\n anyObj.layers.enable(layer);\n }\n };\n\n objects.forEach((obj) => apply(obj, \"set\"));\n lights.forEach((light) => apply(light.object, \"enable\"));\n\n return Array.from(restoredMap.entries()).map(([object, mask]) => ({ object, mask }));\n }\n\n private restoreLayerMask(entries: Array<{ object: I3DObject; mask: number }>): void {\n entries.forEach((entry) => {\n const anyObj = entry.object as any;\n if (this.hasLayers(anyObj)) {\n anyObj.layers.mask = entry.mask;\n }\n });\n }\n\n private setCameraLayer(camera: any, layer: number): number | null {\n if (!camera?.layers || typeof camera.layers.set !== \"function\") return null;\n const prev = camera.layers.mask;\n camera.layers.set(layer);\n return prev;\n }\n\n private restoreCameraLayer(camera: any, mask: number): void {\n if (camera?.layers) {\n camera.layers.mask = mask;\n }\n }\n}\n","import {\r\n I3DEngine,\r\n I3DObject,\r\n I3DMaterial,\r\n I3DGeometry,\r\n I3DQuaternion,\r\n I3DVector3,\r\n I3DEuler,\r\n I3DMatrix4,\r\n I3DBox3,\r\n} from \"./abstractions/I3DEngine\";\r\n\r\nexport class String3DObject {\n public id: string;\n public type: string;\n private _object: I3DObject;\n private _material?: I3DMaterial;\n private _geometry?: I3DGeometry;\n private _texture?: any;\n private _uniforms: Record<string, { value: any }> = {};\r\n private _originalBoundingBox?: I3DBox3 | null;\r\n private _quaternion: I3DQuaternion;\r\n private _originalSize: I3DVector3;\r\n private _bbox: I3DBox3;\r\n public el: any;\r\n private _children: String3DObject[] = [];\n private _flatObjectsCache: I3DObject[] | null = null;\n private _subtreeCache: I3DObject[] | null = null;\n private engine: I3DEngine;\r\n\r\n public get children(): String3DObject[] {\r\n return this._children;\r\n }\r\n\r\n constructor(\n id: string,\n type: string,\n object: I3DObject,\n engine: I3DEngine,\n options: { material?: I3DMaterial; geometry?: I3DGeometry; texture?: any } = {}\n ) {\n this.id = id;\n this.type = type;\n this._object = object;\n this.engine = engine;\n this._material = options.material;\n this._geometry = options.geometry;\n this._texture = options.texture;\n this._quaternion = engine.createQuaternion();\n this._originalSize = engine.createVector3();\n this._bbox = engine.createBox3();\n this.updateBoundingBox();\n }\n\r\n public get object(): I3DObject {\r\n return this._object;\r\n }\r\n\r\n public get material(): I3DMaterial | undefined {\r\n return this._material;\r\n }\r\n\r\n public get originalSize(): I3DVector3 {\r\n return this._originalSize.clone();\r\n }\r\n\r\n public get boundingBox(): I3DBox3 {\r\n return this._bbox.clone();\r\n }\r\n\r\n public addChild(child: String3DObject): void {\n this._children.push(child);\n this.object.add(child.object);\n this.invalidateFlatCache();\n this.invalidateSubtreeCache();\n }\n\r\n public getWorldMatrix(): I3DMatrix4 {\r\n return this._object.matrixWorld.clone();\r\n }\r\n\r\n public getWorldPosition(): I3DVector3 {\r\n return this.engine.createVector3().setFromMatrixPosition(this._object.matrixWorld);\r\n }\r\n\r\n public getOriginalBoundingBox(): I3DBox3 {\r\n if (!this._originalBoundingBox) {\r\n const originalScale = this.object.scale.clone();\r\n this.object.scale.set(1, 1, 1);\r\n this.object.updateMatrixWorld(true);\r\n this._originalBoundingBox = this.engine.computeBoundingBoxRecursively(this.object);\r\n this.object.scale.copy(originalScale);\r\n this.object.updateMatrixWorld(true);\r\n }\r\n return this._originalBoundingBox!.clone();\r\n }\r\n\r\n public syncTransformFromMatrix(matrix: I3DMatrix4): void {\r\n const pos = this.engine.createVector3();\r\n const quat = this.engine.createQuaternion();\r\n const scale = this.engine.createVector3();\r\n matrix.decompose(pos, quat, scale);\r\n this._object.position.copy(pos);\r\n this._object.quaternion.copy(quat);\r\n this._object.scale.copy(scale);\r\n this._object.updateMatrix();\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public applyWorldTransform(\r\n position: I3DVector3,\r\n quaternion: I3DQuaternion,\r\n scale: I3DVector3\r\n ): void {\r\n this._object.position.copy(position);\r\n this._object.quaternion.copy(quaternion);\r\n this._object.scale.copy(scale);\r\n this._object.updateMatrix();\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public set quaternion(quaternion: I3DQuaternion) {\r\n this._quaternion.copy(quaternion);\r\n this._object.quaternion.copy(this._quaternion);\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public set position(position: I3DVector3) {\r\n this._object.position.copy(position);\r\n }\r\n\r\n public set scale(scale: I3DVector3) {\r\n this._object.scale.copy(scale);\r\n }\r\n\r\n public set rotation(euler: I3DEuler) {\r\n this._object.rotation.copy(euler);\r\n }\r\n\r\n public set opacity(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"opacity\" in mat.material) {\r\n mat.material.opacity = value;\r\n }\r\n }\r\n\r\n public set metalness(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"metalness\" in mat.material) {\r\n mat.material.metalness = value;\r\n }\r\n }\r\n\r\n public set roughness(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"roughness\" in mat.material) {\r\n mat.material.roughness = value;\r\n }\r\n }\r\n\r\n public set texture(texture: any) {\n this._texture = texture;\n if ((this._object as any).isMesh && texture?.applyTexture) {\n texture.applyTexture(this._object);\n }\n }\n\n public set material(material: I3DMaterial | undefined) {\n this._material = material;\n }\n\n public set geometry(geometry: I3DGeometry | undefined) {\n this._geometry = geometry;\n }\n\n public updateBoundingBox(): void {\n this._bbox.setFromObject(this._object);\n this._bbox.getSize(this._originalSize);\n }\n\n public destroy(): void {\n this.disposeObjectResources(this._object);\n this._texture?.dispose?.();\n this._material?.dispose();\n this._geometry?.dispose();\n this._subtreeCache = null;\n }\n\n public getFlatObjects(): I3DObject[] {\n if (this._flatObjectsCache) return this._flatObjectsCache;\n const result: I3DObject[] = [];\n const walk = (obj: String3DObject): void => {\n result.push(obj.object);\n obj.children.forEach((child) => walk(child));\n };\n walk(this);\n this._flatObjectsCache = result;\n return result;\n }\n\n public getSubtreeObjects(): I3DObject[] {\n if (this._subtreeCache) return this._subtreeCache;\n const result: I3DObject[] = [];\n const anyObj = this._object as any;\n result.push(this._object);\n if (typeof anyObj.traverse === \"function\") {\n anyObj.traverse((child: any) => {\n if (child && child !== this._object) {\n result.push(child as I3DObject);\n }\n });\n }\n this._subtreeCache = result;\n return result;\n }\n\n private invalidateFlatCache(): void {\n this._flatObjectsCache = null;\n }\n\n private invalidateSubtreeCache(): void {\n this._subtreeCache = null;\n }\n\n private disposeObjectResources(object: I3DObject): void {\n const anyObj = object as any;\n if (anyObj?.geometry?.dispose) {\n anyObj.geometry.dispose();\n }\n const material = anyObj?.material;\n if (Array.isArray(material)) {\n material.forEach((mat) => mat?.dispose?.());\n } else if (material?.dispose) {\n material.dispose();\n }\n if (typeof anyObj?.traverse === \"function\") {\n anyObj.traverse((child: any) => {\n if (child?.geometry?.dispose) {\n child.geometry.dispose();\n }\n const childMat = child?.material;\n if (Array.isArray(childMat)) {\n childMat.forEach((mat: any) => mat?.dispose?.());\n } else if (childMat?.dispose) {\n childMat.dispose();\n }\n });\n }\n }\n}\n","export class StyleReader {\r\n private styleMap: any;\r\n private style: CSSStyleDeclaration;\r\n\r\n constructor(el: HTMLElement) {\r\n this.styleMap = (el as any).computedStyleMap?.();\r\n this.style = getComputedStyle(el);\r\n }\r\n\r\n readNumber(prop: string, fallback: number): number {\r\n const mapValue = this.styleMap?.get?.(prop);\r\n if (mapValue !== undefined && mapValue !== null) {\r\n const val = typeof mapValue === \"object\" ? (mapValue as any).value : mapValue;\r\n const num = typeof val === \"number\" ? val : Number.parseFloat(val);\r\n if (!Number.isNaN(num)) return num;\r\n }\r\n const num = Number.parseFloat(this.style.getPropertyValue(prop));\r\n return Number.isNaN(num) ? fallback : num;\r\n }\r\n\r\n readString(prop: string, fallback = \"\"): string {\r\n const mapValue = this.styleMap?.get?.(prop);\r\n const val = mapValue && typeof mapValue === \"object\" ? (mapValue as any).value : mapValue;\r\n if (typeof val === \"string\") return this.stripQuotes(val.trim()) || fallback;\r\n const raw = this.style.getPropertyValue(prop).trim();\r\n return this.stripQuotes(raw) || fallback;\r\n }\r\n\r\n private stripQuotes(value: string): string {\r\n if (\r\n (value.startsWith(\"'\") && value.endsWith(\"'\")) ||\r\n (value.startsWith('\"') && value.endsWith('\"'))\r\n ) {\r\n return value.slice(1, -1);\r\n }\r\n return value;\r\n }\r\n\r\n readBoolean(prop: string, fallback = false): boolean {\r\n const raw = this.readString(prop, \"\");\r\n if (!raw) return fallback;\r\n const norm = raw.toLowerCase();\r\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\r\n ? true\r\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\r\n ? false\r\n : fallback;\r\n }\r\n}\r\n\r\nexport function readNumberStyle(el: HTMLElement, prop: string, fallback: number): number {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const mapValue = styleMap?.get?.(prop);\r\n if (mapValue !== undefined) {\r\n if (typeof mapValue === \"number\") return mapValue;\r\n if (typeof mapValue === \"string\") {\r\n const parsed = Number.parseFloat(mapValue);\r\n if (!Number.isNaN(parsed)) return parsed;\r\n }\r\n if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"number\") return value;\r\n if (typeof value === \"string\") {\r\n const parsed = Number.parseFloat(value);\r\n if (!Number.isNaN(parsed)) return parsed;\r\n }\r\n }\r\n }\r\n\r\n const style = getComputedStyle(el);\r\n const raw = style.getPropertyValue(prop);\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isNaN(parsed) ? fallback : parsed;\r\n}\r\n\r\nfunction stripQuotes(value: string): string {\r\n if (\r\n (value.startsWith(\"'\") && value.endsWith(\"'\")) ||\r\n (value.startsWith('\"') && value.endsWith('\"'))\r\n ) {\r\n return value.slice(1, -1);\r\n }\r\n return value;\r\n}\r\n\r\nexport function readStringStyle(el: HTMLElement, prop: string, fallback = \"\"): string {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const mapValue = styleMap?.get?.(prop);\r\n if (typeof mapValue === \"string\") {\r\n return stripQuotes(mapValue.trim());\r\n }\r\n if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"string\") {\r\n return stripQuotes(value.trim());\r\n }\r\n }\r\n const style = getComputedStyle(el).getPropertyValue(prop);\r\n const result = style ? stripQuotes(style.trim()) : \"\";\r\n return result || fallback;\r\n}\r\n\r\nexport function readBooleanStyle(el: HTMLElement, prop: string, fallback = false): boolean {\r\n const raw = readStringStyle(el, prop, \"\");\r\n if (!raw) return fallback;\r\n const normalized = raw.toLowerCase().trim();\r\n if (normalized === \"true\" || normalized === \"1\" || normalized === \"yes\") return true;\r\n if (normalized === \"false\" || normalized === \"0\" || normalized === \"no\") return false;\r\n return fallback;\r\n}\r\n\r\nexport function readFilterRaw(el: HTMLElement): string {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n let raw = \"\";\r\n const mapValue = styleMap?.get?.(\"--filter\");\r\n if (mapValue !== undefined) {\r\n if (typeof mapValue === \"string\") {\r\n raw = mapValue;\r\n } else if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"string\") raw = value;\r\n }\r\n }\r\n if (!raw) {\r\n raw = getComputedStyle(el).getPropertyValue(\"--filter\") || \"\";\r\n }\r\n raw = raw.trim();\r\n return raw;\r\n}\r\n","export type UniformType =\r\n | \"float\"\r\n | \"int\"\r\n | \"vec2\"\r\n | \"vec3\"\r\n | \"vec4\"\r\n | \"color\"\r\n | \"texture\"\r\n | \"mat3\"\r\n | \"mat4\";\r\n\r\nexport type UniformDefinition = {\r\n type: UniformType;\r\n value: any;\r\n css?: string;\r\n};\r\n\r\nexport type ShaderInjectionPoint =\r\n | \"vertex_pars\"\r\n | \"vertex_header\"\r\n | \"vertex_transform\"\r\n | \"vertex_output\"\r\n | \"fragment_pars\"\r\n | \"fragment_header\"\r\n | \"fragment_color\"\r\n | \"fragment_normal\"\r\n | \"fragment_emissive\"\r\n | \"fragment_roughness\"\r\n | \"fragment_metalness\"\r\n | \"fragment_ao\"\r\n | \"fragment_transmission\"\r\n | \"fragment_lights\"\r\n | \"fragment_output\";\r\n\r\nexport type ShaderInjection = {\r\n point: ShaderInjectionPoint;\r\n code: string;\r\n order?: number;\r\n};\r\n\r\nexport type MaterialBlendMode = \"normal\" | \"additive\" | \"subtractive\" | \"multiply\";\r\nexport type MaterialSide = \"front\" | \"back\" | \"double\";\r\n\r\nexport type String3DCustomMaterialDefinition = {\r\n name: string;\r\n\r\n extends?: \"basic\" | \"standard\" | \"physical\" | \"shader\";\r\n\r\n vertexShader?: string;\r\n fragmentShader?: string;\r\n\r\n injections?: ShaderInjection[];\r\n\r\n uniforms?: Record<string, UniformDefinition>;\r\n\r\n properties?: {\r\n transparent?: boolean;\r\n side?: MaterialSide;\r\n depthWrite?: boolean;\r\n depthTest?: boolean;\r\n blending?: MaterialBlendMode;\r\n wireframe?: boolean;\r\n };\r\n\r\n lights?: boolean;\r\n\r\n parse?: (element: HTMLElement, style: CSSStyleDeclaration) => Record<string, any>;\r\n};\r\n\r\nexport class String3DCustomMaterialRegistry {\r\n private static materials: Map<string, String3DCustomMaterialDefinition> = new Map();\r\n private static registeredCssVars: Set<string> = new Set();\r\n\r\n static register(definition: String3DCustomMaterialDefinition): void {\r\n const name = definition.name.trim().toLowerCase();\r\n if (!name) {\r\n throw new Error(\"[String3D] Custom material name is required.\");\r\n }\r\n this.materials.set(name, { ...definition, name });\r\n this.registerCssVarsForMaterial(definition);\r\n }\r\n\r\n private static registerCssVarsForMaterial(definition: String3DCustomMaterialDefinition): void {\r\n const css = (globalThis as any).CSS;\r\n if (!css?.registerProperty) return;\r\n\r\n const uniforms = definition.uniforms || {};\r\n for (const def of Object.values(uniforms)) {\r\n const cssVar = def.css?.trim();\r\n if (!cssVar || !cssVar.startsWith(\"--\")) continue;\r\n if (this.registeredCssVars.has(cssVar)) continue;\r\n\r\n const syntax = this.resolveCssSyntax(def.type);\r\n\r\n try {\r\n css.registerProperty({\r\n name: cssVar,\r\n syntax,\r\n inherits: false,\r\n initialValue: this.defaultCssInitialValue(def),\r\n });\r\n this.registeredCssVars.add(cssVar);\r\n } catch (err) {}\r\n }\r\n }\r\n\r\n private static resolveCssSyntax(type: UniformType): string {\r\n switch (type) {\r\n case \"color\":\r\n return \"<color>\";\r\n case \"float\":\r\n case \"int\":\r\n return \"<number>\";\r\n default:\r\n return \"*\";\r\n }\r\n }\r\n\r\n private static defaultCssInitialValue(def: UniformDefinition): string {\r\n if (def.type === \"color\") {\r\n if (typeof def.value === \"string\") return def.value;\r\n return \"#000000\";\r\n }\r\n if (def.type === \"float\" || def.type === \"int\") {\r\n return typeof def.value === \"number\" ? String(def.value) : \"0\";\r\n }\r\n return \"initial\";\r\n }\r\n\r\n static get(name: string): String3DCustomMaterialDefinition | undefined {\r\n return this.materials.get(name.trim().toLowerCase());\r\n }\r\n\r\n static has(name: string): boolean {\r\n return this.materials.has(name.trim().toLowerCase());\r\n }\r\n\r\n static list(): String3DCustomMaterialDefinition[] {\r\n return Array.from(this.materials.values());\r\n }\r\n\r\n static unregister(name: string): boolean {\r\n return this.materials.delete(name.trim().toLowerCase());\r\n }\r\n}\r\n","import type {\n String3DCustomMaterialDefinition,\n UniformDefinition,\n ShaderInjection,\n} from \"./String3DCustomMaterial\";\n\nexport type MaterialUpdateCallback = (uniforms: Record<string, any>) => void;\n\nexport interface IMaterialInstance {\n material: any;\n definition: String3DCustomMaterialDefinition;\n update: MaterialUpdateCallback;\n dispose: () => void;\n}\n\nexport interface IMaterialFactory {\n supports(definition: String3DCustomMaterialDefinition): boolean;\n\n create(\n definition: String3DCustomMaterialDefinition,\n initialUniforms?: Record<string, any>\n ): IMaterialInstance;\n\n parseUniformsFromCSS(\n definition: String3DCustomMaterialDefinition,\n element: HTMLElement,\n style: CSSStyleDeclaration\n ): Record<string, any>;\n}\n\nexport function parseUniformValue(\n def: UniformDefinition,\n cssValue: string | null | undefined\n): any {\n if (cssValue === null || cssValue === undefined || cssValue === \"\" || cssValue === \"none\") {\n return def.value;\n }\n\n const trimmed = cssValue.trim();\n\n switch (def.type) {\n case \"float\":\n case \"int\": {\n const num = parseFloat(trimmed);\n return isNaN(num) ? def.value : num;\n }\n case \"vec2\": {\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\n if (parts.length >= 2 && parts.every((n) => !isNaN(n))) {\n return [parts[0], parts[1]];\n }\n return def.value;\n }\n case \"vec3\": {\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\n if (parts.length >= 3 && parts.every((n) => !isNaN(n))) {\n return [parts[0], parts[1], parts[2]];\n }\n return def.value;\n }\n case \"vec4\": {\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\n if (parts.length >= 4 && parts.every((n) => !isNaN(n))) {\n return [parts[0], parts[1], parts[2], parts[3]];\n }\n return def.value;\n }\n case \"color\": {\n return parseColorValue(trimmed) ?? def.value;\n }\n case \"texture\": {\n const match = trimmed.match(/url\\(['\"]?(.*?)['\"]?\\)/);\n return match ? match[1] : trimmed || def.value;\n }\n default:\n return def.value;\n }\n}\n\nfunction parseColorValue(value: string): [number, number, number] | null {\n if (value.startsWith(\"#\")) {\n const hex = value.slice(1);\n if (hex.length === 3) {\n const r = parseInt(hex[0] + hex[0], 16) / 255;\n const g = parseInt(hex[1] + hex[1], 16) / 255;\n const b = parseInt(hex[2] + hex[2], 16) / 255;\n return [r, g, b];\n }\n if (hex.length === 6) {\n const r = parseInt(hex.slice(0, 2), 16) / 255;\n const g = parseInt(hex.slice(2, 4), 16) / 255;\n const b = parseInt(hex.slice(4, 6), 16) / 255;\n return [r, g, b];\n }\n }\n\n const rgbMatch = value.match(/rgba?\\(\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)/);\n if (rgbMatch) {\n return [parseInt(rgbMatch[1]) / 255, parseInt(rgbMatch[2]) / 255, parseInt(rgbMatch[3]) / 255];\n }\n\n return null;\n}\n\nexport function collectUniformsFromCSS(\n definition: String3DCustomMaterialDefinition,\n element: HTMLElement,\n style: CSSStyleDeclaration\n): Record<string, any> {\n const result: Record<string, any> = {};\n\n if (definition.parse) {\n const parsed = definition.parse(element, style);\n Object.assign(result, parsed);\n }\n\n if (definition.uniforms) {\n for (const [key, def] of Object.entries(definition.uniforms)) {\n if (def.css) {\n const cssValue = style.getPropertyValue(def.css).trim();\n result[key] = parseUniformValue(def, cssValue);\n } else if (!(key in result)) {\n result[key] = def.value;\n }\n }\n }\n\n return result;\n}\n\nexport function mergeInjections(injections: ShaderInjection[]): Map<string, string> {\n const grouped = new Map<string, ShaderInjection[]>();\n\n for (const injection of injections) {\n const list = grouped.get(injection.point) || [];\n list.push(injection);\n grouped.set(injection.point, list);\n }\n\n const result = new Map<string, string>();\n\n for (const [point, list] of grouped) {\n const sorted = list.sort((a, b) => (a.order ?? 0) - (b.order ?? 0));\n result.set(point, sorted.map((i) => i.code).join(\"\\n\"));\n }\n\n return result;\n}\n","import {\r\n I3DEngine,\r\n I3DScene,\r\n I3DLight,\r\n I3DMaterial,\r\n I3DModelLoader,\r\n I3DVector3,\r\n} from \"./abstractions/I3DEngine\";\r\nimport { String3DObject } from \"./String3DObject\";\r\nimport { StringObject } from \"@fiddle-digital/string-tune\";\r\nimport { readBooleanStyle, readNumberStyle, readStringStyle } from \"../modules/string3d/styleUtils\";\r\nimport { String3DCustomMaterialRegistry, IMaterialInstance } from \"./materials\";\r\nimport type { String3DSynchronizer } from \"./synchronizer/String3DSynchronizer\";\r\n\r\nexport interface String3DSceneOptions {\r\n modelLoader?: I3DModelLoader;\r\n modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n}\r\n\r\nexport class String3DScene {\r\n private _scene: I3DScene;\r\n private _objects: Map<string, String3DObject> = new Map();\r\n private _rootObjects: String3DObject[] = [];\r\n private _elementMap: Map<string, HTMLElement> = new Map();\r\n private _materialInstances: Map<string, IMaterialInstance> = new Map();\r\n private engine: I3DEngine;\r\n private _modelLoader?: I3DModelLoader;\r\n private _modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n private _modelLoaderCache: Map<string, I3DModelLoader> = new Map();\r\n private _synchronizer?: String3DSynchronizer;\r\n\r\n public get rootObjects(): String3DObject[] {\r\n return this._rootObjects;\r\n }\r\n\r\n constructor(engine: I3DEngine, options: String3DSceneOptions = {}) {\r\n this.engine = engine;\r\n this._modelLoader = options.modelLoader;\r\n this._modelLoaderFactory = options.modelLoaderFactory;\r\n this._scene = engine.createScene();\r\n }\r\n\r\n public setSynchronizer(synchronizer: String3DSynchronizer): void {\r\n this._synchronizer = synchronizer;\r\n }\r\n\r\n public getScene(): I3DScene {\r\n return this._scene;\r\n }\r\n\r\n public getObject(id: string): String3DObject | undefined {\r\n return this._objects.get(id);\r\n }\r\n\r\n public getObjectForElement(element: HTMLElement): String3DObject | undefined {\r\n for (const [id, el] of this._elementMap) {\r\n if (el === element) {\r\n return this._objects.get(id);\r\n }\r\n }\r\n return undefined;\r\n }\r\n\r\n public getAllObjects(): String3DObject[] {\r\n const result: String3DObject[] = [];\r\n const walk = (obj: String3DObject): void => {\r\n result.push(obj);\r\n obj.children.forEach((child) => walk(child));\r\n };\r\n this._rootObjects.forEach((obj) => walk(obj));\r\n return result;\r\n }\r\n\r\n public hasObject(id: string): boolean {\r\n return this._objects.has(id);\r\n }\r\n\r\n public deleteObject(id: string): boolean {\r\n const obj = this._objects.get(id);\r\n if (obj) {\r\n const element = this._elementMap.get(id);\r\n if (element && this._synchronizer) {\r\n this._synchronizer.cleanupElement(element, obj);\r\n }\r\n\r\n this._scene.remove(obj.object);\r\n this._objects.delete(id);\r\n this._elementMap.delete(id);\r\n this._rootObjects = this._rootObjects.filter((root) => root !== obj);\r\n obj.destroy();\r\n return true;\r\n }\r\n return false;\r\n }\r\n\r\n public createFromElement(object: StringObject): void {\r\n const type = object.getProperty<string>(\"3d\");\r\n if (!type) return;\r\n\r\n const element = object.htmlElement;\r\n if (!element) return;\r\n\r\n const onAdd = (added3DObject: String3DObject) => {\r\n if (added3DObject) {\r\n const parentId = object.getProperty<string>(\"parentId\");\r\n if (parentId == null) {\r\n this._scene.add(added3DObject.object);\r\n this._rootObjects.push(added3DObject);\r\n } else {\r\n this._objects.get(parentId)?.addChild(added3DObject);\r\n }\r\n this._objects.set(object.id, added3DObject);\r\n this._elementMap.set(object.id, element);\r\n added3DObject.el = element;\r\n }\r\n };\r\n\r\n switch (type) {\r\n case \"group\":\r\n this.createGroup(object, onAdd);\r\n break;\r\n case \"pointLight\":\r\n this.createLight(object, \"point\", onAdd);\r\n break;\r\n case \"ambientLight\":\r\n this.createLight(object, \"ambient\", onAdd);\r\n break;\r\n case \"directionalLight\":\r\n this.createLight(object, \"directional\", onAdd);\r\n break;\r\n case \"spotLight\":\r\n this.createLight(object, \"spot\", onAdd);\r\n break;\r\n case \"hemisphereLight\":\r\n this.createLight(object, \"hemisphere\", onAdd);\r\n break;\r\n case \"model\":\r\n this.createModel(object, onAdd);\r\n break;\r\n case \"box\":\r\n this.createBox(object, onAdd);\r\n break;\r\n case \"sphere\":\r\n this.createSphere(object, onAdd);\r\n break;\r\n case \"plane\":\r\n this.createPlane(object, onAdd);\r\n break;\r\n case \"cylinder\":\r\n this.createCylinder(object, onAdd);\r\n break;\r\n case \"particles\":\r\n this.createParticles(object, onAdd);\r\n break;\r\n case \"text\":\r\n this.createText(object, onAdd);\r\n break;\r\n }\r\n }\r\n\r\n private createGroup(object: StringObject, onAdd: (obj: String3DObject) => void): String3DObject {\r\n const group = this.engine.createGroup();\r\n const obj = new String3DObject(object.id, \"group\", group, this.engine);\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createLight(\r\n object: StringObject,\r\n kind: \"point\" | \"ambient\" | \"directional\" | \"spot\" | \"hemisphere\",\r\n onAdd: (obj: String3DObject) => void\r\n ): String3DObject {\r\n const element = object.htmlElement;\r\n const colorRaw = element ? readStringStyle(element, \"--light-color\", \"#ffffff\") : \"#ffffff\";\r\n const color = colorRaw && colorRaw !== \"none\" ? colorRaw : \"#ffffff\";\r\n const intensity = element ? readNumberStyle(element, \"--light-intensity\", 1) : 1;\r\n\r\n let light: I3DLight;\r\n if (kind === \"point\") {\r\n const distance = element ? readNumberStyle(element, \"--light-distance\", 1000) : 1000;\r\n const decay = element ? readNumberStyle(element, \"--light-decay\", 0) : 0;\r\n light = this.engine.createPointLight(color, intensity, distance, decay);\r\n } else if (kind === \"directional\") {\r\n light = this.engine.createDirectionalLight(color, intensity);\r\n } else if (kind === \"spot\") {\r\n const distance = element ? readNumberStyle(element, \"--light-distance\", 0) : 0;\r\n const angle = element ? readNumberStyle(element, \"--light-angle\", Math.PI / 3) : Math.PI / 3;\r\n const penumbra = element ? readNumberStyle(element, \"--light-penumbra\", 0) : 0;\r\n const decay = element ? readNumberStyle(element, \"--light-decay\", 1) : 1;\r\n light = this.engine.createSpotLight(color, intensity, distance, angle, penumbra, decay);\r\n } else if (kind === \"hemisphere\") {\r\n const groundRaw = element\r\n ? readStringStyle(element, \"--light-ground-color\", \"#ffffff\")\r\n : \"#ffffff\";\r\n const groundColor = groundRaw && groundRaw !== \"none\" ? groundRaw : \"#ffffff\";\r\n light = this.engine.createHemisphereLight(color, groundColor, intensity);\r\n } else {\r\n light = this.engine.createAmbientLight(color, intensity);\r\n }\r\n\r\n const castShadow = element ? readBooleanStyle(element, \"--shadow-cast\", false) : false;\r\n if (castShadow && light.shadow) {\r\n light.castShadow = true;\r\n const bias = element ? readNumberStyle(element, \"--shadow-bias\", 0) : 0;\r\n const mapSize = element ? readNumberStyle(element, \"--shadow-map-size\", 512) : 512;\r\n light.shadow.bias = bias;\r\n light.shadow.mapSize.width = mapSize;\r\n light.shadow.mapSize.height = mapSize;\r\n }\r\n\r\n const obj = new String3DObject(object.id, kind + \"Light\", light, this.engine);\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private applyShadowProps(object: StringObject, mesh: any): void {\r\n const element = object.htmlElement;\r\n const castShadow = element ? readBooleanStyle(element, \"--shadow-cast\", false) : false;\r\n const receiveShadow = element ? readBooleanStyle(element, \"--shadow-receive\", false) : false;\r\n mesh.castShadow = castShadow;\r\n mesh.receiveShadow = receiveShadow;\r\n }\r\n\r\n private createBox(object: StringObject, onAdd: (obj: String3DObject) => void): String3DObject {\r\n const geometry = this.engine.createBoxGeometry(1, 1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"box\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createSphere(object: StringObject, onAdd: (obj: String3DObject) => void): String3DObject {\r\n const quality = this.getGeometryQuality(object.htmlElement);\r\n const widthSegments = Math.max(3, Math.round(32 * quality));\r\n const heightSegments = Math.max(2, Math.round(32 * quality));\r\n const geometry = this.engine.createSphereGeometry(0.5, widthSegments, heightSegments);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"sphere\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createPlane(object: StringObject, onAdd: (obj: String3DObject) => void): String3DObject {\r\n const geometry = this.engine.createPlaneGeometry(1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"plane\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createCylinder(\r\n object: StringObject,\r\n onAdd: (obj: String3DObject) => void\r\n ): String3DObject {\r\n const quality = this.getGeometryQuality(object.htmlElement);\r\n const segments = Math.max(3, Math.round(32 * quality));\r\n const geometry = this.engine.createCylinderGeometry(0.5, 0.5, 1, segments);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"cylinder\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createModel(object: StringObject, onAdd: (obj: String3DObject) => void): void {\r\n const modelPath = object.getProperty<string>(\"3d-model\");\r\n if (!modelPath) return;\r\n\r\n const loaderType = object.getProperty<string>(\"3d-model-loader\") || undefined;\r\n const loader = this.resolveModelLoader(loaderType);\r\n if (!loader) {\r\n return;\r\n }\r\n\r\n const element = object.htmlElement;\r\n if (element) {\r\n this.applyModelTextureRemap(loader, element);\r\n }\r\n const shouldCenter = object.getProperty<boolean>(\"3d-model-center\") ?? false;\r\n\r\n loader.load(\r\n modelPath,\r\n (gltf: any) => {\r\n const root = gltf?.scene || gltf?.object || gltf;\r\n if (!root) {\r\n return;\r\n }\r\n\r\n const overrideMaterial =\r\n element && this.shouldOverrideModelMaterial(element)\r\n ? this.createMaterialFromElement(element, object)\r\n : null;\r\n\r\n if (typeof root.traverse === \"function\") {\r\n root.traverse((child: any) => {\r\n if (child.isMesh) {\r\n if (overrideMaterial) {\r\n child.material = overrideMaterial;\r\n }\r\n this.applyShadowProps(object, child);\r\n }\r\n });\r\n }\r\n\r\n if (shouldCenter) {\r\n this.centerObject(root);\r\n }\r\n const obj = new String3DObject(object.id, \"model\", root, this.engine);\r\n onAdd(obj);\r\n },\r\n undefined,\r\n undefined\r\n );\r\n }\r\n\r\n private createParticles(object: StringObject, onAdd: (obj: String3DObject) => void): void {\r\n if (!this.engine.createParticleSystem) {\r\n return;\r\n }\r\n\r\n const element = object.htmlElement;\r\n const config: import(\"./abstractions/I3DEngine\").ParticleSystemConfig = {\r\n mode: \"emitter\",\r\n count: 300,\r\n size: 2,\r\n color: \"#ffffff\",\r\n opacity: 1,\r\n spread: 120,\r\n spreadX: 0,\r\n spreadY: 0,\r\n seed: 1,\r\n emitRate: 30,\r\n emitBurst: 0,\r\n particleLife: 2.5,\r\n particleSpeed: 40,\r\n particleDirection: [0, 1, 0] as [number, number, number],\r\n particleGravity: [0, -30, 0] as [number, number, number],\r\n particleDrag: 0.1,\r\n particleSizeVariation: 0.6,\r\n particleColorVariation: 0.2,\r\n particleShape: \"sphere\",\r\n particleModelUrl: \"\",\r\n particleModelLoader: \"\",\r\n particleModelNode: \"\",\r\n instanceShape: \"sphere\",\r\n instanceModelUrl: \"\",\r\n instanceModelLoader: \"\",\r\n instanceModelNode: \"\",\r\n instanceScale: 1,\r\n instanceScaleVariation: 0.5,\r\n instanceRotationSpeed: 0.4,\r\n instanceJitter: 0.2,\r\n instanceFlow: 0.3,\r\n instanceDisperse: 0,\r\n instanceDisperseScatter: 0,\r\n instanceDisperseScatterX: 0,\r\n instanceDisperseScatterY: 0,\r\n instanceDisperseScatterZ: 0,\r\n modelTransitionDuration: 0,\r\n };\r\n\r\n const system = this.engine.createParticleSystem(config);\r\n const obj = new String3DObject(object.id, \"particles\", system, this.engine);\r\n onAdd(obj);\r\n }\r\n\r\n private createText(object: StringObject, onAdd: (obj: String3DObject) => void): void {\r\n if (!this.engine.createTextGeometry) {\r\n return;\r\n }\r\n\r\n const geometry = this.engine.createBoxGeometry(1, 1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n\r\n const group = this.engine.createGroup();\r\n (group as any).__textMesh = mesh;\r\n group.add(mesh);\r\n\r\n const obj = new String3DObject(object.id, \"text\", group, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n }\r\n\r\n private getGeometryQuality(element?: HTMLElement | null): number {\r\n if (!element) return 1;\r\n const quality = readNumberStyle(element, \"--geometry-quality\", 1);\r\n if (!Number.isFinite(quality) || quality <= 0) return 1;\r\n return quality;\r\n }\r\n\r\n private resolveModelLoader(type?: string): I3DModelLoader | undefined {\r\n if (type) {\r\n if (this._modelLoaderCache.has(type)) {\r\n return this._modelLoaderCache.get(type);\r\n }\r\n if (!this._modelLoaderFactory) {\r\n return undefined;\r\n }\r\n const loader = this._modelLoaderFactory(this.engine, type);\r\n this._modelLoaderCache.set(type, loader);\r\n return loader;\r\n }\r\n\r\n if (this._modelLoader) {\r\n return this._modelLoader;\r\n }\r\n\r\n if (this._modelLoaderFactory) {\r\n return this._modelLoaderFactory(this.engine);\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private centerObject(object: any): void {\r\n if (!object) return;\r\n const bbox = this.engine.computeBoundingBoxRecursively(object);\r\n const center = this.getBoxCenter(bbox);\r\n if (object.position?.set) {\r\n object.position.set(-center.x, -center.y, -center.z);\r\n }\r\n object.updateMatrixWorld(true);\r\n }\r\n\r\n private getBoxCenter(box: any): I3DVector3 {\r\n const center = this.engine.createVector3();\r\n center.x = (box.min.x + box.max.x) / 2;\r\n center.y = (box.min.y + box.max.y) / 2;\r\n center.z = (box.min.z + box.max.z) / 2;\r\n return center;\r\n }\r\n\r\n private createMaterialFromObject(object: StringObject): I3DMaterial {\r\n return this.createMaterialFromElement(object.htmlElement, object);\r\n }\r\n\r\n private createMaterialFromElement(\r\n element: HTMLElement | null,\r\n object?: StringObject\r\n ): I3DMaterial {\r\n const style = element ? getComputedStyle(element) : null;\r\n const getCSS = (prop: string) => (style ? style.getPropertyValue(prop).trim() : \"\");\r\n\r\n const resolve = <T>(cssProp: string, parser: (v: string) => T, defaultValue: T): T => {\r\n const cssVal = getCSS(cssProp);\r\n if (cssVal && cssVal !== \"none\" && cssVal !== \"\") return parser(cssVal);\r\n return defaultValue;\r\n };\r\n\r\n const parseNumber = (v: string) => parseFloat(v);\r\n const parseColor = (v: string) => v;\r\n const parseUrl = (v: string) => {\r\n const match = v.match(/url\\(['\"]?(.*?)['\"]?\\)/);\r\n return match ? match[1] : v;\r\n };\r\n\r\n const type = resolve(\"--material-type\", (v) => v.split(\"[\")[0] || \"basic\", \"basic\");\r\n\r\n const customMaterial = this.tryCreateCustomMaterial(type, element, style, object);\r\n if (customMaterial) {\r\n return customMaterial;\r\n }\r\n\r\n const color = resolve(\"--material-color\", parseColor, \"#ffffff\");\r\n\r\n const opacity = resolve(\"--opacity\", parseNumber, 1);\r\n const metalness = resolve(\"--material-metalness\", parseNumber, 0);\r\n const roughness = resolve(\"--material-roughness\", parseNumber, 1);\r\n const emissive = resolve(\"--material-emissive\", parseColor, \"#000000\");\r\n\r\n const params: any = {\r\n color,\r\n transparent: opacity < 1,\r\n opacity: opacity,\r\n };\r\n\r\n const mapSrc = resolve(\"--texture-map\", parseUrl, \"\");\r\n const normalMapSrc = resolve(\"--texture-normal\", parseUrl, \"\");\r\n const roughnessMapSrc = resolve(\"--texture-roughness\", parseUrl, \"\");\r\n const metalnessMapSrc = resolve(\"--texture-metalness\", parseUrl, \"\");\r\n const aoMapSrc = resolve(\"--texture-ao\", parseUrl, \"\");\r\n\r\n const flipY = this.parseFlipY(element);\r\n const colorSpace = element ? readStringStyle(element, \"--texture-color-space\", \"\") : \"\";\r\n\r\n const hasMaps = !!(mapSrc || normalMapSrc || roughnessMapSrc || metalnessMapSrc || aoMapSrc);\r\n let finalType = type;\r\n if (finalType !== \"standard\" && hasMaps) {\r\n finalType = \"standard\";\r\n }\r\n\r\n if (finalType === \"standard\") {\r\n if (mapSrc) params.map = this.loadTexture(mapSrc, { flipY, colorSpace });\r\n if (normalMapSrc) params.normalMap = this.loadTexture(normalMapSrc, { flipY });\r\n if (roughnessMapSrc) params.roughnessMap = this.loadTexture(roughnessMapSrc, { flipY });\r\n if (metalnessMapSrc) params.metalnessMap = this.loadTexture(metalnessMapSrc, { flipY });\r\n if (aoMapSrc) params.aoMap = this.loadTexture(aoMapSrc, { flipY });\r\n\r\n params.metalness = metalness;\r\n params.roughness = roughness;\r\n params.emissive = emissive;\r\n\r\n return this.engine.createMeshStandardMaterial(params);\r\n }\r\n\r\n return this.engine.createMeshBasicMaterial(params);\r\n }\r\n\r\n private tryCreateCustomMaterial(\r\n type: string,\r\n element: HTMLElement | null,\r\n style: CSSStyleDeclaration | null,\r\n object?: StringObject\r\n ): I3DMaterial | null {\r\n const definition = String3DCustomMaterialRegistry.get(type);\r\n if (!definition) {\r\n return null;\r\n }\r\n\r\n const factory = this.engine.getMaterialFactory?.();\r\n if (!factory) {\r\n return null;\r\n }\r\n if (!factory.supports(definition)) {\r\n return null;\r\n }\r\n\r\n let initialUniforms: Record<string, any> = {};\r\n if (element && style) {\r\n initialUniforms = factory.parseUniformsFromCSS(definition, element, style);\r\n }\r\n\r\n const instance = factory.create(definition, initialUniforms);\r\n\r\n if (object) {\r\n this._materialInstances.set(object.id, instance);\r\n }\r\n\r\n return instance.material;\r\n }\r\n\r\n public updateMaterialUniforms(objectId: string, uniforms: Record<string, any>): void {\r\n const instance = this._materialInstances.get(objectId);\r\n if (instance) {\r\n instance.update(uniforms);\r\n }\r\n }\r\n\r\n public getMaterialInstance(objectId: string): IMaterialInstance | undefined {\r\n return this._materialInstances.get(objectId);\r\n }\r\n\r\n public recreateMaterialForObject(object: String3DObject, element: HTMLElement | null): void {\r\n const oldInstance = this._materialInstances.get(object.id);\r\n if (oldInstance && oldInstance.dispose) {\r\n oldInstance.dispose();\r\n }\r\n this._materialInstances.delete(object.id);\r\n\r\n let stringObject: StringObject | undefined;\r\n for (const [id, el] of this._elementMap) {\r\n if (id === object.id && el === element) {\r\n stringObject = (el as any).__stringObject || (el as any).stringObject;\r\n break;\r\n }\r\n }\r\n\r\n const newMaterial = this.createMaterialFromElement(element, stringObject);\r\n\r\n if (object.object && object.object.traverse) {\r\n object.object.traverse((child: any) => {\r\n if (child.material) {\r\n if (child.material.dispose) {\r\n child.material.dispose();\r\n }\r\n child.material = newMaterial;\r\n }\r\n });\r\n }\r\n\r\n object.material = newMaterial;\r\n }\r\n\r\n private loadTexture(src: string, options: { flipY?: boolean; colorSpace?: string } = {}): any {\r\n const textureLoader = this.engine.createTextureLoader();\r\n const texture = textureLoader.load(src);\r\n if (typeof options.flipY === \"boolean\") {\r\n texture.flipY = options.flipY;\r\n }\r\n const colorSpace = (options.colorSpace || \"\").toLowerCase().trim();\r\n if (colorSpace && \"colorSpace\" in texture) {\r\n texture.colorSpace = colorSpace === \"srgb\" ? \"srgb\" : \"linear\";\r\n }\r\n texture.needsUpdate = true;\r\n return texture;\r\n }\r\n\r\n private parseFlipY(element?: HTMLElement | null): boolean | undefined {\r\n const value = element ? readStringStyle(element, \"--texture-flip-y\", \"\") : \"\";\r\n if (value === undefined || value === null || value === \"\") return undefined;\r\n if (typeof value === \"boolean\") return value;\r\n const normalized = String(value).toLowerCase().trim();\r\n if (normalized === \"false\" || normalized === \"0\" || normalized === \"no\") return false;\r\n if (normalized === \"true\" || normalized === \"1\" || normalized === \"yes\") return true;\r\n return undefined;\r\n }\r\n\r\n private shouldOverrideModelMaterial(element: HTMLElement): boolean {\r\n const style = getComputedStyle(element);\r\n const hasStyle = (prop: string) => {\r\n const val = style.getPropertyValue(prop);\r\n return val && val !== \"0\" && val !== \"none\" && val !== \"\";\r\n };\r\n\r\n if (hasStyle(\"--material-color\") || hasStyle(\"--texture-map\")) return true;\r\n\r\n const cssVars = [\r\n \"--material-type\",\r\n \"--material-metalness\",\r\n \"--material-roughness\",\r\n \"--material-emissive\",\r\n \"--opacity\",\r\n \"--texture-normal\",\r\n \"--texture-roughness\",\r\n \"--texture-metalness\",\r\n \"--texture-ao\",\r\n ];\r\n return cssVars.some((prop) => hasStyle(prop));\r\n }\r\n\r\n private applyModelTextureRemap(loader: any, element: HTMLElement): void {\r\n const baseRaw = (element.getAttribute(\"string-3d-model-texture-base\") || \"\").trim();\r\n const base = baseRaw ? baseRaw.replace(/\\/?$/, \"/\") : \"\";\r\n const mappingRaw = element.getAttribute(\"string-3d-model-textures\");\r\n let mapping: Record<string, string> | null = null;\r\n\r\n if (mappingRaw) {\r\n try {\r\n mapping = JSON.parse(mappingRaw);\r\n } catch (error) {}\r\n }\r\n\r\n const manager = loader?.manager;\r\n if (!manager || typeof manager.setURLModifier !== \"function\") {\r\n return;\r\n }\r\n\r\n manager.setURLModifier((url: string) => {\r\n const mapped = mapping && url in mapping ? mapping[url] : url;\r\n if (!base) return mapped;\r\n if (/^(blob:|data:|https?:|file:|\\/)/i.test(mapped)) return mapped;\r\n return base + mapped.replace(/^\\.?\\//, \"\");\r\n });\r\n }\r\n\r\n public destroy(): void {\r\n this._materialInstances.forEach((instance) => instance.dispose());\r\n this._materialInstances.clear();\r\n this._objects.forEach((obj) => obj.destroy());\r\n this._objects.clear();\r\n this._rootObjects = [];\r\n }\r\n}\r\n","import type { SyncContext } from \"./SyncContext\";\n\nexport class StyleBundleCache<T> {\n private cache: WeakMap<HTMLElement, T> = new WeakMap();\n private meta: WeakMap<HTMLElement, { time: number }> = new WeakMap();\n\n get(el: HTMLElement, ctx: SyncContext, reader: (el: HTMLElement) => T): T {\n const canUseCache = !!ctx.dirtySet && ctx.forceSync === false && !ctx.dirtySet.has(el);\n if (canUseCache) {\n const cached = this.cache.get(el);\n if (cached) return cached;\n }\n\n const now = performance.now();\n const interval = Math.max(0, ctx.styleReadIntervalMs ?? 0);\n if (interval > 0) {\n const metaData = this.meta.get(el);\n const cached = this.cache.get(el);\n if (metaData && cached && now - metaData.time < interval) {\n return cached;\n }\n }\n\n const bundle = reader(el);\n this.cache.set(el, bundle);\n this.meta.set(el, { time: now });\n return bundle;\n }\n\n clear(): void {\n this.cache = new WeakMap();\n this.meta = new WeakMap();\n }\n}\n","import { String3DObject } from \"../String3DObject\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport type { SyncContext } from \"./SyncContext\";\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\n\nconst DEG_TO_RAD = Math.PI / 180;\n\ntype GroupStyleBundle = {\n translateZ: number;\n scale: number;\n rotateX: number;\n rotateY: number;\n rotateZ: number;\n};\n\nexport class GroupSynchronizer implements String3DObjectSyncStrategy {\n private static styleCache = new StyleBundleCache<GroupStyleBundle>();\n\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\n const cached = (el as any).__layoutCache;\n const rect = cached ? cached.rect : el.getBoundingClientRect();\n const bundle = this.readStyleBundle(el, ctx);\n\n const screenCenterX = rect.left + rect.width * 0.5;\n const screenCenterY = rect.top + rect.height * 0.5;\n\n if (ctx.camera.getMode() === \"orthographic\") {\n object.object.position.set(\n screenCenterX - ctx.viewportWidth / 2,\n -(screenCenterY - ctx.viewportHeight / 2),\n bundle.translateZ\n );\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\n const normalizedX = screenCenterX / ctx.viewportWidth;\n const normalizedY = screenCenterY / ctx.viewportHeight;\n object.object.position.set(\n (normalizedX - 0.5) * frustum.width,\n -(normalizedY - 0.5) * frustum.height,\n bundle.translateZ\n );\n }\n\n object.object.scale.set(bundle.scale, bundle.scale, bundle.scale);\n\n object.object.rotation.x = -bundle.rotateX * DEG_TO_RAD;\n object.object.rotation.y = bundle.rotateY * DEG_TO_RAD;\n object.object.rotation.z = -bundle.rotateZ * DEG_TO_RAD;\n object.object.rotation.order = \"XYZ\";\n\n object.object.updateMatrixWorld(true);\n\n return { scale: bundle.scale };\n }\n\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): GroupStyleBundle {\n return GroupSynchronizer.styleCache.get(el, ctx, (el) => {\n const styles = new StyleReader(el);\n return {\n translateZ: styles.readNumber(\"--translate-z\", 0),\n scale: styles.readNumber(\"--scale\", 1),\n rotateX: styles.readNumber(\"--rotate-x\", 0),\n rotateY: styles.readNumber(\"--rotate-y\", 0),\n rotateZ: styles.readNumber(\"--rotate-z\", 0),\n };\n });\n }\n}\n","import { String3DObject } from \"../String3DObject\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport type { SyncContext } from \"./SyncContext\";\nimport { I3DLight } from \"../abstractions/I3DEngine\";\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\n\ntype LightStyleBundle = {\n translateZ: number;\n translateX: number;\n translateY: number;\n color?: string;\n intensity: number;\n distance?: number;\n decay?: number;\n angle?: number;\n penumbra?: number;\n groundColor?: string;\n castShadow: boolean;\n shadowBias?: number;\n shadowMapSize?: number;\n targetId?: string;\n targetOffset?: { x: number; y: number; z: number };\n};\n\nexport class LightSynchronizer implements String3DObjectSyncStrategy {\n private static styleCache = new StyleBundleCache<LightStyleBundle>();\n\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\n const cached = (el as any).__layoutCache;\n const rect = cached ? cached.rect : el.getBoundingClientRect();\n const bundle = this.readStyleBundle(el, ctx, object);\n\n const screenCenterX = rect.left + rect.width * 0.5;\n const screenCenterY = rect.top + rect.height * 0.5;\n\n if (ctx.camera.getMode() === \"orthographic\") {\n object.object.position.set(\n screenCenterX - ctx.viewportWidth / 2 + bundle.translateX,\n -(screenCenterY - ctx.viewportHeight / 2) + bundle.translateY,\n bundle.translateZ\n );\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\n const normalizedX = screenCenterX / ctx.viewportWidth;\n const normalizedY = screenCenterY / ctx.viewportHeight;\n object.object.position.set(\n (normalizedX - 0.5) * frustum.width + bundle.translateX,\n -(normalizedY - 0.5) * frustum.height + bundle.translateY,\n bundle.translateZ\n );\n }\n\n const light = object.object as I3DLight;\n\n if (\n bundle.color &&\n bundle.color !== \"none\" &&\n light.color &&\n typeof light.color.set === \"function\"\n ) {\n light.color.set(bundle.color);\n }\n\n light.intensity = bundle.intensity;\n\n if (typeof light.distance !== \"undefined\" && bundle.distance !== undefined) {\n light.distance = bundle.distance;\n }\n if (typeof light.decay !== \"undefined\" && bundle.decay !== undefined) {\n light.decay = bundle.decay;\n }\n\n if (typeof light.angle !== \"undefined\" && bundle.angle !== undefined) {\n light.angle = bundle.angle;\n }\n if (typeof light.penumbra !== \"undefined\" && bundle.penumbra !== undefined) {\n light.penumbra = bundle.penumbra;\n }\n\n if (\n bundle.groundColor &&\n bundle.groundColor !== \"none\" &&\n (light as any).groundColor &&\n typeof (light as any).groundColor.set === \"function\"\n ) {\n (light as any).groundColor.set(bundle.groundColor);\n }\n\n if (light.castShadow !== bundle.castShadow) {\n light.castShadow = bundle.castShadow;\n }\n if (bundle.castShadow && light.shadow) {\n if (bundle.shadowBias !== undefined) {\n light.shadow.bias = bundle.shadowBias;\n }\n if (\n bundle.shadowMapSize !== undefined &&\n light.shadow.mapSize.width !== bundle.shadowMapSize\n ) {\n light.shadow.mapSize.width = bundle.shadowMapSize;\n light.shadow.mapSize.height = bundle.shadowMapSize;\n }\n }\n\n if (bundle.targetId && bundle.targetId !== \"none\" && light.target) {\n const targetEl = document.querySelector(`[string-id=\"${bundle.targetId}\"]`);\n if (targetEl) {\n const tCached = (targetEl as any).__layoutCache;\n const tRect = tCached ? tCached.rect : targetEl.getBoundingClientRect();\n const tStyles = new StyleReader(targetEl as HTMLElement);\n const tTranslateZ = tStyles.readNumber(\"--translate-z\", 0);\n\n const tScreenCenterX = tRect.left + tRect.width * 0.5;\n const tScreenCenterY = tRect.top + tRect.height * 0.5;\n\n let x: number;\n let y: number;\n let z: number;\n if (ctx.camera.getMode() === \"orthographic\") {\n x = tScreenCenterX - ctx.viewportWidth / 2;\n y = -(tScreenCenterY - ctx.viewportHeight / 2);\n z = tTranslateZ;\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(tTranslateZ);\n const normalizedX = tScreenCenterX / ctx.viewportWidth;\n const normalizedY = tScreenCenterY / ctx.viewportHeight;\n x = (normalizedX - 0.5) * frustum.width;\n y = -(normalizedY - 0.5) * frustum.height;\n z = tTranslateZ;\n }\n\n if (bundle.targetOffset) {\n x += bundle.targetOffset.x;\n y += bundle.targetOffset.y;\n z += bundle.targetOffset.z;\n }\n\n light.target.position.set(x, y, z);\n\n light.target.updateMatrixWorld(true);\n }\n }\n\n return null;\n }\n\n private readStyleBundle(\n el: HTMLElement,\n ctx: SyncContext,\n object: String3DObject\n ): LightStyleBundle {\n return LightSynchronizer.styleCache.get(el, ctx, (el) => {\n const styles = new StyleReader(el);\n const light = object.object as I3DLight;\n\n const bundle: LightStyleBundle = {\n translateZ: styles.readNumber(\"--translate-z\", 0),\n translateX: styles.readNumber(\"--translate-x\", 0),\n translateY: styles.readNumber(\"--translate-y\", 0),\n color: styles.readString(\"--light-color\", \"\") || undefined,\n intensity: styles.readNumber(\"--light-intensity\", light.intensity ?? 1),\n castShadow: styles.readBoolean(\"--shadow-cast\", false),\n };\n\n if (typeof light.distance !== \"undefined\") {\n bundle.distance = styles.readNumber(\"--light-distance\", light.distance ?? 0);\n }\n if (typeof light.decay !== \"undefined\") {\n bundle.decay = styles.readNumber(\"--light-decay\", light.decay ?? 1);\n }\n if (typeof light.angle !== \"undefined\") {\n bundle.angle = styles.readNumber(\"--light-angle\", light.angle ?? Math.PI / 3);\n }\n if (typeof light.penumbra !== \"undefined\") {\n bundle.penumbra = styles.readNumber(\"--light-penumbra\", light.penumbra ?? 0);\n }\n\n const groundColor = styles.readString(\"--light-ground-color\", \"\");\n if (groundColor) bundle.groundColor = groundColor;\n\n if (bundle.castShadow && light.shadow) {\n bundle.shadowBias = styles.readNumber(\"--shadow-bias\", light.shadow.bias ?? 0);\n bundle.shadowMapSize = styles.readNumber(\n \"--shadow-map-size\",\n light.shadow.mapSize.width ?? 512\n );\n }\n\n const targetId = styles.readString(\"--light-target\", \"\").trim();\n if (targetId) bundle.targetId = targetId;\n const offsetRaw = styles.readString(\"--light-target-offset\", \"\").trim();\n if (offsetRaw) {\n const offset = this.parseTargetOffset(offsetRaw);\n if (offset) bundle.targetOffset = offset;\n }\n\n return bundle;\n });\n }\n\n private parseTargetOffset(value: string): { x: number; y: number; z: number } | null {\n const parts = value\n .split(/[\\s,]+/)\n .map((part) => part.trim())\n .filter(Boolean)\n .map((part) => Number.parseFloat(part));\n if (parts.length < 3 || parts.some((num) => Number.isNaN(num))) return null;\n return { x: parts[0], y: parts[1], z: parts[2] };\n }\n}\n","import { String3DObject } from \"../String3DObject\";\nimport type { SyncContext } from \"./SyncContext\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\n\nconst DEG_TO_RAD = Math.PI / 180;\n\nexport class MeshSynchronizer implements String3DObjectSyncStrategy {\n private static styleCache = new StyleBundleCache<StyleBundle>();\n private static layoutCache = new StyleBundleCache<LayoutBundle>();\n private static tempVector3: any = null;\n private static lastVisualProps: WeakMap<\n String3DObject,\n {\n opacity?: number;\n color?: string;\n metalness?: number;\n roughness?: number;\n emissive?: string;\n castShadow?: boolean;\n receiveShadow?: boolean;\n }\n > = new WeakMap();\n private static lastGeometryQuality: WeakMap<String3DObject, number> = new WeakMap();\n\n static applyVisualProps(\n el: HTMLElement,\n object: String3DObject,\n props: {\n opacity?: number;\n color?: string;\n metalness?: number;\n roughness?: number;\n emissive?: string;\n castShadow?: boolean;\n receiveShadow?: boolean;\n }\n ): void {\n const prev = MeshSynchronizer.lastVisualProps.get(object);\n if (prev) {\n if (\n prev.opacity === props.opacity &&\n prev.color === props.color &&\n prev.metalness === props.metalness &&\n prev.roughness === props.roughness &&\n prev.emissive === props.emissive &&\n prev.castShadow === props.castShadow &&\n prev.receiveShadow === props.receiveShadow\n )\n return;\n prev.opacity = props.opacity;\n prev.color = props.color;\n prev.metalness = props.metalness;\n prev.roughness = props.roughness;\n prev.emissive = props.emissive;\n prev.castShadow = props.castShadow;\n prev.receiveShadow = props.receiveShadow;\n } else {\n MeshSynchronizer.lastVisualProps.set(object, {\n opacity: props.opacity,\n color: props.color,\n metalness: props.metalness,\n roughness: props.roughness,\n emissive: props.emissive,\n castShadow: props.castShadow,\n receiveShadow: props.receiveShadow,\n });\n }\n\n const castShadow = props.castShadow ?? false;\n const receiveShadow = props.receiveShadow ?? false;\n\n const opacity = typeof props.opacity === \"number\" ? props.opacity : NaN;\n\n const applyMaterialProps = (mat: any) => {\n if (!mat) return;\n\n if (!isNaN(opacity)) {\n mat.opacity = opacity;\n mat.transparent = opacity < 1;\n }\n\n if (props.color && mat.color && mat.color.set) {\n mat.color.set(props.color);\n }\n\n if (typeof props.metalness === \"number\" && \"metalness\" in mat) {\n mat.metalness = props.metalness;\n }\n\n if (typeof props.roughness === \"number\" && \"roughness\" in mat) {\n mat.roughness = props.roughness;\n }\n\n if (props.emissive && mat.emissive && mat.emissive.set) {\n mat.emissive.set(props.emissive);\n }\n };\n\n if (object.object.traverse) {\n object.object.traverse((child: any) => {\n if (child.isMesh) {\n if (child.castShadow !== castShadow) child.castShadow = castShadow;\n if (child.receiveShadow !== receiveShadow) child.receiveShadow = receiveShadow;\n\n const materials = Array.isArray(child.material) ? child.material : [child.material];\n materials.forEach(applyMaterialProps);\n }\n });\n } else if ((object.object as any).isMesh) {\n const mesh = object.object as any;\n if (mesh.castShadow !== castShadow) mesh.castShadow = castShadow;\n if (mesh.receiveShadow !== receiveShadow) mesh.receiveShadow = receiveShadow;\n\n const materials = Array.isArray(mesh.material) ? mesh.material : [mesh.material];\n materials.forEach(applyMaterialProps);\n }\n }\n\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\n const { rect, width: originalWidth, height: originalHeight } = this.readLayout(el, ctx);\n const bundle = this.readStyleBundle(el, ctx);\n const {\n translateZ,\n cssScale,\n rotateX,\n rotateY,\n rotateZ,\n cssScaleZ,\n opacity,\n color,\n metalness,\n roughness,\n emissive,\n castShadow,\n receiveShadow,\n geometryQuality,\n } = bundle;\n\n const screenCenterX = rect.left + rect.width * 0.5;\n const screenCenterY = rect.top + rect.height * 0.5;\n\n if (ctx.camera.getMode() === \"orthographic\") {\n object.object.position.set(\n screenCenterX - ctx.viewportWidth / 2,\n -(screenCenterY - ctx.viewportHeight / 2),\n translateZ\n );\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(translateZ);\n const normalizedX = screenCenterX / ctx.viewportWidth;\n const normalizedY = screenCenterY / ctx.viewportHeight;\n object.object.position.set(\n (normalizedX - 0.5) * frustum.width,\n -(normalizedY - 0.5) * frustum.height,\n translateZ\n );\n }\n\n object.object.rotation.x = -rotateX * DEG_TO_RAD;\n object.object.rotation.y = rotateY * DEG_TO_RAD;\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\n object.object.rotation.order = \"XYZ\";\n\n const targetWidth = originalWidth * cssScale;\n const targetHeight = originalHeight * cssScale;\n const parentScale = parentData?.scale || 1;\n const baseScaleZ = cssScaleZ * parentScale;\n const minTargetSize = targetWidth < targetHeight ? targetWidth : targetHeight;\n let scaleX: number, scaleY: number, scaleZ: number;\n\n switch (object.type) {\n case \"box\":\n case \"sphere\": {\n const uniformSize = minTargetSize * parentScale;\n scaleX = scaleY = uniformSize;\n scaleZ = uniformSize * cssScaleZ;\n break;\n }\n case \"model\": {\n const bbox = object.getOriginalBoundingBox();\n if (!MeshSynchronizer.tempVector3) {\n MeshSynchronizer.tempVector3 = ctx.engine.createVector3();\n }\n const size = bbox.getSize(MeshSynchronizer.tempVector3);\n const fitMode = el.getAttribute(\"string-3d-model-fit\");\n const modelScale = parseFloat(el.getAttribute(\"string-3d-model-scale\") || \"1\");\n const finalModelScale = Number.isFinite(modelScale)\n ? modelScale * parentScale\n : parentScale;\n\n if (size.x > 0 && size.y > 0) {\n const scaleW = targetWidth / size.x;\n const scaleH = targetHeight / size.y;\n const uniformScale =\n (fitMode === \"cover\"\n ? scaleW > scaleH\n ? scaleW\n : scaleH\n : scaleW < scaleH\n ? scaleW\n : scaleH) * finalModelScale;\n scaleX = scaleY = uniformScale;\n scaleZ = uniformScale * cssScaleZ;\n } else {\n const fallbackSize = minTargetSize * finalModelScale;\n scaleX = scaleY = fallbackSize;\n scaleZ = fallbackSize * cssScaleZ;\n }\n break;\n }\n case \"cylinder\":\n scaleX = targetWidth * parentScale;\n scaleY = targetHeight * parentScale;\n scaleZ = targetWidth * baseScaleZ;\n break;\n default:\n scaleX = targetWidth * parentScale;\n scaleY = targetHeight * parentScale;\n scaleZ = minTargetSize * 0.5 * baseScaleZ;\n break;\n }\n\n object.object.scale.set(scaleX, scaleY, scaleZ);\n\n MeshSynchronizer.applyVisualProps(el, object, {\n opacity,\n color: color && color !== \"none\" ? color : undefined,\n metalness: isNaN(metalness) ? undefined : metalness,\n roughness: isNaN(roughness) ? undefined : roughness,\n emissive: emissive && emissive !== \"none\" ? emissive : undefined,\n castShadow,\n receiveShadow,\n });\n\n this.applyGeometryQuality(object, geometryQuality, ctx);\n\n this.updateCustomUniforms(el, object, ctx);\n\n return { scale: cssScale * parentScale };\n }\n\n private applyGeometryQuality(object: String3DObject, quality: number, ctx: SyncContext): void {\n const engine: any = ctx.engine as any;\n const simplify = engine?.simplifyGeometry?.bind(engine);\n if (typeof simplify !== \"function\") return;\n\n const normalized = Number.isFinite(quality) && quality > 0 ? quality : 1;\n const prev = MeshSynchronizer.lastGeometryQuality.get(object);\n if (typeof prev === \"number\" && Math.abs(prev - normalized) < 0.001) return;\n MeshSynchronizer.lastGeometryQuality.set(object, normalized);\n\n const applyToMesh = (mesh: any) => {\n if (!mesh?.geometry) return;\n const userData = mesh.userData || (mesh.userData = {});\n if (!userData.__originalGeometry) {\n userData.__originalGeometry = mesh.geometry;\n }\n const original = userData.__originalGeometry;\n if (normalized >= 0.999) {\n mesh.geometry = original;\n return;\n }\n if (!userData.__lodCache) {\n userData.__lodCache = new Map<string, any>();\n }\n const key = normalized.toFixed(3);\n if (userData.__lodCache.has(key)) {\n mesh.geometry = userData.__lodCache.get(key);\n return;\n }\n const simplified = simplify(original, normalized);\n if (simplified) {\n userData.__lodCache.set(key, simplified);\n mesh.geometry = simplified;\n }\n };\n\n if (object.object.traverse) {\n object.object.traverse((child: any) => {\n if (child?.isMesh) applyToMesh(child);\n });\n } else if ((object.object as any).isMesh) {\n applyToMesh(object.object as any);\n }\n }\n\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\n const factory = ctx.engine.getMaterialFactory?.();\n if (!factory) return;\n\n const style = getComputedStyle(el);\n\n const apply = (mat: any) => {\n const definition = mat?.userData?.definition;\n if (!definition?.uniforms) return;\n\n const values = factory.parseUniformsFromCSS(definition, el, style);\n\n for (const [key, value] of Object.entries(values)) {\n const def = definition.uniforms?.[key];\n if (!def) continue;\n\n const converter = (factory as any).convertUniformValue?.bind(factory);\n const converted = converter ? converter(def.type, value) : value;\n\n if (mat.userData?.shader?.uniforms?.[key]) {\n mat.userData.shader.uniforms[key].value = converted;\n } else if (mat.userData?.customUniforms?.[key]) {\n mat.userData.customUniforms[key].value = converted;\n } else if (mat.uniforms?.[key]) {\n mat.uniforms[key].value = converted;\n }\n }\n };\n\n if (object.object.traverse) {\n object.object.traverse((child: any) => {\n if (child.isMesh) {\n const materials = Array.isArray(child.material) ? child.material : [child.material];\n materials.forEach(apply);\n }\n });\n } else if ((object.object as any).isMesh) {\n const mesh = object.object as any;\n const materials = Array.isArray(mesh.material) ? mesh.material : [mesh.material];\n materials.forEach(apply);\n }\n }\n\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): StyleBundle {\n return MeshSynchronizer.styleCache.get(el, ctx, (el) => {\n const styleMap = (el as any).computedStyleMap?.();\n const style = getComputedStyle(el);\n\n const readNumber = (prop: string, fallback: number): number => {\n const mapValue = styleMap?.get?.(prop);\n if (mapValue !== undefined && mapValue !== null) {\n const val =\n typeof mapValue === \"object\" && \"value\" in (mapValue as any)\n ? (mapValue as any).value\n : mapValue;\n const num = typeof val === \"number\" ? val : Number.parseFloat(String(val));\n if (!Number.isNaN(num)) return num;\n }\n const num = Number.parseFloat(style.getPropertyValue(prop));\n return Number.isNaN(num) ? fallback : num;\n };\n\n const readString = (prop: string): string | undefined => {\n const mapValue = styleMap?.get?.(prop);\n const val =\n mapValue && typeof mapValue === \"object\" && \"value\" in (mapValue as any)\n ? (mapValue as any).value\n : mapValue;\n if (typeof val === \"string\") return val.trim() || undefined;\n const raw = style.getPropertyValue(prop).trim();\n return raw || undefined;\n };\n\n const readBool = (prop: string, fallback = false): boolean => {\n const raw = readString(prop);\n if (!raw) return fallback;\n const norm = raw.toLowerCase();\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\n ? true\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\n ? false\n : fallback;\n };\n\n return {\n translateZ: readNumber(\"--translate-z\", 0),\n cssScale: readNumber(\"--scale\", 1),\n rotateX: readNumber(\"--rotate-x\", 0),\n rotateY: readNumber(\"--rotate-y\", 0),\n rotateZ: readNumber(\"--rotate-z\", 0),\n cssScaleZ: readNumber(\"--scale-z\", 1),\n opacity: readNumber(\"--opacity\", NaN),\n color: readString(\"--material-color\"),\n metalness: readNumber(\"--material-metalness\", NaN),\n roughness: readNumber(\"--material-roughness\", NaN),\n emissive: readString(\"--material-emissive\"),\n castShadow: readBool(\"--shadow-cast\", false),\n receiveShadow: readBool(\"--shadow-receive\", false),\n geometryQuality: readNumber(\"--geometry-quality\", 1),\n };\n });\n }\n\n private readLayout(el: HTMLElement, ctx: SyncContext): LayoutBundle {\n const cached = (el as any).__layoutCache;\n if (cached) {\n return cached;\n }\n\n return MeshSynchronizer.layoutCache.get(el, ctx, (el) => {\n const rect = el.getBoundingClientRect();\n const width = el.offsetWidth || rect.width;\n const height = el.offsetHeight || rect.height;\n return { rect, width, height };\n });\n }\n}\n\ntype StyleBundle = {\n translateZ: number;\n cssScale: number;\n rotateX: number;\n rotateY: number;\n rotateZ: number;\n cssScaleZ: number;\n opacity: number;\n color?: string;\n metalness: number;\n roughness: number;\n emissive?: string;\n castShadow: boolean;\n receiveShadow: boolean;\n geometryQuality: number;\n};\n\ntype LayoutBundle = {\n rect: DOMRect;\n width: number;\n height: number;\n};\n","import { String3DObject } from \"../String3DObject\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\nimport type { SyncContext } from \"./SyncContext\";\r\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\r\nimport { StyleBundleCache } from \"./StyleBundleCache\";\r\nimport type { ParticleSystemConfig } from \"../abstractions/I3DEngine\";\r\nimport { String3DCustomMaterialRegistry } from \"../materials\";\r\nimport type { IMaterialInstance } from \"../materials\";\r\n\r\ntype ParticleStyleBundle = ParticleSystemConfig & {\r\n translateZ: number;\r\n scale: number;\r\n rotateX: number;\r\n rotateY: number;\r\n rotateZ: number;\r\n particlesFit: boolean;\r\n materialType: string;\r\n};\r\n\r\nconst DEG_TO_RAD = Math.PI / 180;\r\n\r\nconst DEFAULT_CONFIG: ParticleSystemConfig = {\r\n mode: \"emitter\",\r\n count: 300,\r\n size: 2,\r\n color: \"#ffffff\",\r\n opacity: 1,\r\n spread: 120,\r\n spreadX: 120,\r\n spreadY: 120,\r\n seed: 1,\r\n emitRate: 30,\r\n emitBurst: 0,\r\n particleLife: 2.5,\r\n particleSpeed: 40,\r\n particleDirection: [0, 1, 0],\r\n particleGravity: [0, -30, 0],\r\n particleDrag: 0.1,\r\n particleSizeVariation: 0.6,\r\n particleColorVariation: 0.2,\r\n particleShape: \"sphere\",\r\n particleModelUrl: \"\",\r\n particleModelLoader: \"\",\r\n particleModelNode: \"\",\r\n instanceShape: \"sphere\",\r\n instanceModelUrl: \"\",\r\n instanceModelLoader: \"\",\r\n instanceModelNode: \"\",\r\n instanceScale: 1,\r\n instanceScaleVariation: 0.5,\r\n instanceRotationSpeed: 0.4,\r\n instanceJitter: 0.2,\r\n instanceFlow: 0.3,\r\n instanceDisperse: 0,\r\n instanceDisperseScatter: 0,\r\n instanceDisperseScatterX: 0,\r\n instanceDisperseScatterY: 0,\r\n instanceDisperseScatterZ: 0,\r\n modelTransitionDuration: 0,\r\n};\r\n\r\nexport class ParticlesSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<ParticleStyleBundle>();\r\n private static lastConfig: WeakMap<String3DObject, ParticleSystemConfig> = new WeakMap();\r\n private static lastTime: WeakMap<String3DObject, number> = new WeakMap();\r\n private static lastMaterialType: WeakMap<String3DObject, string> = new WeakMap();\r\n private static materialInstances: WeakMap<String3DObject, IMaterialInstance> = new WeakMap();\r\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n const cached = (el as any).__layoutCache;\r\n const rect = cached ? cached.rect : el.getBoundingClientRect();\r\n const bundle = this.readStyleBundle(el, ctx);\r\n\r\n const screenCenterX = rect.left + rect.width * 0.5;\r\n const screenCenterY = rect.top + rect.height * 0.5;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n object.object.position.set(\r\n screenCenterX - ctx.viewportWidth / 2,\r\n -(screenCenterY - ctx.viewportHeight / 2),\r\n bundle.translateZ\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\r\n const normalizedX = screenCenterX / ctx.viewportWidth;\r\n const normalizedY = screenCenterY / ctx.viewportHeight;\r\n object.object.position.set(\r\n (normalizedX - 0.5) * frustum.width,\r\n -(normalizedY - 0.5) * frustum.height,\r\n bundle.translateZ\r\n );\r\n }\r\n\r\n const parentScale = parentData?.scale ?? 1;\r\n const scale = bundle.scale * parentScale;\r\n object.object.scale.set(scale, scale, scale);\r\n\r\n object.object.rotation.x = -bundle.rotateX * DEG_TO_RAD;\r\n object.object.rotation.y = bundle.rotateY * DEG_TO_RAD;\r\n object.object.rotation.z = -bundle.rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n const config = this.buildConfig(bundle, rect, ctx, parentData);\r\n const prev = ParticlesSynchronizer.lastConfig.get(object);\r\n if (!prev || !this.isSameConfig(prev, config)) {\r\n ParticlesSynchronizer.lastConfig.set(object, config);\r\n (object.object as any).setConfig?.(config);\r\n }\r\n\r\n this.updateMaterialOverrides(el, object, ctx, bundle);\r\n this.updateCustomUniforms(el, object, ctx);\r\n\r\n const now = performance.now();\r\n const last = ParticlesSynchronizer.lastTime.get(object) ?? now;\r\n const dt = Math.max(0, (now - last) / 1000);\r\n ParticlesSynchronizer.lastTime.set(object, now);\r\n (object.object as any).update?.(dt);\r\n\r\n return { scale: parentData?.scale ?? 1 };\r\n }\r\n\r\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): ParticleStyleBundle {\r\n return ParticlesSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styles = new StyleReader(el);\r\n const modeRaw = styles.readString(\"--particles-mode\", DEFAULT_CONFIG.mode).toLowerCase();\r\n const mode = modeRaw === \"instanced\" ? \"instanced\" : \"emitter\";\r\n return {\r\n ...DEFAULT_CONFIG,\r\n translateZ: styles.readNumber(\"--translate-z\", 0),\r\n scale: styles.readNumber(\"--scale\", 1),\r\n rotateX: styles.readNumber(\"--rotate-x\", 0),\r\n rotateY: styles.readNumber(\"--rotate-y\", 0),\r\n rotateZ: styles.readNumber(\"--rotate-z\", 0),\r\n particlesFit: styles.readNumber(\"--particles-fit\", 0) > 0.5,\r\n materialType: styles.readString(\"--material-type\", \"basic\"),\r\n mode,\r\n count: styles.readNumber(\"--particles-count\", DEFAULT_CONFIG.count),\r\n size: styles.readNumber(\"--particles-size\", DEFAULT_CONFIG.size),\r\n color: styles.readString(\"--particles-color\", DEFAULT_CONFIG.color),\r\n opacity: styles.readNumber(\"--particles-opacity\", DEFAULT_CONFIG.opacity),\r\n spread: styles.readNumber(\"--particles-spread\", DEFAULT_CONFIG.spread),\r\n seed: styles.readNumber(\"--particles-seed\", DEFAULT_CONFIG.seed),\r\n emitRate: styles.readNumber(\"--emit-rate\", DEFAULT_CONFIG.emitRate),\r\n emitBurst: styles.readNumber(\"--emit-burst\", DEFAULT_CONFIG.emitBurst),\r\n particleLife: styles.readNumber(\"--particle-life\", DEFAULT_CONFIG.particleLife),\r\n particleSpeed: styles.readNumber(\"--particle-speed\", DEFAULT_CONFIG.particleSpeed),\r\n particleDirection: this.parseVec3(\r\n styles.readString(\"--particle-direction\", \"0 1 0\"),\r\n DEFAULT_CONFIG.particleDirection\r\n ),\r\n particleGravity: this.parseVec3(\r\n styles.readString(\"--particle-gravity\", \"0 -30 0\"),\r\n DEFAULT_CONFIG.particleGravity\r\n ),\r\n particleDrag: styles.readNumber(\"--particle-drag\", DEFAULT_CONFIG.particleDrag),\r\n particleSizeVariation: styles.readNumber(\r\n \"--particle-size-variation\",\r\n DEFAULT_CONFIG.particleSizeVariation\r\n ),\r\n particleColorVariation: styles.readNumber(\r\n \"--particle-color-variation\",\r\n DEFAULT_CONFIG.particleColorVariation\r\n ),\r\n particleShape: this.parseShape(\r\n styles.readString(\"--particles-shape\", DEFAULT_CONFIG.particleShape)\r\n ),\r\n particleModelUrl: styles.readString(\"--particles-model\", DEFAULT_CONFIG.particleModelUrl),\r\n particleModelLoader: styles.readString(\r\n \"--particles-model-loader\",\r\n DEFAULT_CONFIG.particleModelLoader\r\n ),\r\n particleModelNode: styles.readString(\r\n \"--particles-model-node\",\r\n DEFAULT_CONFIG.particleModelNode\r\n ),\r\n instanceShape: this.parseDistribution(\r\n styles.readString(\"--instance-shape\", DEFAULT_CONFIG.instanceShape)\r\n ),\r\n instanceModelUrl: styles.readString(\"--instance-model\", DEFAULT_CONFIG.instanceModelUrl),\r\n instanceModelLoader: styles.readString(\r\n \"--instance-model-loader\",\r\n DEFAULT_CONFIG.instanceModelLoader\r\n ),\r\n instanceModelNode: styles.readString(\r\n \"--instance-model-node\",\r\n DEFAULT_CONFIG.instanceModelNode\r\n ),\r\n instanceScale: styles.readNumber(\"--instance-scale\", DEFAULT_CONFIG.instanceScale),\r\n instanceScaleVariation: styles.readNumber(\r\n \"--instance-scale-variation\",\r\n DEFAULT_CONFIG.instanceScaleVariation\r\n ),\r\n instanceRotationSpeed: styles.readNumber(\r\n \"--instance-rotation-speed\",\r\n DEFAULT_CONFIG.instanceRotationSpeed\r\n ),\r\n instanceJitter: styles.readNumber(\"--instance-jitter\", DEFAULT_CONFIG.instanceJitter),\r\n instanceFlow: styles.readNumber(\"--instance-flow\", DEFAULT_CONFIG.instanceFlow),\r\n instanceDisperse: styles.readNumber(\"--instance-disperse\", DEFAULT_CONFIG.instanceDisperse),\r\n instanceDisperseScatter: styles.readNumber(\r\n \"--instance-scatter\",\r\n DEFAULT_CONFIG.instanceDisperseScatter\r\n ),\r\n instanceDisperseScatterX: styles.readNumber(\r\n \"--instance-scatter-x\",\r\n DEFAULT_CONFIG.instanceDisperseScatterX\r\n ),\r\n instanceDisperseScatterY: styles.readNumber(\r\n \"--instance-scatter-y\",\r\n DEFAULT_CONFIG.instanceDisperseScatterY\r\n ),\r\n instanceDisperseScatterZ: styles.readNumber(\r\n \"--instance-scatter-z\",\r\n DEFAULT_CONFIG.instanceDisperseScatterZ\r\n ),\r\n modelTransitionDuration: this.getTransitionDuration(el, \"--instance-model\"),\r\n };\r\n });\r\n }\r\n\r\n private getTransitionDuration(el: HTMLElement, property: string): number {\r\n const style = getComputedStyle(el);\r\n const properties = this.splitTransitionList(style.transitionProperty);\r\n const durations = this.splitTransitionList(style.transitionDuration);\r\n\r\n const index = this.findTransitionIndex(properties, property);\r\n if (index === -1) {\r\n const shorthand = this.parseTransitionShorthand(style.transition);\r\n const match = shorthand.get(property) || shorthand.get(\"all\");\r\n return match ? match.duration : 0;\r\n }\r\n\r\n return this.parseTime(durations[index] || durations[durations.length - 1] || \"0s\");\r\n }\r\n\r\n private splitTransitionList(value: string): string[] {\r\n const result: string[] = [];\r\n let current = \"\";\r\n let depth = 0;\r\n for (let i = 0; i < value.length; i += 1) {\r\n const ch = value[i];\r\n if (ch === \"(\") depth += 1;\r\n if (ch === \")\") depth = Math.max(0, depth - 1);\r\n if (ch === \",\" && depth === 0) {\r\n result.push(current.trim());\r\n current = \"\";\r\n } else {\r\n current += ch;\r\n }\r\n }\r\n if (current.trim()) result.push(current.trim());\r\n return result.length > 0 ? result : [\"all\"];\r\n }\r\n\r\n private findTransitionIndex(properties: string[], name: string): number {\r\n const normalized = properties.map((prop) => prop.trim().toLowerCase());\r\n let index = normalized.indexOf(name);\r\n if (index === -1) {\r\n index = normalized.indexOf(\"all\");\r\n }\r\n return index;\r\n }\r\n\r\n private parseTime(value: string): number {\r\n const raw = value.trim().toLowerCase();\r\n if (raw.endsWith(\"ms\")) {\r\n const num = Number.parseFloat(raw.slice(0, -2));\r\n return Number.isFinite(num) ? num / 1000 : 0;\r\n }\r\n if (raw.endsWith(\"s\")) {\r\n const num = Number.parseFloat(raw.slice(0, -1));\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n const num = Number.parseFloat(raw);\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n\r\n private parseTransitionShorthand(value: string): Map<string, { duration: number }> {\r\n const map = new Map<string, { duration: number }>();\r\n const parts = this.splitTransitionList(value);\r\n parts.forEach((part) => {\r\n if (!part) return;\r\n const tokens = part.trim().split(/\\s+(?![^()]*\\))/g);\r\n let prop = \"\";\r\n let duration = \"\";\r\n tokens.forEach((token) => {\r\n const lower = token.toLowerCase();\r\n if (lower.endsWith(\"ms\") || lower.endsWith(\"s\") || /^[0-9.]+$/.test(lower)) {\r\n if (!duration) duration = lower;\r\n } else if (\r\n lower.startsWith(\"cubic-bezier\") ||\r\n lower.startsWith(\"steps\") ||\r\n lower === \"linear\" ||\r\n lower === \"ease\" ||\r\n lower === \"ease-in\" ||\r\n lower === \"ease-out\" ||\r\n lower === \"ease-in-out\"\r\n ) {\r\n } else if (!prop) {\r\n prop = token;\r\n }\r\n });\r\n if (!prop) return;\r\n map.set(prop.trim().toLowerCase(), {\r\n duration: this.parseTime(duration || \"0s\"),\r\n });\r\n });\r\n return map;\r\n }\r\n\r\n private parseVec3(value: string, fallback: [number, number, number]): [number, number, number] {\r\n const parts = value\r\n .split(/[\\s,]+/)\r\n .map((part) => Number.parseFloat(part))\r\n .filter((num) => !Number.isNaN(num));\r\n if (parts.length >= 3) {\r\n return [parts[0], parts[1], parts[2]];\r\n }\r\n return fallback;\r\n }\r\n\r\n private parseShape(value: string): \"box\" | \"sphere\" | \"model\" {\r\n const normalized = value.trim().toLowerCase();\r\n if (normalized === \"box\") return \"box\";\r\n if (normalized === \"model\") return \"model\";\r\n return \"sphere\";\r\n }\r\n\r\n private parseDistribution(value: string): \"box\" | \"sphere\" | \"model\" {\r\n return this.parseShape(value);\r\n }\r\n\r\n private buildConfig(\r\n bundle: ParticleStyleBundle,\r\n rect: DOMRect,\r\n ctx: SyncContext,\r\n parentData: any\r\n ): ParticleSystemConfig {\r\n const parentScale = parentData?.scale ?? 1;\r\n const scale = parentScale;\r\n const fitMultiplier = 0.5;\r\n let spread: number;\r\n let spreadX: number;\r\n let spreadY: number;\r\n if (bundle.particlesFit) {\r\n spreadX = this.toWorld(rect.width * fitMultiplier, bundle.translateZ, ctx);\r\n spreadY = this.toWorld(rect.height * fitMultiplier, bundle.translateZ, ctx);\r\n spread = Math.max(spreadX, spreadY);\r\n } else {\r\n spread = this.toWorld(bundle.spread, bundle.translateZ, ctx);\r\n spreadX = spread;\r\n spreadY = spread;\r\n }\r\n return {\r\n ...bundle,\r\n count: Math.max(0, Math.floor(bundle.count)),\r\n size: Math.max(0.1, bundle.size),\r\n opacity: Math.max(0, Math.min(1, bundle.opacity)),\r\n spread: Math.max(0, spread * scale),\r\n spreadX: Math.max(0, spreadX * scale),\r\n spreadY: Math.max(0, spreadY * scale),\r\n seed: Math.max(0, Math.floor(bundle.seed)),\r\n emitRate: Math.max(0, bundle.emitRate),\r\n emitBurst: Math.max(0, bundle.emitBurst),\r\n particleLife: Math.max(0.1, bundle.particleLife),\r\n particleSpeed: Math.max(0, bundle.particleSpeed),\r\n particleDrag: Math.max(0, Math.min(1, bundle.particleDrag)),\r\n particleSizeVariation: Math.max(0, bundle.particleSizeVariation),\r\n particleColorVariation: Math.max(0, bundle.particleColorVariation),\r\n instanceScale: Math.max(0.1, bundle.instanceScale),\r\n instanceScaleVariation: Math.max(0, bundle.instanceScaleVariation),\r\n instanceRotationSpeed: Math.max(0, bundle.instanceRotationSpeed),\r\n instanceJitter: Math.max(0, bundle.instanceJitter),\r\n instanceFlow: Math.max(0, bundle.instanceFlow),\r\n instanceDisperse: Math.max(0, bundle.instanceDisperse),\r\n instanceDisperseScatter: Math.max(0, bundle.instanceDisperseScatter),\r\n instanceDisperseScatterX: Math.max(0, bundle.instanceDisperseScatterX),\r\n instanceDisperseScatterY: Math.max(0, bundle.instanceDisperseScatterY),\r\n instanceDisperseScatterZ: Math.max(0, bundle.instanceDisperseScatterZ),\r\n };\r\n }\r\n\r\n private toWorld(value: number, z: number, ctx: SyncContext): number {\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n return value;\r\n }\r\n const frustum = ctx.camera.getFrustumSizeAt(z);\r\n const perPixel = frustum.width / Math.max(1, ctx.viewportWidth);\r\n return value * perPixel;\r\n }\r\n\r\n private isSameConfig(a: ParticleSystemConfig, b: ParticleSystemConfig): boolean {\r\n return JSON.stringify(a) === JSON.stringify(b);\r\n }\r\n\r\n private updateMaterialOverrides(\r\n el: HTMLElement,\r\n object: String3DObject,\r\n ctx: SyncContext,\r\n bundle: ParticleStyleBundle\r\n ): void {\r\n const typeRaw = bundle.materialType || \"basic\";\r\n const type = typeRaw.split(\"[\")[0].trim().toLowerCase();\r\n const definition = String3DCustomMaterialRegistry.get(type);\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n\r\n if (!definition || !factory || !factory.supports(definition)) {\r\n const hasExisting =\r\n ParticlesSynchronizer.materialInstances.has(object) ||\r\n ParticlesSynchronizer.lastMaterialType.has(object);\r\n if (!hasExisting) return;\r\n\r\n const existing = ParticlesSynchronizer.materialInstances.get(object);\r\n if (existing) {\r\n existing.dispose();\r\n ParticlesSynchronizer.materialInstances.delete(object);\r\n }\r\n ParticlesSynchronizer.lastMaterialType.delete(object);\r\n (object.object as any).setMaterial?.(null, { points: true, meshes: true });\r\n return;\r\n }\r\n\r\n const lastType = ParticlesSynchronizer.lastMaterialType.get(object);\r\n if (lastType !== type) {\r\n const existing = ParticlesSynchronizer.materialInstances.get(object);\r\n if (existing) existing.dispose();\r\n\r\n const style = getComputedStyle(el);\r\n const initialUniforms = factory.parseUniformsFromCSS(definition, el, style);\r\n const instance = factory.create(definition, initialUniforms);\r\n ParticlesSynchronizer.materialInstances.set(object, instance);\r\n ParticlesSynchronizer.lastMaterialType.set(object, type);\r\n\r\n const material = instance.material;\r\n const isShader = !!material?.isShaderMaterial;\r\n const system: any = object.object as any;\r\n system.setMaterial?.(material, { meshes: true, points: false });\r\n system.setMaterial?.(isShader ? material : null, { meshes: false, points: true });\r\n }\r\n }\r\n\r\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n if (!factory) return;\r\n\r\n const style = getComputedStyle(el);\r\n\r\n const apply = (mat: any) => {\r\n const definition = mat?.userData?.definition;\r\n if (!definition?.uniforms) return;\r\n\r\n const values = factory.parseUniformsFromCSS(definition, el, style);\r\n\r\n for (const [key, value] of Object.entries(values)) {\r\n const def = definition.uniforms?.[key];\r\n if (!def) continue;\r\n\r\n const converter = (factory as any).convertUniformValue?.bind(factory);\r\n const converted = converter ? converter(def.type, value) : value;\r\n\r\n if (mat.userData?.shader?.uniforms?.[key]) {\r\n mat.userData.shader.uniforms[key].value = converted;\r\n } else if (mat.userData?.customUniforms?.[key]) {\r\n mat.userData.customUniforms[key].value = converted;\r\n } else if (mat.uniforms?.[key]) {\r\n mat.uniforms[key].value = converted;\r\n }\r\n }\r\n };\r\n\r\n if (object.object.traverse) {\r\n object.object.traverse((child: any) => {\r\n if (child.isMesh || child.isPoints) {\r\n const materials = Array.isArray(child.material) ? child.material : [child.material];\r\n materials.forEach(apply);\r\n }\r\n });\r\n }\r\n }\r\n}\r\n","export type String3DFontEntry = {\r\n name: string;\r\n url: string;\r\n};\r\n\r\nexport class String3DFontRegistry {\r\n private static fonts: Map<string, String3DFontEntry> = new Map();\r\n private static defaultFont: string | null = null;\r\n\r\n private static normalizeKey(name: string): string {\r\n return name.trim().toLowerCase();\r\n }\r\n\r\n static register(name: string, url: string): void {\r\n const normalized = name.trim();\r\n if (!normalized) return;\r\n this.fonts.set(this.normalizeKey(normalized), { name: normalized, url });\r\n }\r\n\r\n static setDefault(name: string): void {\r\n const normalized = name.trim();\r\n if (!normalized) return;\r\n this.defaultFont = this.normalizeKey(normalized);\r\n }\r\n\r\n static get(name: string): String3DFontEntry | undefined {\r\n return this.fonts.get(this.normalizeKey(name));\r\n }\r\n\r\n static list(): String3DFontEntry[] {\r\n return Array.from(this.fonts.values());\r\n }\r\n\r\n static resolveFontFamily(fontFamily: string): String3DFontEntry | null {\r\n if (!fontFamily) {\r\n return this.getDefault();\r\n }\r\n\r\n const families = fontFamily\r\n .split(\",\")\r\n .map((value) => value.trim().replace(/^[\"']|[\"']$/g, \"\"))\r\n .filter(Boolean);\r\n\r\n for (const family of families) {\r\n const entry = this.fonts.get(this.normalizeKey(family));\r\n if (entry) return entry;\r\n }\r\n\r\n return this.getDefault();\r\n }\r\n\r\n private static getDefault(): String3DFontEntry | null {\r\n if (!this.defaultFont) return null;\r\n return this.fonts.get(this.defaultFont) || null;\r\n }\r\n}\r\n","export interface FontData {\r\n glyphs: Record<string, GlyphData>;\r\n familyName: string;\r\n ascender: number;\r\n descender: number;\r\n underlinePosition: number;\r\n underlineThickness: number;\r\n boundingBox: { xMin: number; xMax: number; yMin: number; yMax: number };\r\n resolution: number;\r\n outlineFormat: string;\r\n original_font_information: Record<string, any>;\r\n}\r\n\r\nexport interface GlyphData {\r\n ha: number;\r\n x_min: number;\r\n x_max: number;\r\n o: string;\r\n}\r\n\r\nexport type FontSource = string | ArrayBuffer | Uint8Array;\r\n\r\nlet opentypePromise: Promise<any> | null = null;\r\nlet opentypeModule: any = null;\r\n\r\nlet woff2Promise: Promise<any> | null = null;\r\nlet woff2Module: any = null;\r\n\r\nasync function loadOpentype(): Promise<any> {\r\n if (opentypeModule) {\r\n return opentypeModule;\r\n }\r\n\r\n if (!opentypePromise) {\r\n opentypePromise = (async () => {\r\n if (typeof window !== \"undefined\" && (window as any).opentype) {\r\n opentypeModule = (window as any).opentype;\r\n return opentypeModule;\r\n }\r\n\r\n return new Promise((resolve, reject) => {\r\n if (typeof document === \"undefined\") {\r\n reject(new Error(\"[FontConverter] Cannot load opentype.js in non-browser environment\"));\r\n return;\r\n }\r\n const script = document.createElement(\"script\");\r\n script.src = \"https://cdn.jsdelivr.net/npm/opentype.js@1.3.4/dist/opentype.min.js\";\r\n script.onload = () => {\r\n opentypeModule = (window as any).opentype;\r\n resolve(opentypeModule);\r\n };\r\n script.onerror = () => reject(new Error(\"[FontConverter] Failed to load opentype.js\"));\r\n document.head.appendChild(script);\r\n });\r\n })();\r\n }\r\n return opentypePromise;\r\n}\r\n\r\nasync function loadWoff2Decoder(): Promise<any> {\r\n if (woff2Module) {\r\n return woff2Module;\r\n }\r\n\r\n if (!woff2Promise) {\r\n woff2Promise = (async () => {\r\n if (typeof window !== \"undefined\" && (window as any).Module?.decompress) {\r\n woff2Module = (window as any).Module;\r\n return woff2Module;\r\n }\r\n\r\n return new Promise((resolve, reject) => {\r\n if (typeof document === \"undefined\") {\r\n reject(new Error(\"[FontConverter] Cannot load woff2 decoder in non-browser environment\"));\r\n return;\r\n }\r\n const script = document.createElement(\"script\");\r\n script.src = \"https://cdn.jsdelivr.net/npm/wawoff2@2.0.1/build/decompress_binding.js\";\r\n script.onload = () => {\r\n let attempts = 0;\r\n const maxAttempts = 500;\r\n const checkReady = () => {\r\n attempts++;\r\n const win = window as any;\r\n if (win.Module?.decompress) {\r\n woff2Module = win.Module;\r\n resolve(woff2Module);\r\n } else if (attempts >= maxAttempts) {\r\n reject(new Error(\"[FontConverter] woff2 decoder initialization timeout\"));\r\n } else {\r\n setTimeout(checkReady, 10);\r\n }\r\n };\r\n checkReady();\r\n };\r\n script.onerror = () => {\r\n reject(new Error(\"[FontConverter] Failed to load woff2 decoder\"));\r\n };\r\n document.head.appendChild(script);\r\n });\r\n })();\r\n }\r\n return woff2Promise;\r\n}\r\n\r\nasync function decompressWoff2(buffer: ArrayBuffer): Promise<ArrayBuffer> {\r\n const woff2 = await loadWoff2Decoder();\r\n const inputArray = new Uint8Array(buffer);\r\n const outputArray = woff2.decompress(inputArray);\r\n\r\n if (outputArray instanceof Uint8Array) {\r\n const newBuffer = new ArrayBuffer(outputArray.length);\r\n const newArray = new Uint8Array(newBuffer);\r\n newArray.set(outputArray);\r\n return newBuffer;\r\n }\r\n\r\n return outputArray.buffer;\r\n}\r\n\r\nfunction isWoff2(buffer: ArrayBuffer): boolean {\r\n const view = new DataView(buffer);\r\n return view.getUint32(0, false) === 0x774f4632;\r\n}\r\n\r\nfunction isWoff(buffer: ArrayBuffer): boolean {\r\n const view = new DataView(buffer);\r\n return view.getUint32(0, false) === 0x774f4646;\r\n}\r\n\r\nexport class FontConverter {\r\n private static cache: Map<string, FontData> = new Map();\r\n private static loadingPromises: Map<string, Promise<FontData>> = new Map();\r\n\r\n static async load(source: FontSource): Promise<FontData> {\r\n const cacheKey = typeof source === \"string\" ? source : \"buffer-\" + Date.now();\r\n\r\n const cached = this.cache.get(cacheKey);\r\n if (cached) return cached;\r\n\r\n const loading = this.loadingPromises.get(cacheKey);\r\n if (loading) return loading;\r\n\r\n const promise = this.doLoad(source, cacheKey);\r\n this.loadingPromises.set(cacheKey, promise);\r\n\r\n try {\r\n const result = await promise;\r\n this.cache.set(cacheKey, result);\r\n return result;\r\n } finally {\r\n this.loadingPromises.delete(cacheKey);\r\n }\r\n }\r\n\r\n private static async doLoad(source: FontSource, cacheKey: string): Promise<FontData> {\r\n const opentype = await loadOpentype();\r\n\r\n let buffer: ArrayBuffer;\r\n\r\n if (typeof source === \"string\") {\r\n const response = await fetch(source);\r\n buffer = await response.arrayBuffer();\r\n } else if (source instanceof ArrayBuffer) {\r\n buffer = source;\r\n } else if (source instanceof Uint8Array) {\r\n buffer = source.buffer as ArrayBuffer;\r\n } else {\r\n throw new Error(\"[FontConverter] Invalid font source\");\r\n }\r\n\r\n if (isWoff2(buffer)) {\r\n buffer = await decompressWoff2(buffer);\r\n }\r\n\r\n const font = opentype.parse(buffer);\r\n\r\n if (!font) {\r\n throw new Error(\"[FontConverter] Failed to parse font\");\r\n }\r\n\r\n return this.convertToTypeFace(font);\r\n }\r\n\r\n private static convertToTypeFace(font: any): FontData {\r\n const scale = 1000 / font.unitsPerEm;\r\n\r\n const glyphs: Record<string, GlyphData> = {};\r\n\r\n const cmap = font.tables?.cmap?.glyphIndexMap;\r\n if (cmap && typeof cmap === \"object\") {\r\n for (const [codeStr, glyphIndex] of Object.entries(cmap)) {\r\n const code = Number(codeStr);\r\n if (!Number.isFinite(code)) continue;\r\n const glyph = font.glyphs.get(glyphIndex as number);\r\n if (!glyph) continue;\r\n\r\n const path = glyph.getPath(0, 0, font.unitsPerEm);\r\n const outline = this.pathToOutline(path, scale);\r\n const advanceWidth = glyph.advanceWidth ?? glyph.xMax ?? font.unitsPerEm * 0.5;\r\n const char = String.fromCharCode(code);\r\n if (glyphs[char]) continue;\r\n glyphs[char] = {\r\n ha: Math.round(advanceWidth * scale),\r\n x_min: glyph.xMin !== undefined ? Math.round(glyph.xMin * scale) : 0,\r\n x_max: glyph.xMax !== undefined ? Math.round(glyph.xMax * scale) : 0,\r\n o: outline,\r\n };\r\n }\r\n } else {\r\n for (let i = 0; i < font.glyphs.length; i++) {\r\n const glyph = font.glyphs.get(i);\r\n const unicodeValues = Array.isArray(glyph.unicodes)\r\n ? glyph.unicodes\r\n : glyph.unicode\r\n ? [glyph.unicode]\r\n : [];\r\n if (unicodeValues.length === 0) continue;\r\n\r\n const path = glyph.getPath(0, 0, font.unitsPerEm);\r\n const outline = this.pathToOutline(path, scale);\r\n const advanceWidth = glyph.advanceWidth ?? glyph.xMax ?? font.unitsPerEm * 0.5;\r\n\r\n unicodeValues.forEach((code: number) => {\r\n if (!Number.isFinite(code)) return;\r\n const char = String.fromCharCode(code);\r\n if (glyphs[char]) return;\r\n glyphs[char] = {\r\n ha: Math.round(advanceWidth * scale),\r\n x_min: glyph.xMin !== undefined ? Math.round(glyph.xMin * scale) : 0,\r\n x_max: glyph.xMax !== undefined ? Math.round(glyph.xMax * scale) : 0,\r\n o: outline,\r\n };\r\n });\r\n }\r\n }\r\n\r\n if (!glyphs[\" \"]) {\r\n const spaceGlyph = font.charToGlyph(\" \");\r\n glyphs[\" \"] = {\r\n ha: Math.round((spaceGlyph?.advanceWidth || font.unitsPerEm * 0.25) * scale),\r\n x_min: 0,\r\n x_max: 0,\r\n o: \"\",\r\n };\r\n }\r\n\r\n return {\r\n glyphs,\r\n familyName: font.names.fontFamily?.en || font.names.fullName?.en || \"Unknown\",\r\n ascender: Math.round(font.ascender * scale),\r\n descender: Math.round(font.descender * scale),\r\n underlinePosition: Math.round((font.tables.post?.underlinePosition || -100) * scale),\r\n underlineThickness: Math.round((font.tables.post?.underlineThickness || 50) * scale),\r\n boundingBox: {\r\n xMin: Math.round((font.tables.head?.xMin || 0) * scale),\r\n xMax: Math.round((font.tables.head?.xMax || 1000) * scale),\r\n yMin: Math.round((font.tables.head?.yMin || -200) * scale),\r\n yMax: Math.round((font.tables.head?.yMax || 800) * scale),\r\n },\r\n resolution: 1000,\r\n outlineFormat: (font.outlinesFormat || font.outlineFormat || \"\").toString(),\r\n original_font_information: {\r\n format: 0,\r\n copyright: font.names.copyright?.en || \"\",\r\n fontFamily: font.names.fontFamily?.en || \"\",\r\n fontSubfamily: font.names.fontSubfamily?.en || \"\",\r\n uniqueID: font.names.uniqueID?.en || \"\",\r\n fullName: font.names.fullName?.en || \"\",\r\n version: font.names.version?.en || \"\",\r\n postScriptName: font.names.postScriptName?.en || \"\",\r\n },\r\n };\r\n }\r\n\r\n private static pathToOutline(path: any, scale: number): string {\r\n const commands: string[] = [];\r\n\r\n for (const cmd of path.commands) {\r\n switch (cmd.type) {\r\n case \"M\":\r\n commands.push(`m ${this.round(cmd.x * scale)} ${this.round(cmd.y * scale)}`);\r\n break;\r\n case \"L\":\r\n commands.push(`l ${this.round(cmd.x * scale)} ${this.round(cmd.y * scale)}`);\r\n break;\r\n case \"Q\":\r\n commands.push(\r\n `q ${this.round(cmd.x1 * scale)} ${this.round(cmd.y1 * scale)} ${this.round(\r\n cmd.x * scale\r\n )} ${this.round(cmd.y * scale)}`\r\n );\r\n break;\r\n case \"C\":\r\n commands.push(\r\n `b ${this.round(cmd.x1 * scale)} ${this.round(cmd.y1 * scale)} ${this.round(\r\n cmd.x2 * scale\r\n )} ${this.round(cmd.y2 * scale)} ${this.round(cmd.x * scale)} ${this.round(\r\n cmd.y * scale\r\n )}`\r\n );\r\n break;\r\n case \"Z\":\r\n commands.push(\"z\");\r\n break;\r\n }\r\n }\r\n\r\n return commands.join(\" \");\r\n }\r\n\r\n private static round(value: number): number {\r\n return Math.round(value * 10000) / 10000;\r\n }\r\n\r\n static isTypefaceJson(url: string): boolean {\r\n const lower = url.toLowerCase();\r\n return lower.endsWith(\".json\") || lower.includes(\"typeface\");\r\n }\r\n\r\n static isFontFile(url: string): boolean {\r\n const lower = url.toLowerCase();\r\n const fontExtensions = /\\.(ttf|otf|woff2?)(\\?|$)/i;\r\n if (fontExtensions.test(lower)) return true;\r\n if (lower.includes(\"fonts.gstatic.com\")) return true;\r\n if (lower.includes(\"/fonts/\") && !lower.endsWith(\".json\")) return true;\r\n return false;\r\n }\r\n\r\n static clearCache(): void {\r\n this.cache.clear();\r\n }\r\n}\r\n","import { String3DObject } from \"../String3DObject\";\r\nimport type { SyncContext } from \"./SyncContext\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\nimport { StyleBundleCache } from \"./StyleBundleCache\";\r\nimport { String3DFontRegistry } from \"../text\";\r\nimport { MeshSynchronizer } from \"./MeshSynchronizer\";\r\n\r\nconst DEG_TO_RAD = Math.PI / 180;\r\n\r\nconst DEBUG_TEXT_SYNC = false;\r\n\r\nconst PSEUDO_ELEMENT_CSS = `\r\n[data-string3d-text] {\r\n -webkit-text-fill-color: transparent;\r\n}\r\n\r\n[data-string3d-text]::before {\r\n content: attr(data-string3d-text);\r\n position: absolute;\r\n left: 0;\r\n top: 0;\r\n width: 100%;\r\n height: 100%;\r\n pointer-events: none;\r\n \r\n color: inherit;\r\n -webkit-text-fill-color: initial;\r\n font: inherit;\r\n text-transform: inherit;\r\n letter-spacing: inherit;\r\n line-height: inherit;\r\n text-align: inherit;\r\n white-space: inherit;\r\n word-spacing: inherit;\r\n \r\n transform: var(--string3d-transform, none);\r\n transform-style: preserve-3d;\r\n transform-origin: center center;\r\n}\r\n`;\r\n\r\nexport class TextSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<StyleBundle>();\r\n private static layoutCache = new StyleBundleCache<LayoutBundle>();\r\n private static geometryKeys: WeakMap<String3DObject, string> = new WeakMap();\r\n private static lastMaterialType: WeakMap<String3DObject, string> = new WeakMap();\r\n private static fontCache: Map<string, any> = new Map();\r\n private static fontPromises: Map<string, Promise<any>> = new Map();\r\n private static pendingFontObjects: Map<string, Set<String3DObject>> = new Map();\r\n private static contentObservers: WeakMap<HTMLElement, MutationObserver> = new WeakMap();\r\n private static warnedMissingFont = false;\r\n private static warnedMissingLoader = false;\r\n private static pseudoStyleInjected = false;\r\n\r\n private static markObjectPendingFont(fontUrl: string, object: String3DObject): void {\r\n let set = this.pendingFontObjects.get(fontUrl);\r\n if (!set) {\r\n set = new Set();\r\n this.pendingFontObjects.set(fontUrl, set);\r\n }\r\n set.add(object);\r\n }\r\n\r\n private static clearObjectPendingFont(fontUrl: string, object: String3DObject): void {\r\n const set = this.pendingFontObjects.get(fontUrl);\r\n if (set) {\r\n set.delete(object);\r\n }\r\n }\r\n\r\n private static invalidatePendingObjects(fontUrl: string): void {\r\n const set = this.pendingFontObjects.get(fontUrl);\r\n if (set) {\r\n set.forEach((obj) => {\r\n this.geometryKeys.delete(obj);\r\n });\r\n set.clear();\r\n }\r\n }\r\n\r\n private static injectPseudoElementStyles(): void {\r\n if (this.pseudoStyleInjected || typeof document === \"undefined\") return;\r\n\r\n const style = document.createElement(\"style\");\r\n style.setAttribute(\"data-string3d\", \"pseudo-text\");\r\n style.textContent = PSEUDO_ELEMENT_CSS;\r\n document.head.appendChild(style);\r\n this.pseudoStyleInjected = true;\r\n }\r\n\r\n private static setupSelectableText(el: HTMLElement): void {\r\n const textContent = el.textContent || \"\";\r\n\r\n if (el.dataset.string3dText !== textContent) {\r\n el.dataset.string3dText = textContent;\r\n }\r\n\r\n const computed = getComputedStyle(el);\r\n if (computed.position === \"static\") {\r\n el.style.position = \"relative\";\r\n }\r\n\r\n const rx = computed.getPropertyValue(\"--rotate-x\").trim() || \"0\";\r\n const ry = computed.getPropertyValue(\"--rotate-y\").trim() || \"0\";\r\n const rz = computed.getPropertyValue(\"--rotate-z\").trim() || \"0\";\r\n const tx = computed.getPropertyValue(\"--translate-x\").trim() || \"0px\";\r\n const ty = computed.getPropertyValue(\"--translate-y\").trim() || \"0px\";\r\n const tz = computed.getPropertyValue(\"--translate-z\").trim() || \"0px\";\r\n const s = computed.getPropertyValue(\"--scale\").trim() || \"1\";\r\n\r\n const transform = [\r\n tx !== \"0px\" && tx !== \"0\" ? `translateX(${tx})` : \"\",\r\n ty !== \"0px\" && ty !== \"0\" ? `translateY(${ty})` : \"\",\r\n tz !== \"0px\" && tz !== \"0\" ? `translateZ(${tz})` : \"\",\r\n rx !== \"0\" ? `rotateX(${rx}deg)` : \"\",\r\n ry !== \"0\" ? `rotateY(${ry}deg)` : \"\",\r\n rz !== \"0\" ? `rotateZ(${rz}deg)` : \"\",\r\n s !== \"1\" ? `scale(${s})` : \"\",\r\n ]\r\n .filter(Boolean)\r\n .join(\" \");\r\n\r\n el.style.setProperty(\"--string3d-transform\", transform || \"none\");\r\n }\r\n\r\n private static setupContentObserver(el: HTMLElement, object: String3DObject): void {\r\n if (this.contentObservers.has(el)) return;\r\n\r\n let lastContent = el.textContent || \"\";\r\n\r\n const observer = new MutationObserver((mutations) => {\r\n const currentContent = el.textContent || \"\";\r\n if (currentContent === lastContent) {\r\n return;\r\n }\r\n\r\n lastContent = currentContent;\r\n\r\n const string3d = (window as any).StringTune3D?.String3D?.getInstance?.();\r\n const currentObject = string3d?.scene?.getObjectForElement?.(el);\r\n\r\n if (currentObject) {\r\n this.geometryKeys.delete(currentObject);\r\n this.layoutCache.invalidate(el);\r\n\r\n if (el.dataset.string3dText !== currentContent) {\r\n el.dataset.string3dText = currentContent;\r\n }\r\n }\r\n });\r\n\r\n observer.observe(el, {\r\n characterData: true,\r\n childList: true,\r\n subtree: true,\r\n });\r\n\r\n this.contentObservers.set(el, observer);\r\n }\r\n\r\n private static cleanupContentObserver(el: HTMLElement): void {\r\n const observer = this.contentObservers.get(el);\r\n if (observer) {\r\n observer.disconnect();\r\n this.contentObservers.delete(el);\r\n }\r\n }\r\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n TextSynchronizer.injectPseudoElementStyles();\r\n TextSynchronizer.setupSelectableText(el);\r\n TextSynchronizer.setupContentObserver(el, object);\r\n\r\n const { rect, width: originalWidth, height: originalHeight } = this.readLayout(el, ctx);\r\n const bundle = this.readStyleBundle(el, ctx);\r\n\r\n const {\r\n translateZ,\r\n cssScale,\r\n rotateX,\r\n rotateY,\r\n rotateZ,\r\n cssScaleZ,\r\n opacity,\r\n color,\r\n metalness,\r\n roughness,\r\n emissive,\r\n castShadow,\r\n receiveShadow,\r\n materialType,\r\n fontFamily,\r\n fontSize,\r\n textTransform,\r\n textDepth,\r\n textCurveSegments,\r\n bevelEnabled,\r\n bevelSize,\r\n bevelThickness,\r\n bevelOffset,\r\n bevelSegments,\r\n fontCss,\r\n } = bundle;\r\n\r\n const screenCenterX = rect.left + rect.width * 0.5;\r\n const screenCenterY = rect.top + rect.height * 0.5;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n object.object.position.set(\r\n screenCenterX - ctx.viewportWidth / 2,\r\n -(screenCenterY - ctx.viewportHeight / 2),\r\n translateZ\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(translateZ);\r\n const normalizedX = screenCenterX / ctx.viewportWidth;\r\n const normalizedY = screenCenterY / ctx.viewportHeight;\r\n object.object.position.set(\r\n (normalizedX - 0.5) * frustum.width,\r\n -(normalizedY - 0.5) * frustum.height,\r\n translateZ\r\n );\r\n }\r\n\r\n object.object.rotation.x = -rotateX * DEG_TO_RAD;\r\n object.object.rotation.y = rotateY * DEG_TO_RAD;\r\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n const layout = this.extractCharacterLayout(el, textTransform);\r\n const textContent = layout.map((l) => l.char).join(\"\");\r\n const useCanvasText = Boolean(fontCss);\r\n\r\n const mesh = this.getTextMesh(object);\r\n if (!mesh) {\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (layout.length === 0) {\r\n mesh.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (opacity === 0) {\r\n object.object.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n object.object.visible = true;\r\n\r\n mesh.visible = true;\r\n\r\n const fontEntry = String3DFontRegistry.resolveFontFamily(fontFamily || \"\");\r\n if (!fontEntry) {\r\n if (!TextSynchronizer.warnedMissingFont) {\r\n TextSynchronizer.warnedMissingFont = true;\r\n }\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (!ctx.engine.loadFont || !ctx.engine.createTextGeometry) {\r\n if (!TextSynchronizer.warnedMissingLoader) {\r\n TextSynchronizer.warnedMissingLoader = true;\r\n }\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n const fontUrl = fontEntry.url;\r\n let font = TextSynchronizer.fontCache.get(fontUrl);\r\n if (!font) {\r\n TextSynchronizer.markObjectPendingFont(fontUrl, object);\r\n if (!TextSynchronizer.fontPromises.has(fontUrl)) {\r\n const promise = ctx.engine.loadFont(fontUrl).then((loaded) => {\r\n if (loaded) {\r\n TextSynchronizer.fontCache.set(fontUrl, loaded);\r\n TextSynchronizer.invalidatePendingObjects(fontUrl);\r\n }\r\n return loaded;\r\n });\r\n TextSynchronizer.fontPromises.set(fontUrl, promise);\r\n }\r\n mesh.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n TextSynchronizer.clearObjectPendingFont(fontUrl, object);\r\n\r\n const layoutSig =\r\n layout.length > 0\r\n ? `${layout.length}:${layout[0].x.toFixed(1)},${layout[0].y.toFixed(1)}:${layout[\r\n layout.length - 1\r\n ].x.toFixed(1)},${layout[layout.length - 1].y.toFixed(1)}`\r\n : \"empty\";\r\n\r\n const key = [\r\n textContent,\r\n fontSize.toFixed(3),\r\n fontCss || \"\",\r\n rect.width.toFixed(1),\r\n rect.height.toFixed(1),\r\n layoutSig,\r\n textDepth.toFixed(3),\r\n textCurveSegments.toFixed(3),\r\n bevelEnabled ? \"1\" : \"0\",\r\n bevelSize.toFixed(3),\r\n bevelThickness.toFixed(3),\r\n bevelOffset.toFixed(3),\r\n bevelSegments.toFixed(3),\r\n ].join(\"|\");\r\n\r\n const prevKey = TextSynchronizer.geometryKeys.get(object);\r\n if (prevKey !== key) {\r\n const geometry = ctx.engine.createTextGeometry(textContent, font, {\r\n size: fontSize,\r\n height: textDepth,\r\n curveSegments: Math.max(1, Math.round(textCurveSegments)),\r\n bevelEnabled,\r\n bevelThickness,\r\n bevelSize,\r\n bevelOffset,\r\n bevelSegments: Math.max(0, Math.round(bevelSegments)),\r\n lineHeight: 0,\r\n letterSpacing: 0,\r\n align: \"left\",\r\n layout,\r\n elementWidth: rect.width,\r\n elementHeight: rect.height,\r\n });\r\n\r\n if (geometry) {\r\n geometry.computeBoundingBox();\r\n if (mesh.geometry) {\r\n mesh.geometry.dispose?.();\r\n }\r\n mesh.geometry = geometry;\r\n object.geometry = geometry;\r\n TextSynchronizer.geometryKeys.set(object, key);\r\n }\r\n }\r\n\r\n const parentScale = parentData?.scale || 1;\r\n const perPixel =\r\n ctx.camera.getMode() === \"orthographic\"\r\n ? 1\r\n : ctx.camera.getScaleAtZ(translateZ, ctx.viewportHeight);\r\n\r\n const scaleFactor = cssScale * parentScale * perPixel;\r\n\r\n const scaleZ = scaleFactor * cssScaleZ;\r\n object.object.scale.set(scaleFactor, scaleFactor, scaleZ);\r\n\r\n const localOffsetX = -originalWidth * 0.5;\r\n const localOffsetY = originalHeight * 0.5;\r\n\r\n mesh.position.set(localOffsetX, localOffsetY, 0);\r\n\r\n const prevMaterialType = TextSynchronizer.lastMaterialType.get(object);\r\n if (prevMaterialType !== undefined && prevMaterialType !== materialType) {\r\n if (ctx.scene && (ctx.scene as any).recreateMaterialForObject) {\r\n requestAnimationFrame(() => {\r\n if (ctx.scene && (ctx.scene as any).recreateMaterialForObject) {\r\n (ctx.scene as any).recreateMaterialForObject(object, el);\r\n }\r\n });\r\n }\r\n }\r\n\r\n TextSynchronizer.lastMaterialType.set(object, materialType);\r\n\r\n MeshSynchronizer.applyVisualProps(el, object, {\r\n opacity,\r\n color: color && color !== \"none\" ? color : undefined,\r\n metalness: Number.isFinite(metalness) ? metalness : undefined,\r\n roughness: Number.isFinite(roughness) ? roughness : undefined,\r\n emissive: emissive && emissive !== \"none\" ? emissive : undefined,\r\n castShadow,\r\n receiveShadow,\r\n });\r\n\r\n this.updateCustomUniforms(el, object, ctx);\r\n\r\n return { scale: scaleFactor };\r\n }\r\n\r\n cleanup(el: HTMLElement, object: String3DObject): void {\r\n TextSynchronizer.cleanupContentObserver(el);\r\n TextSynchronizer.geometryKeys.delete(object);\r\n }\r\n\r\n private extractCharacterLayout(\r\n el: HTMLElement,\r\n transform: string\r\n ): Array<{\r\n char: string;\r\n x: number;\r\n y: number;\r\n width?: number;\r\n height?: number;\r\n scale?: number;\r\n }> {\r\n const layout: Array<{\r\n char: string;\r\n x: number;\r\n y: number;\r\n width?: number;\r\n height?: number;\r\n scale?: number;\r\n }> = [];\r\n if (typeof document === \"undefined\" || !document.createRange) return layout;\r\n\r\n const range = document.createRange();\r\n const elRect = el.getBoundingClientRect();\r\n const walker = document.createTreeWalker(el, NodeFilter.SHOW_TEXT);\r\n let node: Node | null;\r\n\r\n while ((node = walker.nextNode())) {\r\n const text = node.textContent || \"\";\r\n if (!text.trim() && text !== \" \") continue;\r\n\r\n for (let i = 0; i < text.length; i++) {\r\n const char = text[i];\r\n if (char === \"\\n\" || char === \"\\r\") continue;\r\n\r\n if (!char.trim()) continue;\r\n\r\n range.setStart(node, i);\r\n range.setEnd(node, i + 1);\r\n const rects = range.getClientRects();\r\n\r\n if (rects.length > 0) {\r\n const r = rects[0];\r\n const x = r.left - elRect.left;\r\n const y = r.top - elRect.top;\r\n\r\n const visibleChar = this.applyTextTransform(char, transform);\r\n\r\n layout.push({\r\n char: visibleChar,\r\n x,\r\n y,\r\n width: r.width,\r\n height: r.height,\r\n });\r\n }\r\n }\r\n }\r\n return layout;\r\n }\r\n\r\n private getTextMesh(object: String3DObject): any | null {\r\n const anyObj = object.object as any;\r\n if (anyObj?.__textMesh) return anyObj.__textMesh;\r\n if (anyObj?.isMesh) return anyObj;\r\n if (Array.isArray(anyObj?.children)) {\r\n const found = anyObj.children.find((child: any) => child?.isMesh);\r\n if (found) {\r\n anyObj.__textMesh = found;\r\n return found;\r\n }\r\n }\r\n return null;\r\n }\r\n\r\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n if (!factory) return;\r\n\r\n const style = getComputedStyle(el);\r\n\r\n const apply = (mat: any) => {\r\n const definition = mat?.userData?.definition;\r\n if (!definition?.uniforms) return;\r\n\r\n const values = factory.parseUniformsFromCSS(definition, el, style);\r\n for (const [key, value] of Object.entries(values)) {\r\n const def = definition.uniforms?.[key];\r\n if (!def) continue;\r\n const converter = (factory as any).convertUniformValue?.bind(factory);\r\n const converted = converter ? converter(def.type, value) : value;\r\n\r\n if (mat.userData?.shader?.uniforms?.[key]) {\r\n mat.userData.shader.uniforms[key].value = converted;\r\n } else if (mat.userData?.customUniforms?.[key]) {\r\n mat.userData.customUniforms[key].value = converted;\r\n } else if (mat.uniforms?.[key]) {\r\n mat.uniforms[key].value = converted;\r\n }\r\n }\r\n };\r\n\r\n if (object.object.traverse) {\r\n object.object.traverse((child: any) => {\r\n if (child.isMesh) {\r\n const materials = Array.isArray(child.material) ? child.material : [child.material];\r\n materials.forEach(apply);\r\n }\r\n });\r\n } else {\r\n const mesh = this.getTextMesh(object);\r\n if (!mesh) return;\r\n const materials = Array.isArray(mesh.material) ? mesh.material : [mesh.material];\r\n materials.forEach(apply);\r\n }\r\n }\r\n\r\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): StyleBundle {\r\n return TextSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const style = getComputedStyle(el);\r\n\r\n const readNumber = (prop: string, fallback: number): number => {\r\n const mapValue = styleMap?.get?.(prop);\r\n if (mapValue !== undefined && mapValue !== null) {\r\n const val =\r\n typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n const num = typeof val === \"number\" ? val : Number.parseFloat(String(val));\r\n if (!Number.isNaN(num)) return num;\r\n }\r\n const raw = style.getPropertyValue(prop);\r\n const num = Number.parseFloat(raw);\r\n return Number.isNaN(num) ? fallback : num;\r\n };\r\n\r\n const readString = (prop: string): string => {\r\n const mapValue = styleMap?.get?.(prop);\r\n const val =\r\n mapValue && typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n if (typeof val === \"string\") return val.trim();\r\n return style.getPropertyValue(prop).trim();\r\n };\r\n\r\n const readBool = (prop: string, fallback = false): boolean => {\r\n const raw = readString(prop);\r\n if (!raw) return fallback;\r\n const norm = raw.toLowerCase();\r\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\r\n ? true\r\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\r\n ? false\r\n : fallback;\r\n };\r\n\r\n const colorVar = readString(\"--material-color\");\r\n const color = colorVar && colorVar !== \"none\" ? colorVar : style.color.trim();\r\n\r\n const fontSize = (() => {\r\n const raw = style.fontSize || \"\";\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isFinite(parsed) ? parsed : 16;\r\n })();\r\n\r\n const lineHeight = (() => {\r\n const raw = style.lineHeight || \"\";\r\n if (!raw || raw === \"normal\") return fontSize * 1.2;\r\n const parsed = Number.parseFloat(raw);\r\n if (!Number.isFinite(parsed)) return fontSize * 1.2;\r\n return raw.endsWith(\"px\") ? parsed : parsed * fontSize;\r\n })();\r\n\r\n const letterSpacing = (() => {\r\n const raw = style.letterSpacing || \"\";\r\n if (!raw || raw === \"normal\") return 0;\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isFinite(parsed) ? parsed : 0;\r\n })();\r\n\r\n const fit = readString(\"--text-fit\") || \"none\";\r\n\r\n const depthRaw = readNumber(\"--text-depth\", NaN);\r\n const depth = Number.isFinite(depthRaw) ? depthRaw : Math.max(1, fontSize * 0.2);\r\n\r\n const bevelSize = readNumber(\"--text-bevel-size\", 0);\r\n const bevelThickness = readNumber(\"--text-bevel-thickness\", 0);\r\n const bevelOffset = readNumber(\"--text-bevel-offset\", 0);\r\n const bevelSegments = readNumber(\"--text-bevel-steps\", 0);\r\n\r\n const alignRaw = (style.textAlign || \"left\").toLowerCase();\r\n const align =\r\n alignRaw === \"center\"\r\n ? \"center\"\r\n : alignRaw === \"right\" || alignRaw === \"end\"\r\n ? \"right\"\r\n : \"left\";\r\n\r\n const fontCss = style.font?.trim();\r\n const computedFont =\r\n fontCss && fontCss.length > 0\r\n ? fontCss\r\n : [\r\n style.fontStyle || \"normal\",\r\n style.fontWeight || \"normal\",\r\n `${style.fontSize || \"16px\"}/${style.lineHeight || \"normal\"}`,\r\n style.fontFamily || \"sans-serif\",\r\n ].join(\" \");\r\n\r\n return {\r\n translateZ: readNumber(\"--translate-z\", 0),\r\n cssScale: readNumber(\"--scale\", 1),\r\n rotateX: readNumber(\"--rotate-x\", 0),\r\n rotateY: readNumber(\"--rotate-y\", 0),\r\n rotateZ: readNumber(\"--rotate-z\", 0),\r\n cssScaleZ: readNumber(\"--scale-z\", 1),\r\n opacity: readNumber(\"--opacity\", NaN),\r\n color,\r\n metalness: readNumber(\"--material-metalness\", NaN),\r\n roughness: readNumber(\"--material-roughness\", NaN),\r\n emissive: readString(\"--material-emissive\"),\r\n castShadow: readBool(\"--shadow-cast\", false),\r\n receiveShadow: readBool(\"--shadow-receive\", false),\r\n materialType: readString(\"--material-type\", \"basic\").split(\"[\")[0] || \"basic\",\r\n fontFamily: style.fontFamily || \"\",\r\n fontCss: computedFont,\r\n fontSize,\r\n lineHeight,\r\n letterSpacing,\r\n textAlign: align,\r\n textTransform: (style.textTransform || \"\").toLowerCase(),\r\n textDepth: depth,\r\n textCurveSegments: readNumber(\"--text-curve-segments\", 8),\r\n bevelEnabled: bevelSize > 0 || bevelThickness > 0,\r\n bevelSize,\r\n bevelThickness,\r\n bevelOffset,\r\n bevelSegments,\r\n textFit: fit === \"cover\" || fit === \"none\" ? fit : \"contain\",\r\n };\r\n });\r\n }\r\n\r\n private applyTextTransform(text: string, transform: string): string {\r\n if (!transform || transform === \"none\") return text;\r\n if (transform === \"uppercase\") return text.toUpperCase();\r\n if (transform === \"lowercase\") return text.toLowerCase();\r\n if (transform === \"capitalize\") {\r\n return text.replace(/\\b(\\p{L})/gu, (match) => match.toUpperCase());\r\n }\r\n return text;\r\n }\r\n\r\n private readLayout(el: HTMLElement, ctx: SyncContext): LayoutBundle {\r\n const cached = (el as any).__layoutCache;\r\n if (cached) {\r\n return cached;\r\n }\r\n\r\n return TextSynchronizer.layoutCache.get(el, ctx, (el) => {\r\n const rect = el.getBoundingClientRect();\r\n return { rect, width: rect.width, height: rect.height };\r\n });\r\n }\r\n}\r\n\r\ntype StyleBundle = {\r\n translateZ: number;\r\n cssScale: number;\r\n rotateX: number;\r\n rotateY: number;\r\n rotateZ: number;\r\n cssScaleZ: number;\r\n opacity: number;\r\n color: string;\r\n metalness: number;\r\n roughness: number;\r\n emissive: string;\r\n castShadow: boolean;\r\n receiveShadow: boolean;\r\n materialType: string;\r\n fontFamily: string;\r\n fontCss: string;\r\n fontSize: number;\r\n lineHeight: number;\r\n letterSpacing: number;\r\n textAlign: \"left\" | \"center\" | \"right\";\r\n textTransform: string;\r\n textDepth: number;\r\n textCurveSegments: number;\r\n bevelEnabled: boolean;\r\n bevelSize: number;\r\n bevelThickness: number;\r\n bevelOffset: number;\r\n bevelSegments: number;\r\n textFit: \"contain\" | \"cover\" | \"none\";\r\n};\r\n\r\ntype LayoutBundle = {\r\n rect: DOMRect;\r\n width: number;\r\n height: number;\r\n};\r\n","import { String3DCamera } from \"../String3DCamera\";\r\nimport { String3DObject } from \"../String3DObject\";\r\nimport { I3DEngine } from \"../abstractions/I3DEngine\";\r\nimport { GroupSynchronizer } from \"./GroupSynchronizer\";\r\nimport { LightSynchronizer } from \"./LightSynchronizer\";\r\nimport { MeshSynchronizer } from \"./MeshSynchronizer\";\r\nimport { ParticlesSynchronizer } from \"./ParticlesSynchronizer\";\r\nimport { TextSynchronizer } from \"./TextSynchronizer\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\n\r\nexport class String3DSynchronizer {\r\n private strategies: Map<string, String3DObjectSyncStrategy> = new Map();\r\n private styleReadIntervalMs = 0;\r\n private layoutReadIntervalMs = 0;\r\n\r\n constructor(\r\n public camera: String3DCamera,\r\n public viewportWidth: number,\r\n public viewportHeight: number,\r\n public engine: I3DEngine\r\n ) {\r\n this.strategies.set(\"box\", new MeshSynchronizer());\r\n this.strategies.set(\"sphere\", new MeshSynchronizer());\r\n this.strategies.set(\"plane\", new MeshSynchronizer());\r\n this.strategies.set(\"cylinder\", new MeshSynchronizer());\r\n this.strategies.set(\"model\", new MeshSynchronizer());\r\n this.strategies.set(\"group\", new GroupSynchronizer());\r\n this.strategies.set(\"pointLight\", new LightSynchronizer());\r\n this.strategies.set(\"ambientLight\", new LightSynchronizer());\r\n this.strategies.set(\"directionalLight\", new LightSynchronizer());\r\n this.strategies.set(\"spotLight\", new LightSynchronizer());\r\n this.strategies.set(\"hemisphereLight\", new LightSynchronizer());\r\n this.strategies.set(\"particles\", new ParticlesSynchronizer());\r\n this.strategies.set(\"text\", new TextSynchronizer());\r\n }\r\n\r\n public syncElement(\r\n el: HTMLElement,\r\n object: String3DObject,\r\n parentData: any,\r\n hints?: { dirtySet?: Set<HTMLElement> | null; forceSync?: boolean }\r\n ): any {\r\n const strategy = this.strategies.get(object.type);\r\n if (!strategy) {\r\n return null;\r\n }\r\n\r\n return strategy.sync(\r\n el,\r\n object,\r\n {\r\n camera: this.camera,\r\n viewportWidth: this.viewportWidth,\r\n viewportHeight: this.viewportHeight,\r\n engine: this.engine,\r\n dirtySet: hints?.dirtySet,\r\n forceSync: hints?.forceSync,\r\n styleReadIntervalMs: this.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.layoutReadIntervalMs,\r\n },\r\n parentData\r\n );\r\n }\r\n\r\n public setSyncOptions(options: {\r\n styleReadIntervalMs?: number;\r\n layoutReadIntervalMs?: number;\r\n }): void {\r\n this.styleReadIntervalMs = Math.max(0, options.styleReadIntervalMs ?? 0);\r\n this.layoutReadIntervalMs = Math.max(0, options.layoutReadIntervalMs ?? 0);\r\n }\r\n\r\n public updateViewportSize(width: number, height: number): void {\r\n this.viewportWidth = width;\r\n this.viewportHeight = height;\r\n }\r\n\r\n public cleanupElement(el: HTMLElement, object: String3DObject): void {\r\n const strategy = this.strategies.get(object.type);\r\n if (strategy?.cleanup) {\r\n strategy.cleanup(el, object);\r\n }\r\n }\r\n}\r\n","import { String3DObject } from \"../../core/String3DObject\";\n\nexport class DirtySyncManager {\n private readonly attributeFilter: string[];\n private readonly handleScrollBound = () => this.handleScroll();\n private dirtyElements: Set<HTMLElement> = new Set();\n private observedElements: Set<HTMLElement> = new Set();\n private resizeObserver: ResizeObserver | null = null;\n private mutationObserver: MutationObserver | null = null;\n private enabled = false;\n private domVersion = 0;\n\n constructor(attributeFilter: string[]) {\n this.attributeFilter = attributeFilter;\n }\n\n enable(): void {\n if (this.enabled) return;\n this.enabled = true;\n this.setupObservers();\n this.setupScrollListeners();\n }\n\n disable(): void {\n if (!this.enabled) return;\n this.enabled = false;\n this.removeScrollListeners();\n this.resizeObserver?.disconnect();\n this.mutationObserver?.disconnect();\n this.dirtyElements.clear();\n this.observedElements.clear();\n }\n\n observeElement(el: HTMLElement): void {\n if (!this.enabled || this.observedElements.has(el)) return;\n this.observedElements.add(el);\n this.resizeObserver?.observe(el);\n this.mutationObserver?.observe(el, {\n attributes: true,\n attributeFilter: this.attributeFilter,\n });\n }\n\n observeScene(rootObjects: String3DObject[]): void {\n if (!this.enabled) return;\n rootObjects.forEach((obj) => this.observeRecursive(obj));\n }\n\n markDirty(el: HTMLElement): void {\n if (!this.enabled) return;\n this.dirtyElements.add(el);\n this.bumpVersion();\n }\n\n markAllDirty(): void {\n if (!this.enabled) return;\n this.observedElements.forEach((el) => this.dirtyElements.add(el));\n this.bumpVersion();\n }\n\n getDirtySet(): Set<HTMLElement> | null {\n return this.enabled ? this.dirtyElements : null;\n }\n\n clearDirty(): void {\n this.dirtyElements.clear();\n }\n\n getVersion(): number {\n return this.domVersion;\n }\n\n isEnabled(): boolean {\n return this.enabled;\n }\n\n private observeRecursive(object: String3DObject): void {\n if (object.el instanceof HTMLElement) {\n this.observeElement(object.el);\n }\n object.children.forEach((child) => this.observeRecursive(child));\n }\n\n private handleScroll(): void {\n this.markAllDirty();\n }\n\n private setupObservers(): void {\n if (typeof ResizeObserver !== \"undefined\") {\n this.resizeObserver = new ResizeObserver((entries) => {\n entries.forEach((entry) => {\n if (entry.target instanceof HTMLElement) {\n this.markDirty(entry.target);\n }\n });\n });\n }\n\n if (typeof MutationObserver !== \"undefined\") {\n this.mutationObserver = new MutationObserver((mutations) => {\n mutations.forEach((mutation) => {\n if (mutation.target instanceof HTMLElement) {\n this.markDirty(mutation.target);\n }\n });\n });\n }\n }\n\n private setupScrollListeners(): void {\n window.addEventListener(\"scroll\", this.handleScrollBound, { passive: true });\n window.addEventListener(\"resize\", this.handleScrollBound, { passive: true });\n if (window.visualViewport) {\n window.visualViewport.addEventListener(\"scroll\", this.handleScrollBound, { passive: true });\n window.visualViewport.addEventListener(\"resize\", this.handleScrollBound, { passive: true });\n }\n }\n\n private removeScrollListeners(): void {\n window.removeEventListener(\"scroll\", this.handleScrollBound);\n window.removeEventListener(\"resize\", this.handleScrollBound);\n if (window.visualViewport) {\n window.visualViewport.removeEventListener(\"scroll\", this.handleScrollBound);\n window.visualViewport.removeEventListener(\"resize\", this.handleScrollBound);\n }\n }\n\n private bumpVersion(): void {\n this.domVersion += 1;\n }\n}\n","import { String3DObject } from \"../../core/String3DObject\";\r\nimport { String3DCustomFilterRegistry } from \"../../core/filters/String3DCustomFilter\";\r\nimport {\r\n String3DFilterChain,\r\n String3DFilterEffect,\r\n String3DFilterTarget,\r\n} from \"../../core/filters/String3DFilterTypes\";\r\nimport { readFilterRaw } from \"./styleUtils\";\r\n\r\ntype FilterTransitionState = {\r\n raw: string;\r\n effects: String3DFilterChain;\r\n animating: boolean;\r\n from: String3DFilterChain;\r\n to: String3DFilterChain;\r\n startTime: number;\r\n duration: number;\r\n easing: (t: number) => number;\r\n clearOnComplete: boolean;\r\n lastDuration: number;\r\n lastDelay: number;\r\n lastEasing: (t: number) => number;\r\n pendingRaw?: string;\r\n pendingEffects?: String3DFilterChain;\r\n effectsKey?: string;\r\n};\r\n\r\nexport class FilterController {\r\n private filterStates: WeakMap<HTMLElement, FilterTransitionState> = new WeakMap();\r\n private filterWarnings: WeakMap<HTMLElement, string> = new WeakMap();\r\n\r\n constructor(private easingParser?: (value: string) => (t: number) => number) {}\r\n\r\n collectTargets(\r\n rootObjects: String3DObject[],\r\n now: number,\r\n useDirtySync: boolean,\r\n dirtySet: Set<HTMLElement> | null\r\n ): String3DFilterTarget[] {\r\n const targets: String3DFilterTarget[] = [];\r\n const walk = (obj: String3DObject): void => {\r\n const el = obj.el as HTMLElement | undefined;\r\n if (el) {\r\n const animating = this.filterStates.get(el)?.animating === true;\r\n const shouldReadStyle = !useDirtySync || !dirtySet || dirtySet.has(el) || animating;\r\n const chain = this.readFilterChain(el, now, shouldReadStyle);\r\n if (chain && chain.length > 0) {\r\n const dirty = !useDirtySync || !dirtySet || dirtySet.has(el) || animating;\r\n const effectsKey =\r\n this.filterStates.get(el)?.effectsKey || this.stringifyFilterChain(chain);\r\n targets.push({\r\n object: obj,\r\n effects: chain,\r\n effectsKey,\r\n dirty,\r\n });\r\n return;\r\n }\r\n }\r\n obj.children.forEach((child) => walk(child));\r\n };\r\n rootObjects.forEach((obj) => walk(obj));\r\n return targets;\r\n }\r\n\r\n clear(): void {\r\n this.filterStates = new WeakMap();\r\n this.filterWarnings = new WeakMap();\r\n }\r\n\r\n private readFilterChain(\r\n el: HTMLElement,\r\n now: number,\r\n shouldReadStyle: boolean\r\n ): String3DFilterChain | null {\r\n const existing = this.filterStates.get(el);\r\n if (!shouldReadStyle && existing) {\r\n if (existing.animating) {\r\n return this.sampleTransition(existing, now);\r\n }\r\n return existing.effects;\r\n }\r\n\r\n const raw = readFilterRaw(el);\r\n if (!raw || raw === \"none\") {\r\n if (existing) {\r\n if (existing.animating && existing.clearOnComplete) {\r\n const current = this.sampleTransition(existing, now);\r\n if (!existing.animating) {\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n return current;\r\n }\r\n let { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration <= 0 && existing.lastDuration > 0) {\r\n duration = existing.lastDuration;\r\n delay = existing.lastDelay;\r\n easing = existing.lastEasing;\r\n }\r\n if (duration > 0) {\r\n const zero = this.makeZeroChain(existing.effects);\r\n existing.from = existing.effects;\r\n existing.to = zero;\r\n existing.startTime = now + delay;\r\n existing.duration = duration;\r\n existing.easing = easing;\r\n existing.animating = true;\r\n existing.clearOnComplete = true;\r\n existing.lastDuration = duration;\r\n existing.lastDelay = delay;\r\n existing.lastEasing = easing;\r\n return this.sampleTransition(existing, now);\r\n }\r\n }\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n\r\n const { effects, warnings } = this.parseFilterChain(raw);\r\n this.warnFilterIssues(el, raw, warnings);\r\n if (effects.length === 0) return null;\r\n\r\n const state = this.filterStates.get(el);\r\n if (!state) {\r\n const { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration > 0) {\r\n const zero = this.makeZeroChain(effects);\r\n const newState: FilterTransitionState = {\r\n raw,\r\n effects,\r\n animating: true,\r\n from: zero,\r\n to: effects,\r\n startTime: now + delay,\r\n duration,\r\n easing,\r\n clearOnComplete: false,\r\n lastDuration: duration,\r\n lastDelay: delay,\r\n lastEasing: easing,\r\n };\r\n newState.effectsKey = this.stringifyFilterChain(effects);\r\n this.filterStates.set(el, newState);\r\n return this.sampleTransition(newState, now);\r\n }\r\n this.filterStates.set(el, {\r\n raw,\r\n effects,\r\n animating: false,\r\n from: effects,\r\n to: effects,\r\n startTime: 0,\r\n duration: 0,\r\n easing: (t) => t,\r\n clearOnComplete: false,\r\n lastDuration: 0,\r\n lastDelay: 0,\r\n lastEasing: (t) => t,\r\n effectsKey: this.stringifyFilterChain(effects),\r\n });\r\n return effects;\r\n }\r\n\r\n if (state.raw === raw) {\r\n if (state.animating) {\r\n const current = this.sampleTransition(state, now);\r\n if (!state.animating && state.clearOnComplete) {\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n return current;\r\n }\r\n return state.effects;\r\n }\r\n\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n\r\n let { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration <= 0 && state.lastDuration > 0) {\r\n duration = state.lastDuration;\r\n delay = state.lastDelay;\r\n easing = state.lastEasing;\r\n }\r\n if (duration > 0) {\r\n const canTween = this.canInterpolate(state.effects, effects);\r\n const current = state.animating ? this.getCurrentChain(state, now) : state.effects;\r\n if (!canTween && this.isZeroChain(effects)) {\r\n state.pendingRaw = raw;\r\n state.pendingEffects = effects;\r\n state.raw = raw;\r\n state.effects = current;\r\n state.from = current;\r\n state.to = this.makeZeroChain(current);\r\n state.startTime = now + delay;\r\n state.duration = duration;\r\n state.easing = easing;\r\n state.animating = true;\r\n state.clearOnComplete = false;\r\n state.lastDuration = duration;\r\n state.lastDelay = delay;\r\n state.lastEasing = easing;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return this.sampleTransition(state, now);\r\n }\r\n\r\n const fromChain = canTween ? current : this.makeZeroChain(effects);\r\n state.raw = raw;\r\n state.effects = effects;\r\n state.from = fromChain;\r\n state.to = effects;\r\n state.startTime = now + delay;\r\n state.duration = duration;\r\n state.easing = easing;\r\n state.animating = true;\r\n state.clearOnComplete = false;\r\n state.lastDuration = duration;\r\n state.lastDelay = delay;\r\n state.lastEasing = easing;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return this.sampleTransition(state, now);\r\n }\r\n\r\n state.raw = raw;\r\n state.effects = effects;\r\n state.animating = false;\r\n state.clearOnComplete = false;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return effects;\r\n }\r\n\r\n private warnFilterIssues(el: HTMLElement, raw: string, warnings: string[]): void {\r\n if (warnings.length === 0) return;\r\n const lastRaw = this.filterWarnings.get(el);\r\n if (lastRaw === raw) return;\r\n this.filterWarnings.set(el, raw);\r\n }\r\n\r\n private parseFilterChain(raw: string): { effects: String3DFilterChain; warnings: string[] } {\r\n const warnings: string[] = [];\r\n const effects: String3DFilterChain = [];\r\n\r\n const parseNumber = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n const match = cleaned.match(/^(-?\\d*\\.?\\d+)(px)?$/);\r\n if (!match) return null;\r\n const num = Number.parseFloat(match[1]);\r\n return Number.isFinite(num) ? num : null;\r\n };\r\n\r\n const parseRatio = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n if (!cleaned) return null;\r\n if (cleaned.endsWith(\"%\")) {\r\n const num = Number.parseFloat(cleaned.slice(0, -1));\r\n return Number.isFinite(num) ? num / 100 : null;\r\n }\r\n const num = Number.parseFloat(cleaned);\r\n return Number.isFinite(num) ? num : null;\r\n };\r\n\r\n const parseAngle = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n if (!cleaned) return null;\r\n if (cleaned.endsWith(\"rad\")) {\r\n const num = Number.parseFloat(cleaned.slice(0, -3));\r\n return Number.isFinite(num) ? num : null;\r\n }\r\n const stripped = cleaned.endsWith(\"deg\") ? cleaned.slice(0, -3) : cleaned;\r\n const num = Number.parseFloat(stripped);\r\n return Number.isFinite(num) ? (num * Math.PI) / 180 : null;\r\n };\r\n\r\n const parseBloom = (value: string): { intensity: number; threshold: number } | null => {\r\n const parts = value.split(\",\").map((part) => part.trim());\r\n const intensity = parseNumber(parts[0] || \"\");\r\n if (intensity === null) return null;\r\n const threshold = parts[1] ? parseRatio(parts[1]) : null;\r\n return {\r\n intensity: Math.max(0, intensity),\r\n threshold: threshold === null ? 0.8 : Math.max(0, Math.min(1, threshold)),\r\n };\r\n };\r\n\r\n const parseAmount = (value: string, name: string, allowZero = false): number | null => {\r\n const amount = parseNumber(value);\r\n if (amount === null) {\r\n warnings.push(`[String3D] Invalid ${name} value \"${value}\".`);\r\n return null;\r\n }\r\n if (!allowZero && amount <= 0) {\r\n warnings.push(`[String3D] ${name} must be > 0.`);\r\n return null;\r\n }\r\n return amount;\r\n };\r\n\r\n const parseRatioAmount = (value: string, name: string): number | null => {\r\n const amount = parseRatio(value);\r\n if (amount === null) {\r\n warnings.push(`[String3D] Invalid ${name} value \"${value}\".`);\r\n return null;\r\n }\r\n return amount;\r\n };\r\n\r\n const re = /([a-zA-Z-]+)\\(([^)]*)\\)/g;\r\n let match: RegExpExecArray | null;\r\n while ((match = re.exec(raw))) {\r\n const name = match[1].toLowerCase();\r\n const args = (match[2] || \"\").trim();\r\n\r\n if (name === \"blur\") {\r\n const amount = parseAmount(args, \"blur\", true);\r\n if (amount !== null) effects.push({ type: \"blur\", amount });\r\n } else if (name === \"pixel\" || name === \"pixelate\") {\r\n const size = parseAmount(args, \"pixel\", true);\r\n if (size !== null) effects.push({ type: \"pixel\", size });\r\n } else if (name === \"bloom\") {\r\n const bloom = parseBloom(args);\r\n if (bloom) effects.push({ type: \"bloom\", ...bloom });\r\n else warnings.push(`[String3D] Invalid bloom value \"${args}\".`);\r\n } else if (name === \"brightness\") {\r\n const amount = parseRatioAmount(args, \"brightness\");\r\n if (amount !== null) effects.push({ type: \"brightness\", amount: Math.max(0, amount) });\r\n } else if (name === \"contrast\") {\r\n const amount = parseRatioAmount(args, \"contrast\");\r\n if (amount !== null) effects.push({ type: \"contrast\", amount: Math.max(0, amount) });\r\n } else if (name === \"saturate\") {\r\n const amount = parseRatioAmount(args, \"saturate\");\r\n if (amount !== null) effects.push({ type: \"saturate\", amount: Math.max(0, amount) });\r\n } else if (name === \"grayscale\") {\r\n const amount = parseRatioAmount(args, \"grayscale\");\r\n if (amount !== null)\r\n effects.push({ type: \"grayscale\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"sepia\") {\r\n const amount = parseRatioAmount(args, \"sepia\");\r\n if (amount !== null)\r\n effects.push({ type: \"sepia\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"invert\") {\r\n const amount = parseRatioAmount(args, \"invert\");\r\n if (amount !== null)\r\n effects.push({ type: \"invert\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"hue-rotate\") {\r\n const angle = parseAngle(args);\r\n if (angle !== null) effects.push({ type: \"hue-rotate\", angle });\r\n else warnings.push(`[String3D] Invalid hue-rotate value \"${args}\".`);\r\n } else if (name) {\r\n const custom = String3DCustomFilterRegistry.get(name);\r\n if (custom) {\r\n const parsed = custom.parse ? custom.parse(args) : {};\r\n if (parsed === null) {\r\n warnings.push(`[String3D] Invalid custom filter \"${name}\" args \"${args}\".`);\r\n } else {\r\n effects.push({ type: \"custom\", name, uniforms: parsed });\r\n }\r\n } else {\r\n warnings.push(`[String3D] Unknown filter \"${name}\".`);\r\n }\r\n }\r\n }\r\n\r\n if (effects.length === 0) {\r\n warnings.push(\"[String3D] No valid filters parsed from --filter.\");\r\n }\r\n\r\n return { effects, warnings };\r\n }\r\n\r\n private getFilterTransition(el: HTMLElement): {\r\n duration: number;\r\n delay: number;\r\n easing: (t: number) => number;\r\n } {\r\n const style = getComputedStyle(el);\r\n const properties = this.splitTransitionList(style.transitionProperty);\r\n const durations = this.splitTransitionList(style.transitionDuration);\r\n const delays = this.splitTransitionList(style.transitionDelay);\r\n const timings = this.splitTransitionList(style.transitionTimingFunction);\r\n\r\n const index = this.findTransitionIndex(properties, \"--filter\");\r\n if (index === -1) {\r\n const shorthand = this.parseTransitionShorthand(style.transition);\r\n const fallback = shorthand.get(\"--filter\") || shorthand.get(\"all\");\r\n if (fallback) {\r\n return fallback;\r\n }\r\n return { duration: 0, delay: 0, easing: (t) => t };\r\n }\r\n\r\n const duration = this.parseTime(durations[index] || durations[durations.length - 1] || \"0s\");\r\n const delay = this.parseTime(delays[index] || delays[delays.length - 1] || \"0s\");\r\n const easingRaw = timings[index] || timings[timings.length - 1] || \"linear\";\r\n return { duration, delay, easing: this.parseEasing(easingRaw) };\r\n }\r\n\r\n private splitTransitionList(value: string): string[] {\r\n const result: string[] = [];\r\n let current = \"\";\r\n let depth = 0;\r\n for (let i = 0; i < value.length; i += 1) {\r\n const ch = value[i];\r\n if (ch === \"(\") depth += 1;\r\n if (ch === \")\") depth = Math.max(0, depth - 1);\r\n if (ch === \",\" && depth === 0) {\r\n result.push(current.trim());\r\n current = \"\";\r\n } else {\r\n current += ch;\r\n }\r\n }\r\n if (current.trim()) result.push(current.trim());\r\n return result.length > 0 ? result : [\"all\"];\r\n }\r\n\r\n private findTransitionIndex(properties: string[], name: string): number {\r\n const normalized = properties.map((prop) => prop.trim().toLowerCase());\r\n let index = normalized.indexOf(name);\r\n if (index === -1) {\r\n index = normalized.indexOf(\"all\");\r\n }\r\n return index;\r\n }\r\n\r\n private parseTime(value: string): number {\r\n const raw = value.trim().toLowerCase();\r\n if (raw.endsWith(\"ms\")) {\r\n const num = Number.parseFloat(raw.slice(0, -2));\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n if (raw.endsWith(\"s\")) {\r\n const num = Number.parseFloat(raw.slice(0, -1));\r\n return Number.isFinite(num) ? num * 1000 : 0;\r\n }\r\n const num = Number.parseFloat(raw);\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n\r\n private parseTransitionShorthand(\r\n value: string\r\n ): Map<string, { duration: number; delay: number; easing: (t: number) => number }> {\r\n const map = new Map<\r\n string,\r\n { duration: number; delay: number; easing: (t: number) => number }\r\n >();\r\n const parts = this.splitTransitionList(value);\r\n parts.forEach((part) => {\r\n if (!part) return;\r\n const tokens = part.trim().split(/\\s+(?![^()]*\\))/g);\r\n let prop = \"\";\r\n let duration = \"\";\r\n let delay = \"\";\r\n let easing = \"\";\r\n tokens.forEach((token) => {\r\n const lower = token.toLowerCase();\r\n if (lower.endsWith(\"ms\") || lower.endsWith(\"s\") || /^[0-9.]+$/.test(lower)) {\r\n if (!duration) duration = lower;\r\n else if (!delay) delay = lower;\r\n } else if (\r\n lower.startsWith(\"cubic-bezier\") ||\r\n lower.startsWith(\"steps\") ||\r\n lower === \"linear\" ||\r\n lower === \"ease\" ||\r\n lower === \"ease-in\" ||\r\n lower === \"ease-out\" ||\r\n lower === \"ease-in-out\"\r\n ) {\r\n easing = token;\r\n } else if (!prop) {\r\n prop = token;\r\n }\r\n });\r\n if (!prop) return;\r\n map.set(prop.trim().toLowerCase(), {\r\n duration: this.parseTime(duration || \"0s\"),\r\n delay: this.parseTime(delay || \"0s\"),\r\n easing: this.parseEasing(easing || \"linear\"),\r\n });\r\n });\r\n return map;\r\n }\r\n\r\n private parseEasing(value: string): (t: number) => number {\r\n const raw = value.trim();\r\n if (!raw) return (t) => t;\r\n if (!this.easingParser) return (t) => t;\r\n try {\r\n const fn = this.easingParser(raw);\r\n return typeof fn === \"function\" ? fn : (t) => t;\r\n } catch {\r\n return (t) => t;\r\n }\r\n }\r\n\r\n private canInterpolate(from: String3DFilterChain, to: String3DFilterChain): boolean {\r\n if (from.length !== to.length) return false;\r\n return from.every((effect, index) => {\r\n const other = to[index];\r\n if (effect.type !== other.type) return false;\r\n if (effect.type === \"custom\" && other.type === \"custom\") {\r\n if (effect.name !== other.name) return false;\r\n const keys = Object.keys(effect.uniforms || {});\r\n const otherKeys = Object.keys(other.uniforms || {});\r\n if (keys.length !== otherKeys.length) return false;\r\n return keys.every(\r\n (key) => key in (other.uniforms || {}) && this.isNumeric(effect.uniforms?.[key])\r\n );\r\n }\r\n return true;\r\n });\r\n }\r\n\r\n private makeZeroChain(chain: String3DFilterChain): String3DFilterChain {\r\n return chain.map((effect) => {\r\n switch (effect.type) {\r\n case \"blur\":\r\n return { type: \"blur\", amount: 0 };\r\n case \"pixel\":\r\n return { type: \"pixel\", size: 0 };\r\n case \"bloom\":\r\n return { type: \"bloom\", intensity: 0, threshold: effect.threshold };\r\n case \"brightness\":\r\n return { type: \"brightness\", amount: 1 };\r\n case \"contrast\":\r\n return { type: \"contrast\", amount: 1 };\r\n case \"saturate\":\r\n return { type: \"saturate\", amount: 1 };\r\n case \"grayscale\":\r\n return { type: \"grayscale\", amount: 0 };\r\n case \"sepia\":\r\n return { type: \"sepia\", amount: 0 };\r\n case \"invert\":\r\n return { type: \"invert\", amount: 0 };\r\n case \"hue-rotate\":\r\n return { type: \"hue-rotate\", angle: 0 };\r\n case \"custom\": {\r\n const uniforms: Record<string, any> = {};\r\n Object.entries(effect.uniforms || {}).forEach(([key, value]) => {\r\n uniforms[key] = this.isNumeric(value) ? 0 : value;\r\n });\r\n return { type: \"custom\", name: effect.name, uniforms };\r\n }\r\n default:\r\n return effect;\r\n }\r\n });\r\n }\r\n\r\n private sampleTransition(state: FilterTransitionState, now: number): String3DFilterChain {\r\n if (!state.animating) return state.effects;\r\n if (now < state.startTime) {\r\n return state.from;\r\n }\r\n const elapsed = now - state.startTime;\r\n const duration = Math.max(1, state.duration);\r\n const t = Math.min(1, Math.max(0, elapsed / duration));\r\n const eased = state.easing(t);\r\n const interpolated = this.interpolateChain(state.from, state.to, eased);\r\n if (t >= 1) {\r\n state.animating = false;\r\n state.from = state.to;\r\n if (state.pendingEffects && state.pendingRaw === state.raw) {\r\n state.effects = state.pendingEffects;\r\n state.raw = state.pendingRaw || state.raw;\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n } else if (state.pendingEffects) {\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n }\r\n }\r\n return interpolated;\r\n }\r\n\r\n private getCurrentChain(state: FilterTransitionState, now: number): String3DFilterChain {\r\n if (!state.animating) return state.effects;\r\n if (now < state.startTime) return state.from;\r\n const elapsed = now - state.startTime;\r\n const duration = Math.max(1, state.duration);\r\n const t = Math.min(1, Math.max(0, elapsed / duration));\r\n const eased = state.easing(t);\r\n return this.interpolateChain(state.from, state.to, eased);\r\n }\r\n\r\n private interpolateChain(\r\n from: String3DFilterChain,\r\n to: String3DFilterChain,\r\n t: number\r\n ): String3DFilterChain {\r\n if (!this.canInterpolate(from, to)) return to;\r\n return from.map((effect, index) => this.interpolateEffect(effect, to[index], t));\r\n }\r\n\r\n private interpolateEffect(\r\n from: String3DFilterEffect,\r\n to: String3DFilterEffect,\r\n t: number\r\n ): String3DFilterEffect {\r\n const lerp = (a: number, b: number) => a + (b - a) * t;\r\n if (from.type === \"blur\" && to.type === \"blur\") {\r\n return { type: \"blur\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"pixel\" && to.type === \"pixel\") {\r\n return { type: \"pixel\", size: lerp(from.size, to.size) };\r\n }\r\n if (from.type === \"bloom\" && to.type === \"bloom\") {\r\n return {\r\n type: \"bloom\",\r\n intensity: lerp(from.intensity, to.intensity),\r\n threshold: lerp(from.threshold, to.threshold),\r\n };\r\n }\r\n if (from.type === \"brightness\" && to.type === \"brightness\") {\r\n return { type: \"brightness\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"contrast\" && to.type === \"contrast\") {\r\n return { type: \"contrast\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"saturate\" && to.type === \"saturate\") {\r\n return { type: \"saturate\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"grayscale\" && to.type === \"grayscale\") {\r\n return { type: \"grayscale\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"sepia\" && to.type === \"sepia\") {\r\n return { type: \"sepia\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"invert\" && to.type === \"invert\") {\r\n return { type: \"invert\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"hue-rotate\" && to.type === \"hue-rotate\") {\r\n return { type: \"hue-rotate\", angle: lerp(from.angle, to.angle) };\r\n }\r\n if (from.type === \"custom\" && to.type === \"custom\" && from.name === to.name) {\r\n const uniforms: Record<string, any> = {};\r\n Object.entries(to.uniforms || {}).forEach(([key, value]) => {\r\n const fromValue = from.uniforms?.[key];\r\n if (this.isNumeric(fromValue) && this.isNumeric(value)) {\r\n uniforms[key] = lerp(fromValue, value);\r\n } else {\r\n uniforms[key] = value;\r\n }\r\n });\r\n return { type: \"custom\", name: to.name, uniforms };\r\n }\r\n return to;\r\n }\r\n\r\n private stringifyFilterChain(chain: String3DFilterChain): string {\r\n const parts = chain.map((effect) => {\r\n if (effect.type === \"blur\") return `blur:${effect.amount}`;\r\n if (effect.type === \"pixel\") return `pixel:${effect.size}`;\r\n if (effect.type === \"bloom\") return `bloom:${effect.intensity},${effect.threshold}`;\r\n if (effect.type === \"brightness\") return `brightness:${effect.amount}`;\r\n if (effect.type === \"contrast\") return `contrast:${effect.amount}`;\r\n if (effect.type === \"saturate\") return `saturate:${effect.amount}`;\r\n if (effect.type === \"grayscale\") return `grayscale:${effect.amount}`;\r\n if (effect.type === \"sepia\") return `sepia:${effect.amount}`;\r\n if (effect.type === \"invert\") return `invert:${effect.amount}`;\r\n if (effect.type === \"hue-rotate\") return `hue-rotate:${effect.angle}`;\r\n if (effect.type === \"custom\") {\r\n const uniforms = Object.keys(effect.uniforms || {})\r\n .sort()\r\n .map((key) => `${key}=${(effect.uniforms as any)[key]}`)\r\n .join(\",\");\r\n return `custom:${effect.name}:${uniforms}`;\r\n }\r\n return \"unknown\";\r\n });\r\n return parts.join(\"|\");\r\n }\r\n\r\n private isNumeric(value: unknown): value is number {\r\n return typeof value === \"number\" && Number.isFinite(value);\r\n }\r\n\r\n private isZeroChain(chain: String3DFilterChain): boolean {\r\n return chain.every((effect) => {\r\n switch (effect.type) {\r\n case \"blur\":\r\n return effect.amount <= 0;\r\n case \"pixel\":\r\n return effect.size <= 0;\r\n case \"bloom\":\r\n return effect.intensity <= 0;\r\n case \"brightness\":\r\n return effect.amount === 1;\r\n case \"contrast\":\r\n return effect.amount === 1;\r\n case \"saturate\":\r\n return effect.amount === 1;\r\n case \"grayscale\":\r\n return effect.amount === 0;\r\n case \"sepia\":\r\n return effect.amount === 0;\r\n case \"invert\":\r\n return effect.amount === 0;\r\n case \"hue-rotate\":\r\n return effect.angle === 0;\r\n case \"custom\":\r\n return false;\r\n default:\r\n return false;\r\n }\r\n });\r\n }\r\n}\r\n","import type {\n String3DCustomMaterialDefinition,\n IMaterialInstance,\n IMaterialFactory,\n} from \"../core/materials\";\nimport { collectUniformsFromCSS, mergeInjections } from \"../core/materials\";\n\nexport class ThreeJSMaterialFactory implements IMaterialFactory {\n private THREE: any;\n private textureLoader: any;\n private textureCache: Map<string, any> = new Map();\n\n constructor(THREE: any) {\n this.THREE = THREE;\n this.textureLoader = new THREE.TextureLoader();\n }\n\n supports(definition: String3DCustomMaterialDefinition): boolean {\n return true;\n }\n\n create(\n definition: String3DCustomMaterialDefinition,\n initialUniforms?: Record<string, any>\n ): IMaterialInstance {\n const uniforms = this.buildUniforms(definition, initialUniforms);\n\n let material: any;\n\n if (definition.extends === \"shader\" || (!definition.extends && definition.vertexShader)) {\n material = this.createShaderMaterial(definition, uniforms);\n } else {\n material = this.createExtendedMaterial(definition, uniforms);\n }\n\n this.applyMaterialProperties(material, definition);\n\n const update = (newUniforms: Record<string, any>) => {\n this.updateUniforms(material, definition, newUniforms);\n };\n\n const dispose = () => {\n material.dispose();\n };\n\n return { material, definition, update, dispose };\n }\n\n parseUniformsFromCSS(\n definition: String3DCustomMaterialDefinition,\n element: HTMLElement,\n style: CSSStyleDeclaration\n ): Record<string, any> {\n return collectUniformsFromCSS(definition, element, style);\n }\n\n private buildUniforms(\n definition: String3DCustomMaterialDefinition,\n initialValues?: Record<string, any>\n ): Record<string, { value: any }> {\n const result: Record<string, { value: any }> = {};\n\n if (definition.uniforms) {\n for (const [key, def] of Object.entries(definition.uniforms)) {\n let value = initialValues?.[key] ?? def.value;\n value = this.convertUniformValue(def.type, value);\n result[key] = { value };\n }\n }\n\n return result;\n }\n\n private convertUniformValue(type: string, value: any): any {\n switch (type) {\n case \"vec2\":\n if (Array.isArray(value)) {\n return new this.THREE.Vector2(value[0], value[1]);\n }\n return value;\n case \"vec3\":\n if (Array.isArray(value)) {\n return new this.THREE.Vector3(value[0], value[1], value[2]);\n }\n return value;\n case \"vec4\":\n if (Array.isArray(value)) {\n return new this.THREE.Vector4(value[0], value[1], value[2], value[3]);\n }\n return value;\n case \"color\":\n if (Array.isArray(value)) {\n return new this.THREE.Color(value[0], value[1], value[2]);\n }\n if (typeof value === \"string\") {\n return new this.THREE.Color(value);\n }\n return value;\n case \"texture\":\n if (typeof value === \"string\" && value) {\n return this.loadTexture(value);\n }\n return value;\n default:\n return value;\n }\n }\n\n private loadTexture(url: string): any {\n if (this.textureCache.has(url)) {\n return this.textureCache.get(url);\n }\n const texture = this.textureLoader.load(url);\n this.textureCache.set(url, texture);\n return texture;\n }\n\n private createShaderMaterial(\n definition: String3DCustomMaterialDefinition,\n uniforms: Record<string, { value: any }>\n ): any {\n const material = new this.THREE.ShaderMaterial({\n uniforms,\n vertexShader: definition.vertexShader || this.getDefaultVertexShader(),\n fragmentShader: definition.fragmentShader || this.getDefaultFragmentShader(),\n lights: definition.lights ?? false,\n transparent: definition.properties?.transparent ?? false,\n });\n material.userData.customUniforms = uniforms;\n material.userData.definition = definition;\n return material;\n }\n\n private createExtendedMaterial(\n definition: String3DCustomMaterialDefinition,\n uniforms: Record<string, { value: any }>\n ): any {\n const baseType = definition.extends || \"standard\";\n let BaseMaterial: any;\n\n switch (baseType) {\n case \"basic\":\n BaseMaterial = this.THREE.MeshBasicMaterial;\n break;\n case \"physical\":\n BaseMaterial = this.THREE.MeshPhysicalMaterial;\n break;\n case \"standard\":\n default:\n BaseMaterial = this.THREE.MeshStandardMaterial;\n break;\n }\n\n const material = new BaseMaterial({\n transparent: definition.properties?.transparent ?? false,\n });\n\n if (definition.injections && definition.injections.length > 0) {\n const injectionMap = mergeInjections(definition.injections);\n\n material.onBeforeCompile = (shader: any) => {\n Object.assign(shader.uniforms, uniforms);\n\n shader.vertexShader = this.injectVertexShader(shader.vertexShader, injectionMap, uniforms);\n shader.fragmentShader = this.injectFragmentShader(\n shader.fragmentShader,\n injectionMap,\n uniforms\n );\n\n material.userData.shader = shader;\n };\n }\n\n material.userData.customUniforms = uniforms;\n material.userData.definition = definition;\n\n return material;\n }\n\n private injectVertexShader(\n shader: string,\n injections: Map<string, string>,\n uniforms: Record<string, { value: any }>\n ): string {\n let result = shader;\n\n const pars = injections.get(\"vertex_pars\");\n if (pars) {\n result = result.replace(\"#include <common>\", `#include <common>\\n${pars}`);\n }\n\n const header = injections.get(\"vertex_header\");\n if (header) {\n const uniformDeclarations = this.generateUniformDeclarations(uniforms);\n result = result.replace(\"void main() {\", `${uniformDeclarations}\\n${header}\\nvoid main() {`);\n }\n\n const transform = injections.get(\"vertex_transform\");\n if (transform) {\n result = result.replace(\"#include <begin_vertex>\", `#include <begin_vertex>\\n${transform}`);\n }\n\n const output = injections.get(\"vertex_output\");\n if (output) {\n result = result.replace(\"#include <project_vertex>\", `${output}\\n#include <project_vertex>`);\n }\n\n return result;\n }\n\n private injectFragmentShader(\n shader: string,\n injections: Map<string, string>,\n uniforms: Record<string, { value: any }>\n ): string {\n let result = shader;\n\n const pars = injections.get(\"fragment_pars\");\n if (pars) {\n result = result.replace(\"#include <common>\", `#include <common>\\n${pars}`);\n }\n\n const header = injections.get(\"fragment_header\");\n if (header) {\n const uniformDeclarations = this.generateUniformDeclarations(uniforms);\n result = result.replace(\"void main() {\", `${uniformDeclarations}\\n${header}\\nvoid main() {`);\n }\n\n const color = injections.get(\"fragment_color\");\n if (color) {\n result = result.replace(\"#include <color_fragment>\", `#include <color_fragment>\\n${color}`);\n }\n\n const normal = injections.get(\"fragment_normal\");\n if (normal) {\n result = result.replace(\n \"#include <normal_fragment_maps>\",\n `#include <normal_fragment_maps>\\n${normal}`\n );\n }\n\n const roughness = injections.get(\"fragment_roughness\");\n if (roughness) {\n result = result.replace(\n \"#include <roughnessmap_fragment>\",\n `#include <roughnessmap_fragment>\\n${roughness}`\n );\n }\n\n const metalness = injections.get(\"fragment_metalness\");\n if (metalness) {\n result = result.replace(\n \"#include <metalnessmap_fragment>\",\n `#include <metalnessmap_fragment>\\n${metalness}`\n );\n }\n\n const ao = injections.get(\"fragment_ao\");\n if (ao) {\n result = result.replace(\"#include <aomap_fragment>\", `#include <aomap_fragment>\\n${ao}`);\n }\n\n const transmission = injections.get(\"fragment_transmission\");\n if (transmission) {\n result = result.replace(\n \"#include <transmission_fragment>\",\n `#include <transmission_fragment>\\n${transmission}`\n );\n }\n\n const lights = injections.get(\"fragment_lights\");\n if (lights) {\n result = result.replace(\n \"#include <lights_physical_fragment>\",\n `#include <lights_physical_fragment>\\n${lights}`\n );\n }\n\n const emissive = injections.get(\"fragment_emissive\");\n if (emissive) {\n result = result.replace(\n \"#include <emissivemap_fragment>\",\n `#include <emissivemap_fragment>\\n${emissive}`\n );\n }\n\n const output = injections.get(\"fragment_output\");\n if (output) {\n result = result.replace(\n \"#include <dithering_fragment>\",\n `${output}\\n#include <dithering_fragment>`\n );\n }\n\n return result;\n }\n\n private generateUniformDeclarations(uniforms: Record<string, { value: any }>): string {\n const lines: string[] = [];\n\n for (const [name, uniform] of Object.entries(uniforms)) {\n const type = this.inferGLSLType(uniform.value);\n lines.push(`uniform ${type} ${name};`);\n }\n\n return lines.join(\"\\n\");\n }\n\n private inferGLSLType(value: any): string {\n if (typeof value === \"number\") return \"float\";\n if (typeof value === \"boolean\") return \"bool\";\n if (value instanceof this.THREE.Vector2) return \"vec2\";\n if (value instanceof this.THREE.Vector3) return \"vec3\";\n if (value instanceof this.THREE.Vector4) return \"vec4\";\n if (value instanceof this.THREE.Color) return \"vec3\";\n if (value instanceof this.THREE.Matrix3) return \"mat3\";\n if (value instanceof this.THREE.Matrix4) return \"mat4\";\n if (value?.isTexture) return \"sampler2D\";\n return \"float\";\n }\n\n private applyMaterialProperties(\n material: any,\n definition: String3DCustomMaterialDefinition\n ): void {\n const props = definition.properties;\n if (!props) return;\n\n if (props.transparent !== undefined) {\n material.transparent = props.transparent;\n }\n\n if (props.side !== undefined) {\n switch (props.side) {\n case \"front\":\n material.side = this.THREE.FrontSide;\n break;\n case \"back\":\n material.side = this.THREE.BackSide;\n break;\n case \"double\":\n material.side = this.THREE.DoubleSide;\n break;\n }\n }\n\n if (props.depthWrite !== undefined) {\n material.depthWrite = props.depthWrite;\n }\n\n if (props.depthTest !== undefined) {\n material.depthTest = props.depthTest;\n }\n\n if (props.blending !== undefined) {\n switch (props.blending) {\n case \"additive\":\n material.blending = this.THREE.AdditiveBlending;\n break;\n case \"subtractive\":\n material.blending = this.THREE.SubtractiveBlending;\n break;\n case \"multiply\":\n material.blending = this.THREE.MultiplyBlending;\n break;\n default:\n material.blending = this.THREE.NormalBlending;\n }\n }\n\n if (props.wireframe !== undefined) {\n material.wireframe = props.wireframe;\n }\n }\n\n private updateUniforms(\n material: any,\n definition: String3DCustomMaterialDefinition,\n newValues: Record<string, any>\n ): void {\n const shader = material.userData?.shader;\n const customUniforms = material.userData?.customUniforms;\n\n if (shader?.uniforms) {\n for (const [key, value] of Object.entries(newValues)) {\n const uniformDef = definition.uniforms?.[key];\n if (uniformDef && shader.uniforms[key]) {\n shader.uniforms[key].value = this.convertUniformValue(uniformDef.type, value);\n }\n }\n } else if (customUniforms) {\n for (const [key, value] of Object.entries(newValues)) {\n const uniformDef = definition.uniforms?.[key];\n if (uniformDef && customUniforms[key]) {\n customUniforms[key].value = this.convertUniformValue(uniformDef.type, value);\n }\n }\n }\n\n if (material.uniforms) {\n for (const [key, value] of Object.entries(newValues)) {\n const uniformDef = definition.uniforms?.[key];\n if (uniformDef && material.uniforms[key]) {\n material.uniforms[key].value = this.convertUniformValue(uniformDef.type, value);\n }\n }\n }\n }\n\n private getDefaultVertexShader(): string {\n return `\n varying vec2 vUv;\n varying vec3 vNormal;\n varying vec3 vPosition;\n\n void main() {\n vUv = uv;\n vNormal = normalize(normalMatrix * normal);\n vPosition = (modelMatrix * vec4(position, 1.0)).xyz;\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\n }\n `;\n }\n\n private getDefaultFragmentShader(): string {\n return `\n varying vec2 vUv;\n varying vec3 vNormal;\n varying vec3 vPosition;\n\n void main() {\n gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0);\n }\n `;\n }\n\n dispose(): void {\n this.textureCache.forEach((texture) => texture.dispose());\n this.textureCache.clear();\n }\n}\n","import {\r\n I3DEngine,\r\n I3DVector3,\r\n I3DVector2,\r\n I3DQuaternion,\r\n I3DEuler,\r\n I3DMatrix4,\r\n I3DBox3,\r\n I3DScene,\r\n I3DRenderer,\r\n I3DPerspectiveCamera,\r\n I3DOrthographicCamera,\r\n I3DObject,\r\n I3DMesh,\r\n I3DGeometry,\r\n I3DMaterial,\r\n I3DRenderTarget,\r\n I3DLight,\r\n I3DTextureLoader,\r\n I3DModelLoader,\r\n ParticleSystemConfig,\r\n I3DParticleSystem,\r\n} from \"../core/abstractions/I3DEngine\";\r\nimport { I3DEngineProvider } from \"../core/abstractions/I3DEngineProvider\";\r\nimport { IMaterialFactory } from \"../core/materials\";\r\nimport { ThreeJSMaterialFactory } from \"./ThreeJSMaterialFactory\";\r\nimport { FontConverter } from \"../core/text\";\r\n\r\nexport class ThreeJSEngine implements I3DEngine {\r\n private THREE: any;\r\n private loaders: Record<string, any>;\r\n private materialFactory: ThreeJSMaterialFactory | null = null;\r\n private particleModelCache: Map<string, any> = new Map();\r\n private particleModelPromiseCache: Map<string, Promise<any>> = new Map();\r\n private fontCache: Map<string, any> = new Map();\r\n private fontPromiseCache: Map<string, Promise<any>> = new Map();\r\n private fontMetricsCache: Map<string, { ascent: number; descent: number }> = new Map();\r\n\r\n constructor(THREE: any, loaders: Record<string, any> = {}) {\r\n this.THREE = THREE;\r\n this.loaders = loaders;\r\n this.materialFactory = new ThreeJSMaterialFactory(THREE);\r\n }\r\n\r\n getMaterialFactory(): IMaterialFactory | null {\r\n return this.materialFactory;\r\n }\r\n\r\n createVector3(x = 0, y = 0, z = 0): I3DVector3 {\r\n return new this.THREE.Vector3(x, y, z);\r\n }\r\n\r\n createVector2(x = 0, y = 0): I3DVector2 {\r\n return new this.THREE.Vector2(x, y);\r\n }\r\n\r\n createQuaternion(x = 0, y = 0, z = 0, w = 1): I3DQuaternion {\r\n return new this.THREE.Quaternion(x, y, z, w);\r\n }\r\n\r\n createEuler(x = 0, y = 0, z = 0, order = \"XYZ\"): I3DEuler {\r\n return new this.THREE.Euler(x, y, z, order);\r\n }\r\n\r\n createMatrix4(): I3DMatrix4 {\r\n return new this.THREE.Matrix4();\r\n }\r\n\r\n createBox3(min?: I3DVector3, max?: I3DVector3): I3DBox3 {\r\n return new this.THREE.Box3(min, max);\r\n }\r\n\r\n createScene(): I3DScene {\r\n return new this.THREE.Scene();\r\n }\r\n\r\n createRenderer(options?: {\r\n antialias?: boolean;\r\n alpha?: boolean;\r\n logarithmicDepthBuffer?: boolean;\r\n }): I3DRenderer {\r\n const renderer = new this.THREE.WebGLRenderer(options);\r\n renderer.outputEncoding = this.THREE.sRGBEncoding;\r\n return renderer;\r\n }\r\n\r\n createPerspectiveCamera(fov = 45, aspect = 1, near = 0.1, far = 2000): I3DPerspectiveCamera {\r\n return new this.THREE.PerspectiveCamera(fov, aspect, near, far);\r\n }\r\n\r\n createOrthographicCamera(\r\n left: number,\r\n right: number,\r\n top: number,\r\n bottom: number,\r\n near = 0.1,\r\n far = 10000\r\n ): I3DOrthographicCamera {\r\n return new this.THREE.OrthographicCamera(left, right, top, bottom, near, far);\r\n }\r\n\r\n createGroup(): I3DObject {\r\n return new this.THREE.Group();\r\n }\r\n\r\n createMesh(geometry: I3DGeometry, material: I3DMaterial): I3DMesh {\r\n return new this.THREE.Mesh(geometry, material);\r\n }\r\n\r\n createBoxGeometry(width: number, height: number, depth: number): I3DGeometry {\r\n return new this.THREE.BoxGeometry(width, height, depth);\r\n }\r\n\r\n createSphereGeometry(radius: number, widthSegments = 32, heightSegments = 32): I3DGeometry {\r\n return new this.THREE.SphereGeometry(radius, widthSegments, heightSegments);\r\n }\r\n\r\n createPlaneGeometry(width: number, height: number): I3DGeometry {\r\n return new this.THREE.PlaneGeometry(width, height);\r\n }\r\n\r\n createCylinderGeometry(\r\n radiusTop: number,\r\n radiusBottom: number,\r\n height: number,\r\n segments = 32\r\n ): I3DGeometry {\r\n return new this.THREE.CylinderGeometry(radiusTop, radiusBottom, height, segments);\r\n }\r\n\r\n createMeshBasicMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.MeshBasicMaterial(params);\r\n }\r\n\r\n createMeshStandardMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.MeshStandardMaterial(params);\r\n }\r\n\r\n createShaderMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.ShaderMaterial(params);\r\n }\r\n createPointLight(color?: string | number, intensity = 1, distance = 0, decay = 2): I3DLight {\r\n return new this.THREE.PointLight(color, intensity, distance, decay);\r\n }\r\n\r\n createSpotLight(\r\n color?: string | number,\r\n intensity = 1,\r\n distance = 0,\r\n angle = Math.PI / 3,\r\n penumbra = 0,\r\n decay = 1\r\n ): I3DLight {\r\n return new this.THREE.SpotLight(color, intensity, distance, angle, penumbra, decay);\r\n }\r\n\r\n createHemisphereLight(\r\n skyColor?: string | number,\r\n groundColor?: string | number,\r\n intensity = 1\r\n ): I3DLight {\r\n return new this.THREE.HemisphereLight(skyColor, groundColor, intensity);\r\n }\r\n\r\n createAmbientLight(color?: string | number, intensity = 1): I3DLight {\r\n return new this.THREE.AmbientLight(color, intensity);\r\n }\r\n\r\n createDirectionalLight(color?: string | number, intensity = 1): I3DLight {\r\n return new this.THREE.DirectionalLight(color, intensity);\r\n }\r\n\r\n createTextureLoader(): I3DTextureLoader {\r\n return new this.THREE.TextureLoader();\r\n }\r\n\r\n createModelLoader(type: string): I3DModelLoader {\r\n const LoaderClass = this.loaders[type];\r\n if (!LoaderClass) {\r\n throw new Error(`[ThreeJSEngine] Model loader \"${type}\" not registered`);\r\n }\r\n return new LoaderClass();\r\n }\r\n\r\n createRenderTarget(width: number, height: number, options: any = {}): I3DRenderTarget {\r\n const defaults = {\r\n minFilter: this.THREE.LinearFilter,\r\n magFilter: this.THREE.LinearFilter,\r\n format: this.THREE.RGBAFormat,\r\n depthBuffer: true,\r\n stencilBuffer: false,\r\n };\r\n return new this.THREE.WebGLRenderTarget(width, height, { ...defaults, ...options });\r\n }\r\n\r\n loadFont(url: string): Promise<any> {\r\n const normalized = url.trim();\r\n if (!normalized || normalized === \"none\") {\r\n return Promise.resolve(null);\r\n }\r\n if (this.fontCache.has(normalized)) {\r\n return Promise.resolve(this.fontCache.get(normalized));\r\n }\r\n const cachedPromise = this.fontPromiseCache.get(normalized);\r\n if (cachedPromise) return cachedPromise;\r\n\r\n const isFontFile = FontConverter.isFontFile(normalized);\r\n\r\n let promise: Promise<any>;\r\n\r\n if (isFontFile) {\r\n promise = this.loadFontWithConverter(normalized);\r\n } else {\r\n promise = this.loadFontWithLoader(normalized);\r\n }\r\n\r\n this.fontPromiseCache.set(normalized, promise);\r\n return promise;\r\n }\r\n\r\n private async loadFontWithConverter(url: string): Promise<any> {\r\n try {\r\n const fontData = await FontConverter.load(url);\r\n const font = this.createFontFromData(fontData);\r\n this.fontCache.set(url, font);\r\n return font;\r\n } catch (error) {\r\n return null;\r\n }\r\n }\r\n\r\n private loadFontWithLoader(url: string): Promise<any> {\r\n const LoaderClass = this.loaders.font || this.loaders.FontLoader;\r\n if (!LoaderClass) {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const loader = new LoaderClass();\r\n return new Promise<any>((resolve) => {\r\n loader.load(\r\n url,\r\n (font: any) => {\r\n this.fontCache.set(url, font);\r\n resolve(font);\r\n },\r\n undefined,\r\n () => {\r\n resolve(null);\r\n }\r\n );\r\n });\r\n }\r\n\r\n private createFontFromData(fontData: any): any {\r\n const LoaderClass = this.loaders.font || this.loaders.FontLoader;\r\n if (LoaderClass && LoaderClass.utils && LoaderClass.utils.convert) {\r\n const loader = new LoaderClass();\r\n if (loader.parse) {\r\n return loader.parse(fontData);\r\n }\r\n }\r\n\r\n const font = {\r\n data: fontData,\r\n isFont: true,\r\n generateShapes: (text: string, size: number) => {\r\n return this.generateShapesFromFontData(fontData, text, size, false);\r\n },\r\n generateNormalizedShapes: (text: string, size: number) => {\r\n return this.generateShapesFromFontData(fontData, text, size, true);\r\n },\r\n };\r\n return font;\r\n }\r\n\r\n private generateShapesFromFontData(\r\n fontData: any,\r\n text: string,\r\n size: number,\r\n normalizePosition: boolean = false\r\n ): any[] {\r\n const shapes: any[] = [];\r\n const scale = size / fontData.resolution;\r\n\r\n const char = text[0];\r\n if (!char) return shapes;\r\n\r\n const glyph = fontData.glyphs[char];\r\n if (!glyph || !glyph.o) return shapes;\r\n\r\n let xOffset = 0;\r\n if (normalizePosition) {\r\n const xMin = this.getOutlineXMin(glyph.o);\r\n xOffset = -xMin * scale;\r\n }\r\n\r\n const charShapes = this.parseOutlineToShapes(glyph.o, scale, xOffset, fontData?.outlineFormat);\r\n shapes.push(...charShapes);\r\n\r\n return shapes;\r\n }\r\n\r\n private getOutlineXMin(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let minX = Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 3]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 3]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 5]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return minX === Infinity ? 0 : minX;\r\n }\r\n\r\n private getOutlineXMax(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let maxX = -Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 3]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 3]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 5]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return maxX === -Infinity ? 0 : maxX;\r\n }\r\n\r\n private getOutlineYMin(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let minY = Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 4]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 4]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 6]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return minY === Infinity ? 0 : minY;\r\n }\r\n\r\n private pointInPolygon(\r\n px: number,\r\n py: number,\r\n polygon: Array<{ x: number; y: number }>\r\n ): boolean {\r\n let inside = false;\r\n for (let i = 0, j = polygon.length - 1; i < polygon.length; j = i++) {\r\n const xi = polygon[i].x;\r\n const yi = polygon[i].y;\r\n const xj = polygon[j].x;\r\n const yj = polygon[j].y;\r\n\r\n if (yi > py !== yj > py && px < ((xj - xi) * (py - yi)) / (yj - yi) + xi) {\r\n inside = !inside;\r\n }\r\n }\r\n return inside;\r\n }\r\n\r\n private samplePathPoints(path: any, numSamples: number = 80): Array<{ x: number; y: number }> {\r\n if (!path?.getPoints) return [];\r\n return path.getPoints(numSamples).map((p: any) => ({ x: p.x, y: p.y }));\r\n }\r\n\r\n private getBoundingBox(points: Array<{ x: number; y: number }>): {\r\n minX: number;\r\n maxX: number;\r\n minY: number;\r\n maxY: number;\r\n area: number;\r\n } {\r\n if (points.length === 0) {\r\n return { minX: 0, maxX: 0, minY: 0, maxY: 0, area: 0 };\r\n }\r\n let minX = Infinity;\r\n let maxX = -Infinity;\r\n let minY = Infinity;\r\n let maxY = -Infinity;\r\n for (const p of points) {\r\n if (p.x < minX) minX = p.x;\r\n if (p.x > maxX) maxX = p.x;\r\n if (p.y < minY) minY = p.y;\r\n if (p.y > maxY) maxY = p.y;\r\n }\r\n return { minX, maxX, minY, maxY, area: (maxX - minX) * (maxY - minY) };\r\n }\r\n\r\n private getInteriorPoint(points: Array<{ x: number; y: number }>): { x: number; y: number } {\r\n if (points.length < 3) return points[0] || { x: 0, y: 0 };\r\n const contour = points.map((p) => new this.THREE.Vector2(p.x, p.y));\r\n const triangles = this.THREE.ShapeUtils.triangulateShape(contour, []);\r\n for (const tri of triangles) {\r\n const a = contour[tri[0]];\r\n const b = contour[tri[1]];\r\n const c = contour[tri[2]];\r\n const cx = (a.x + b.x + c.x) / 3;\r\n const cy = (a.y + b.y + c.y) / 3;\r\n if (this.pointInPolygon(cx, cy, points)) {\r\n return { x: cx, y: cy };\r\n }\r\n }\r\n return points[0];\r\n }\r\n\r\n private parseOutlineToShapes(\r\n outline: string,\r\n scale: number,\r\n offsetX: number = 0,\r\n outlineFormat?: string\r\n ): any[] {\r\n if (!outline) return [];\r\n\r\n const shapePath = new this.THREE.ShapePath();\r\n const commands = outline.split(\" \");\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n {\r\n const mx = parseFloat(commands[i + 1]) * scale + offsetX;\r\n const my = -parseFloat(commands[i + 2]) * scale;\r\n shapePath.moveTo(mx, my);\r\n i += 3;\r\n }\r\n break;\r\n case \"l\":\r\n {\r\n const lx = parseFloat(commands[i + 1]) * scale + offsetX;\r\n const ly = -parseFloat(commands[i + 2]) * scale;\r\n shapePath.lineTo(lx, ly);\r\n i += 3;\r\n }\r\n break;\r\n case \"q\":\r\n {\r\n const qx = parseFloat(commands[i + 3]) * scale + offsetX;\r\n const qy = -parseFloat(commands[i + 4]) * scale;\r\n shapePath.quadraticCurveTo(\r\n parseFloat(commands[i + 1]) * scale + offsetX,\r\n -parseFloat(commands[i + 2]) * scale,\r\n qx,\r\n qy\r\n );\r\n i += 5;\r\n }\r\n break;\r\n case \"b\":\r\n {\r\n const bx = parseFloat(commands[i + 5]) * scale + offsetX;\r\n const by = -parseFloat(commands[i + 6]) * scale;\r\n shapePath.bezierCurveTo(\r\n parseFloat(commands[i + 1]) * scale + offsetX,\r\n -parseFloat(commands[i + 2]) * scale,\r\n parseFloat(commands[i + 3]) * scale + offsetX,\r\n -parseFloat(commands[i + 4]) * scale,\r\n bx,\r\n by\r\n );\r\n i += 7;\r\n }\r\n break;\r\n case \"z\":\r\n {\r\n if (typeof shapePath.closePath === \"function\") {\r\n shapePath.closePath();\r\n } else if (\r\n shapePath.currentPath &&\r\n typeof shapePath.currentPath.closePath === \"function\"\r\n ) {\r\n shapePath.currentPath.closePath();\r\n }\r\n i += 1;\r\n }\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n const subPaths = shapePath.subPaths;\r\n if (!subPaths || subPaths.length === 0) return [];\r\n\r\n const paths = subPaths.map((sp: any) => {\r\n const points = sp.getPoints();\r\n const area = this.THREE.ShapeUtils.area(points);\r\n const bbox = this.getBoundingBox(points.map((p: any) => ({ x: p.x, y: p.y })));\r\n return {\r\n path: sp,\r\n points,\r\n area: Math.abs(area),\r\n signedArea: area,\r\n bbox,\r\n };\r\n });\r\n\r\n paths.sort((a: any, b: any) => b.area - a.area);\r\n\r\n const finalShapes: any[] = [];\r\n const used = new Set<number>();\r\n\r\n for (let i = 0; i < paths.length; i++) {\r\n if (used.has(i)) continue;\r\n\r\n const outerPath = paths[i];\r\n const shape = new this.THREE.Shape(outerPath.points);\r\n used.add(i);\r\n\r\n for (let j = 0; j < paths.length; j++) {\r\n if (used.has(j) || i === j) continue;\r\n\r\n const innerPath = paths[j];\r\n\r\n if (\r\n innerPath.bbox.minX < outerPath.bbox.minX ||\r\n innerPath.bbox.maxX > outerPath.bbox.maxX ||\r\n innerPath.bbox.minY < outerPath.bbox.minY ||\r\n innerPath.bbox.maxY > outerPath.bbox.maxY\r\n ) {\r\n continue;\r\n }\r\n\r\n let allPointsInside = true;\r\n const testPoints = [\r\n innerPath.points[0],\r\n innerPath.points[Math.floor(innerPath.points.length / 2)],\r\n ];\r\n\r\n for (const testPoint of testPoints) {\r\n if (\r\n !testPoint ||\r\n !this.pointInPolygon(\r\n testPoint.x,\r\n testPoint.y,\r\n outerPath.points.map((p: any) => ({ x: p.x, y: p.y }))\r\n )\r\n ) {\r\n allPointsInside = false;\r\n break;\r\n }\r\n }\r\n\r\n if (allPointsInside) {\r\n shape.holes.push(new this.THREE.Path(innerPath.points));\r\n used.add(j);\r\n }\r\n }\r\n\r\n finalShapes.push(shape);\r\n }\r\n\r\n return finalShapes.length > 0 ? finalShapes : shapePath.toShapes(true);\r\n }\r\n\r\n private reversePath(path: any): any {\r\n const newPath = new this.THREE.Path();\r\n if (!path.curves || path.curves.length === 0) return newPath;\r\n\r\n const lastCurve = path.curves[path.curves.length - 1];\r\n const endPoint =\r\n lastCurve.v2 || lastCurve.v3 || (lastCurve.getPoint ? lastCurve.getPoint(1) : null);\r\n if (endPoint) {\r\n newPath.moveTo(endPoint.x, endPoint.y);\r\n }\r\n\r\n for (let i = path.curves.length - 1; i >= 0; i--) {\r\n const curve = path.curves[i];\r\n if (curve.isLineCurve || curve.type === \"LineCurve\" || curve.type === \"LineCurve3\") {\r\n newPath.lineTo(curve.v1.x, curve.v1.y);\r\n } else if (\r\n curve.isQuadraticBezierCurve ||\r\n curve.type === \"QuadraticBezierCurve\" ||\r\n curve.type === \"QuadraticBezierCurve3\"\r\n ) {\r\n newPath.quadraticCurveTo(curve.v1.x, curve.v1.y, curve.v0.x, curve.v0.y);\r\n } else if (\r\n curve.isCubicBezierCurve ||\r\n curve.type === \"CubicBezierCurve\" ||\r\n curve.type === \"CubicBezierCurve3\"\r\n ) {\r\n newPath.bezierCurveTo(\r\n curve.v2.x,\r\n curve.v2.y,\r\n curve.v1.x,\r\n curve.v1.y,\r\n curve.v0.x,\r\n curve.v0.y\r\n );\r\n }\r\n }\r\n\r\n return newPath;\r\n }\r\n\r\n createTextGeometry(text: string, font: any, options: any): I3DGeometry | null {\r\n if (!text || !font) return null;\r\n\r\n const size = Math.max(0.001, options.size || 16);\r\n const height = Math.max(0, options.height || 0);\r\n const lineHeight = Math.max(0.001, options.lineHeight || size * 1.2);\r\n const letterSpacing = Number.isFinite(options.letterSpacing) ? options.letterSpacing : 0;\r\n const align = options.align || \"left\";\r\n const bevelEnabled = !!options.bevelEnabled;\r\n const bevelThickness = Math.max(0, options.bevelThickness || 0);\r\n const bevelSize = Math.max(0, options.bevelSize || 0);\r\n const bevelOffset = options.bevelOffset || 0;\r\n const bevelSegments = Math.max(0, options.bevelSegments || 0);\r\n const curveSegments = Math.max(1, Math.round(options.curveSegments || 8));\r\n\r\n const lines = String(text).split(/\\r?\\n/);\r\n const shapes: any[] = [];\r\n\r\n const fontData = font?.data;\r\n const resolution = fontData?.resolution || 1000;\r\n if (options.layout && options.layout.length > 0) {\r\n const fontAscender = fontData?.ascender || resolution * 0.8;\r\n const fontDescender = fontData?.descender || -resolution * 0.2;\r\n const fontEmHeight = fontAscender - fontDescender;\r\n const baselineRatio = fontAscender / fontEmHeight;\r\n\r\n const elementWidth = options.elementWidth || 0;\r\n const elementHeight = options.elementHeight || 0;\r\n const centerOffsetX = 0;\r\n const centerOffsetY = 0;\r\n\r\n options.layout.forEach((item: any) => {\r\n const charShapes = font.generateShapes(item.char, size);\r\n\r\n const offsetX = item.x + centerOffsetX;\r\n\r\n const charHeight = item.height || size;\r\n const baselineFromTop = charHeight * baselineRatio;\r\n const offsetY = -(item.y + centerOffsetY) - baselineFromTop;\r\n\r\n charShapes.forEach((shape: any) => {\r\n let finalShape = this.translateShape(shape, offsetX, offsetY);\r\n if (item.scale && item.scale !== 1) {\r\n finalShape = this.scaleShape(finalShape, item.scale);\r\n }\r\n shapes.push(finalShape);\r\n });\r\n });\r\n } else {\r\n lines.forEach((line, index) => {\r\n const { shapes: lineShapes, width } = this.buildLineShapes(line, font, size, letterSpacing);\r\n let offsetX = 0;\r\n if (align === \"center\") {\r\n offsetX = -width * 0.5;\r\n } else if (align === \"right\") {\r\n offsetX = -width;\r\n }\r\n const offsetY = -index * lineHeight;\r\n lineShapes.forEach((shape) => {\r\n shapes.push(this.translateShape(shape, offsetX, offsetY));\r\n });\r\n });\r\n }\r\n\r\n if (!shapes.length) {\r\n return null;\r\n }\r\n\r\n const geometry = new this.THREE.ExtrudeGeometry(shapes, {\r\n depth: height,\r\n curveSegments,\r\n bevelEnabled,\r\n bevelThickness,\r\n bevelSize,\r\n bevelOffset,\r\n bevelSegments,\r\n });\r\n geometry.computeBoundingBox();\r\n return geometry;\r\n }\r\n\r\n private buildLineShapes(\r\n line: string,\r\n font: any,\r\n size: number,\r\n letterSpacing: number\r\n ): { shapes: any[]; width: number } {\r\n const shapes: any[] = [];\r\n let x = 0;\r\n const chars = Array.from(line);\r\n\r\n chars.forEach((char, index) => {\r\n const charShapes = font.generateShapes(char, size);\r\n charShapes.forEach((shape: any) => {\r\n const translated = this.translateShape(shape, x, 0);\r\n shapes.push(translated);\r\n });\r\n const advance = this.getGlyphAdvance(font, char, size);\r\n\r\n x += advance;\r\n if (letterSpacing !== 0 && index < chars.length - 1) {\r\n x += letterSpacing;\r\n }\r\n });\r\n\r\n return { shapes, width: x };\r\n }\r\n\r\n private getGlyphAdvance(font: any, char: string, size: number): number {\r\n const data = font?.data;\r\n const glyphs = data?.glyphs || {};\r\n const glyph = glyphs[char] || glyphs[char.charCodeAt(0)] || glyphs[\"?\"];\r\n const ha = glyph?.ha ?? data?.ha;\r\n const resolution = data?.resolution || 1000;\r\n if (typeof ha === \"number\") {\r\n return (ha / resolution) * size;\r\n }\r\n return size * 0.5;\r\n }\r\n\r\n private translateShape(shape: any, x: number, y: number): any {\r\n if (!shape || (!x && !y)) return shape;\r\n if (typeof shape.translate === \"function\") {\r\n shape.translate(x, y);\r\n return shape;\r\n }\r\n if (typeof shape.applyMatrix4 === \"function\") {\r\n const matrix = new this.THREE.Matrix4().makeTranslation(x, y, 0);\r\n shape.applyMatrix4(matrix);\r\n return shape;\r\n }\r\n if (typeof shape.extractPoints === \"function\") {\r\n const { shape: points, holes } = shape.extractPoints(12);\r\n const toVec2 = (pt: any) => new this.THREE.Vector2((pt.x || 0) + x, (pt.y || 0) + y);\r\n const newShape = new this.THREE.Shape(points.map(toVec2));\r\n if (Array.isArray(holes)) {\r\n holes.forEach((hole: any[]) => {\r\n const holePath = new this.THREE.Path();\r\n holePath.setFromPoints(hole.map(toVec2));\r\n newShape.holes.push(holePath);\r\n });\r\n }\r\n return newShape;\r\n }\r\n return shape;\r\n }\r\n\r\n private scaleShape(shape: any, s: number): any {\r\n if (s === 1) return shape;\r\n if (typeof shape.scale === \"function\") {\r\n shape.scale(s, s);\r\n return shape;\r\n }\r\n if (typeof shape.applyMatrix4 === \"function\") {\r\n const matrix = new this.THREE.Matrix4().makeScale(s, s, 1);\r\n shape.applyMatrix4(matrix);\r\n return shape;\r\n }\r\n\r\n if (typeof shape.extractPoints === \"function\") {\r\n const { shape: points, holes } = shape.extractPoints(12);\r\n const toVec2 = (pt: any) => new this.THREE.Vector2((pt.x || 0) * s, (pt.y || 0) * s);\r\n const newShape = new this.THREE.Shape(points.map(toVec2));\r\n if (Array.isArray(holes)) {\r\n holes.forEach((hole: any[]) => {\r\n const holePath = new this.THREE.Path();\r\n holePath.setFromPoints(hole.map(toVec2));\r\n newShape.holes.push(holePath);\r\n });\r\n }\r\n return newShape;\r\n }\r\n return shape;\r\n }\r\n\r\n private resolveParticleModelGeometry(\r\n modelUrl: string,\r\n loaderType?: string,\r\n nodeName?: string\r\n ): Promise<any | null> {\r\n const url = modelUrl.trim();\r\n if (!url || url === \"none\") {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const normalizedLoader =\r\n loaderType && loaderType !== \"none\"\r\n ? loaderType\r\n : this.loaders.gltf\r\n ? \"gltf\"\r\n : Object.keys(this.loaders)[0];\r\n if (!normalizedLoader) {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const nodeKey = (nodeName || \"\").trim();\r\n const cacheKey = `${normalizedLoader}|${url}|${nodeKey}`;\r\n if (this.particleModelCache.has(cacheKey)) {\r\n return Promise.resolve(this.particleModelCache.get(cacheKey));\r\n }\r\n const cachedPromise = this.particleModelPromiseCache.get(cacheKey);\r\n if (cachedPromise) {\r\n return cachedPromise;\r\n }\r\n\r\n const promise = new Promise<any | null>((resolve) => {\r\n let loader: I3DModelLoader | null = null;\r\n try {\r\n loader = this.createModelLoader(normalizedLoader);\r\n } catch (error) {\r\n resolve(null);\r\n return;\r\n }\r\n\r\n loader.load(\r\n url,\r\n (gltf: any) => {\r\n const root = gltf?.scene || gltf?.object || gltf;\r\n if (!root) {\r\n resolve(null);\r\n return;\r\n }\r\n let mesh: any = null;\r\n if (nodeKey) {\r\n if (root.getObjectByName) {\r\n const found = root.getObjectByName(nodeKey);\r\n if (found?.isMesh) mesh = found;\r\n }\r\n if (!mesh && root.traverse) {\r\n root.traverse((child: any) => {\r\n if (mesh) return;\r\n if (child?.isMesh && child?.name === nodeKey) {\r\n mesh = child;\r\n }\r\n });\r\n }\r\n }\r\n if (!mesh) {\r\n if (root.isMesh) {\r\n mesh = root;\r\n } else if (root.traverse) {\r\n root.traverse((child: any) => {\r\n if (!mesh && child?.isMesh) {\r\n mesh = child;\r\n }\r\n });\r\n }\r\n }\r\n\r\n const geometry = mesh?.geometry || null;\r\n if (!geometry) {\r\n resolve(null);\r\n return;\r\n }\r\n this.particleModelCache.set(cacheKey, geometry);\r\n resolve(geometry);\r\n },\r\n undefined,\r\n () => {\r\n resolve(null);\r\n }\r\n );\r\n });\r\n\r\n this.particleModelPromiseCache.set(cacheKey, promise);\r\n return promise;\r\n }\r\n\r\n createParticleSystem(config: ParticleSystemConfig): I3DParticleSystem {\r\n const THREE = this.THREE;\r\n const engine = this;\r\n\r\n const makeRng = (seed: number) => {\r\n let s = Math.max(1, seed | 0);\r\n return () => {\r\n s ^= s << 13;\r\n s ^= s >> 17;\r\n s ^= s << 5;\r\n return ((s >>> 0) % 100000) / 100000;\r\n };\r\n };\r\n\r\n class ParticleSystem extends THREE.Object3D {\r\n private cfg: ParticleSystemConfig;\r\n private rng = makeRng(config.seed);\r\n private points: any = null;\r\n private instanced: any = null;\r\n private positions: Float32Array = new Float32Array(0);\r\n private velocities: Float32Array = new Float32Array(0);\r\n private life: Float32Array = new Float32Array(0);\r\n private colors: Float32Array = new Float32Array(0);\r\n private sizeFactors: Float32Array = new Float32Array(0);\r\n private alive = 0;\r\n private emitRemainder = 0;\r\n private pendingBurst = 0;\r\n private basePositions: Float32Array = new Float32Array(0);\r\n private baseScales: Float32Array = new Float32Array(0);\r\n private baseJitter: Float32Array = new Float32Array(0);\r\n private basePhase: Float32Array = new Float32Array(0);\r\n private elapsed = 0;\r\n private modelGeometry: any = null;\r\n private modelKey = \"\";\r\n private instancedUsesSharedGeometry = false;\r\n private distributionGeometry: any = null;\r\n private distributionKey = \"\";\r\n private materialOverride: any = null;\r\n private materialOverrideForPoints: any = null;\r\n private defaultEmitterMaterial: any = null;\r\n private defaultInstancedMaterial: any = null;\r\n private transitionStartTime = 0;\r\n private transitionDuration = 0;\r\n private isTransitioning = false;\r\n private transitionFromPositions: Float32Array = new Float32Array(0);\r\n private transitionToPositions: Float32Array = new Float32Array(0);\r\n private pendingTransition = false;\r\n private pendingTransitionKey = \"\";\r\n private pendingDistributionLoad = false;\r\n\r\n constructor(cfg: ParticleSystemConfig) {\r\n super();\r\n this.cfg = { ...cfg };\r\n this.refreshModelGeometry();\r\n this.rebuild();\r\n }\r\n\r\n setConfig(config: ParticleSystemConfig): void {\r\n const prev = this.cfg;\r\n this.cfg = { ...config };\r\n const emitterReset =\r\n this.cfg.mode === \"emitter\" &&\r\n (prev.emitRate !== this.cfg.emitRate ||\r\n prev.emitBurst !== this.cfg.emitBurst ||\r\n prev.particleLife !== this.cfg.particleLife ||\r\n prev.particleSpeed !== this.cfg.particleSpeed ||\r\n !this.isVec3Equal(prev.particleDirection, this.cfg.particleDirection) ||\r\n !this.isVec3Equal(prev.particleGravity, this.cfg.particleGravity) ||\r\n prev.particleDrag !== this.cfg.particleDrag ||\r\n prev.particleSizeVariation !== this.cfg.particleSizeVariation ||\r\n prev.particleColorVariation !== this.cfg.particleColorVariation ||\r\n prev.color !== this.cfg.color);\r\n const needsRebuild =\r\n prev.mode !== this.cfg.mode ||\r\n prev.count !== this.cfg.count ||\r\n prev.seed !== this.cfg.seed ||\r\n prev.spread !== this.cfg.spread ||\r\n prev.particleShape !== this.cfg.particleShape ||\r\n prev.particleModelUrl !== this.cfg.particleModelUrl ||\r\n prev.particleModelLoader !== this.cfg.particleModelLoader ||\r\n prev.particleModelNode !== this.cfg.particleModelNode ||\r\n prev.instanceShape !== this.cfg.instanceShape ||\r\n prev.instanceModelUrl !== this.cfg.instanceModelUrl ||\r\n prev.instanceModelLoader !== this.cfg.instanceModelLoader ||\r\n prev.instanceModelNode !== this.cfg.instanceModelNode ||\r\n prev.instanceScale !== this.cfg.instanceScale ||\r\n prev.instanceScaleVariation !== this.cfg.instanceScaleVariation;\r\n if (needsRebuild) {\r\n const isParticleModelChange =\r\n this.cfg.mode === \"instanced\" &&\r\n this.instanced &&\r\n this.cfg.modelTransitionDuration > 0 &&\r\n (prev.particleModelUrl !== this.cfg.particleModelUrl ||\r\n prev.particleModelLoader !== this.cfg.particleModelLoader ||\r\n prev.particleModelNode !== this.cfg.particleModelNode ||\r\n prev.particleShape !== this.cfg.particleShape);\r\n\r\n const isInstanceModelChange =\r\n this.cfg.mode === \"instanced\" &&\r\n this.instanced &&\r\n this.cfg.modelTransitionDuration > 0 &&\r\n (prev.instanceModelUrl !== this.cfg.instanceModelUrl ||\r\n prev.instanceModelLoader !== this.cfg.instanceModelLoader ||\r\n prev.instanceModelNode !== this.cfg.instanceModelNode ||\r\n prev.instanceShape !== this.cfg.instanceShape);\r\n\r\n if (isParticleModelChange || isInstanceModelChange) {\r\n this.startModelTransition();\r\n } else {\r\n this.refreshModelGeometry();\r\n this.refreshDistributionGeometry();\r\n this.rebuild();\r\n }\r\n return;\r\n }\r\n if (emitterReset) {\r\n this.resetEmitter();\r\n }\r\n if (this.points) {\r\n const uniforms = this.points.material.uniforms;\r\n if (uniforms) {\r\n if (uniforms.uOpacity) {\r\n uniforms.uOpacity.value = this.cfg.opacity;\r\n }\r\n if (uniforms.uSize) {\r\n uniforms.uSize.value = this.cfg.size;\r\n }\r\n if (uniforms.uSizeVar) {\r\n uniforms.uSizeVar.value = this.cfg.particleSizeVariation;\r\n }\r\n if (uniforms.uPointSize) {\r\n uniforms.uPointSize.value = this.cfg.size;\r\n }\r\n }\r\n }\r\n if (this.instanced) {\r\n this.instanced.material.opacity = this.cfg.opacity;\r\n this.instanced.material.color = new THREE.Color(this.cfg.color);\r\n }\r\n this.pendingBurst = this.cfg.emitBurst;\r\n }\r\n\r\n private startModelTransition(): void {\r\n this.transitionFromPositions = new Float32Array(this.basePositions);\r\n this.transitionDuration = this.cfg.modelTransitionDuration;\r\n\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n this.pendingTransition = true;\r\n this.pendingTransitionKey = key;\r\n\r\n this.refreshModelGeometry();\r\n this.refreshDistributionGeometryForTransition();\r\n }\r\n\r\n private refreshDistributionGeometryForTransition(): void {\r\n if (this.cfg.instanceShape !== \"model\") {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n\r\n if (this.distributionKey === key && this.distributionGeometry) {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n\r\n this.distributionKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.instanceModelLoader,\r\n this.cfg.instanceModelNode\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.distributionKey !== key) return;\r\n if (!this.pendingTransition || this.pendingTransitionKey !== key) return;\r\n\r\n this.distributionGeometry = geometry;\r\n this.startMorphTransition();\r\n });\r\n }\r\n\r\n private startMorphTransition(): void {\r\n this.pendingTransition = false;\r\n this.pendingTransitionKey = \"\";\r\n\r\n const count = Math.max(1, this.cfg.count);\r\n this.transitionToPositions = new Float32Array(count * 3);\r\n\r\n const useModel = this.cfg.instanceShape === \"model\" && this.distributionGeometry;\r\n if (useModel) {\r\n this.fillFromModelToArray(count, this.distributionGeometry, this.transitionToPositions);\r\n } else {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos =\r\n this.cfg.instanceShape === \"box\"\r\n ? this.randomInBox(this.cfg.spread)\r\n : this.randomInSphere(this.cfg.spread);\r\n this.transitionToPositions.set(pos, i * 3);\r\n }\r\n }\r\n\r\n this.transitionStartTime = this.elapsed;\r\n this.isTransitioning = true;\r\n }\r\n\r\n private cleanupOutgoing(): void {\r\n this.isTransitioning = false;\r\n this.pendingTransition = false;\r\n this.pendingTransitionKey = \"\";\r\n this.transitionFromPositions = new Float32Array(0);\r\n this.transitionToPositions = new Float32Array(0);\r\n }\r\n\r\n private updateTransition(): void {\r\n if (!this.isTransitioning) return;\r\n\r\n const elapsed = this.elapsed - this.transitionStartTime;\r\n const progress = Math.min(1, elapsed / this.transitionDuration);\r\n\r\n const eased =\r\n progress < 0.5 ? 2 * progress * progress : 1 - Math.pow(-2 * progress + 2, 2) / 2;\r\n\r\n const count = Math.min(\r\n this.transitionFromPositions.length / 3,\r\n this.transitionToPositions.length / 3,\r\n this.basePositions.length / 3\r\n );\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.basePositions[i3] =\r\n this.transitionFromPositions[i3] +\r\n (this.transitionToPositions[i3] - this.transitionFromPositions[i3]) * eased;\r\n this.basePositions[i3 + 1] =\r\n this.transitionFromPositions[i3 + 1] +\r\n (this.transitionToPositions[i3 + 1] - this.transitionFromPositions[i3 + 1]) * eased;\r\n this.basePositions[i3 + 2] =\r\n this.transitionFromPositions[i3 + 2] +\r\n (this.transitionToPositions[i3 + 2] - this.transitionFromPositions[i3 + 2]) * eased;\r\n }\r\n\r\n if (progress >= 1) {\r\n for (let i = 0; i < count * 3; i += 1) {\r\n this.basePositions[i] = this.transitionToPositions[i];\r\n }\r\n this.cleanupOutgoing();\r\n }\r\n }\r\n\r\n private fillFromModelToArray(count: number, geometry: any, targetArray: Float32Array): void {\r\n const attr = geometry?.attributes?.position;\r\n if (!attr?.array || attr.itemSize < 3) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n targetArray.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n const array = attr.array as ArrayLike<number>;\r\n const itemSize = attr.itemSize;\r\n const vertexCount = Math.floor(array.length / itemSize);\r\n if (vertexCount <= 0) {\r\n return;\r\n }\r\n\r\n const indexArray = geometry?.index?.array as ArrayLike<number> | undefined;\r\n const triangleCount = indexArray\r\n ? Math.floor(indexArray.length / 3)\r\n : Math.floor(vertexCount / 3);\r\n if (triangleCount <= 0) {\r\n return;\r\n }\r\n\r\n let minX = Infinity;\r\n let minY = Infinity;\r\n let minZ = Infinity;\r\n let maxX = -Infinity;\r\n let maxY = -Infinity;\r\n let maxZ = -Infinity;\r\n for (let i = 0; i < vertexCount; i += 1) {\r\n const idx = i * itemSize;\r\n const x = array[idx];\r\n const y = array[idx + 1];\r\n const z = array[idx + 2];\r\n minX = Math.min(minX, x);\r\n minY = Math.min(minY, y);\r\n minZ = Math.min(minZ, z);\r\n maxX = Math.max(maxX, x);\r\n maxY = Math.max(maxY, y);\r\n maxZ = Math.max(maxZ, z);\r\n }\r\n const sizeX = Math.max(1e-6, maxX - minX);\r\n const sizeY = Math.max(1e-6, maxY - minY);\r\n const sizeZ = Math.max(1e-6, maxZ - minZ);\r\n const targetX = (this.cfg.spreadX > 0 ? this.cfg.spreadX : this.cfg.spread) * 2;\r\n const targetY = (this.cfg.spreadY > 0 ? this.cfg.spreadY : this.cfg.spread) * 2;\r\n const scaleX = targetX > 0 ? targetX / sizeX : 1;\r\n const scaleY = targetY > 0 ? targetY / sizeY : 1;\r\n const scale = Math.min(scaleX, scaleY);\r\n const centerX = (minX + maxX) * 0.5;\r\n const centerY = (minY + maxY) * 0.5;\r\n const centerZ = (minZ + maxZ) * 0.5;\r\n\r\n const cumulativeAreas = new Float32Array(triangleCount);\r\n let totalArea = 0;\r\n for (let i = 0; i < triangleCount; i += 1) {\r\n const base = i * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const abx = bx - ax;\r\n const aby = by - ay;\r\n const abz = bz - az;\r\n const acx = cx - ax;\r\n const acy = cy - ay;\r\n const acz = cz - az;\r\n const crossX = aby * acz - abz * acy;\r\n const crossY = abz * acx - abx * acz;\r\n const crossZ = abx * acy - aby * acx;\r\n const area = Math.sqrt(crossX * crossX + crossY * crossY + crossZ * crossZ) * 0.5;\r\n totalArea += area;\r\n cumulativeAreas[i] = totalArea;\r\n }\r\n if (totalArea <= 0) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n targetArray.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const r = this.rng() * totalArea;\r\n let lo = 0;\r\n let hi = triangleCount - 1;\r\n while (lo < hi) {\r\n const mid = Math.floor((lo + hi) / 2);\r\n if (r <= cumulativeAreas[mid]) {\r\n hi = mid;\r\n } else {\r\n lo = mid + 1;\r\n }\r\n }\r\n const base = lo * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const u = this.rng();\r\n const v = this.rng();\r\n const su = Math.sqrt(u);\r\n const w1 = 1 - su;\r\n const w2 = su * (1 - v);\r\n const w3 = su * v;\r\n const x = (ax * w1 + bx * w2 + cx * w3 - centerX) * scale;\r\n const y = (ay * w1 + by * w2 + cy * w3 - centerY) * scale;\r\n const z = (az * w1 + bz * w2 + cz * w3 - centerZ) * scale;\r\n targetArray[i * 3] = x;\r\n targetArray[i * 3 + 1] = y;\r\n targetArray[i * 3 + 2] = z;\r\n }\r\n }\r\n\r\n update(dt: number): void {\r\n if (dt <= 0) return;\r\n this.elapsed += dt;\r\n\r\n this.updateTransition();\r\n\r\n if (this.cfg.mode === \"emitter\") {\r\n this.updateEmitter(dt);\r\n } else {\r\n this.updateInstanced(this.elapsed);\r\n }\r\n }\r\n\r\n dispose(): void {\r\n this.cleanupOutgoing();\r\n if (this.points) {\r\n this.points.geometry.dispose();\r\n this.points.material.dispose();\r\n }\r\n if (this.instanced) {\r\n if (!this.instancedUsesSharedGeometry) {\r\n this.instanced.geometry.dispose();\r\n }\r\n this.instanced.material.dispose();\r\n }\r\n }\r\n\r\n private rebuild(): void {\r\n if (this.points) {\r\n this.remove(this.points);\r\n this.points.geometry.dispose();\r\n this.points.material.dispose();\r\n this.points = null;\r\n }\r\n if (this.instanced) {\r\n this.remove(this.instanced);\r\n if (!this.instancedUsesSharedGeometry) {\r\n this.instanced.geometry.dispose();\r\n }\r\n this.instanced.material.dispose();\r\n this.instanced = null;\r\n }\r\n this.elapsed = 0;\r\n\r\n if (this.cfg.mode === \"emitter\") {\r\n this.buildEmitter();\r\n } else {\r\n const needsModel = this.cfg.instanceShape === \"model\";\r\n const hasModel = this.distributionGeometry !== null;\r\n if (needsModel && !hasModel) {\r\n this.pendingDistributionLoad = true;\r\n this.refreshDistributionGeometry();\r\n return;\r\n }\r\n this.pendingDistributionLoad = false;\r\n this.refreshDistributionGeometry();\r\n this.buildInstanced();\r\n }\r\n this.applyMaterialOverrides();\r\n }\r\n\r\n private buildEmitter(): void {\r\n const count = Math.max(1, this.cfg.count);\r\n this.positions = new Float32Array(count * 3);\r\n this.velocities = new Float32Array(count * 3);\r\n this.life = new Float32Array(count);\r\n this.colors = new Float32Array(count * 3);\r\n this.sizeFactors = new Float32Array(count);\r\n const hide = 1e6;\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.positions[i3] = hide;\r\n this.positions[i3 + 1] = hide;\r\n this.positions[i3 + 2] = hide;\r\n }\r\n this.alive = 0;\r\n this.emitRemainder = 0;\r\n this.pendingBurst = this.cfg.emitBurst;\r\n\r\n const geometry = new THREE.BufferGeometry();\r\n geometry.setAttribute(\"position\", new THREE.BufferAttribute(this.positions, 3));\r\n geometry.setAttribute(\"color\", new THREE.BufferAttribute(this.colors, 3));\r\n geometry.setAttribute(\"sizeFactor\", new THREE.BufferAttribute(this.sizeFactors, 1));\r\n const material = new THREE.ShaderMaterial({\r\n transparent: this.cfg.opacity < 1,\r\n depthWrite: false,\r\n uniforms: {\r\n uOpacity: { value: this.cfg.opacity },\r\n uSize: { value: this.cfg.size },\r\n uSizeVar: { value: this.cfg.particleSizeVariation },\r\n },\r\n vertexShader: `\r\n attribute vec3 color;\r\n attribute float sizeFactor;\r\n varying vec3 vColor;\r\n uniform float uSize;\r\n uniform float uSizeVar;\r\n void main() {\r\n vColor = color;\r\n float size = uSize * mix(1.0 - uSizeVar, 1.0, sizeFactor);\r\n gl_PointSize = size;\r\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\r\n }\r\n `,\r\n fragmentShader: `\r\n varying vec3 vColor;\r\n uniform float uOpacity;\r\n void main() {\r\n float dist = length(gl_PointCoord - vec2(0.5));\r\n if (dist > 0.5) discard;\r\n gl_FragColor = vec4(vColor, uOpacity);\r\n }\r\n `,\r\n });\r\n this.points = new THREE.Points(geometry, material);\r\n this.defaultEmitterMaterial = material;\r\n this.add(this.points);\r\n }\r\n\r\n private buildInstanced(): void {\r\n const count = Math.max(1, this.cfg.count);\r\n const useSharedGeometry = this.cfg.particleShape === \"model\" && this.modelGeometry;\r\n const geometry =\r\n this.cfg.particleShape === \"model\" && this.modelGeometry\r\n ? this.modelGeometry\r\n : this.cfg.particleShape === \"box\"\r\n ? new THREE.BoxGeometry(1, 1, 1)\r\n : new THREE.SphereGeometry(0.5, 8, 8);\r\n this.instancedUsesSharedGeometry = useSharedGeometry;\r\n const material = new THREE.MeshStandardMaterial({\r\n color: new THREE.Color(this.cfg.color),\r\n transparent: this.cfg.opacity < 1,\r\n opacity: this.cfg.opacity,\r\n });\r\n this.defaultInstancedMaterial = material;\r\n this.instanced = new THREE.InstancedMesh(geometry, material, count);\r\n this.basePositions = new Float32Array(count * 3);\r\n this.baseScales = new Float32Array(count);\r\n this.baseJitter = new Float32Array(count * 3);\r\n this.basePhase = new Float32Array(count);\r\n this.fillBasePositions(count);\r\n this.applyInstancedTransforms(0);\r\n this.add(this.instanced);\r\n }\r\n\r\n setMaterial(\r\n material: any | null,\r\n options: { points?: boolean; meshes?: boolean } = {}\r\n ): void {\r\n const setPoints = options.points ?? true;\r\n const setMeshes = options.meshes ?? true;\r\n if (setMeshes) {\r\n this.materialOverride = material;\r\n }\r\n if (setPoints) {\r\n this.materialOverrideForPoints = material;\r\n }\r\n this.applyMaterialOverrides();\r\n }\r\n\r\n private updateEmitter(dt: number): void {\r\n const count = this.cfg.count;\r\n const dir = this.normalize(this.cfg.particleDirection);\r\n const gravity = this.cfg.particleGravity;\r\n const drag = Math.max(0, Math.min(1, this.cfg.particleDrag));\r\n const emitRate = this.cfg.emitRate;\r\n const totalToEmit = emitRate * dt + this.emitRemainder;\r\n const emitCount = Math.floor(totalToEmit);\r\n this.emitRemainder = totalToEmit - emitCount;\r\n let colorDirty = false;\r\n const hide = 1e6;\r\n\r\n for (let i = 0; i < emitCount; i += 1) {\r\n this.spawnParticle(dir);\r\n }\r\n while (this.pendingBurst > 0) {\r\n this.spawnParticle(dir);\r\n this.pendingBurst -= 1;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n if (this.life[i] <= 0) continue;\r\n this.life[i] -= dt;\r\n if (this.life[i] <= 0) {\r\n this.life[i] = 0;\r\n const i3 = i * 3;\r\n this.positions[i3] = hide;\r\n this.positions[i3 + 1] = hide;\r\n this.positions[i3 + 2] = hide;\r\n this.colors[i3] = 0;\r\n this.colors[i3 + 1] = 0;\r\n this.colors[i3 + 2] = 0;\r\n colorDirty = true;\r\n continue;\r\n }\r\n const idx = i * 3;\r\n this.velocities[idx] += gravity[0] * dt;\r\n this.velocities[idx + 1] += gravity[1] * dt;\r\n this.velocities[idx + 2] += gravity[2] * dt;\r\n this.velocities[idx] *= 1 - drag * dt;\r\n this.velocities[idx + 1] *= 1 - drag * dt;\r\n this.velocities[idx + 2] *= 1 - drag * dt;\r\n this.positions[idx] += this.velocities[idx] * dt;\r\n this.positions[idx + 1] += this.velocities[idx + 1] * dt;\r\n this.positions[idx + 2] += this.velocities[idx + 2] * dt;\r\n }\r\n\r\n if (this.points) {\r\n this.points.geometry.attributes.position.needsUpdate = true;\r\n if (colorDirty) {\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n }\r\n }\r\n }\r\n\r\n private spawnParticle(dir: [number, number, number]): void {\r\n const count = this.cfg.count;\r\n let idx = -1;\r\n for (let i = 0; i < count; i += 1) {\r\n if (this.life[i] <= 0) {\r\n idx = i;\r\n break;\r\n }\r\n }\r\n if (idx === -1) return;\r\n\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n const speed =\r\n this.cfg.particleSpeed *\r\n (1 - this.cfg.particleSizeVariation + this.rng() * this.cfg.particleSizeVariation);\r\n const vel = [\r\n dir[0] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n dir[1] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n dir[2] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n ];\r\n\r\n const i3 = idx * 3;\r\n this.positions.set(pos, i3);\r\n this.velocities.set(vel, i3);\r\n this.life[idx] = this.cfg.particleLife;\r\n this.sizeFactors[idx] = this.rng();\r\n\r\n const color = new THREE.Color(this.cfg.color);\r\n if (this.cfg.particleColorVariation > 0) {\r\n color.offsetHSL((this.rng() - 0.5) * this.cfg.particleColorVariation, 0, 0);\r\n }\r\n this.colors[i3] = color.r;\r\n this.colors[i3 + 1] = color.g;\r\n this.colors[i3 + 2] = color.b;\r\n if (this.points) {\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n this.points.geometry.attributes.sizeFactor.needsUpdate = true;\r\n }\r\n }\r\n\r\n private updateInstanced(time: number): void {\r\n this.applyInstancedTransforms(time);\r\n if (this.instanced) {\r\n this.instanced.instanceMatrix.needsUpdate = true;\r\n }\r\n }\r\n\r\n private applyInstancedTransforms(time: number): void {\r\n if (!this.instanced) return;\r\n const count = this.cfg.count;\r\n const jitter = this.cfg.instanceJitter;\r\n const flow = this.cfg.instanceFlow;\r\n const disperse = Math.max(0, this.cfg.instanceDisperse);\r\n const scatter = Math.max(0, this.cfg.instanceDisperseScatter);\r\n const scatterX =\r\n this.cfg.instanceDisperseScatterX > 0 ? this.cfg.instanceDisperseScatterX : scatter;\r\n const scatterY =\r\n this.cfg.instanceDisperseScatterY > 0 ? this.cfg.instanceDisperseScatterY : scatter;\r\n const scatterZ =\r\n this.cfg.instanceDisperseScatterZ > 0 ? this.cfg.instanceDisperseScatterZ : scatter;\r\n const rotSpeed = this.cfg.instanceRotationSpeed;\r\n const temp = new THREE.Object3D();\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n const baseX = this.basePositions[i3];\r\n const baseY = this.basePositions[i3 + 1];\r\n const baseZ = this.basePositions[i3 + 2];\r\n const phase = this.basePhase[i];\r\n const driftX = Math.sin((baseY + time * 1.4) * 0.7 + phase) * flow * this.cfg.spread;\r\n const driftY = Math.cos((baseX - time * 1.1) * 0.6 + phase) * flow * this.cfg.spread;\r\n const driftZ = Math.sin((baseZ + time * 1.2) * 0.8 + phase) * flow * this.cfg.spread;\r\n const jitterX = Math.sin(time * 2.1 + phase + this.baseJitter[i3] * 2.5) * jitter;\r\n const jitterY = Math.cos(time * 1.7 + phase + this.baseJitter[i3 + 1] * 2.5) * jitter;\r\n const jitterZ = Math.sin(time * 1.9 + phase + this.baseJitter[i3 + 2] * 2.5) * jitter;\r\n const dispersal = 1 + disperse;\r\n const dirX = this.baseJitter[i3];\r\n const dirY = this.baseJitter[i3 + 1];\r\n const dirZ = this.baseJitter[i3 + 2];\r\n const dirLen = Math.sqrt(dirX * dirX + dirY * dirY + dirZ * dirZ) || 1;\r\n const scatterScale = disperse * this.cfg.spread;\r\n const scatterOffsetX = (dirX / dirLen) * scatterX * scatterScale;\r\n const scatterOffsetY = (dirY / dirLen) * scatterY * scatterScale;\r\n const scatterOffsetZ = (dirZ / dirLen) * scatterZ * scatterScale;\r\n temp.position.set(\r\n baseX * dispersal + scatterOffsetX + driftX + jitterX,\r\n baseY * dispersal + scatterOffsetY + driftY + jitterY,\r\n baseZ * dispersal + scatterOffsetZ + driftZ + jitterZ\r\n );\r\n temp.rotation.set(\r\n this.baseJitter[i3] * 0.5,\r\n time * rotSpeed + i * 0.1,\r\n this.baseJitter[i3 + 2] * 0.5\r\n );\r\n const scale = this.baseScales[i] * this.cfg.size;\r\n temp.scale.set(scale, scale, scale);\r\n temp.updateMatrix();\r\n this.instanced.setMatrixAt(i, temp.matrix);\r\n }\r\n }\r\n\r\n private applyMaterialOverrides(): void {\r\n if (this.points) {\r\n const next = this.materialOverrideForPoints || this.defaultEmitterMaterial;\r\n if (next && this.points.material !== next) {\r\n this.points.material = next;\r\n this.ensurePointMaterial(next);\r\n }\r\n }\r\n if (this.instanced) {\r\n const next = this.materialOverride || this.defaultInstancedMaterial;\r\n if (next && this.instanced.material !== next) {\r\n this.instanced.material = next;\r\n }\r\n }\r\n }\r\n\r\n private ensurePointMaterial(material: any): void {\r\n if (!material?.isShaderMaterial) return;\r\n if (!material.uniforms) {\r\n material.uniforms = {};\r\n }\r\n if (!material.uniforms.uPointSize) {\r\n material.uniforms.uPointSize = { value: this.cfg.size };\r\n }\r\n if (!material.uniforms.uOpacity) {\r\n material.uniforms.uOpacity = { value: this.cfg.opacity };\r\n }\r\n if (!material.vertexShader.includes(\"gl_PointSize\")) {\r\n if (!material.vertexShader.includes(\"uPointSize\")) {\r\n material.vertexShader = `uniform float uPointSize;\\n${material.vertexShader}`;\r\n }\r\n material.vertexShader = material.vertexShader.replace(\r\n /void\\\\s+main\\\\s*\\\\(\\\\)\\\\s*\\\\{/,\r\n \"void main() {\\\\n gl_PointSize = uPointSize;\"\r\n );\r\n material.needsUpdate = true;\r\n }\r\n }\r\n\r\n private refreshModelGeometry(): void {\r\n if (this.cfg.particleShape !== \"model\") {\r\n this.modelGeometry = null;\r\n this.modelKey = \"\";\r\n return;\r\n }\r\n const url = this.cfg.particleModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.modelGeometry = null;\r\n this.modelKey = \"\";\r\n return;\r\n }\r\n const key = `${this.cfg.particleModelLoader}|${url}|${this.cfg.particleModelNode}`;\r\n if (this.modelKey === key && this.modelGeometry) {\r\n return;\r\n }\r\n this.modelKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.particleModelLoader,\r\n this.cfg.particleModelNode\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.modelKey !== key) return;\r\n this.modelGeometry = geometry;\r\n if (this.cfg.mode === \"instanced\" && this.cfg.particleShape === \"model\") {\r\n this.rebuild();\r\n }\r\n });\r\n }\r\n\r\n private refreshDistributionGeometry(): void {\r\n if (this.cfg.instanceShape !== \"model\") {\r\n this.distributionGeometry = null;\r\n this.distributionKey = \"\";\r\n return;\r\n }\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.distributionGeometry = null;\r\n this.distributionKey = \"\";\r\n return;\r\n }\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n if (this.distributionKey === key && this.distributionGeometry) {\r\n return;\r\n }\r\n this.distributionKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.instanceModelLoader,\r\n this.cfg.instanceModelNode\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.distributionKey !== key) return;\r\n this.distributionGeometry = geometry;\r\n if (this.cfg.mode === \"instanced\" && this.cfg.instanceShape === \"model\") {\r\n if (this.pendingDistributionLoad) {\r\n this.pendingDistributionLoad = false;\r\n this.buildInstanced();\r\n this.applyMaterialOverrides();\r\n } else {\r\n this.rebuild();\r\n }\r\n }\r\n });\r\n }\r\n\r\n private fillBasePositions(count: number): void {\r\n const useModel = this.cfg.instanceShape === \"model\" && this.distributionGeometry;\r\n if (useModel) {\r\n this.fillFromModel(count, this.distributionGeometry);\r\n } else {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos =\r\n this.cfg.instanceShape === \"box\"\r\n ? this.randomInBox(this.cfg.spread)\r\n : this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.baseJitter[i3] = this.rng() * 2 - 1;\r\n this.baseJitter[i3 + 1] = this.rng() * 2 - 1;\r\n this.baseJitter[i3 + 2] = this.rng() * 2 - 1;\r\n this.basePhase[i] = this.rng() * Math.PI * 2;\r\n const scale =\r\n this.cfg.instanceScale *\r\n (1 - this.cfg.instanceScaleVariation + this.rng() * this.cfg.instanceScaleVariation);\r\n this.baseScales[i] = scale;\r\n }\r\n }\r\n\r\n private fillFromModel(count: number, geometry: any): void {\r\n const attr = geometry?.attributes?.position;\r\n if (!attr?.array || attr.itemSize < 3) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n const array = attr.array as ArrayLike<number>;\r\n const itemSize = attr.itemSize;\r\n const vertexCount = Math.floor(array.length / itemSize);\r\n if (vertexCount <= 0) {\r\n return;\r\n }\r\n\r\n const indexArray = geometry?.index?.array as ArrayLike<number> | undefined;\r\n const triangleCount = indexArray\r\n ? Math.floor(indexArray.length / 3)\r\n : Math.floor(vertexCount / 3);\r\n if (triangleCount <= 0) {\r\n return;\r\n }\r\n\r\n let minX = Infinity;\r\n let minY = Infinity;\r\n let minZ = Infinity;\r\n let maxX = -Infinity;\r\n let maxY = -Infinity;\r\n let maxZ = -Infinity;\r\n for (let i = 0; i < vertexCount; i += 1) {\r\n const idx = i * itemSize;\r\n const x = array[idx];\r\n const y = array[idx + 1];\r\n const z = array[idx + 2];\r\n minX = Math.min(minX, x);\r\n minY = Math.min(minY, y);\r\n minZ = Math.min(minZ, z);\r\n maxX = Math.max(maxX, x);\r\n maxY = Math.max(maxY, y);\r\n maxZ = Math.max(maxZ, z);\r\n }\r\n const sizeX = Math.max(1e-6, maxX - minX);\r\n const sizeY = Math.max(1e-6, maxY - minY);\r\n const sizeZ = Math.max(1e-6, maxZ - minZ);\r\n const targetX = (this.cfg.spreadX > 0 ? this.cfg.spreadX : this.cfg.spread) * 2;\r\n const targetY = (this.cfg.spreadY > 0 ? this.cfg.spreadY : this.cfg.spread) * 2;\r\n const scaleX = targetX > 0 ? targetX / sizeX : 1;\r\n const scaleY = targetY > 0 ? targetY / sizeY : 1;\r\n const scale = Math.min(scaleX, scaleY);\r\n const centerX = (minX + maxX) * 0.5;\r\n const centerY = (minY + maxY) * 0.5;\r\n const centerZ = (minZ + maxZ) * 0.5;\r\n\r\n const cumulativeAreas = new Float32Array(triangleCount);\r\n let totalArea = 0;\r\n for (let i = 0; i < triangleCount; i += 1) {\r\n const base = i * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const abx = bx - ax;\r\n const aby = by - ay;\r\n const abz = bz - az;\r\n const acx = cx - ax;\r\n const acy = cy - ay;\r\n const acz = cz - az;\r\n const crossX = aby * acz - abz * acy;\r\n const crossY = abz * acx - abx * acz;\r\n const crossZ = abx * acy - aby * acx;\r\n const area = Math.sqrt(crossX * crossX + crossY * crossY + crossZ * crossZ) * 0.5;\r\n totalArea += area;\r\n cumulativeAreas[i] = totalArea;\r\n }\r\n if (totalArea <= 0) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const r = this.rng() * totalArea;\r\n let lo = 0;\r\n let hi = triangleCount - 1;\r\n while (lo < hi) {\r\n const mid = Math.floor((lo + hi) / 2);\r\n if (r <= cumulativeAreas[mid]) {\r\n hi = mid;\r\n } else {\r\n lo = mid + 1;\r\n }\r\n }\r\n const base = lo * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const u = this.rng();\r\n const v = this.rng();\r\n const su = Math.sqrt(u);\r\n const w1 = 1 - su;\r\n const w2 = su * (1 - v);\r\n const w3 = su * v;\r\n const x = (ax * w1 + bx * w2 + cx * w3 - centerX) * scale;\r\n const y = (ay * w1 + by * w2 + cy * w3 - centerY) * scale;\r\n const z = (az * w1 + bz * w2 + cz * w3 - centerZ) * scale;\r\n this.basePositions[i * 3] = x;\r\n this.basePositions[i * 3 + 1] = y;\r\n this.basePositions[i * 3 + 2] = z;\r\n }\r\n }\r\n\r\n private resetEmitter(): void {\r\n if (!this.points) return;\r\n const hide = 1e6;\r\n for (let i = 0; i < this.positions.length; i += 3) {\r\n this.positions[i] = hide;\r\n this.positions[i + 1] = hide;\r\n this.positions[i + 2] = hide;\r\n }\r\n this.velocities.fill(0);\r\n this.life.fill(0);\r\n this.colors.fill(0);\r\n this.sizeFactors.fill(0);\r\n this.alive = 0;\r\n this.emitRemainder = 0;\r\n this.pendingBurst = this.cfg.emitBurst;\r\n this.points.geometry.attributes.position.needsUpdate = true;\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n this.points.geometry.attributes.sizeFactor.needsUpdate = true;\r\n }\r\n\r\n private normalize(vec: [number, number, number]): [number, number, number] {\r\n const len = Math.sqrt(vec[0] * vec[0] + vec[1] * vec[1] + vec[2] * vec[2]) || 1;\r\n return [vec[0] / len, vec[1] / len, vec[2] / len];\r\n }\r\n\r\n private isVec3Equal(a: [number, number, number], b: [number, number, number]): boolean {\r\n return a[0] === b[0] && a[1] === b[1] && a[2] === b[2];\r\n }\r\n\r\n private randomInSphere(radius: number): [number, number, number] {\r\n const u = this.rng();\r\n const v = this.rng();\r\n const theta = u * Math.PI * 2;\r\n const phi = Math.acos(2 * v - 1);\r\n const r = Math.cbrt(this.rng()) * radius;\r\n return [\r\n r * Math.sin(phi) * Math.cos(theta),\r\n r * Math.sin(phi) * Math.sin(theta),\r\n r * Math.cos(phi),\r\n ];\r\n }\r\n\r\n private randomInBox(size: number): [number, number, number] {\r\n const half = size * 0.5;\r\n return [\r\n (this.rng() * 2 - 1) * half,\r\n (this.rng() * 2 - 1) * half,\r\n (this.rng() * 2 - 1) * half,\r\n ];\r\n }\r\n }\r\n\r\n return new ParticleSystem(config) as unknown as I3DParticleSystem;\r\n }\r\n\r\n simplifyGeometry(geometry: I3DGeometry, quality: number): I3DGeometry | null {\r\n const Modifier = (this.THREE as any)?.SimplifyModifier;\r\n if (!Modifier) return null;\r\n const anyGeom: any = geometry as any;\r\n const count = anyGeom?.attributes?.position?.count;\r\n if (!Number.isFinite(count)) return null;\r\n const clamped = Math.max(0.05, Math.min(1, quality));\r\n const target = Math.max(3, Math.floor(count * clamped));\r\n if (target >= count) return geometry;\r\n try {\r\n const modifier = new Modifier();\r\n return modifier.modify(anyGeom, target);\r\n } catch {\r\n return null;\r\n }\r\n }\r\n\r\n degToRad(degrees: number): number {\r\n return this.THREE.MathUtils.degToRad(degrees);\r\n }\r\n\r\n radToDeg(radians: number): number {\r\n return this.THREE.MathUtils.radToDeg(radians);\r\n }\r\n\r\n computeBoundingBoxRecursively(object: I3DObject): I3DBox3 {\r\n const boundingBox = new this.THREE.Box3();\r\n let hasBox = false;\r\n\r\n if (object.traverse) {\r\n object.traverse((child: any) => {\r\n if (!child.visible) return;\r\n if (child.geometry) {\r\n if (typeof child.geometry.computeBoundingBox === \"function\") {\r\n child.geometry.computeBoundingBox();\r\n }\r\n const box = child.geometry.boundingBox;\r\n if (box) {\r\n const childBox = box.clone().applyMatrix4(child.matrixWorld);\r\n boundingBox.union(childBox);\r\n hasBox = true;\r\n }\r\n }\r\n });\r\n }\r\n\r\n return hasBox ? boundingBox : new this.THREE.Box3();\r\n }\r\n}\r\n\r\nexport class ThreeJSProvider implements I3DEngineProvider {\r\n private engine: ThreeJSEngine;\r\n\r\n constructor(THREE: any, loaders: Record<string, any> = {}) {\r\n this.engine = new ThreeJSEngine(THREE, loaders);\r\n }\r\n\r\n getEngine(): I3DEngine {\r\n return this.engine;\r\n }\r\n\r\n getName(): string {\r\n return \"Three.js\";\r\n }\r\n}\r\n"],"mappings":"AAAA,OAAS,gBAAAA,OAAoB,8BCItB,IAAMC,GAAN,KAAqB,CAU1B,YACEC,EACAC,EAAmB,cACnBC,EAAM,GACNC,EAAO,GACPC,EAAM,IACN,CAfF,KAAQ,WAAa,IAAI,IAGzB,KAAQ,OAAS,EACjB,KAAQ,QAAU,EAYhB,KAAK,OAASJ,EACd,KAAK,KAAOC,EACZ,KAAK,eAAiBC,EAElBD,IAAS,eACX,KAAK,QAAUD,EAAO,yBAAyB,GAAI,EAAG,EAAG,GAAIG,EAAMC,CAAG,EAEtE,KAAK,QAAUJ,EAAO,wBAAwBE,EAAK,EAAGC,EAAMC,CAAG,EAGjE,KAAK,UAAYJ,EAAO,cAAc,EAAG,EAAG,GAAI,EAChD,KAAK,OAAO,CACd,CAEA,IAAW,QAAoB,CAC7B,OAAO,KAAK,OACd,CAEO,OAAOK,EAAeC,EAAsB,CAIjD,GAHA,KAAK,OAASD,EACd,KAAK,QAAUC,EAEX,KAAK,OAAS,eAAgB,CAChC,IAAMC,EAAQ,KAAK,QACnBA,EAAM,KAAO,CAACF,EAAQ,EACtBE,EAAM,MAAQF,EAAQ,EACtBE,EAAM,IAAMD,EAAS,EACrBC,EAAM,OAAS,CAACD,EAAS,CAC3B,MACE,KAAK,QAAQ,OAASD,EAAQC,EAGhC,KAAK,OAAO,CACd,CAEO,YAAYE,EAAWC,EAAWC,EAAiB,CACxD,KAAK,UAAU,IAAIF,EAAGC,EAAGC,CAAC,EAC1B,KAAK,QAAQ,SAAS,KAAK,KAAK,SAAS,EACzC,KAAK,OAAO,CACd,CAEO,OAAOF,EAAWC,EAAWC,EAAiB,CACnD,KAAK,QAAQ,OAAOF,EAAGC,EAAGC,CAAC,EAC3B,KAAK,OAAO,CACd,CAEO,QAAe,CACpB,KAAK,QAAQ,uBAAuB,EACnC,KAAK,QAAgB,oBAAoB,CAC5C,CAEO,cAAcC,EAAiBC,EAAiBF,EAAI,EAAe,CACxE,GAAI,KAAK,OAAS,eAAgB,CAChC,IAAMF,EAAIG,EAAU,KAAK,OAAS,EAC5BF,EAAI,EAAEG,EAAU,KAAK,QAAU,GACrC,OAAO,KAAK,OAAO,cAAcJ,EAAGC,EAAGC,CAAC,CAC1C,KAAO,CACL,GAAM,CAAE,MAAAL,EAAO,OAAAC,CAAO,EAAI,KAAK,iBAAiBI,CAAC,EAC3CG,EAAcF,EAAU,KAAK,OAC7BG,EAAcF,EAAU,KAAK,QAC7BJ,GAAKK,EAAc,IAAOR,EAC1BI,EAAI,EAAEK,EAAc,IAAOR,EACjC,OAAO,KAAK,OAAO,cAAcE,EAAGC,EAAGC,CAAC,CAC1C,CACF,CAEO,iBAAiBA,EAA8C,CACpE,GAAI,KAAK,OAAS,eAChB,MAAO,CAAE,MAAO,KAAK,OAAQ,OAAQ,KAAK,OAAQ,EAGpD,IAAMR,EAAM,KAAK,OAAO,SAAS,KAAK,cAAc,EAC9Ca,EAAW,KAAK,IAAIL,EAAI,KAAK,QAAQ,SAAS,CAAC,EAC/CJ,EAAS,EAAI,KAAK,IAAIJ,EAAM,CAAC,EAAIa,EAEvC,MAAO,CAAE,MADKT,EAAS,KAAK,QAAQ,OACpB,OAAAA,CAAO,CACzB,CAEO,YAAYI,EAAWM,EAAgC,CAC5D,GAAI,KAAK,OAAS,eAChB,MAAO,GAGT,IAAMC,EAAW,KAAK,MAAMP,EAAI,GAAI,EAAI,IACxC,GAAI,KAAK,WAAW,IAAIO,CAAQ,EAC9B,OAAO,KAAK,WAAW,IAAIA,CAAQ,EAGrC,GAAM,CAAE,OAAAX,CAAO,EAAI,KAAK,iBAAiBI,CAAC,EACpCQ,EAAQZ,EAASU,EACvB,YAAK,WAAW,IAAIC,EAAUC,CAAK,EAC5BA,CACT,CAEO,iBAAwB,CAC7B,KAAK,WAAW,MAAM,CACxB,CAEO,SAAsB,CAC3B,OAAO,KAAK,IACd,CAEO,mBAA4B,CACjC,OAAO,KAAK,cACd,CAEO,cAAuB,CAC5B,OAAO,KAAK,UAAU,CACxB,CACF,EC3HO,IAAMC,GAAN,KAAmC,CAGxC,OAAO,SAASC,EAAkD,CAChE,IAAMC,EAAOD,EAAW,KAAK,KAAK,EAAE,YAAY,EAChD,GAAI,CAACC,EACH,MAAM,IAAI,MAAM,4CAA4C,EAE9D,KAAK,QAAQ,IAAIA,EAAM,CAAE,GAAGD,EAAY,KAAAC,CAAK,CAAC,CAChD,CAEA,OAAO,IAAIA,EAA0D,CACnE,OAAO,KAAK,QAAQ,IAAIA,EAAK,KAAK,EAAE,YAAY,CAAC,CACnD,CAEA,OAAO,IAAIA,EAAuB,CAChC,OAAO,KAAK,QAAQ,IAAIA,EAAK,KAAK,EAAE,YAAY,CAAC,CACnD,CAEA,OAAO,MAAyC,CAC9C,OAAO,MAAM,KAAK,KAAK,QAAQ,OAAO,CAAC,CACzC,CACF,EAtBaF,GACI,QAAuD,IAAI,ICM5E,IAAMG,GAAN,KAAuB,CAIrB,YAAYC,EAA6B,CAHzC,KAAQ,KAA0B,CAAC,EAIjC,KAAK,OAASA,CAChB,CAEA,QAAQC,EAAeC,EAAiC,CACtD,IAAMC,EAAS,KAAK,KAAK,IAAI,GAAK,KAAK,OAAOF,EAAOC,CAAM,EAC3D,OAAIC,EAAO,QAAUF,GAASE,EAAO,SAAWD,IAC9CC,EAAO,QAAQF,EAAOC,CAAM,EAEvBC,CACT,CAEA,QAAQA,EAA+B,CACrC,KAAK,KAAK,KAAKA,CAAM,CACvB,CAEA,SAAgB,CACd,KAAK,KAAK,QAASA,GAAWA,EAAO,QAAQ,CAAC,EAC9C,KAAK,KAAO,CAAC,CACf,CACF,EAEaC,GAAN,KAA6B,CAkBlC,YAAYC,EAAmBC,EAAuBL,EAAeC,EAAgB,CAbrF,KAAQ,MAAQ,EAUhB,KAAQ,gBAA4C,IAAI,IAItD,KAAK,OAASG,EACd,KAAK,SAAWC,EAChB,KAAK,MAAQL,EACb,KAAK,OAASC,EAEd,KAAK,MAAQG,EAAO,YAAY,EAChC,KAAK,OAASA,EAAO,yBAAyB,GAAI,EAAG,EAAG,GAAI,EAAG,CAAC,EAEhE,IAAME,EAAWF,EAAO,oBAAoB,EAAG,CAAC,EAChD,KAAK,aAAe,KAAK,mBAAmB,EAC5C,KAAK,aAAe,KAAK,mBAAmB,EAC5C,KAAK,cAAgB,KAAK,oBAAoB,EAC9C,KAAK,qBAAuB,KAAK,2BAA2B,EAC5D,KAAK,iBAAmB,KAAK,uBAAuB,EACpD,KAAK,cAAgB,KAAK,oBAAoB,EAE9C,KAAK,KAAOA,EAAO,WAAWE,EAAU,KAAK,YAAY,EACzD,KAAK,MAAM,IAAI,KAAK,IAAI,EAExB,IAAMP,EAAS,CAACQ,EAAWC,IAAc,CACvC,GAAI,CAAC,KAAK,OAAO,mBACf,MAAM,IAAI,MAAM,yDAAyD,EAE3E,OAAO,KAAK,OAAO,mBAAmBD,EAAGC,CAAC,CAC5C,EACA,KAAK,KAAO,IAAIV,GAAiBC,CAAM,CACzC,CAEO,aAAuB,CAC5B,MACE,CAAC,CAAC,KAAK,OAAO,oBACd,CAAC,CAAC,KAAK,OAAO,sBACd,CAAC,CAAC,KAAK,SAAS,eAEpB,CAEO,OAAOC,EAAeC,EAAsB,CACjD,KAAK,MAAQD,EACb,KAAK,OAASC,CAChB,CAEO,SAASQ,EAAqB,CACnC,IAAMC,EAAO,KAAK,IAAI,IAAM,KAAK,IAAI,EAAGD,CAAK,CAAC,EAC9C,KAAK,MAAQC,CACf,CAEO,aACLC,EACAC,EACAC,EAAU,EACO,CACjB,IAAIC,EAAUH,EACRI,EAA4B,CAAC,EAE7BC,EAAgBd,GAAkC,CACtD,IAAMe,EAAMF,EAAO,QAAQb,CAAM,EAC7Be,GAAO,IACTF,EAAO,OAAOE,EAAK,CAAC,EACpB,KAAK,KAAK,QAAQf,CAAM,EAE5B,EAEMgB,EAAU,IAAuB,CACrC,GAAM,CAAE,MAAAlB,EAAO,OAAAC,CAAO,EAAI,KAAK,cAAc,EACvCC,EAAS,KAAK,KAAK,QAAQF,EAAOC,CAAM,EAC9C,OAAAc,EAAO,KAAKb,CAAM,EACXA,CACT,EAEA,OAAAU,EAAQ,QAASO,GAAW,CAC1B,GAAIA,EAAO,OAAS,OAAQ,CAC1B,IAAMC,EAASD,EAAO,OAASN,EAC/B,GAAIO,GAAU,KAAQ,OACtB,IAAMC,EAAQH,EAAQ,EACtB,KAAK,WAAW,KAAK,aAAcJ,EAASO,EAAO,CACjD,WAAY,CAAC,EAAG,CAAC,EACjB,QAASD,CACX,CAAC,EACD,IAAME,EAASJ,EAAQ,EACvB,KAAK,WAAW,KAAK,aAAcG,EAAOC,EAAQ,CAChD,WAAY,CAAC,EAAG,CAAC,EACjB,QAASF,CACX,CAAC,EACDJ,EAAaK,CAAK,EACdP,IAAYH,GACdK,EAAaF,CAAO,EAEtBA,EAAUQ,CACZ,SAAWH,EAAO,OAAS,QAAS,CAClC,GAAIA,EAAO,MAAQ,GAAK,OACxB,IAAMI,EAASL,EAAQ,EACvB,KAAK,WAAW,KAAK,cAAeJ,EAASS,EAAQ,CACnD,WAAYJ,EAAO,IACrB,CAAC,EACGL,IAAYH,GACdK,EAAaF,CAAO,EAEtBA,EAAUS,CACZ,SAAWJ,EAAO,OAAS,QAAS,CAClC,IAAMK,EAAYL,EAAO,UAEzB,GADIK,GAAa,MACbL,EAAO,WAAa,IAAM,OAC9B,IAAMM,EAAa,KAAK,IAAI,EAAG,EAAIZ,CAAO,EACpCa,EAAYR,EAAQ,EAC1B,KAAK,WAAW,KAAK,qBAAsBJ,EAASY,EAAW,CAC7D,WAAYP,EAAO,SACrB,CAAC,EAED,IAAMQ,EAAQT,EAAQ,EACtB,KAAK,WAAW,KAAK,aAAcQ,EAAWC,EAAO,CACnD,WAAY,CAAC,EAAG,CAAC,EACjB,QAASF,CACX,CAAC,EACD,IAAMG,EAAQV,EAAQ,EACtB,KAAK,WAAW,KAAK,aAAcS,EAAOC,EAAO,CAC/C,WAAY,CAAC,EAAG,CAAC,EACjB,QAASH,CACX,CAAC,EAEDT,EAAaU,CAAS,EACtBV,EAAaW,CAAK,EAElB,IAAME,EAAWX,EAAQ,EACzB,KAAK,cAAcJ,EAASc,EAAOC,EAAUL,CAAS,EACtDR,EAAaY,CAAK,EAEdd,IAAYH,GACdK,EAAaF,CAAO,EAEtBA,EAAUe,CACZ,SACEV,EAAO,OAAS,cAChBA,EAAO,OAAS,YAChBA,EAAO,OAAS,YAChBA,EAAO,OAAS,aAChBA,EAAO,OAAS,SAChBA,EAAO,OAAS,UAChBA,EAAO,OAAS,aAChB,CACA,IAAMI,EAASL,EAAQ,EACjBY,EAAO,KAAK,aAAaX,EAAO,IAAI,EACpCY,EAASZ,EAAO,OAAS,aAAeA,EAAO,MAAQA,EAAO,OACpE,KAAK,WAAW,KAAK,cAAeL,EAASS,EAAQ,CACnD,MAAOO,EACP,QAASC,CACX,CAAC,EACGjB,IAAYH,GACdK,EAAaF,CAAO,EAEtBA,EAAUS,CACZ,SAAWJ,EAAO,OAAS,SAAU,CACnC,IAAMI,EAASL,EAAQ,EACjBc,EAAW,KAAK,kBAAkBb,EAAO,IAAI,EAC/Ca,GACF,KAAK,WAAWA,EAAUlB,EAASS,EAAQJ,EAAO,QAAQ,EACtDL,IAAYH,GACdK,EAAaF,CAAO,EAEtBA,EAAUS,GAEVP,EAAaO,CAAM,CAEvB,CACF,CAAC,EAEDR,EAAO,QAASb,GAAW,CACrBA,IAAWY,GACb,KAAK,KAAK,QAAQZ,CAAM,CAE5B,CAAC,EAEMY,CACT,CAEO,eAAiC,CACtC,GAAM,CAAE,MAAAd,EAAO,OAAAC,CAAO,EAAI,KAAK,cAAc,EAC7C,OAAO,KAAK,KAAK,QAAQD,EAAOC,CAAM,CACxC,CAEO,cAAcC,EAA+B,CAClD,KAAK,KAAK,QAAQA,CAAM,CAC1B,CAEO,eAAeS,EAA8B,CAClD,KAAK,WAAW,KAAK,aAAcA,EAAO,KAAM,CAAC,EAAG,EAAK,CAC3D,CAEO,SAAgB,CACrB,KAAK,KAAK,QAAQ,EAClB,KAAK,gBAAgB,QAASqB,GAAaA,EAAS,QAAQ,CAAC,EAC7D,KAAK,gBAAgB,MAAM,CAC7B,CAEQ,WACNA,EACArB,EACAY,EACAU,EAAgC,CAAC,EACjCC,EAAQ,GACF,CACN,IAAM7B,EAAW,KAAK,SAClBA,EAAS,iBACXA,EAAS,gBAAgBkB,CAAM,EAGjC,KAAK,YAAY,KAAK,KAAMS,CAAQ,EACpC,KAAK,WAAWA,EAAU,WAAYrB,EAAM,OAAO,EACnD,GAAM,CAAE,MAAAX,EAAO,OAAAC,CAAO,EAAI,KAAK,cAAc,EAC7C,KAAK,WAAW+B,EAAU,cAAe,CAAChC,EAAOC,CAAM,CAAC,EACxD,KAAK,WAAW+B,EAAU,SAAU,CAAC,EAAIhC,EAAO,EAAIC,CAAM,CAAC,EAC3D,OAAO,QAAQgC,CAAQ,EAAE,QAAQ,CAAC,CAACE,EAAKC,CAAK,IAAM,KAAK,WAAWJ,EAAUG,EAAKC,CAAK,CAAC,EAEpFF,GAAS7B,EAAS,OACpBA,EAAS,MAAM,GAAM,GAAM,EAAI,EAEjC,KAAK,SAAS,OAAO,KAAK,MAAO,KAAK,MAAM,CAC9C,CAEQ,cACNgC,EACAC,EACAf,EACAC,EACM,CACN,IAAMnB,EAAW,KAAK,SAClBA,EAAS,iBACXA,EAAS,gBAAgBkB,CAAM,EAGjC,KAAK,YAAY,KAAK,KAAM,KAAK,gBAAgB,EACjD,KAAK,WAAW,KAAK,iBAAkB,QAASc,EAAK,OAAO,EAC5D,KAAK,WAAW,KAAK,iBAAkB,SAAUC,EAAM,OAAO,EAC9D,KAAK,WAAW,KAAK,iBAAkB,aAAcd,CAAS,EAC9D,GAAM,CAAE,MAAAxB,EAAO,OAAAC,CAAO,EAAI,KAAK,cAAc,EAC7C,KAAK,WAAW,KAAK,iBAAkB,cAAe,CAACD,EAAOC,CAAM,CAAC,EAEjEI,EAAS,OACXA,EAAS,MAAM,GAAM,GAAM,EAAI,EAEjC,KAAK,SAAS,OAAO,KAAK,MAAO,KAAK,MAAM,CAC9C,CAEQ,YAAYkC,EAAmBP,EAA6B,CAClE,IAAMQ,EAASD,EACXC,EAAO,WAAaR,IACtBQ,EAAO,SAAWR,EAEtB,CAEQ,WAAWA,EAAuBS,EAAcL,EAAkB,CACxE,IAAMH,EAAYD,EAAiB,SAC9BC,IACAA,EAASQ,CAAI,EAGhBR,EAASQ,CAAI,EAAE,MAAQL,EAFvBH,EAASQ,CAAI,EAAI,CAAE,MAAAL,CAAM,EAI7B,CAEQ,oBAAkC,CACxC,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CAAE,SAAU,CAAE,MAAO,IAAK,CAAE,EACtC,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAOhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,qBAAmC,CACzC,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CACR,SAAU,CAAE,MAAO,IAAK,EACxB,YAAa,CAAE,MAAO,CAAC,KAAK,MAAO,KAAK,MAAM,CAAE,EAChD,WAAY,CAAE,MAAO,CAAE,CACzB,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAWhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,oBAAkC,CACxC,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CACR,SAAU,CAAE,MAAO,IAAK,EACxB,OAAQ,CAAE,MAAO,CAAC,EAAI,KAAK,MAAO,EAAI,KAAK,MAAM,CAAE,EACnD,WAAY,CAAE,MAAO,CAAC,EAAG,CAAC,CAAE,EAC5B,QAAS,CAAE,MAAO,CAAE,CACtB,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAuBhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,4BAA0C,CAChD,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CACR,SAAU,CAAE,MAAO,IAAK,EACxB,WAAY,CAAE,MAAO,EAAI,CAC3B,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAUhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,wBAAsC,CAC5C,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CACR,MAAO,CAAE,MAAO,IAAK,EACrB,OAAQ,CAAE,MAAO,IAAK,EACtB,WAAY,CAAE,MAAO,CAAE,EACvB,YAAa,CAAE,MAAO,CAAC,KAAK,MAAO,KAAK,MAAM,CAAE,CAClD,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAWhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,qBAAmC,CACzC,OAAO,KAAK,qBAAqB,CAC/B,SAAU,CACR,SAAU,CAAE,MAAO,IAAK,EACxB,MAAO,CAAE,MAAO,CAAE,EAClB,QAAS,CAAE,MAAO,CAAE,CACtB,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAmDhB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,CACH,CAEQ,aAAaM,EAAsB,CACzC,OAAQA,EAAM,CACZ,IAAK,aACH,MAAO,GACT,IAAK,WACH,MAAO,GACT,IAAK,WACH,MAAO,GACT,IAAK,YACH,MAAO,GACT,IAAK,QACH,MAAO,GACT,IAAK,SACH,MAAO,GACT,IAAK,aACH,MAAO,GACT,QACE,MAAO,EACX,CACF,CAEQ,qBAAqBC,EAA0B,CACrD,GAAI,CAAC,KAAK,OAAO,qBACf,MAAM,IAAI,MAAM,2DAA2D,EAE7E,OAAO,KAAK,OAAO,qBAAqBA,CAAM,CAChD,CAEQ,kBAAkBF,EAAkC,CAC1D,IAAMG,EAAaH,EAAK,KAAK,EAAE,YAAY,EAC3C,GAAI,CAACG,EAAY,OAAO,KACxB,GAAI,KAAK,gBAAgB,IAAIA,CAAU,EACrC,OAAO,KAAK,gBAAgB,IAAIA,CAAU,EAE5C,IAAMC,EAAMC,GAA6B,IAAIF,CAAU,EACvD,GAAI,CAACC,EAAK,OAAO,KAEjB,IAAMZ,EAAgC,CAAE,SAAU,CAAE,MAAO,IAAK,CAAE,EAC5D,CAAE,MAAAjC,EAAO,OAAAC,CAAO,EAAI,KAAK,cAAc,EAC7CgC,EAAS,YAAc,CAAE,MAAO,CAACjC,EAAOC,CAAM,CAAE,EAChDgC,EAAS,OAAS,CAAE,MAAO,CAAC,EAAIjC,EAAO,EAAIC,CAAM,CAAE,EACnD,OAAO,QAAQ4C,EAAI,UAAY,CAAC,CAAC,EAAE,QAAQ,CAAC,CAACV,EAAKC,CAAK,IAAM,CAC3DH,EAASE,CAAG,EAAI,CAAE,MAAAC,CAAM,CAC1B,CAAC,EAED,IAAMJ,EAAW,KAAK,qBAAqB,CACzC,SAAAC,EACA,aAAc,KAAK,gBAAgB,EACnC,eAAgBY,EAAI,eACpB,YAAa,GACb,UAAW,GACX,WAAY,EACd,CAAC,EAED,YAAK,gBAAgB,IAAID,EAAYZ,CAAQ,EACtCA,CACT,CAEQ,eAAmD,CACzD,IAAMhC,EAAQ,KAAK,IAAI,EAAG,KAAK,MAAM,KAAK,MAAQ,KAAK,KAAK,CAAC,EACvDC,EAAS,KAAK,IAAI,EAAG,KAAK,MAAM,KAAK,OAAS,KAAK,KAAK,CAAC,EAC/D,MAAO,CAAE,MAAAD,EAAO,OAAAC,CAAO,CACzB,CAEQ,iBAA0B,CAChC,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAOT,CACF,EC3jBO,IAAM8C,GAAN,KAAuB,CAe5B,YAAYC,EAAwBC,EAAmB,CATvD,KAAQ,eAAgD,KACxD,KAAQ,YAA6C,IAAI,IACzD,KAAQ,QAAU,EAClB,KAAQ,cAAgB,YAAY,IAAI,EACxC,KAAQ,WAAa,KACrB,KAAQ,aAAe,EACvB,KAAQ,kBAAoB,EAC5B,KAAQ,YAAc,EAGpB,KAAK,OAASA,EACd,KAAK,WAAaD,EAClB,GAAM,CAAE,MAAAE,EAAO,OAAAC,CAAO,EAAIH,EAAU,sBAAsB,EAC1D,KAAK,OAASE,EACd,KAAK,QAAUC,EAEf,KAAK,UAAYF,EAAO,eAAe,CACrC,UAAW,GACX,MAAO,GACP,uBAAwB,EAC1B,CAAC,EACD,IAAMG,EAAc,KAAK,UACrB,OAAOA,EAAY,eAAkB,YACvCA,EAAY,cAAc,EAAU,CAAC,EAEvC,KAAK,UAAU,cAAc,OAAO,gBAAgB,EACpD,KAAK,UAAU,QAAQF,EAAOC,CAAM,EAEhC,KAAK,UAAU,YACjB,KAAK,UAAU,UAAU,QAAU,GAEvC,CAEO,QAAe,CACpB,KAAK,WAAW,YAAY,KAAK,UAAU,UAAU,CACvD,CAEO,OACLE,EACAC,EACAC,EAAwC,CAAC,EACnC,CACN,GAAIA,EAAc,SAAW,EAAG,CAC9B,KAAK,UAAU,OAAOF,EAAM,SAAS,EAAGC,EAAO,MAAM,EACrD,MACF,CAEA,IAAME,EAAW,KAAK,qBAAqB,EAC3C,GAAI,CAACA,GAAU,YAAY,EAAG,CAC5B,KAAK,UAAU,OAAOH,EAAM,SAAS,EAAGC,EAAO,MAAM,EACrD,MACF,CAEA,KAAK,SAAW,EAChB,KAAK,cAAcC,EAAc,OAAQC,CAAQ,EAEjD,IAAMC,EAAaJ,EAAM,cAAc,EACjCK,EAAa,IAAI,IACvBD,EAAW,QAASE,GAAQ,CAC1B,IAAMC,EAASD,EAAI,OACf,YAAaC,GACfF,EAAW,IAAIC,EAAI,OAAQC,EAAO,OAAO,CAE7C,CAAC,EAED,IAAMC,EAAc,IAAI,IACxBN,EAAc,QAASO,GAAW,CAChC,KAAK,sBAAsBA,EAAO,OAAQD,CAAW,CACvD,CAAC,EAEDJ,EAAW,QAASE,GAAQ,CACtBE,EAAY,IAAIF,EAAI,MAAM,GAC5B,KAAK,WAAWA,EAAI,OAAQ,EAAK,CAErC,CAAC,EAED,IAAMP,EAAc,KAAK,UACnBW,EAAgBX,EAAY,UAClCA,EAAY,UAAY,GACpBA,EAAY,iBACdA,EAAY,gBAAgB,IAAI,EAE9BA,EAAY,OACdA,EAAY,MAAM,GAAM,GAAM,EAAI,EAEpC,KAAK,UAAU,OAAOC,EAAM,SAAS,EAAGC,EAAO,MAAM,EAErDF,EAAY,UAAY,GAExBK,EAAW,QAASE,GAAQ,CAC1B,IAAMK,EAAkBN,EAAW,IAAIC,EAAI,MAAM,EAC7C,OAAOK,EAAoB,KAC7B,KAAK,WAAWL,EAAI,OAAQK,CAAe,CAE/C,CAAC,EAED,IAAMC,EAASR,EAAW,OAAQE,GAAQA,EAAI,KAAK,SAAS,OAAO,CAAC,EAC9DO,EAAiB,KAAK,eAAeZ,EAAO,OAAQG,CAAU,EAEpEF,EAAc,QAASO,GAAW,CAChC,IAAMK,EAAQ,KAAK,YAAY,IAAIL,EAAO,OAAO,EAAE,EAOnD,GALE,CAACA,EAAO,OACRK,GACAA,EAAM,aAAeL,EAAO,YAC5BK,EAAM,eAAiB,KAAK,aAEb,CACfA,EAAM,cAAgB,KAAK,QAC3BX,EAAS,eAAeW,EAAM,MAAM,EACpC,MACF,CAEA,IAAMC,EAAU,KAAK,oBACnBN,EAAO,OAAO,GACdA,EAAO,OACT,EAEMO,EAAU,IAAI,IACpB,KAAK,sBAAsBP,EAAO,OAAQO,CAAO,EAEjD,IAAIC,EAA4D,CAAC,EAC7DC,EAAmC,KAEvC,GAAIL,EAAgB,CAClB,IAAMM,EAAUV,EAAO,OAAO,kBAAkB,EAChDQ,EAAgB,KAAK,eAAeE,EAASP,EAAQ,KAAK,WAAW,EACrEM,EAAoB,KAAK,eAAejB,EAAO,OAAQ,KAAK,WAAW,CACzE,MACEG,EAAW,QAASE,GAAQ,CAE1B,GADwBD,EAAW,IAAIC,EAAI,MAAM,IACzB,GAAO,CAC7B,KAAK,WAAWA,EAAI,OAAQ,EAAK,EACjC,MACF,CAEA,GAAIA,EAAI,KAAK,SAAS,OAAO,EAAG,CAC9B,KAAK,WAAWA,EAAI,OAAQ,EAAI,EAChC,MACF,CAEA,KAAK,WAAWA,EAAI,OAAQU,EAAQ,IAAIV,EAAI,MAAM,CAAC,CACrD,CAAC,EAGH,IAAMc,EAAQjB,EAAS,cAAc,EACjCJ,EAAY,iBACdA,EAAY,gBAAgBqB,CAAK,EAE/BrB,EAAY,OACdA,EAAY,MAAM,GAAM,GAAM,EAAI,EAEpC,KAAK,UAAU,OAAOC,EAAM,SAAS,EAAGC,EAAO,MAAM,EAErD,IAAMoB,EAASlB,EAAS,aAAaiB,EAAOL,EAAS,KAAK,YAAY,EAClEhB,EAAY,iBACdA,EAAY,gBAAgB,IAAI,EAElCI,EAAS,eAAekB,CAAM,EAE1BR,IACF,KAAK,iBAAiBI,CAAa,EAC/BC,IAAsB,MACxB,KAAK,mBAAmBjB,EAAO,OAAQiB,CAAiB,GAIxDG,IAAWD,GACbjB,EAAS,cAAciB,CAAK,EAG9B,IAAME,EAA0B,CAC9B,OAAQD,EACR,WAAYZ,EAAO,WACnB,cAAe,KAAK,QACpB,aAAc,KAAK,YACrB,EACMc,EAAW,KAAK,YAAY,IAAId,EAAO,OAAO,EAAE,EAClDc,GAAYA,EAAS,SAAWF,GAClClB,EAAS,cAAcoB,EAAS,MAAM,EAExC,KAAK,YAAY,IAAId,EAAO,OAAO,GAAIa,CAAK,CAC9C,CAAC,EAEIT,GACHT,EAAW,QAASE,GAAQ,CAC1B,IAAMK,EAAkBN,EAAW,IAAIC,EAAI,MAAM,EAC7C,OAAOK,EAAoB,KAC7B,KAAK,WAAWL,EAAI,OAAQK,CAAe,CAE/C,CAAC,EAGHZ,EAAY,UAAYW,EAExB,KAAK,WAAW,CAClB,CAEO,OAAOT,EAA8B,CAC1C,GAAM,CAAE,MAAAJ,EAAO,OAAAC,CAAO,EAAI,KAAK,WAAW,sBAAsB,EAChE,KAAK,OAASD,EACd,KAAK,QAAUC,EACf,KAAK,UAAU,QAAQD,EAAOC,CAAM,EACpCG,EAAO,OAAOJ,EAAOC,CAAM,EAC3B,KAAK,gBAAgB,OAAOD,EAAOC,CAAM,EACzC,KAAK,sBAAsB,CAC7B,CAEA,IAAW,OAAgB,CACzB,OAAO,KAAK,MACd,CAEA,IAAW,QAAiB,CAC1B,OAAO,KAAK,OACd,CAEA,IAAW,UAAwB,CACjC,OAAO,KAAK,SACd,CAEO,SAAgB,CACrB,KAAK,UAAU,QAAQ,EACvB,KAAK,gBAAgB,QAAQ,EAC7B,KAAK,YAAY,MAAM,CACzB,CAEQ,sBAAsD,CAC5D,OAAK,KAAK,wBAAwB,GAG7B,KAAK,iBACR,KAAK,eAAiB,IAAI0B,GACxB,KAAK,OACL,KAAK,UACL,KAAK,OACL,KAAK,OACP,EACA,KAAK,eAAe,SAAS,KAAK,YAAY,GAEzC,KAAK,gBAXH,IAYX,CAEQ,yBAAmC,CACzC,OACE,OAAO,KAAK,OAAO,oBAAuB,YAC1C,OAAO,KAAK,OAAO,sBAAyB,YAC5C,OAAQ,KAAK,UAAkB,iBAAoB,UAEvD,CAEQ,sBACNC,EACAC,EACM,CACNA,EAAI,IAAID,EAAO,MAAM,EACrBA,EAAO,SAAS,QAASE,GAAU,KAAK,sBAAsBA,EAAOD,CAAG,CAAC,CAC3E,CAEQ,WAAWD,EAAmBG,EAAwB,CAC5D,IAAMrB,EAASkB,EACX,YAAalB,IACfA,EAAO,QAAUqB,EAErB,CAEQ,gBAAgBC,EAA+C,CACrE,GAAI,CAACA,GAAM,CAAC,KAAK,QAAU,CAAC,KAAK,QAAS,MAAO,CAAC,GAAK,EAAG,EAC1D,IAAMC,EAAUD,EAAW,cACrBE,EAAOD,EAASA,EAAO,KAAOD,EAAG,sBAAsB,EACvDG,GAAMD,EAAK,KAAOA,EAAK,MAAQ,GAAK,KAAK,OACzCE,EAAK,GAAKF,EAAK,IAAMA,EAAK,OAAS,GAAK,KAAK,QAC7CG,EAASC,GAAkB,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGA,CAAK,CAAC,EAC/D,MAAO,CAACD,EAAMF,CAAE,EAAGE,EAAMD,CAAE,CAAC,CAC9B,CAEQ,oBACNJ,EACAd,EACwB,CACxB,GAAI,CAACA,EAAQ,KAAMqB,GAAWA,EAAO,OAAS,QAAQ,EACpD,OAAOrB,EAET,IAAMsB,EAAS,KAAK,gBAAgBR,CAAE,EAClCS,EAAU,GACRC,EAAOxB,EAAQ,IAAKqB,GAAW,CAEnC,GADIA,EAAO,OAAS,UAChBA,EAAO,UAAY,YAAaA,EAAO,SAAU,OAAOA,EAC5D,IAAMI,EAAW,CAAE,GAAIJ,EAAO,UAAY,CAAC,EAAI,QAASC,CAAO,EAC/D,OAAAC,EAAU,GACH,CAAE,GAAGF,EAAQ,SAAAI,CAAS,CAC/B,CAAC,EACD,OAAOF,EAAUC,EAAOxB,CAC1B,CAEQ,cAAc0B,EAAqBtC,EAAwC,CACjF,IAAMuC,EAAM,YAAY,IAAI,EACtBC,EAAK,KAAK,IAAI,GAAKD,EAAM,KAAK,aAAa,EACjD,KAAK,cAAgBA,EACrB,KAAK,WAAa,KAAK,WAAa,GAAMC,EAAK,GAE/C,IAAMC,EAAM,IAAO,KAAK,WAClBC,EAAa,KAAK,IAAI,IAAM,EAAI,KAAK,IAAI,GAAKJ,EAAc,GAAI,CAAC,EACnEK,EAAcD,EAEdD,EAAM,KAAIE,EAAc,KAAK,IAAI,IAAMD,EAAa,EAAG,GACvDD,EAAM,KAAIE,EAAc,KAAK,IAAI,IAAMD,EAAa,EAAG,GACvDD,EAAM,KAAIE,EAAc,KAAK,IAAI,EAAGD,EAAa,GAAI,GAErD,KAAK,IAAIC,EAAc,KAAK,YAAY,GAAK,KAAQJ,EAAM,KAAK,kBAAoB,MACtF,KAAK,aAAeI,EACpB,KAAK,kBAAoBJ,EACzBvC,EAAS,SAAS,KAAK,YAAY,EACnC,KAAK,sBAAsB,EAE/B,CAEQ,uBAA8B,CAC/B,KAAK,iBACV,KAAK,YAAY,QAASmB,GAAU,CAClC,KAAK,gBAAgB,cAAcA,EAAM,MAAM,CACjD,CAAC,EACD,KAAK,YAAY,MAAM,EACzB,CAEQ,YAAmB,CACzB,GAAI,CAAC,KAAK,eAAgB,OAC1B,IAAMyB,EAAS,IACf,KAAK,YAAY,QAAQ,CAACzB,EAAO0B,IAAQ,CACnC,KAAK,QAAU1B,EAAM,cAAgByB,IACvC,KAAK,gBAAgB,cAAczB,EAAM,MAAM,EAC/C,KAAK,YAAY,OAAO0B,CAAG,EAE/B,CAAC,CACH,CAEQ,eAAe/C,EAAagD,EAAgD,CAClF,MAAI,CAAChD,GAAQ,QAAU,OAAOA,EAAO,OAAO,KAAQ,WAAmB,GAChEgD,EAAQ,KAAM3C,GAAQ,KAAK,UAAUA,EAAI,MAAM,CAAC,CACzD,CAEQ,UAAUmB,EAAsB,CACtC,OAAOA,GAAQ,QAAU,OAAOA,EAAO,OAAO,KAAQ,UACxD,CAEQ,eACNwB,EACArC,EACAsC,EAC4C,CAC5C,IAAMC,EAAc,IAAI,IAClBC,EAAQ,CAAC9C,EAAgB+C,IAA8B,CAC3D,IAAM9C,EAASD,EACV,KAAK,UAAUC,CAAM,IACrB4C,EAAY,IAAI7C,CAAG,GACtB6C,EAAY,IAAI7C,EAAKC,EAAO,OAAO,IAAI,EAErC8C,IAAY,MACd9C,EAAO,OAAO,IAAI2C,CAAK,EAEvB3C,EAAO,OAAO,OAAO2C,CAAK,EAE9B,EAEA,OAAAD,EAAQ,QAAS3C,GAAQ8C,EAAM9C,EAAK,KAAK,CAAC,EAC1CM,EAAO,QAAS0C,GAAUF,EAAME,EAAM,OAAQ,QAAQ,CAAC,EAEhD,MAAM,KAAKH,EAAY,QAAQ,CAAC,EAAE,IAAI,CAAC,CAAC1B,EAAQ8B,CAAI,KAAO,CAAE,OAAA9B,EAAQ,KAAA8B,CAAK,EAAE,CACrF,CAEQ,iBAAiBC,EAA2D,CAClFA,EAAQ,QAASlC,GAAU,CACzB,IAAMf,EAASe,EAAM,OACjB,KAAK,UAAUf,CAAM,IACvBA,EAAO,OAAO,KAAOe,EAAM,KAE/B,CAAC,CACH,CAEQ,eAAerB,EAAaiD,EAA8B,CAChE,GAAI,CAACjD,GAAQ,QAAU,OAAOA,EAAO,OAAO,KAAQ,WAAY,OAAO,KACvE,IAAMwD,EAAOxD,EAAO,OAAO,KAC3B,OAAAA,EAAO,OAAO,IAAIiD,CAAK,EAChBO,CACT,CAEQ,mBAAmBxD,EAAasD,EAAoB,CACtDtD,GAAQ,SACVA,EAAO,OAAO,KAAOsD,EAEzB,CACF,EC9YO,IAAMG,GAAN,KAAqB,CAsB1B,YACEC,EACAC,EACAC,EACAC,EACAC,EAA6E,CAAC,EAC9E,CArBF,KAAQ,UAA4C,CAAC,EAMrD,KAAQ,UAA8B,CAAC,EACvC,KAAQ,kBAAwC,KAChD,KAAQ,cAAoC,KAc1C,KAAK,GAAKJ,EACV,KAAK,KAAOC,EACZ,KAAK,QAAUC,EACf,KAAK,OAASC,EACd,KAAK,UAAYC,EAAQ,SACzB,KAAK,UAAYA,EAAQ,SACzB,KAAK,SAAWA,EAAQ,QACxB,KAAK,YAAcD,EAAO,iBAAiB,EAC3C,KAAK,cAAgBA,EAAO,cAAc,EAC1C,KAAK,MAAQA,EAAO,WAAW,EAC/B,KAAK,kBAAkB,CACzB,CAtBA,IAAW,UAA6B,CACtC,OAAO,KAAK,SACd,CAsBA,IAAW,QAAoB,CAC7B,OAAO,KAAK,OACd,CAEA,IAAW,UAAoC,CAC7C,OAAO,KAAK,SACd,CAEA,IAAW,cAA2B,CACpC,OAAO,KAAK,cAAc,MAAM,CAClC,CAEA,IAAW,aAAuB,CAChC,OAAO,KAAK,MAAM,MAAM,CAC1B,CAEO,SAASE,EAA6B,CAC3C,KAAK,UAAU,KAAKA,CAAK,EACzB,KAAK,OAAO,IAAIA,EAAM,MAAM,EAC5B,KAAK,oBAAoB,EACzB,KAAK,uBAAuB,CAC9B,CAEO,gBAA6B,CAClC,OAAO,KAAK,QAAQ,YAAY,MAAM,CACxC,CAEO,kBAA+B,CACpC,OAAO,KAAK,OAAO,cAAc,EAAE,sBAAsB,KAAK,QAAQ,WAAW,CACnF,CAEO,wBAAkC,CACvC,GAAI,CAAC,KAAK,qBAAsB,CAC9B,IAAMC,EAAgB,KAAK,OAAO,MAAM,MAAM,EAC9C,KAAK,OAAO,MAAM,IAAI,EAAG,EAAG,CAAC,EAC7B,KAAK,OAAO,kBAAkB,EAAI,EAClC,KAAK,qBAAuB,KAAK,OAAO,8BAA8B,KAAK,MAAM,EACjF,KAAK,OAAO,MAAM,KAAKA,CAAa,EACpC,KAAK,OAAO,kBAAkB,EAAI,CACpC,CACA,OAAO,KAAK,qBAAsB,MAAM,CAC1C,CAEO,wBAAwBC,EAA0B,CACvD,IAAMC,EAAM,KAAK,OAAO,cAAc,EAChCC,EAAO,KAAK,OAAO,iBAAiB,EACpCC,EAAQ,KAAK,OAAO,cAAc,EACxCH,EAAO,UAAUC,EAAKC,EAAMC,CAAK,EACjC,KAAK,QAAQ,SAAS,KAAKF,CAAG,EAC9B,KAAK,QAAQ,WAAW,KAAKC,CAAI,EACjC,KAAK,QAAQ,MAAM,KAAKC,CAAK,EAC7B,KAAK,QAAQ,aAAa,EAC1B,KAAK,QAAQ,kBAAkB,CACjC,CAEO,oBACLC,EACAC,EACAF,EACM,CACN,KAAK,QAAQ,SAAS,KAAKC,CAAQ,EACnC,KAAK,QAAQ,WAAW,KAAKC,CAAU,EACvC,KAAK,QAAQ,MAAM,KAAKF,CAAK,EAC7B,KAAK,QAAQ,aAAa,EAC1B,KAAK,QAAQ,kBAAkB,CACjC,CAEA,IAAW,WAAWE,EAA2B,CAC/C,KAAK,YAAY,KAAKA,CAAU,EAChC,KAAK,QAAQ,WAAW,KAAK,KAAK,WAAW,EAC7C,KAAK,QAAQ,kBAAkB,CACjC,CAEA,IAAW,SAASD,EAAsB,CACxC,KAAK,QAAQ,SAAS,KAAKA,CAAQ,CACrC,CAEA,IAAW,MAAMD,EAAmB,CAClC,KAAK,QAAQ,MAAM,KAAKA,CAAK,CAC/B,CAEA,IAAW,SAASG,EAAiB,CACnC,KAAK,QAAQ,SAAS,KAAKA,CAAK,CAClC,CAEA,IAAW,QAAQC,EAAe,CAChC,IAAMC,EAAM,KAAK,QACbA,EAAI,UAAY,YAAaA,EAAI,WACnCA,EAAI,SAAS,QAAUD,EAE3B,CAEA,IAAW,UAAUA,EAAe,CAClC,IAAMC,EAAM,KAAK,QACbA,EAAI,UAAY,cAAeA,EAAI,WACrCA,EAAI,SAAS,UAAYD,EAE7B,CAEA,IAAW,UAAUA,EAAe,CAClC,IAAMC,EAAM,KAAK,QACbA,EAAI,UAAY,cAAeA,EAAI,WACrCA,EAAI,SAAS,UAAYD,EAE7B,CAEA,IAAW,QAAQE,EAAc,CAC/B,KAAK,SAAWA,EACX,KAAK,QAAgB,QAAUA,GAAS,cAC3CA,EAAQ,aAAa,KAAK,OAAO,CAErC,CAEA,IAAW,SAASC,EAAmC,CACrD,KAAK,UAAYA,CACnB,CAEA,IAAW,SAASC,EAAmC,CACrD,KAAK,UAAYA,CACnB,CAEO,mBAA0B,CAC/B,KAAK,MAAM,cAAc,KAAK,OAAO,EACrC,KAAK,MAAM,QAAQ,KAAK,aAAa,CACvC,CAEO,SAAgB,CACrB,KAAK,uBAAuB,KAAK,OAAO,EACxC,KAAK,UAAU,UAAU,EACzB,KAAK,WAAW,QAAQ,EACxB,KAAK,WAAW,QAAQ,EACxB,KAAK,cAAgB,IACvB,CAEO,gBAA8B,CACnC,GAAI,KAAK,kBAAmB,OAAO,KAAK,kBACxC,IAAMC,EAAsB,CAAC,EACvBC,EAAQC,GAA8B,CAC1CF,EAAO,KAAKE,EAAI,MAAM,EACtBA,EAAI,SAAS,QAAShB,GAAUe,EAAKf,CAAK,CAAC,CAC7C,EACA,OAAAe,EAAK,IAAI,EACT,KAAK,kBAAoBD,EAClBA,CACT,CAEO,mBAAiC,CACtC,GAAI,KAAK,cAAe,OAAO,KAAK,cACpC,IAAMA,EAAsB,CAAC,EACvBG,EAAS,KAAK,QACpB,OAAAH,EAAO,KAAK,KAAK,OAAO,EACpB,OAAOG,EAAO,UAAa,YAC7BA,EAAO,SAAUjB,GAAe,CAC1BA,GAASA,IAAU,KAAK,SAC1Bc,EAAO,KAAKd,CAAkB,CAElC,CAAC,EAEH,KAAK,cAAgBc,EACdA,CACT,CAEQ,qBAA4B,CAClC,KAAK,kBAAoB,IAC3B,CAEQ,wBAA+B,CACrC,KAAK,cAAgB,IACvB,CAEQ,uBAAuBjB,EAAyB,CACtD,IAAMoB,EAASpB,EACXoB,GAAQ,UAAU,SACpBA,EAAO,SAAS,QAAQ,EAE1B,IAAML,EAAWK,GAAQ,SACrB,MAAM,QAAQL,CAAQ,EACxBA,EAAS,QAASF,GAAQA,GAAK,UAAU,CAAC,EACjCE,GAAU,SACnBA,EAAS,QAAQ,EAEf,OAAOK,GAAQ,UAAa,YAC9BA,EAAO,SAAUjB,GAAe,CAC1BA,GAAO,UAAU,SACnBA,EAAM,SAAS,QAAQ,EAEzB,IAAMkB,EAAWlB,GAAO,SACpB,MAAM,QAAQkB,CAAQ,EACxBA,EAAS,QAASR,GAAaA,GAAK,UAAU,CAAC,EACtCQ,GAAU,SACnBA,EAAS,QAAQ,CAErB,CAAC,CAEL,CACF,ECzPO,IAAMC,GAAN,KAAkB,CAIvB,YAAYC,EAAiB,CAC3B,KAAK,SAAYA,EAAW,mBAAmB,EAC/C,KAAK,MAAQ,iBAAiBA,CAAE,CAClC,CAEA,WAAWC,EAAcC,EAA0B,CACjD,IAAMC,EAAW,KAAK,UAAU,MAAMF,CAAI,EAC1C,GAA8BE,GAAa,KAAM,CAC/C,IAAMC,EAAM,OAAOD,GAAa,SAAYA,EAAiB,MAAQA,EAC/DE,EAAM,OAAOD,GAAQ,SAAWA,EAAM,OAAO,WAAWA,CAAG,EACjE,GAAI,CAAC,OAAO,MAAMC,CAAG,EAAG,OAAOA,CACjC,CACA,IAAMA,EAAM,OAAO,WAAW,KAAK,MAAM,iBAAiBJ,CAAI,CAAC,EAC/D,OAAO,OAAO,MAAMI,CAAG,EAAIH,EAAWG,CACxC,CAEA,WAAWJ,EAAcC,EAAW,GAAY,CAC9C,IAAMC,EAAW,KAAK,UAAU,MAAMF,CAAI,EACpCG,EAAMD,GAAY,OAAOA,GAAa,SAAYA,EAAiB,MAAQA,EACjF,GAAI,OAAOC,GAAQ,SAAU,OAAO,KAAK,YAAYA,EAAI,KAAK,CAAC,GAAKF,EACpE,IAAMI,EAAM,KAAK,MAAM,iBAAiBL,CAAI,EAAE,KAAK,EACnD,OAAO,KAAK,YAAYK,CAAG,GAAKJ,CAClC,CAEQ,YAAYK,EAAuB,CACzC,OACGA,EAAM,WAAW,GAAG,GAAKA,EAAM,SAAS,GAAG,GAC3CA,EAAM,WAAW,GAAG,GAAKA,EAAM,SAAS,GAAG,EAErCA,EAAM,MAAM,EAAG,EAAE,EAEnBA,CACT,CAEA,YAAYN,EAAcC,EAAW,GAAgB,CACnD,IAAMI,EAAM,KAAK,WAAWL,EAAM,EAAE,EACpC,GAAI,CAACK,EAAK,OAAOJ,EACjB,IAAMM,EAAOF,EAAI,YAAY,EAC7B,OAAOE,IAAS,QAAUA,IAAS,KAAOA,IAAS,MAC/C,GACAA,IAAS,SAAWA,IAAS,KAAOA,IAAS,KAC7C,GACAN,CACN,CACF,EAEO,SAASO,GAAgBT,EAAiBC,EAAcC,EAA0B,CAEvF,IAAMC,EADYH,EAAW,mBAAmB,GACrB,MAAMC,CAAI,EACrC,GAAIE,IAAa,OAAW,CAC1B,GAAI,OAAOA,GAAa,SAAU,OAAOA,EACzC,GAAI,OAAOA,GAAa,SAAU,CAChC,IAAMO,EAAS,OAAO,WAAWP,CAAQ,EACzC,GAAI,CAAC,OAAO,MAAMO,CAAM,EAAG,OAAOA,CACpC,CACA,GAAIP,GAAY,OAAOA,GAAa,SAAU,CAC5C,IAAMI,EAASJ,EAAiB,MAChC,GAAI,OAAOI,GAAU,SAAU,OAAOA,EACtC,GAAI,OAAOA,GAAU,SAAU,CAC7B,IAAMG,EAAS,OAAO,WAAWH,CAAK,EACtC,GAAI,CAAC,OAAO,MAAMG,CAAM,EAAG,OAAOA,CACpC,CACF,CACF,CAGA,IAAMJ,EADQ,iBAAiBN,CAAE,EACf,iBAAiBC,CAAI,EACjCS,EAAS,OAAO,WAAWJ,CAAG,EACpC,OAAO,OAAO,MAAMI,CAAM,EAAIR,EAAWQ,CAC3C,CAEA,SAASC,GAAYJ,EAAuB,CAC1C,OACGA,EAAM,WAAW,GAAG,GAAKA,EAAM,SAAS,GAAG,GAC3CA,EAAM,WAAW,GAAG,GAAKA,EAAM,SAAS,GAAG,EAErCA,EAAM,MAAM,EAAG,EAAE,EAEnBA,CACT,CAEO,SAASK,GAAgBZ,EAAiBC,EAAcC,EAAW,GAAY,CAEpF,IAAMC,EADYH,EAAW,mBAAmB,GACrB,MAAMC,CAAI,EACrC,GAAI,OAAOE,GAAa,SACtB,OAAOQ,GAAYR,EAAS,KAAK,CAAC,EAEpC,GAAIA,GAAY,OAAOA,GAAa,SAAU,CAC5C,IAAMI,EAASJ,EAAiB,MAChC,GAAI,OAAOI,GAAU,SACnB,OAAOI,GAAYJ,EAAM,KAAK,CAAC,CAEnC,CACA,IAAMM,EAAQ,iBAAiBb,CAAE,EAAE,iBAAiBC,CAAI,EAExD,OADeY,EAAQF,GAAYE,EAAM,KAAK,CAAC,EAAI,KAClCX,CACnB,CAEO,SAASY,GAAiBd,EAAiBC,EAAcC,EAAW,GAAgB,CACzF,IAAMI,EAAMM,GAAgBZ,EAAIC,EAAM,EAAE,EACxC,GAAI,CAACK,EAAK,OAAOJ,EACjB,IAAMa,EAAaT,EAAI,YAAY,EAAE,KAAK,EAC1C,OAAIS,IAAe,QAAUA,IAAe,KAAOA,IAAe,MAAc,GAC5EA,IAAe,SAAWA,IAAe,KAAOA,IAAe,KAAa,GACzEb,CACT,CAEO,SAASc,GAAchB,EAAyB,CACrD,IAAMiB,EAAYjB,EAAW,mBAAmB,EAC5CM,EAAM,GACJH,EAAWc,GAAU,MAAM,UAAU,EAC3C,GAAId,IAAa,QACf,GAAI,OAAOA,GAAa,SACtBG,EAAMH,UACGA,GAAY,OAAOA,GAAa,SAAU,CACnD,IAAMI,EAASJ,EAAiB,MAC5B,OAAOI,GAAU,WAAUD,EAAMC,EACvC,EAEF,OAAKD,IACHA,EAAM,iBAAiBN,CAAE,EAAE,iBAAiB,UAAU,GAAK,IAE7DM,EAAMA,EAAI,KAAK,EACRA,CACT,CC3DO,IAAMY,GAAN,KAAqC,CAI1C,OAAO,SAASC,EAAoD,CAClE,IAAMC,EAAOD,EAAW,KAAK,KAAK,EAAE,YAAY,EAChD,GAAI,CAACC,EACH,MAAM,IAAI,MAAM,8CAA8C,EAEhE,KAAK,UAAU,IAAIA,EAAM,CAAE,GAAGD,EAAY,KAAAC,CAAK,CAAC,EAChD,KAAK,2BAA2BD,CAAU,CAC5C,CAEA,OAAe,2BAA2BA,EAAoD,CAC5F,IAAME,EAAO,WAAmB,IAChC,GAAI,CAACA,GAAK,iBAAkB,OAE5B,IAAMC,EAAWH,EAAW,UAAY,CAAC,EACzC,QAAWI,KAAO,OAAO,OAAOD,CAAQ,EAAG,CACzC,IAAME,EAASD,EAAI,KAAK,KAAK,EAE7B,GADI,CAACC,GAAU,CAACA,EAAO,WAAW,IAAI,GAClC,KAAK,kBAAkB,IAAIA,CAAM,EAAG,SAExC,IAAMC,EAAS,KAAK,iBAAiBF,EAAI,IAAI,EAE7C,GAAI,CACFF,EAAI,iBAAiB,CACnB,KAAMG,EACN,OAAAC,EACA,SAAU,GACV,aAAc,KAAK,uBAAuBF,CAAG,CAC/C,CAAC,EACD,KAAK,kBAAkB,IAAIC,CAAM,CACnC,MAAc,CAAC,CACjB,CACF,CAEA,OAAe,iBAAiBE,EAA2B,CACzD,OAAQA,EAAM,CACZ,IAAK,QACH,MAAO,UACT,IAAK,QACL,IAAK,MACH,MAAO,WACT,QACE,MAAO,GACX,CACF,CAEA,OAAe,uBAAuBH,EAAgC,CACpE,OAAIA,EAAI,OAAS,QACX,OAAOA,EAAI,OAAU,SAAiBA,EAAI,MACvC,UAELA,EAAI,OAAS,SAAWA,EAAI,OAAS,MAChC,OAAOA,EAAI,OAAU,SAAW,OAAOA,EAAI,KAAK,EAAI,IAEtD,SACT,CAEA,OAAO,IAAIH,EAA4D,CACrE,OAAO,KAAK,UAAU,IAAIA,EAAK,KAAK,EAAE,YAAY,CAAC,CACrD,CAEA,OAAO,IAAIA,EAAuB,CAChC,OAAO,KAAK,UAAU,IAAIA,EAAK,KAAK,EAAE,YAAY,CAAC,CACrD,CAEA,OAAO,MAA2C,CAChD,OAAO,MAAM,KAAK,KAAK,UAAU,OAAO,CAAC,CAC3C,CAEA,OAAO,WAAWA,EAAuB,CACvC,OAAO,KAAK,UAAU,OAAOA,EAAK,KAAK,EAAE,YAAY,CAAC,CACxD,CACF,EA3EaF,GACI,UAA2D,IAAI,IADnEA,GAEI,kBAAiC,IAAI,ICzC/C,SAASS,GACdC,EACAC,EACK,CACL,GAAIA,GAAa,MAAkCA,IAAa,IAAMA,IAAa,OACjF,OAAOD,EAAI,MAGb,IAAME,EAAUD,EAAS,KAAK,EAE9B,OAAQD,EAAI,KAAM,CAChB,IAAK,QACL,IAAK,MAAO,CACV,IAAMG,EAAM,WAAWD,CAAO,EAC9B,OAAO,MAAMC,CAAG,EAAIH,EAAI,MAAQG,CAClC,CACA,IAAK,OAAQ,CACX,IAAMC,EAAQF,EAAQ,MAAM,QAAQ,EAAE,IAAKG,GAAM,WAAWA,EAAE,KAAK,CAAC,CAAC,EACrE,OAAID,EAAM,QAAU,GAAKA,EAAM,MAAOE,GAAM,CAAC,MAAMA,CAAC,CAAC,EAC5C,CAACF,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAErBJ,EAAI,KACb,CACA,IAAK,OAAQ,CACX,IAAMI,EAAQF,EAAQ,MAAM,QAAQ,EAAE,IAAKG,GAAM,WAAWA,EAAE,KAAK,CAAC,CAAC,EACrE,OAAID,EAAM,QAAU,GAAKA,EAAM,MAAOE,GAAM,CAAC,MAAMA,CAAC,CAAC,EAC5C,CAACF,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAE/BJ,EAAI,KACb,CACA,IAAK,OAAQ,CACX,IAAMI,EAAQF,EAAQ,MAAM,QAAQ,EAAE,IAAKG,GAAM,WAAWA,EAAE,KAAK,CAAC,CAAC,EACrE,OAAID,EAAM,QAAU,GAAKA,EAAM,MAAOE,GAAM,CAAC,MAAMA,CAAC,CAAC,EAC5C,CAACF,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAEzCJ,EAAI,KACb,CACA,IAAK,QACH,OAAOO,GAAgBL,CAAO,GAAKF,EAAI,MAEzC,IAAK,UAAW,CACd,IAAMQ,EAAQN,EAAQ,MAAM,wBAAwB,EACpD,OAAOM,EAAQA,EAAM,CAAC,EAAIN,GAAWF,EAAI,KAC3C,CACA,QACE,OAAOA,EAAI,KACf,CACF,CAEA,SAASO,GAAgBE,EAAgD,CACvE,GAAIA,EAAM,WAAW,GAAG,EAAG,CACzB,IAAMC,EAAMD,EAAM,MAAM,CAAC,EACzB,GAAIC,EAAI,SAAW,EAAG,CACpB,IAAMC,EAAI,SAASD,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAG,EAAE,EAAI,IACpCE,EAAI,SAASF,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAG,EAAE,EAAI,IACpCG,EAAI,SAASH,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAG,EAAE,EAAI,IAC1C,MAAO,CAACC,EAAGC,EAAGC,CAAC,CACjB,CACA,GAAIH,EAAI,SAAW,EAAG,CACpB,IAAMC,EAAI,SAASD,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IACpCE,EAAI,SAASF,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IACpCG,EAAI,SAASH,EAAI,MAAM,EAAG,CAAC,EAAG,EAAE,EAAI,IAC1C,MAAO,CAACC,EAAGC,EAAGC,CAAC,CACjB,CACF,CAEA,IAAMC,EAAWL,EAAM,MAAM,yCAAyC,EACtE,OAAIK,EACK,CAAC,SAASA,EAAS,CAAC,CAAC,EAAI,IAAK,SAASA,EAAS,CAAC,CAAC,EAAI,IAAK,SAASA,EAAS,CAAC,CAAC,EAAI,GAAG,EAGxF,IACT,CAEO,SAASC,GACdC,EACAC,EACAC,EACqB,CACrB,IAAMC,EAA8B,CAAC,EAErC,GAAIH,EAAW,MAAO,CACpB,IAAMI,EAASJ,EAAW,MAAMC,EAASC,CAAK,EAC9C,OAAO,OAAOC,EAAQC,CAAM,CAC9B,CAEA,GAAIJ,EAAW,SACb,OAAW,CAACK,EAAKrB,CAAG,IAAK,OAAO,QAAQgB,EAAW,QAAQ,EACzD,GAAIhB,EAAI,IAAK,CACX,IAAMC,EAAWiB,EAAM,iBAAiBlB,EAAI,GAAG,EAAE,KAAK,EACtDmB,EAAOE,CAAG,EAAItB,GAAkBC,EAAKC,CAAQ,CAC/C,MAAaoB,KAAOF,IAClBA,EAAOE,CAAG,EAAIrB,EAAI,OAKxB,OAAOmB,CACT,CAEO,SAASG,GAAgBC,EAAoD,CAClF,IAAMC,EAAU,IAAI,IAEpB,QAAWC,KAAaF,EAAY,CAClC,IAAMG,EAAOF,EAAQ,IAAIC,EAAU,KAAK,GAAK,CAAC,EAC9CC,EAAK,KAAKD,CAAS,EACnBD,EAAQ,IAAIC,EAAU,MAAOC,CAAI,CACnC,CAEA,IAAMP,EAAS,IAAI,IAEnB,OAAW,CAACQ,EAAOD,CAAI,IAAKF,EAAS,CACnC,IAAMI,EAASF,EAAK,KAAK,CAAC,EAAGb,KAAO,EAAE,OAAS,IAAMA,EAAE,OAAS,EAAE,EAClEM,EAAO,IAAIQ,EAAOC,EAAO,IAAKC,GAAMA,EAAE,IAAI,EAAE,KAAK;AAAA,CAAI,CAAC,CACxD,CAEA,OAAOV,CACT,CChIO,IAAMW,GAAN,KAAoB,CAgBzB,YAAYC,EAAmBC,EAAgC,CAAC,EAAG,CAdnE,KAAQ,SAAwC,IAAI,IACpD,KAAQ,aAAiC,CAAC,EAC1C,KAAQ,YAAwC,IAAI,IACpD,KAAQ,mBAAqD,IAAI,IAIjE,KAAQ,kBAAiD,IAAI,IAQ3D,KAAK,OAASD,EACd,KAAK,aAAeC,EAAQ,YAC5B,KAAK,oBAAsBA,EAAQ,mBACnC,KAAK,OAASD,EAAO,YAAY,CACnC,CATA,IAAW,aAAgC,CACzC,OAAO,KAAK,YACd,CASO,gBAAgBE,EAA0C,CAC/D,KAAK,cAAgBA,CACvB,CAEO,UAAqB,CAC1B,OAAO,KAAK,MACd,CAEO,UAAUC,EAAwC,CACvD,OAAO,KAAK,SAAS,IAAIA,CAAE,CAC7B,CAEO,oBAAoBC,EAAkD,CAC3E,OAAW,CAACD,EAAIE,CAAE,IAAK,KAAK,YAC1B,GAAIA,IAAOD,EACT,OAAO,KAAK,SAAS,IAAID,CAAE,CAIjC,CAEO,eAAkC,CACvC,IAAMG,EAA2B,CAAC,EAC5BC,EAAQC,GAA8B,CAC1CF,EAAO,KAAKE,CAAG,EACfA,EAAI,SAAS,QAASC,GAAUF,EAAKE,CAAK,CAAC,CAC7C,EACA,YAAK,aAAa,QAASD,GAAQD,EAAKC,CAAG,CAAC,EACrCF,CACT,CAEO,UAAUH,EAAqB,CACpC,OAAO,KAAK,SAAS,IAAIA,CAAE,CAC7B,CAEO,aAAaA,EAAqB,CACvC,IAAMK,EAAM,KAAK,SAAS,IAAIL,CAAE,EAChC,GAAIK,EAAK,CACP,IAAMJ,EAAU,KAAK,YAAY,IAAID,CAAE,EACvC,OAAIC,GAAW,KAAK,eAClB,KAAK,cAAc,eAAeA,EAASI,CAAG,EAGhD,KAAK,OAAO,OAAOA,EAAI,MAAM,EAC7B,KAAK,SAAS,OAAOL,CAAE,EACvB,KAAK,YAAY,OAAOA,CAAE,EAC1B,KAAK,aAAe,KAAK,aAAa,OAAQO,GAASA,IAASF,CAAG,EACnEA,EAAI,QAAQ,EACL,EACT,CACA,MAAO,EACT,CAEO,kBAAkBG,EAA4B,CACnD,IAAMC,EAAOD,EAAO,YAAoB,IAAI,EAC5C,GAAI,CAACC,EAAM,OAEX,IAAMR,EAAUO,EAAO,YACvB,GAAI,CAACP,EAAS,OAEd,IAAMS,EAASC,GAAkC,CAC/C,GAAIA,EAAe,CACjB,IAAMC,EAAWJ,EAAO,YAAoB,UAAU,EAClDI,GAAY,MACd,KAAK,OAAO,IAAID,EAAc,MAAM,EACpC,KAAK,aAAa,KAAKA,CAAa,GAEpC,KAAK,SAAS,IAAIC,CAAQ,GAAG,SAASD,CAAa,EAErD,KAAK,SAAS,IAAIH,EAAO,GAAIG,CAAa,EAC1C,KAAK,YAAY,IAAIH,EAAO,GAAIP,CAAO,EACvCU,EAAc,GAAKV,CACrB,CACF,EAEA,OAAQQ,EAAM,CACZ,IAAK,QACH,KAAK,YAAYD,EAAQE,CAAK,EAC9B,MACF,IAAK,aACH,KAAK,YAAYF,EAAQ,QAASE,CAAK,EACvC,MACF,IAAK,eACH,KAAK,YAAYF,EAAQ,UAAWE,CAAK,EACzC,MACF,IAAK,mBACH,KAAK,YAAYF,EAAQ,cAAeE,CAAK,EAC7C,MACF,IAAK,YACH,KAAK,YAAYF,EAAQ,OAAQE,CAAK,EACtC,MACF,IAAK,kBACH,KAAK,YAAYF,EAAQ,aAAcE,CAAK,EAC5C,MACF,IAAK,QACH,KAAK,YAAYF,EAAQE,CAAK,EAC9B,MACF,IAAK,MACH,KAAK,UAAUF,EAAQE,CAAK,EAC5B,MACF,IAAK,SACH,KAAK,aAAaF,EAAQE,CAAK,EAC/B,MACF,IAAK,QACH,KAAK,YAAYF,EAAQE,CAAK,EAC9B,MACF,IAAK,WACH,KAAK,eAAeF,EAAQE,CAAK,EACjC,MACF,IAAK,YACH,KAAK,gBAAgBF,EAAQE,CAAK,EAClC,MACF,IAAK,OACH,KAAK,WAAWF,EAAQE,CAAK,EAC7B,KACJ,CACF,CAEQ,YAAYF,EAAsBE,EAAsD,CAC9F,IAAMG,EAAQ,KAAK,OAAO,YAAY,EAChCR,EAAM,IAAIS,GAAeN,EAAO,GAAI,QAASK,EAAO,KAAK,MAAM,EACrE,OAAAH,EAAML,CAAG,EACFA,CACT,CAEQ,YACNG,EACAO,EACAL,EACgB,CAChB,IAAMT,EAAUO,EAAO,YACjBQ,EAAWf,EAAUgB,GAAgBhB,EAAS,gBAAiB,SAAS,EAAI,UAC5EiB,EAAQF,GAAYA,IAAa,OAASA,EAAW,UACrDG,EAAYlB,EAAUmB,GAAgBnB,EAAS,oBAAqB,CAAC,EAAI,EAE3EoB,EACJ,GAAIN,IAAS,QAAS,CACpB,IAAMO,EAAWrB,EAAUmB,GAAgBnB,EAAS,mBAAoB,GAAI,EAAI,IAC1EsB,EAAQtB,EAAUmB,GAAgBnB,EAAS,gBAAiB,CAAC,EAAI,EACvEoB,EAAQ,KAAK,OAAO,iBAAiBH,EAAOC,EAAWG,EAAUC,CAAK,CACxE,SAAWR,IAAS,cAClBM,EAAQ,KAAK,OAAO,uBAAuBH,EAAOC,CAAS,UAClDJ,IAAS,OAAQ,CAC1B,IAAMO,EAAWrB,EAAUmB,GAAgBnB,EAAS,mBAAoB,CAAC,EAAI,EACvEuB,EAAQvB,EAAUmB,GAAgBnB,EAAS,gBAAiB,KAAK,GAAK,CAAC,EAAI,KAAK,GAAK,EACrFwB,EAAWxB,EAAUmB,GAAgBnB,EAAS,mBAAoB,CAAC,EAAI,EACvEsB,EAAQtB,EAAUmB,GAAgBnB,EAAS,gBAAiB,CAAC,EAAI,EACvEoB,EAAQ,KAAK,OAAO,gBAAgBH,EAAOC,EAAWG,EAAUE,EAAOC,EAAUF,CAAK,CACxF,SAAWR,IAAS,aAAc,CAChC,IAAMW,EAAYzB,EACdgB,GAAgBhB,EAAS,uBAAwB,SAAS,EAC1D,UACE0B,EAAcD,GAAaA,IAAc,OAASA,EAAY,UACpEL,EAAQ,KAAK,OAAO,sBAAsBH,EAAOS,EAAaR,CAAS,CACzE,MACEE,EAAQ,KAAK,OAAO,mBAAmBH,EAAOC,CAAS,EAIzD,IADmBlB,EAAU2B,GAAiB3B,EAAS,gBAAiB,EAAK,EAAI,KAC/DoB,EAAM,OAAQ,CAC9BA,EAAM,WAAa,GACnB,IAAMQ,EAAO5B,EAAUmB,GAAgBnB,EAAS,gBAAiB,CAAC,EAAI,EAChE6B,EAAU7B,EAAUmB,GAAgBnB,EAAS,oBAAqB,GAAG,EAAI,IAC/EoB,EAAM,OAAO,KAAOQ,EACpBR,EAAM,OAAO,QAAQ,MAAQS,EAC7BT,EAAM,OAAO,QAAQ,OAASS,CAChC,CAEA,IAAMzB,EAAM,IAAIS,GAAeN,EAAO,GAAIO,EAAO,QAASM,EAAO,KAAK,MAAM,EAC5E,OAAAX,EAAML,CAAG,EACFA,CACT,CAEQ,iBAAiBG,EAAsBuB,EAAiB,CAC9D,IAAM9B,EAAUO,EAAO,YACjBwB,EAAa/B,EAAU2B,GAAiB3B,EAAS,gBAAiB,EAAK,EAAI,GAC3EgC,EAAgBhC,EAAU2B,GAAiB3B,EAAS,mBAAoB,EAAK,EAAI,GACvF8B,EAAK,WAAaC,EAClBD,EAAK,cAAgBE,CACvB,CAEQ,UAAUzB,EAAsBE,EAAsD,CAC5F,IAAMwB,EAAW,KAAK,OAAO,kBAAkB,EAAG,EAAG,CAAC,EAChDC,EAAW,KAAK,yBAAyB3B,CAAM,EAC/CuB,EAAO,KAAK,OAAO,WAAWG,EAAUC,CAAQ,EACtD,KAAK,iBAAiB3B,EAAQuB,CAAI,EAClC,IAAM1B,EAAM,IAAIS,GAAeN,EAAO,GAAI,MAAOuB,EAAM,KAAK,OAAQ,CAClE,SAAAG,EACA,SAAAC,CACF,CAAC,EACD,OAAAzB,EAAML,CAAG,EACFA,CACT,CAEQ,aAAaG,EAAsBE,EAAsD,CAC/F,IAAM0B,EAAU,KAAK,mBAAmB5B,EAAO,WAAW,EACpD6B,EAAgB,KAAK,IAAI,EAAG,KAAK,MAAM,GAAKD,CAAO,CAAC,EACpDE,EAAiB,KAAK,IAAI,EAAG,KAAK,MAAM,GAAKF,CAAO,CAAC,EACrDF,EAAW,KAAK,OAAO,qBAAqB,GAAKG,EAAeC,CAAc,EAC9EH,EAAW,KAAK,yBAAyB3B,CAAM,EAC/CuB,EAAO,KAAK,OAAO,WAAWG,EAAUC,CAAQ,EACtD,KAAK,iBAAiB3B,EAAQuB,CAAI,EAClC,IAAM1B,EAAM,IAAIS,GAAeN,EAAO,GAAI,SAAUuB,EAAM,KAAK,OAAQ,CACrE,SAAAG,EACA,SAAAC,CACF,CAAC,EACD,OAAAzB,EAAML,CAAG,EACFA,CACT,CAEQ,YAAYG,EAAsBE,EAAsD,CAC9F,IAAMwB,EAAW,KAAK,OAAO,oBAAoB,EAAG,CAAC,EAC/CC,EAAW,KAAK,yBAAyB3B,CAAM,EAC/CuB,EAAO,KAAK,OAAO,WAAWG,EAAUC,CAAQ,EACtD,KAAK,iBAAiB3B,EAAQuB,CAAI,EAClC,IAAM1B,EAAM,IAAIS,GAAeN,EAAO,GAAI,QAASuB,EAAM,KAAK,OAAQ,CACpE,SAAAG,EACA,SAAAC,CACF,CAAC,EACD,OAAAzB,EAAML,CAAG,EACFA,CACT,CAEQ,eACNG,EACAE,EACgB,CAChB,IAAM0B,EAAU,KAAK,mBAAmB5B,EAAO,WAAW,EACpD+B,EAAW,KAAK,IAAI,EAAG,KAAK,MAAM,GAAKH,CAAO,CAAC,EAC/CF,EAAW,KAAK,OAAO,uBAAuB,GAAK,GAAK,EAAGK,CAAQ,EACnEJ,EAAW,KAAK,yBAAyB3B,CAAM,EAC/CuB,EAAO,KAAK,OAAO,WAAWG,EAAUC,CAAQ,EACtD,KAAK,iBAAiB3B,EAAQuB,CAAI,EAClC,IAAM1B,EAAM,IAAIS,GAAeN,EAAO,GAAI,WAAYuB,EAAM,KAAK,OAAQ,CACvE,SAAAG,EACA,SAAAC,CACF,CAAC,EACD,OAAAzB,EAAML,CAAG,EACFA,CACT,CAEQ,YAAYG,EAAsBE,EAA4C,CACpF,IAAM8B,EAAYhC,EAAO,YAAoB,UAAU,EACvD,GAAI,CAACgC,EAAW,OAEhB,IAAMC,EAAajC,EAAO,YAAoB,iBAAiB,GAAK,OAC9DkC,EAAS,KAAK,mBAAmBD,CAAU,EACjD,GAAI,CAACC,EACH,OAGF,IAAMzC,EAAUO,EAAO,YACnBP,GACF,KAAK,uBAAuByC,EAAQzC,CAAO,EAE7C,IAAM0C,EAAenC,EAAO,YAAqB,iBAAiB,GAAK,GAEvEkC,EAAO,KACLF,EACCI,GAAc,CACb,IAAMrC,EAAOqC,GAAM,OAASA,GAAM,QAAUA,EAC5C,GAAI,CAACrC,EACH,OAGF,IAAMsC,EACJ5C,GAAW,KAAK,4BAA4BA,CAAO,EAC/C,KAAK,0BAA0BA,EAASO,CAAM,EAC9C,KAEF,OAAOD,EAAK,UAAa,YAC3BA,EAAK,SAAUD,GAAe,CACxBA,EAAM,SACJuC,IACFvC,EAAM,SAAWuC,GAEnB,KAAK,iBAAiBrC,EAAQF,CAAK,EAEvC,CAAC,EAGCqC,GACF,KAAK,aAAapC,CAAI,EAExB,IAAMF,EAAM,IAAIS,GAAeN,EAAO,GAAI,QAASD,EAAM,KAAK,MAAM,EACpEG,EAAML,CAAG,CACX,EACA,OACA,MACF,CACF,CAEQ,gBAAgBG,EAAsBE,EAA4C,CACxF,GAAI,CAAC,KAAK,OAAO,qBACf,OAGF,IAAMT,EAAUO,EAAO,YACjBsC,EAAkE,CACtE,KAAM,UACN,MAAO,IACP,KAAM,EACN,MAAO,UACP,QAAS,EACT,OAAQ,IACR,QAAS,EACT,QAAS,EACT,KAAM,EACN,SAAU,GACV,UAAW,EACX,aAAc,IACd,cAAe,GACf,kBAAmB,CAAC,EAAG,EAAG,CAAC,EAC3B,gBAAiB,CAAC,EAAG,IAAK,CAAC,EAC3B,aAAc,GACd,sBAAuB,GACvB,uBAAwB,GACxB,cAAe,SACf,iBAAkB,GAClB,oBAAqB,GACrB,kBAAmB,GACnB,cAAe,SACf,iBAAkB,GAClB,oBAAqB,GACrB,kBAAmB,GACnB,cAAe,EACf,uBAAwB,GACxB,sBAAuB,GACvB,eAAgB,GAChB,aAAc,GACd,iBAAkB,EAClB,wBAAyB,EACzB,yBAA0B,EAC1B,yBAA0B,EAC1B,yBAA0B,EAC1B,wBAAyB,CAC3B,EAEMC,EAAS,KAAK,OAAO,qBAAqBD,CAAM,EAChDzC,EAAM,IAAIS,GAAeN,EAAO,GAAI,YAAauC,EAAQ,KAAK,MAAM,EAC1ErC,EAAML,CAAG,CACX,CAEQ,WAAWG,EAAsBE,EAA4C,CACnF,GAAI,CAAC,KAAK,OAAO,mBACf,OAGF,IAAMwB,EAAW,KAAK,OAAO,kBAAkB,EAAG,EAAG,CAAC,EAChDC,EAAW,KAAK,yBAAyB3B,CAAM,EAC/CuB,EAAO,KAAK,OAAO,WAAWG,EAAUC,CAAQ,EACtD,KAAK,iBAAiB3B,EAAQuB,CAAI,EAElC,IAAMlB,EAAQ,KAAK,OAAO,YAAY,EACrCA,EAAc,WAAakB,EAC5BlB,EAAM,IAAIkB,CAAI,EAEd,IAAM1B,EAAM,IAAIS,GAAeN,EAAO,GAAI,OAAQK,EAAO,KAAK,OAAQ,CACpE,SAAAqB,EACA,SAAAC,CACF,CAAC,EACDzB,EAAML,CAAG,CACX,CAEQ,mBAAmBJ,EAAsC,CAC/D,GAAI,CAACA,EAAS,MAAO,GACrB,IAAMmC,EAAUhB,GAAgBnB,EAAS,qBAAsB,CAAC,EAChE,MAAI,CAAC,OAAO,SAASmC,CAAO,GAAKA,GAAW,EAAU,EAC/CA,CACT,CAEQ,mBAAmB3B,EAA2C,CACpE,GAAIA,EAAM,CACR,GAAI,KAAK,kBAAkB,IAAIA,CAAI,EACjC,OAAO,KAAK,kBAAkB,IAAIA,CAAI,EAExC,GAAI,CAAC,KAAK,oBACR,OAEF,IAAMiC,EAAS,KAAK,oBAAoB,KAAK,OAAQjC,CAAI,EACzD,YAAK,kBAAkB,IAAIA,EAAMiC,CAAM,EAChCA,CACT,CAEA,GAAI,KAAK,aACP,OAAO,KAAK,aAGd,GAAI,KAAK,oBACP,OAAO,KAAK,oBAAoB,KAAK,MAAM,CAI/C,CAEQ,aAAalC,EAAmB,CACtC,GAAI,CAACA,EAAQ,OACb,IAAMwC,EAAO,KAAK,OAAO,8BAA8BxC,CAAM,EACvDyC,EAAS,KAAK,aAAaD,CAAI,EACjCxC,EAAO,UAAU,KACnBA,EAAO,SAAS,IAAI,CAACyC,EAAO,EAAG,CAACA,EAAO,EAAG,CAACA,EAAO,CAAC,EAErDzC,EAAO,kBAAkB,EAAI,CAC/B,CAEQ,aAAa0C,EAAsB,CACzC,IAAMD,EAAS,KAAK,OAAO,cAAc,EACzC,OAAAA,EAAO,GAAKC,EAAI,IAAI,EAAIA,EAAI,IAAI,GAAK,EACrCD,EAAO,GAAKC,EAAI,IAAI,EAAIA,EAAI,IAAI,GAAK,EACrCD,EAAO,GAAKC,EAAI,IAAI,EAAIA,EAAI,IAAI,GAAK,EAC9BD,CACT,CAEQ,yBAAyBzC,EAAmC,CAClE,OAAO,KAAK,0BAA0BA,EAAO,YAAaA,CAAM,CAClE,CAEQ,0BACNP,EACAO,EACa,CACb,IAAM2C,EAAQlD,EAAU,iBAAiBA,CAAO,EAAI,KAC9CmD,EAAUC,GAAkBF,EAAQA,EAAM,iBAAiBE,CAAI,EAAE,KAAK,EAAI,GAE1EC,EAAU,CAAIC,EAAiBC,EAA0BC,IAAuB,CACpF,IAAMC,EAASN,EAAOG,CAAO,EAC7B,OAAIG,GAAUA,IAAW,QAAUA,IAAW,GAAWF,EAAOE,CAAM,EAC/DD,CACT,EAEME,EAAeC,GAAc,WAAWA,CAAC,EACzCC,EAAcD,GAAcA,EAC5BE,EAAYF,GAAc,CAC9B,IAAMG,EAAQH,EAAE,MAAM,wBAAwB,EAC9C,OAAOG,EAAQA,EAAM,CAAC,EAAIH,CAC5B,EAEMnD,EAAO6C,EAAQ,kBAAoBM,GAAMA,EAAE,MAAM,GAAG,EAAE,CAAC,GAAK,QAAS,OAAO,EAE5EI,EAAiB,KAAK,wBAAwBvD,EAAMR,EAASkD,EAAO3C,CAAM,EAChF,GAAIwD,EACF,OAAOA,EAGT,IAAM9C,EAAQoC,EAAQ,mBAAoBO,EAAY,SAAS,EAEzDI,EAAUX,EAAQ,YAAaK,EAAa,CAAC,EAC7CO,EAAYZ,EAAQ,uBAAwBK,EAAa,CAAC,EAC1DQ,EAAYb,EAAQ,uBAAwBK,EAAa,CAAC,EAC1DS,EAAWd,EAAQ,sBAAuBO,EAAY,SAAS,EAE/DQ,EAAc,CAClB,MAAAnD,EACA,YAAa+C,EAAU,EACvB,QAASA,CACX,EAEMK,EAAShB,EAAQ,gBAAiBQ,EAAU,EAAE,EAC9CS,EAAejB,EAAQ,mBAAoBQ,EAAU,EAAE,EACvDU,EAAkBlB,EAAQ,sBAAuBQ,EAAU,EAAE,EAC7DW,EAAkBnB,EAAQ,sBAAuBQ,EAAU,EAAE,EAC7DY,EAAWpB,EAAQ,eAAgBQ,EAAU,EAAE,EAE/Ca,EAAQ,KAAK,WAAW1E,CAAO,EAC/B2E,EAAa3E,EAAUgB,GAAgBhB,EAAS,wBAAyB,EAAE,EAAI,GAE/E4E,EAAU,CAAC,EAAEP,GAAUC,GAAgBC,GAAmBC,GAAmBC,GAC/EI,EAAYrE,EAKhB,OAJIqE,IAAc,YAAcD,IAC9BC,EAAY,YAGVA,IAAc,YACZR,IAAQD,EAAO,IAAM,KAAK,YAAYC,EAAQ,CAAE,MAAAK,EAAO,WAAAC,CAAW,CAAC,GACnEL,IAAcF,EAAO,UAAY,KAAK,YAAYE,EAAc,CAAE,MAAAI,CAAM,CAAC,GACzEH,IAAiBH,EAAO,aAAe,KAAK,YAAYG,EAAiB,CAAE,MAAAG,CAAM,CAAC,GAClFF,IAAiBJ,EAAO,aAAe,KAAK,YAAYI,EAAiB,CAAE,MAAAE,CAAM,CAAC,GAClFD,IAAUL,EAAO,MAAQ,KAAK,YAAYK,EAAU,CAAE,MAAAC,CAAM,CAAC,GAEjEN,EAAO,UAAYH,EACnBG,EAAO,UAAYF,EACnBE,EAAO,SAAWD,EAEX,KAAK,OAAO,2BAA2BC,CAAM,GAG/C,KAAK,OAAO,wBAAwBA,CAAM,CACnD,CAEQ,wBACN5D,EACAR,EACAkD,EACA3C,EACoB,CACpB,IAAMuE,EAAaC,GAA+B,IAAIvE,CAAI,EAC1D,GAAI,CAACsE,EACH,OAAO,KAGT,IAAME,EAAU,KAAK,OAAO,qBAAqB,EAIjD,GAHI,CAACA,GAGD,CAACA,EAAQ,SAASF,CAAU,EAC9B,OAAO,KAGT,IAAIG,EAAuC,CAAC,EACxCjF,GAAWkD,IACb+B,EAAkBD,EAAQ,qBAAqBF,EAAY9E,EAASkD,CAAK,GAG3E,IAAMgC,EAAWF,EAAQ,OAAOF,EAAYG,CAAe,EAE3D,OAAI1E,GACF,KAAK,mBAAmB,IAAIA,EAAO,GAAI2E,CAAQ,EAG1CA,EAAS,QAClB,CAEO,uBAAuBC,EAAkBC,EAAqC,CACnF,IAAMF,EAAW,KAAK,mBAAmB,IAAIC,CAAQ,EACjDD,GACFA,EAAS,OAAOE,CAAQ,CAE5B,CAEO,oBAAoBD,EAAiD,CAC1E,OAAO,KAAK,mBAAmB,IAAIA,CAAQ,CAC7C,CAEO,0BAA0B5E,EAAwBP,EAAmC,CAC1F,IAAMqF,EAAc,KAAK,mBAAmB,IAAI9E,EAAO,EAAE,EACrD8E,GAAeA,EAAY,SAC7BA,EAAY,QAAQ,EAEtB,KAAK,mBAAmB,OAAO9E,EAAO,EAAE,EAExC,IAAI+E,EACJ,OAAW,CAACvF,EAAIE,CAAE,IAAK,KAAK,YAC1B,GAAIF,IAAOQ,EAAO,IAAMN,IAAOD,EAAS,CACtCsF,EAAgBrF,EAAW,gBAAmBA,EAAW,aACzD,KACF,CAGF,IAAMsF,EAAc,KAAK,0BAA0BvF,EAASsF,CAAY,EAEpE/E,EAAO,QAAUA,EAAO,OAAO,UACjCA,EAAO,OAAO,SAAUF,GAAe,CACjCA,EAAM,WACJA,EAAM,SAAS,SACjBA,EAAM,SAAS,QAAQ,EAEzBA,EAAM,SAAWkF,EAErB,CAAC,EAGHhF,EAAO,SAAWgF,CACpB,CAEQ,YAAYC,EAAa3F,EAAoD,CAAC,EAAQ,CAE5F,IAAM4F,EADgB,KAAK,OAAO,oBAAoB,EACxB,KAAKD,CAAG,EAClC,OAAO3F,EAAQ,OAAU,YAC3B4F,EAAQ,MAAQ5F,EAAQ,OAE1B,IAAM8E,GAAc9E,EAAQ,YAAc,IAAI,YAAY,EAAE,KAAK,EACjE,OAAI8E,GAAc,eAAgBc,IAChCA,EAAQ,WAAad,IAAe,OAAS,OAAS,UAExDc,EAAQ,YAAc,GACfA,CACT,CAEQ,WAAWzF,EAAmD,CACpE,IAAM0F,EAAQ1F,EAAUgB,GAAgBhB,EAAS,mBAAoB,EAAE,EAAI,GAC3E,GAA2B0F,GAAU,MAAQA,IAAU,GAAI,OAC3D,GAAI,OAAOA,GAAU,UAAW,OAAOA,EACvC,IAAMC,EAAa,OAAOD,CAAK,EAAE,YAAY,EAAE,KAAK,EACpD,GAAIC,IAAe,SAAWA,IAAe,KAAOA,IAAe,KAAM,MAAO,GAChF,GAAIA,IAAe,QAAUA,IAAe,KAAOA,IAAe,MAAO,MAAO,EAElF,CAEQ,4BAA4B3F,EAA+B,CACjE,IAAMkD,EAAQ,iBAAiBlD,CAAO,EAChC4F,EAAYxC,GAAiB,CACjC,IAAMyC,EAAM3C,EAAM,iBAAiBE,CAAI,EACvC,OAAOyC,GAAOA,IAAQ,KAAOA,IAAQ,QAAUA,IAAQ,EACzD,EAEA,OAAID,EAAS,kBAAkB,GAAKA,EAAS,eAAe,EAAU,GAEtD,CACd,kBACA,uBACA,uBACA,sBACA,YACA,mBACA,sBACA,sBACA,cACF,EACe,KAAMxC,GAASwC,EAASxC,CAAI,CAAC,CAC9C,CAEQ,uBAAuBX,EAAazC,EAA4B,CACtE,IAAM8F,GAAW9F,EAAQ,aAAa,8BAA8B,GAAK,IAAI,KAAK,EAC5E+F,EAAOD,EAAUA,EAAQ,QAAQ,OAAQ,GAAG,EAAI,GAChDE,EAAahG,EAAQ,aAAa,0BAA0B,EAC9DiG,EAAyC,KAE7C,GAAID,EACF,GAAI,CACFC,EAAU,KAAK,MAAMD,CAAU,CACjC,MAAgB,CAAC,CAGnB,IAAME,EAAUzD,GAAQ,QACpB,CAACyD,GAAW,OAAOA,EAAQ,gBAAmB,YAIlDA,EAAQ,eAAgBC,GAAgB,CACtC,IAAMC,EAASH,GAAWE,KAAOF,EAAUA,EAAQE,CAAG,EAAIA,EAE1D,MADI,CAACJ,GACD,mCAAmC,KAAKK,CAAM,EAAUA,EACrDL,EAAOK,EAAO,QAAQ,SAAU,EAAE,CAC3C,CAAC,CACH,CAEO,SAAgB,CACrB,KAAK,mBAAmB,QAASlB,GAAaA,EAAS,QAAQ,CAAC,EAChE,KAAK,mBAAmB,MAAM,EAC9B,KAAK,SAAS,QAAS9E,GAAQA,EAAI,QAAQ,CAAC,EAC5C,KAAK,SAAS,MAAM,EACpB,KAAK,aAAe,CAAC,CACvB,CACF,EC3qBO,IAAMiG,EAAN,KAA0B,CAA1B,cACL,KAAQ,MAAiC,IAAI,QAC7C,KAAQ,KAA+C,IAAI,QAE3D,IAAIC,EAAiBC,EAAkBC,EAAmC,CAExE,GADoB,CAAC,CAACD,EAAI,UAAYA,EAAI,YAAc,IAAS,CAACA,EAAI,SAAS,IAAID,CAAE,EACpE,CACf,IAAMG,EAAS,KAAK,MAAM,IAAIH,CAAE,EAChC,GAAIG,EAAQ,OAAOA,CACrB,CAEA,IAAMC,EAAM,YAAY,IAAI,EACtBC,EAAW,KAAK,IAAI,EAAGJ,EAAI,qBAAuB,CAAC,EACzD,GAAII,EAAW,EAAG,CAChB,IAAMC,EAAW,KAAK,KAAK,IAAIN,CAAE,EAC3BG,EAAS,KAAK,MAAM,IAAIH,CAAE,EAChC,GAAIM,GAAYH,GAAUC,EAAME,EAAS,KAAOD,EAC9C,OAAOF,CAEX,CAEA,IAAMI,EAASL,EAAOF,CAAE,EACxB,YAAK,MAAM,IAAIA,EAAIO,CAAM,EACzB,KAAK,KAAK,IAAIP,EAAI,CAAE,KAAMI,CAAI,CAAC,EACxBG,CACT,CAEA,OAAc,CACZ,KAAK,MAAQ,IAAI,QACjB,KAAK,KAAO,IAAI,OAClB,CACF,EC3BA,IAAMC,GAAa,KAAK,GAAK,IAUhBC,GAAN,MAAMA,EAAwD,CAGnE,KAAKC,EAAiBC,EAAwBC,EAAkBC,EAAsB,CACpF,IAAMC,EAAUJ,EAAW,cACrBK,EAAOD,EAASA,EAAO,KAAOJ,EAAG,sBAAsB,EACvDM,EAAS,KAAK,gBAAgBN,EAAIE,CAAG,EAErCK,EAAgBF,EAAK,KAAOA,EAAK,MAAQ,GACzCG,EAAgBH,EAAK,IAAMA,EAAK,OAAS,GAE/C,GAAIH,EAAI,OAAO,QAAQ,IAAM,eAC3BD,EAAO,OAAO,SAAS,IACrBM,EAAgBL,EAAI,cAAgB,EACpC,EAAEM,EAAgBN,EAAI,eAAiB,GACvCI,EAAO,UACT,MACK,CACL,IAAMG,EAAUP,EAAI,OAAO,iBAAiBI,EAAO,UAAU,EACvDI,EAAcH,EAAgBL,EAAI,cAClCS,EAAcH,EAAgBN,EAAI,eACxCD,EAAO,OAAO,SAAS,KACpBS,EAAc,IAAOD,EAAQ,MAC9B,EAAEE,EAAc,IAAOF,EAAQ,OAC/BH,EAAO,UACT,CACF,CAEA,OAAAL,EAAO,OAAO,MAAM,IAAIK,EAAO,MAAOA,EAAO,MAAOA,EAAO,KAAK,EAEhEL,EAAO,OAAO,SAAS,EAAI,CAACK,EAAO,QAAUR,GAC7CG,EAAO,OAAO,SAAS,EAAIK,EAAO,QAAUR,GAC5CG,EAAO,OAAO,SAAS,EAAI,CAACK,EAAO,QAAUR,GAC7CG,EAAO,OAAO,SAAS,MAAQ,MAE/BA,EAAO,OAAO,kBAAkB,EAAI,EAE7B,CAAE,MAAOK,EAAO,KAAM,CAC/B,CAEQ,gBAAgBN,EAAiBE,EAAoC,CAC3E,OAAOH,GAAkB,WAAW,IAAIC,EAAIE,EAAMF,GAAO,CACvD,IAAMY,EAAS,IAAIC,GAAYb,CAAE,EACjC,MAAO,CACL,WAAYY,EAAO,WAAW,gBAAiB,CAAC,EAChD,MAAOA,EAAO,WAAW,UAAW,CAAC,EACrC,QAASA,EAAO,WAAW,aAAc,CAAC,EAC1C,QAASA,EAAO,WAAW,aAAc,CAAC,EAC1C,QAASA,EAAO,WAAW,aAAc,CAAC,CAC5C,CACF,CAAC,CACH,CACF,EApDab,GACI,WAAa,IAAIe,EAD3B,IAAMC,GAANhB,GCSA,IAAMiB,GAAN,MAAMA,EAAwD,CAGnE,KAAKC,EAAiBC,EAAwBC,EAAkBC,EAAsB,CACpF,IAAMC,EAAUJ,EAAW,cACrBK,EAAOD,EAASA,EAAO,KAAOJ,EAAG,sBAAsB,EACvDM,EAAS,KAAK,gBAAgBN,EAAIE,EAAKD,CAAM,EAE7CM,EAAgBF,EAAK,KAAOA,EAAK,MAAQ,GACzCG,EAAgBH,EAAK,IAAMA,EAAK,OAAS,GAE/C,GAAIH,EAAI,OAAO,QAAQ,IAAM,eAC3BD,EAAO,OAAO,SAAS,IACrBM,EAAgBL,EAAI,cAAgB,EAAII,EAAO,WAC/C,EAAEE,EAAgBN,EAAI,eAAiB,GAAKI,EAAO,WACnDA,EAAO,UACT,MACK,CACL,IAAMG,EAAUP,EAAI,OAAO,iBAAiBI,EAAO,UAAU,EACvDI,EAAcH,EAAgBL,EAAI,cAClCS,EAAcH,EAAgBN,EAAI,eACxCD,EAAO,OAAO,SAAS,KACpBS,EAAc,IAAOD,EAAQ,MAAQH,EAAO,WAC7C,EAAEK,EAAc,IAAOF,EAAQ,OAASH,EAAO,WAC/CA,EAAO,UACT,CACF,CAEA,IAAMM,EAAQX,EAAO,OAoDrB,GAjDEK,EAAO,OACPA,EAAO,QAAU,QACjBM,EAAM,OACN,OAAOA,EAAM,MAAM,KAAQ,YAE3BA,EAAM,MAAM,IAAIN,EAAO,KAAK,EAG9BM,EAAM,UAAYN,EAAO,UAErB,OAAOM,EAAM,SAAa,KAAeN,EAAO,WAAa,SAC/DM,EAAM,SAAWN,EAAO,UAEtB,OAAOM,EAAM,MAAU,KAAeN,EAAO,QAAU,SACzDM,EAAM,MAAQN,EAAO,OAGnB,OAAOM,EAAM,MAAU,KAAeN,EAAO,QAAU,SACzDM,EAAM,MAAQN,EAAO,OAEnB,OAAOM,EAAM,SAAa,KAAeN,EAAO,WAAa,SAC/DM,EAAM,SAAWN,EAAO,UAIxBA,EAAO,aACPA,EAAO,cAAgB,QACtBM,EAAc,aACf,OAAQA,EAAc,YAAY,KAAQ,YAEzCA,EAAc,YAAY,IAAIN,EAAO,WAAW,EAG/CM,EAAM,aAAeN,EAAO,aAC9BM,EAAM,WAAaN,EAAO,YAExBA,EAAO,YAAcM,EAAM,SACzBN,EAAO,aAAe,SACxBM,EAAM,OAAO,KAAON,EAAO,YAG3BA,EAAO,gBAAkB,QACzBM,EAAM,OAAO,QAAQ,QAAUN,EAAO,gBAEtCM,EAAM,OAAO,QAAQ,MAAQN,EAAO,cACpCM,EAAM,OAAO,QAAQ,OAASN,EAAO,gBAIrCA,EAAO,UAAYA,EAAO,WAAa,QAAUM,EAAM,OAAQ,CACjE,IAAMC,EAAW,SAAS,cAAc,eAAeP,EAAO,QAAQ,IAAI,EAC1E,GAAIO,EAAU,CACZ,IAAMC,EAAWD,EAAiB,cAC5BE,EAAQD,EAAUA,EAAQ,KAAOD,EAAS,sBAAsB,EAEhEG,EADU,IAAIC,GAAYJ,CAAuB,EAC3B,WAAW,gBAAiB,CAAC,EAEnDK,EAAiBH,EAAM,KAAOA,EAAM,MAAQ,GAC5CI,EAAiBJ,EAAM,IAAMA,EAAM,OAAS,GAE9CK,EACA,EACAC,EACJ,GAAInB,EAAI,OAAO,QAAQ,IAAM,eAC3BkB,EAAIF,EAAiBhB,EAAI,cAAgB,EACzC,EAAI,EAAEiB,EAAiBjB,EAAI,eAAiB,GAC5CmB,EAAIL,MACC,CACL,IAAMP,EAAUP,EAAI,OAAO,iBAAiBc,CAAW,EACjDN,EAAcQ,EAAiBhB,EAAI,cACnCS,EAAcQ,EAAiBjB,EAAI,eACzCkB,GAAKV,EAAc,IAAOD,EAAQ,MAClC,EAAI,EAAEE,EAAc,IAAOF,EAAQ,OACnCY,EAAIL,CACN,CAEIV,EAAO,eACTc,GAAKd,EAAO,aAAa,EACzB,GAAKA,EAAO,aAAa,EACzBe,GAAKf,EAAO,aAAa,GAG3BM,EAAM,OAAO,SAAS,IAAIQ,EAAG,EAAGC,CAAC,EAEjCT,EAAM,OAAO,kBAAkB,EAAI,CACrC,CACF,CAEA,OAAO,IACT,CAEQ,gBACNZ,EACAE,EACAD,EACkB,CAClB,OAAOF,GAAkB,WAAW,IAAIC,EAAIE,EAAMF,GAAO,CACvD,IAAMsB,EAAS,IAAIL,GAAYjB,CAAE,EAC3BY,EAAQX,EAAO,OAEfK,EAA2B,CAC/B,WAAYgB,EAAO,WAAW,gBAAiB,CAAC,EAChD,WAAYA,EAAO,WAAW,gBAAiB,CAAC,EAChD,WAAYA,EAAO,WAAW,gBAAiB,CAAC,EAChD,MAAOA,EAAO,WAAW,gBAAiB,EAAE,GAAK,OACjD,UAAWA,EAAO,WAAW,oBAAqBV,EAAM,WAAa,CAAC,EACtE,WAAYU,EAAO,YAAY,gBAAiB,EAAK,CACvD,EAEI,OAAOV,EAAM,SAAa,MAC5BN,EAAO,SAAWgB,EAAO,WAAW,mBAAoBV,EAAM,UAAY,CAAC,GAEzE,OAAOA,EAAM,MAAU,MACzBN,EAAO,MAAQgB,EAAO,WAAW,gBAAiBV,EAAM,OAAS,CAAC,GAEhE,OAAOA,EAAM,MAAU,MACzBN,EAAO,MAAQgB,EAAO,WAAW,gBAAiBV,EAAM,OAAS,KAAK,GAAK,CAAC,GAE1E,OAAOA,EAAM,SAAa,MAC5BN,EAAO,SAAWgB,EAAO,WAAW,mBAAoBV,EAAM,UAAY,CAAC,GAG7E,IAAMW,EAAcD,EAAO,WAAW,uBAAwB,EAAE,EAC5DC,IAAajB,EAAO,YAAciB,GAElCjB,EAAO,YAAcM,EAAM,SAC7BN,EAAO,WAAagB,EAAO,WAAW,gBAAiBV,EAAM,OAAO,MAAQ,CAAC,EAC7EN,EAAO,cAAgBgB,EAAO,WAC5B,oBACAV,EAAM,OAAO,QAAQ,OAAS,GAChC,GAGF,IAAMY,EAAWF,EAAO,WAAW,iBAAkB,EAAE,EAAE,KAAK,EAC1DE,IAAUlB,EAAO,SAAWkB,GAChC,IAAMC,EAAYH,EAAO,WAAW,wBAAyB,EAAE,EAAE,KAAK,EACtE,GAAIG,EAAW,CACb,IAAMC,EAAS,KAAK,kBAAkBD,CAAS,EAC3CC,IAAQpB,EAAO,aAAeoB,EACpC,CAEA,OAAOpB,CACT,CAAC,CACH,CAEQ,kBAAkBqB,EAA2D,CACnF,IAAMC,EAAQD,EACX,MAAM,QAAQ,EACd,IAAKE,GAASA,EAAK,KAAK,CAAC,EACzB,OAAO,OAAO,EACd,IAAKA,GAAS,OAAO,WAAWA,CAAI,CAAC,EACxC,OAAID,EAAM,OAAS,GAAKA,EAAM,KAAME,GAAQ,OAAO,MAAMA,CAAG,CAAC,EAAU,KAChE,CAAE,EAAGF,EAAM,CAAC,EAAG,EAAGA,EAAM,CAAC,EAAG,EAAGA,EAAM,CAAC,CAAE,CACjD,CACF,EAzLa7B,GACI,WAAa,IAAIgC,EAD3B,IAAMC,GAANjC,GCpBP,IAAMkC,GAAa,KAAK,GAAK,IAEhBC,EAAN,MAAMA,CAAuD,CAkBlE,OAAO,iBACLC,EACAC,EACAC,EASM,CACN,IAAMC,EAAOJ,EAAiB,gBAAgB,IAAIE,CAAM,EACxD,GAAIE,EAAM,CACR,GACEA,EAAK,UAAYD,EAAM,SACvBC,EAAK,QAAUD,EAAM,OACrBC,EAAK,YAAcD,EAAM,WACzBC,EAAK,YAAcD,EAAM,WACzBC,EAAK,WAAaD,EAAM,UACxBC,EAAK,aAAeD,EAAM,YAC1BC,EAAK,gBAAkBD,EAAM,cAE7B,OACFC,EAAK,QAAUD,EAAM,QACrBC,EAAK,MAAQD,EAAM,MACnBC,EAAK,UAAYD,EAAM,UACvBC,EAAK,UAAYD,EAAM,UACvBC,EAAK,SAAWD,EAAM,SACtBC,EAAK,WAAaD,EAAM,WACxBC,EAAK,cAAgBD,EAAM,aAC7B,MACEH,EAAiB,gBAAgB,IAAIE,EAAQ,CAC3C,QAASC,EAAM,QACf,MAAOA,EAAM,MACb,UAAWA,EAAM,UACjB,UAAWA,EAAM,UACjB,SAAUA,EAAM,SAChB,WAAYA,EAAM,WAClB,cAAeA,EAAM,aACvB,CAAC,EAGH,IAAME,EAAaF,EAAM,YAAc,GACjCG,EAAgBH,EAAM,eAAiB,GAEvCI,EAAU,OAAOJ,EAAM,SAAY,SAAWA,EAAM,QAAU,IAE9DK,EAAsBC,GAAa,CAClCA,IAEA,MAAMF,CAAO,IAChBE,EAAI,QAAUF,EACdE,EAAI,YAAcF,EAAU,GAG1BJ,EAAM,OAASM,EAAI,OAASA,EAAI,MAAM,KACxCA,EAAI,MAAM,IAAIN,EAAM,KAAK,EAGvB,OAAOA,EAAM,WAAc,UAAY,cAAeM,IACxDA,EAAI,UAAYN,EAAM,WAGpB,OAAOA,EAAM,WAAc,UAAY,cAAeM,IACxDA,EAAI,UAAYN,EAAM,WAGpBA,EAAM,UAAYM,EAAI,UAAYA,EAAI,SAAS,KACjDA,EAAI,SAAS,IAAIN,EAAM,QAAQ,EAEnC,EAEA,GAAID,EAAO,OAAO,SAChBA,EAAO,OAAO,SAAUQ,GAAe,CACjCA,EAAM,SACJA,EAAM,aAAeL,IAAYK,EAAM,WAAaL,GACpDK,EAAM,gBAAkBJ,IAAeI,EAAM,cAAgBJ,IAE/C,MAAM,QAAQI,EAAM,QAAQ,EAAIA,EAAM,SAAW,CAACA,EAAM,QAAQ,GACxE,QAAQF,CAAkB,EAExC,CAAC,UACSN,EAAO,OAAe,OAAQ,CACxC,IAAMS,EAAOT,EAAO,OAChBS,EAAK,aAAeN,IAAYM,EAAK,WAAaN,GAClDM,EAAK,gBAAkBL,IAAeK,EAAK,cAAgBL,IAE7C,MAAM,QAAQK,EAAK,QAAQ,EAAIA,EAAK,SAAW,CAACA,EAAK,QAAQ,GACrE,QAAQH,CAAkB,CACtC,CACF,CAEA,KAAKP,EAAiBC,EAAwBU,EAAkBC,EAAsB,CACpF,GAAM,CAAE,KAAAC,EAAM,MAAOC,EAAe,OAAQC,CAAe,EAAI,KAAK,WAAWf,EAAIW,CAAG,EAChFK,EAAS,KAAK,gBAAgBhB,EAAIW,CAAG,EACrC,CACJ,WAAAM,EACA,SAAAC,EACA,QAAAC,EACA,QAAAC,EACA,QAAAC,EACA,UAAAC,EACA,QAAAhB,EACA,MAAAiB,EACA,UAAAC,EACA,UAAAC,EACA,SAAAC,EACA,WAAAtB,EACA,cAAAC,EACA,gBAAAsB,CACF,EAAIX,EAEEY,EAAgBf,EAAK,KAAOA,EAAK,MAAQ,GACzCgB,EAAgBhB,EAAK,IAAMA,EAAK,OAAS,GAE/C,GAAIF,EAAI,OAAO,QAAQ,IAAM,eAC3BV,EAAO,OAAO,SAAS,IACrB2B,EAAgBjB,EAAI,cAAgB,EACpC,EAAEkB,EAAgBlB,EAAI,eAAiB,GACvCM,CACF,MACK,CACL,IAAMa,EAAUnB,EAAI,OAAO,iBAAiBM,CAAU,EAChDc,EAAcH,EAAgBjB,EAAI,cAClCqB,EAAcH,EAAgBlB,EAAI,eACxCV,EAAO,OAAO,SAAS,KACpB8B,EAAc,IAAOD,EAAQ,MAC9B,EAAEE,EAAc,IAAOF,EAAQ,OAC/Bb,CACF,CACF,CAEAhB,EAAO,OAAO,SAAS,EAAI,CAACkB,EAAUrB,GACtCG,EAAO,OAAO,SAAS,EAAImB,EAAUtB,GACrCG,EAAO,OAAO,SAAS,EAAI,CAACoB,EAAUvB,GACtCG,EAAO,OAAO,SAAS,MAAQ,MAE/B,IAAMgC,EAAcnB,EAAgBI,EAC9BgB,EAAenB,EAAiBG,EAChCiB,EAAcvB,GAAY,OAAS,EACnCwB,EAAad,EAAYa,EACzBE,EAAgBJ,EAAcC,EAAeD,EAAcC,EAC7DI,EAAgBC,EAAgBC,EAEpC,OAAQvC,EAAO,KAAM,CACnB,IAAK,MACL,IAAK,SAAU,CACb,IAAMwC,EAAcJ,EAAgBF,EACpCG,EAASC,EAASE,EAClBD,EAASC,EAAcnB,EACvB,KACF,CACA,IAAK,QAAS,CACZ,IAAMoB,EAAOzC,EAAO,uBAAuB,EACtCF,EAAiB,cACpBA,EAAiB,YAAcY,EAAI,OAAO,cAAc,GAE1D,IAAMgC,EAAOD,EAAK,QAAQ3C,EAAiB,WAAW,EAChD6C,EAAU5C,EAAG,aAAa,qBAAqB,EAC/C6C,EAAa,WAAW7C,EAAG,aAAa,uBAAuB,GAAK,GAAG,EACvE8C,EAAkB,OAAO,SAASD,CAAU,EAC9CA,EAAaV,EACbA,EAEJ,GAAIQ,EAAK,EAAI,GAAKA,EAAK,EAAI,EAAG,CAC5B,IAAMI,EAASd,EAAcU,EAAK,EAC5BK,EAASd,EAAeS,EAAK,EAC7BM,GACHL,IAAY,QACTG,EAASC,EACPD,EACAC,EACFD,EAASC,EACTD,EACAC,GAAUF,EAChBR,EAASC,EAASU,EAClBT,EAASS,EAAe3B,CAC1B,KAAO,CACL,IAAM4B,EAAeb,EAAgBS,EACrCR,EAASC,EAASW,EAClBV,EAASU,EAAe5B,CAC1B,CACA,KACF,CACA,IAAK,WACHgB,EAASL,EAAcE,EACvBI,EAASL,EAAeC,EACxBK,EAASP,EAAcG,EACvB,MACF,QACEE,EAASL,EAAcE,EACvBI,EAASL,EAAeC,EACxBK,EAASH,EAAgB,GAAMD,EAC/B,KACJ,CAEA,OAAAnC,EAAO,OAAO,MAAM,IAAIqC,EAAQC,EAAQC,CAAM,EAE9CzC,EAAiB,iBAAiBC,EAAIC,EAAQ,CAC5C,QAAAK,EACA,MAAOiB,GAASA,IAAU,OAASA,EAAQ,OAC3C,UAAW,MAAMC,CAAS,EAAI,OAAYA,EAC1C,UAAW,MAAMC,CAAS,EAAI,OAAYA,EAC1C,SAAUC,GAAYA,IAAa,OAASA,EAAW,OACvD,WAAAtB,EACA,cAAAC,CACF,CAAC,EAED,KAAK,qBAAqBJ,EAAQ0B,EAAiBhB,CAAG,EAEtD,KAAK,qBAAqBX,EAAIC,EAAQU,CAAG,EAElC,CAAE,MAAOO,EAAWiB,CAAY,CACzC,CAEQ,qBAAqBlC,EAAwBkD,EAAiBxC,EAAwB,CAC5F,IAAMyC,EAAczC,EAAI,OAClB0C,EAAWD,GAAQ,kBAAkB,KAAKA,CAAM,EACtD,GAAI,OAAOC,GAAa,WAAY,OAEpC,IAAMC,EAAa,OAAO,SAASH,CAAO,GAAKA,EAAU,EAAIA,EAAU,EACjEhD,EAAOJ,EAAiB,oBAAoB,IAAIE,CAAM,EAC5D,GAAI,OAAOE,GAAS,UAAY,KAAK,IAAIA,EAAOmD,CAAU,EAAI,KAAO,OACrEvD,EAAiB,oBAAoB,IAAIE,EAAQqD,CAAU,EAE3D,IAAMC,EAAe7C,GAAc,CACjC,GAAI,CAACA,GAAM,SAAU,OACrB,IAAM8C,EAAW9C,EAAK,WAAaA,EAAK,SAAW,CAAC,GAC/C8C,EAAS,qBACZA,EAAS,mBAAqB9C,EAAK,UAErC,IAAM+C,EAAWD,EAAS,mBAC1B,GAAIF,GAAc,KAAO,CACvB5C,EAAK,SAAW+C,EAChB,MACF,CACKD,EAAS,aACZA,EAAS,WAAa,IAAI,KAE5B,IAAME,EAAMJ,EAAW,QAAQ,CAAC,EAChC,GAAIE,EAAS,WAAW,IAAIE,CAAG,EAAG,CAChChD,EAAK,SAAW8C,EAAS,WAAW,IAAIE,CAAG,EAC3C,MACF,CACA,IAAMC,EAAaN,EAASI,EAAUH,CAAU,EAC5CK,IACFH,EAAS,WAAW,IAAIE,EAAKC,CAAU,EACvCjD,EAAK,SAAWiD,EAEpB,EAEI1D,EAAO,OAAO,SAChBA,EAAO,OAAO,SAAUQ,GAAe,CACjCA,GAAO,QAAQ8C,EAAY9C,CAAK,CACtC,CAAC,EACSR,EAAO,OAAe,QAChCsD,EAAYtD,EAAO,MAAa,CAEpC,CAEQ,qBAAqBD,EAAiBC,EAAwBU,EAAwB,CAC5F,IAAMiD,EAAUjD,EAAI,OAAO,qBAAqB,EAChD,GAAI,CAACiD,EAAS,OAEd,IAAMC,EAAQ,iBAAiB7D,CAAE,EAE3B8D,EAAStD,GAAa,CAC1B,IAAMuD,EAAavD,GAAK,UAAU,WAClC,GAAI,CAACuD,GAAY,SAAU,OAE3B,IAAMC,EAASJ,EAAQ,qBAAqBG,EAAY/D,EAAI6D,CAAK,EAEjE,OAAW,CAACH,EAAKO,CAAK,IAAK,OAAO,QAAQD,CAAM,EAAG,CACjD,IAAME,EAAMH,EAAW,WAAWL,CAAG,EACrC,GAAI,CAACQ,EAAK,SAEV,IAAMC,EAAaP,EAAgB,qBAAqB,KAAKA,CAAO,EAC9DQ,EAAYD,EAAYA,EAAUD,EAAI,KAAMD,CAAK,EAAIA,EAEvDzD,EAAI,UAAU,QAAQ,WAAWkD,CAAG,EACtClD,EAAI,SAAS,OAAO,SAASkD,CAAG,EAAE,MAAQU,EACjC5D,EAAI,UAAU,iBAAiBkD,CAAG,EAC3ClD,EAAI,SAAS,eAAekD,CAAG,EAAE,MAAQU,EAChC5D,EAAI,WAAWkD,CAAG,IAC3BlD,EAAI,SAASkD,CAAG,EAAE,MAAQU,EAE9B,CACF,EAEA,GAAInE,EAAO,OAAO,SAChBA,EAAO,OAAO,SAAUQ,GAAe,CACjCA,EAAM,SACU,MAAM,QAAQA,EAAM,QAAQ,EAAIA,EAAM,SAAW,CAACA,EAAM,QAAQ,GACxE,QAAQqD,CAAK,CAE3B,CAAC,UACS7D,EAAO,OAAe,OAAQ,CACxC,IAAMS,EAAOT,EAAO,QACF,MAAM,QAAQS,EAAK,QAAQ,EAAIA,EAAK,SAAW,CAACA,EAAK,QAAQ,GACrE,QAAQoD,CAAK,CACzB,CACF,CAEQ,gBAAgB9D,EAAiBW,EAA+B,CACtE,OAAOZ,EAAiB,WAAW,IAAIC,EAAIW,EAAMX,GAAO,CACtD,IAAMqE,EAAYrE,EAAW,mBAAmB,EAC1C6D,EAAQ,iBAAiB7D,CAAE,EAE3BsE,EAAa,CAACC,EAAcC,IAA6B,CAC7D,IAAMC,EAAWJ,GAAU,MAAME,CAAI,EACrC,GAA8BE,GAAa,KAAM,CAC/C,IAAMC,EACJ,OAAOD,GAAa,UAAY,UAAYA,EACvCA,EAAiB,MAClBA,EACAE,EAAM,OAAOD,GAAQ,SAAWA,EAAM,OAAO,WAAW,OAAOA,CAAG,CAAC,EACzE,GAAI,CAAC,OAAO,MAAMC,CAAG,EAAG,OAAOA,CACjC,CACA,IAAMA,EAAM,OAAO,WAAWd,EAAM,iBAAiBU,CAAI,CAAC,EAC1D,OAAO,OAAO,MAAMI,CAAG,EAAIH,EAAWG,CACxC,EAEMC,EAAcL,GAAqC,CACvD,IAAME,EAAWJ,GAAU,MAAME,CAAI,EAC/BG,EACJD,GAAY,OAAOA,GAAa,UAAY,UAAYA,EACnDA,EAAiB,MAClBA,EACN,OAAI,OAAOC,GAAQ,SAAiBA,EAAI,KAAK,GAAK,OACtCb,EAAM,iBAAiBU,CAAI,EAAE,KAAK,GAChC,MAChB,EAEMM,EAAW,CAACN,EAAcC,EAAW,KAAmB,CAC5D,IAAMM,EAAMF,EAAWL,CAAI,EAC3B,GAAI,CAACO,EAAK,OAAON,EACjB,IAAMO,EAAOD,EAAI,YAAY,EAC7B,OAAOC,IAAS,QAAUA,IAAS,KAAOA,IAAS,MAC/C,GACAA,IAAS,SAAWA,IAAS,KAAOA,IAAS,KAC7C,GACAP,CACN,EAEA,MAAO,CACL,WAAYF,EAAW,gBAAiB,CAAC,EACzC,SAAUA,EAAW,UAAW,CAAC,EACjC,QAASA,EAAW,aAAc,CAAC,EACnC,QAASA,EAAW,aAAc,CAAC,EACnC,QAASA,EAAW,aAAc,CAAC,EACnC,UAAWA,EAAW,YAAa,CAAC,EACpC,QAASA,EAAW,YAAa,GAAG,EACpC,MAAOM,EAAW,kBAAkB,EACpC,UAAWN,EAAW,uBAAwB,GAAG,EACjD,UAAWA,EAAW,uBAAwB,GAAG,EACjD,SAAUM,EAAW,qBAAqB,EAC1C,WAAYC,EAAS,gBAAiB,EAAK,EAC3C,cAAeA,EAAS,mBAAoB,EAAK,EACjD,gBAAiBP,EAAW,qBAAsB,CAAC,CACrD,CACF,CAAC,CACH,CAEQ,WAAWtE,EAAiBW,EAAgC,CAClE,IAAMqE,EAAUhF,EAAW,cAC3B,OAAIgF,GAIGjF,EAAiB,YAAY,IAAIC,EAAIW,EAAMX,GAAO,CACvD,IAAMa,EAAOb,EAAG,sBAAsB,EAChCiF,EAAQjF,EAAG,aAAea,EAAK,MAC/BqE,EAASlF,EAAG,cAAgBa,EAAK,OACvC,MAAO,CAAE,KAAAA,EAAM,MAAAoE,EAAO,OAAAC,CAAO,CAC/B,CAAC,CACH,CACF,EA5YanF,EACI,WAAa,IAAIoF,EADrBpF,EAEI,YAAc,IAAIoF,EAFtBpF,EAGI,YAAmB,KAHvBA,EAII,gBAWX,IAAI,QAfGA,EAgBI,oBAAuD,IAAI,QAhBrE,IAAMqF,GAANrF,ECYP,IAAMsF,GAAa,KAAK,GAAK,IAEvBC,EAAuC,CAC3C,KAAM,UACN,MAAO,IACP,KAAM,EACN,MAAO,UACP,QAAS,EACT,OAAQ,IACR,QAAS,IACT,QAAS,IACT,KAAM,EACN,SAAU,GACV,UAAW,EACX,aAAc,IACd,cAAe,GACf,kBAAmB,CAAC,EAAG,EAAG,CAAC,EAC3B,gBAAiB,CAAC,EAAG,IAAK,CAAC,EAC3B,aAAc,GACd,sBAAuB,GACvB,uBAAwB,GACxB,cAAe,SACf,iBAAkB,GAClB,oBAAqB,GACrB,kBAAmB,GACnB,cAAe,SACf,iBAAkB,GAClB,oBAAqB,GACrB,kBAAmB,GACnB,cAAe,EACf,uBAAwB,GACxB,sBAAuB,GACvB,eAAgB,GAChB,aAAc,GACd,iBAAkB,EAClB,wBAAyB,EACzB,yBAA0B,EAC1B,yBAA0B,EAC1B,yBAA0B,EAC1B,wBAAyB,CAC3B,EAEaC,EAAN,MAAMA,CAA4D,CAOvE,KAAKC,EAAiBC,EAAwBC,EAAkBC,EAAsB,CACpF,IAAMC,EAAUJ,EAAW,cACrBK,EAAOD,EAASA,EAAO,KAAOJ,EAAG,sBAAsB,EACvDM,EAAS,KAAK,gBAAgBN,EAAIE,CAAG,EAErCK,EAAgBF,EAAK,KAAOA,EAAK,MAAQ,GACzCG,EAAgBH,EAAK,IAAMA,EAAK,OAAS,GAE/C,GAAIH,EAAI,OAAO,QAAQ,IAAM,eAC3BD,EAAO,OAAO,SAAS,IACrBM,EAAgBL,EAAI,cAAgB,EACpC,EAAEM,EAAgBN,EAAI,eAAiB,GACvCI,EAAO,UACT,MACK,CACL,IAAMG,EAAUP,EAAI,OAAO,iBAAiBI,EAAO,UAAU,EACvDI,EAAcH,EAAgBL,EAAI,cAClCS,EAAcH,EAAgBN,EAAI,eACxCD,EAAO,OAAO,SAAS,KACpBS,EAAc,IAAOD,EAAQ,MAC9B,EAAEE,EAAc,IAAOF,EAAQ,OAC/BH,EAAO,UACT,CACF,CAEA,IAAMM,EAAcT,GAAY,OAAS,EACnCU,EAAQP,EAAO,MAAQM,EAC7BX,EAAO,OAAO,MAAM,IAAIY,EAAOA,EAAOA,CAAK,EAE3CZ,EAAO,OAAO,SAAS,EAAI,CAACK,EAAO,QAAUT,GAC7CI,EAAO,OAAO,SAAS,EAAIK,EAAO,QAAUT,GAC5CI,EAAO,OAAO,SAAS,EAAI,CAACK,EAAO,QAAUT,GAC7CI,EAAO,OAAO,SAAS,MAAQ,MAE/B,IAAMa,EAAS,KAAK,YAAYR,EAAQD,EAAMH,EAAKC,CAAU,EACvDY,EAAOhB,EAAsB,WAAW,IAAIE,CAAM,GACpD,CAACc,GAAQ,CAAC,KAAK,aAAaA,EAAMD,CAAM,KAC1Cf,EAAsB,WAAW,IAAIE,EAAQa,CAAM,EAClDb,EAAO,OAAe,YAAYa,CAAM,GAG3C,KAAK,wBAAwBd,EAAIC,EAAQC,EAAKI,CAAM,EACpD,KAAK,qBAAqBN,EAAIC,EAAQC,CAAG,EAEzC,IAAMc,EAAM,YAAY,IAAI,EACtBC,EAAOlB,EAAsB,SAAS,IAAIE,CAAM,GAAKe,EACrDE,EAAK,KAAK,IAAI,GAAIF,EAAMC,GAAQ,GAAI,EAC1C,OAAAlB,EAAsB,SAAS,IAAIE,EAAQe,CAAG,EAC7Cf,EAAO,OAAe,SAASiB,CAAE,EAE3B,CAAE,MAAOf,GAAY,OAAS,CAAE,CACzC,CAEQ,gBAAgBH,EAAiBE,EAAuC,CAC9E,OAAOH,EAAsB,WAAW,IAAIC,EAAIE,EAAMF,GAAO,CAC3D,IAAMmB,EAAS,IAAIC,GAAYpB,CAAE,EAE3BqB,EADUF,EAAO,WAAW,mBAAoBrB,EAAe,IAAI,EAAE,YAAY,IAC9D,YAAc,YAAc,UACrD,MAAO,CACL,GAAGA,EACH,WAAYqB,EAAO,WAAW,gBAAiB,CAAC,EAChD,MAAOA,EAAO,WAAW,UAAW,CAAC,EACrC,QAASA,EAAO,WAAW,aAAc,CAAC,EAC1C,QAASA,EAAO,WAAW,aAAc,CAAC,EAC1C,QAASA,EAAO,WAAW,aAAc,CAAC,EAC1C,aAAcA,EAAO,WAAW,kBAAmB,CAAC,EAAI,GACxD,aAAcA,EAAO,WAAW,kBAAmB,OAAO,EAC1D,KAAAE,EACA,MAAOF,EAAO,WAAW,oBAAqBrB,EAAe,KAAK,EAClE,KAAMqB,EAAO,WAAW,mBAAoBrB,EAAe,IAAI,EAC/D,MAAOqB,EAAO,WAAW,oBAAqBrB,EAAe,KAAK,EAClE,QAASqB,EAAO,WAAW,sBAAuBrB,EAAe,OAAO,EACxE,OAAQqB,EAAO,WAAW,qBAAsBrB,EAAe,MAAM,EACrE,KAAMqB,EAAO,WAAW,mBAAoBrB,EAAe,IAAI,EAC/D,SAAUqB,EAAO,WAAW,cAAerB,EAAe,QAAQ,EAClE,UAAWqB,EAAO,WAAW,eAAgBrB,EAAe,SAAS,EACrE,aAAcqB,EAAO,WAAW,kBAAmBrB,EAAe,YAAY,EAC9E,cAAeqB,EAAO,WAAW,mBAAoBrB,EAAe,aAAa,EACjF,kBAAmB,KAAK,UACtBqB,EAAO,WAAW,uBAAwB,OAAO,EACjDrB,EAAe,iBACjB,EACA,gBAAiB,KAAK,UACpBqB,EAAO,WAAW,qBAAsB,SAAS,EACjDrB,EAAe,eACjB,EACA,aAAcqB,EAAO,WAAW,kBAAmBrB,EAAe,YAAY,EAC9E,sBAAuBqB,EAAO,WAC5B,4BACArB,EAAe,qBACjB,EACA,uBAAwBqB,EAAO,WAC7B,6BACArB,EAAe,sBACjB,EACA,cAAe,KAAK,WAClBqB,EAAO,WAAW,oBAAqBrB,EAAe,aAAa,CACrE,EACA,iBAAkBqB,EAAO,WAAW,oBAAqBrB,EAAe,gBAAgB,EACxF,oBAAqBqB,EAAO,WAC1B,2BACArB,EAAe,mBACjB,EACA,kBAAmBqB,EAAO,WACxB,yBACArB,EAAe,iBACjB,EACA,cAAe,KAAK,kBAClBqB,EAAO,WAAW,mBAAoBrB,EAAe,aAAa,CACpE,EACA,iBAAkBqB,EAAO,WAAW,mBAAoBrB,EAAe,gBAAgB,EACvF,oBAAqBqB,EAAO,WAC1B,0BACArB,EAAe,mBACjB,EACA,kBAAmBqB,EAAO,WACxB,wBACArB,EAAe,iBACjB,EACA,cAAeqB,EAAO,WAAW,mBAAoBrB,EAAe,aAAa,EACjF,uBAAwBqB,EAAO,WAC7B,6BACArB,EAAe,sBACjB,EACA,sBAAuBqB,EAAO,WAC5B,4BACArB,EAAe,qBACjB,EACA,eAAgBqB,EAAO,WAAW,oBAAqBrB,EAAe,cAAc,EACpF,aAAcqB,EAAO,WAAW,kBAAmBrB,EAAe,YAAY,EAC9E,iBAAkBqB,EAAO,WAAW,sBAAuBrB,EAAe,gBAAgB,EAC1F,wBAAyBqB,EAAO,WAC9B,qBACArB,EAAe,uBACjB,EACA,yBAA0BqB,EAAO,WAC/B,uBACArB,EAAe,wBACjB,EACA,yBAA0BqB,EAAO,WAC/B,uBACArB,EAAe,wBACjB,EACA,yBAA0BqB,EAAO,WAC/B,uBACArB,EAAe,wBACjB,EACA,wBAAyB,KAAK,sBAAsBE,EAAI,kBAAkB,CAC5E,CACF,CAAC,CACH,CAEQ,sBAAsBA,EAAiBsB,EAA0B,CACvE,IAAMC,EAAQ,iBAAiBvB,CAAE,EAC3BwB,EAAa,KAAK,oBAAoBD,EAAM,kBAAkB,EAC9DE,EAAY,KAAK,oBAAoBF,EAAM,kBAAkB,EAE7DG,EAAQ,KAAK,oBAAoBF,EAAYF,CAAQ,EAC3D,GAAII,IAAU,GAAI,CAChB,IAAMC,EAAY,KAAK,yBAAyBJ,EAAM,UAAU,EAC1DK,EAAQD,EAAU,IAAIL,CAAQ,GAAKK,EAAU,IAAI,KAAK,EAC5D,OAAOC,EAAQA,EAAM,SAAW,CAClC,CAEA,OAAO,KAAK,UAAUH,EAAUC,CAAK,GAAKD,EAAUA,EAAU,OAAS,CAAC,GAAK,IAAI,CACnF,CAEQ,oBAAoBI,EAAyB,CACnD,IAAMC,EAAmB,CAAC,EACtBC,EAAU,GACVC,EAAQ,EACZ,QAASC,EAAI,EAAGA,EAAIJ,EAAM,OAAQI,GAAK,EAAG,CACxC,IAAMC,EAAKL,EAAMI,CAAC,EACdC,IAAO,MAAKF,GAAS,GACrBE,IAAO,MAAKF,EAAQ,KAAK,IAAI,EAAGA,EAAQ,CAAC,GACzCE,IAAO,KAAOF,IAAU,GAC1BF,EAAO,KAAKC,EAAQ,KAAK,CAAC,EAC1BA,EAAU,IAEVA,GAAWG,CAEf,CACA,OAAIH,EAAQ,KAAK,GAAGD,EAAO,KAAKC,EAAQ,KAAK,CAAC,EACvCD,EAAO,OAAS,EAAIA,EAAS,CAAC,KAAK,CAC5C,CAEQ,oBAAoBN,EAAsBW,EAAsB,CACtE,IAAMC,EAAaZ,EAAW,IAAKa,GAASA,EAAK,KAAK,EAAE,YAAY,CAAC,EACjEX,EAAQU,EAAW,QAAQD,CAAI,EACnC,OAAIT,IAAU,KACZA,EAAQU,EAAW,QAAQ,KAAK,GAE3BV,CACT,CAEQ,UAAUG,EAAuB,CACvC,IAAMS,EAAMT,EAAM,KAAK,EAAE,YAAY,EACrC,GAAIS,EAAI,SAAS,IAAI,EAAG,CACtB,IAAMC,EAAM,OAAO,WAAWD,EAAI,MAAM,EAAG,EAAE,CAAC,EAC9C,OAAO,OAAO,SAASC,CAAG,EAAIA,EAAM,IAAO,CAC7C,CACA,GAAID,EAAI,SAAS,GAAG,EAAG,CACrB,IAAMC,EAAM,OAAO,WAAWD,EAAI,MAAM,EAAG,EAAE,CAAC,EAC9C,OAAO,OAAO,SAASC,CAAG,EAAIA,EAAM,CACtC,CACA,IAAMA,EAAM,OAAO,WAAWD,CAAG,EACjC,OAAO,OAAO,SAASC,CAAG,EAAIA,EAAM,CACtC,CAEQ,yBAAyBV,EAAkD,CACjF,IAAMW,EAAM,IAAI,IAEhB,OADc,KAAK,oBAAoBX,CAAK,EACtC,QAASY,GAAS,CACtB,GAAI,CAACA,EAAM,OACX,IAAMC,EAASD,EAAK,KAAK,EAAE,MAAM,kBAAkB,EAC/CJ,EAAO,GACPM,EAAW,GACfD,EAAO,QAASE,GAAU,CACxB,IAAMC,EAAQD,EAAM,YAAY,EAC5BC,EAAM,SAAS,IAAI,GAAKA,EAAM,SAAS,GAAG,GAAK,YAAY,KAAKA,CAAK,EAClEF,IAAUA,EAAWE,GAE1BA,EAAM,WAAW,cAAc,GAC/BA,EAAM,WAAW,OAAO,GACxBA,IAAU,UACVA,IAAU,QACVA,IAAU,WACVA,IAAU,YACVA,IAAU,eAEAR,IACVA,EAAOO,EAEX,CAAC,EACIP,GACLG,EAAI,IAAIH,EAAK,KAAK,EAAE,YAAY,EAAG,CACjC,SAAU,KAAK,UAAUM,GAAY,IAAI,CAC3C,CAAC,CACH,CAAC,EACMH,CACT,CAEQ,UAAUX,EAAeiB,EAA8D,CAC7F,IAAMC,EAAQlB,EACX,MAAM,QAAQ,EACd,IAAKY,GAAS,OAAO,WAAWA,CAAI,CAAC,EACrC,OAAQF,GAAQ,CAAC,OAAO,MAAMA,CAAG,CAAC,EACrC,OAAIQ,EAAM,QAAU,EACX,CAACA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAE/BD,CACT,CAEQ,WAAWjB,EAA2C,CAC5D,IAAMO,EAAaP,EAAM,KAAK,EAAE,YAAY,EAC5C,OAAIO,IAAe,MAAc,MAC7BA,IAAe,QAAgB,QAC5B,QACT,CAEQ,kBAAkBP,EAA2C,CACnE,OAAO,KAAK,WAAWA,CAAK,CAC9B,CAEQ,YACNvB,EACAD,EACAH,EACAC,EACsB,CAEtB,IAAMU,EADcV,GAAY,OAAS,EAEnC6C,EAAgB,GAClBC,EACAC,EACAC,EACJ,OAAI7C,EAAO,cACT4C,EAAU,KAAK,QAAQ7C,EAAK,MAAQ2C,EAAe1C,EAAO,WAAYJ,CAAG,EACzEiD,EAAU,KAAK,QAAQ9C,EAAK,OAAS2C,EAAe1C,EAAO,WAAYJ,CAAG,EAC1E+C,EAAS,KAAK,IAAIC,EAASC,CAAO,IAElCF,EAAS,KAAK,QAAQ3C,EAAO,OAAQA,EAAO,WAAYJ,CAAG,EAC3DgD,EAAUD,EACVE,EAAUF,GAEL,CACL,GAAG3C,EACH,MAAO,KAAK,IAAI,EAAG,KAAK,MAAMA,EAAO,KAAK,CAAC,EAC3C,KAAM,KAAK,IAAI,GAAKA,EAAO,IAAI,EAC/B,QAAS,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGA,EAAO,OAAO,CAAC,EAChD,OAAQ,KAAK,IAAI,EAAG2C,EAASpC,CAAK,EAClC,QAAS,KAAK,IAAI,EAAGqC,EAAUrC,CAAK,EACpC,QAAS,KAAK,IAAI,EAAGsC,EAAUtC,CAAK,EACpC,KAAM,KAAK,IAAI,EAAG,KAAK,MAAMP,EAAO,IAAI,CAAC,EACzC,SAAU,KAAK,IAAI,EAAGA,EAAO,QAAQ,EACrC,UAAW,KAAK,IAAI,EAAGA,EAAO,SAAS,EACvC,aAAc,KAAK,IAAI,GAAKA,EAAO,YAAY,EAC/C,cAAe,KAAK,IAAI,EAAGA,EAAO,aAAa,EAC/C,aAAc,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGA,EAAO,YAAY,CAAC,EAC1D,sBAAuB,KAAK,IAAI,EAAGA,EAAO,qBAAqB,EAC/D,uBAAwB,KAAK,IAAI,EAAGA,EAAO,sBAAsB,EACjE,cAAe,KAAK,IAAI,GAAKA,EAAO,aAAa,EACjD,uBAAwB,KAAK,IAAI,EAAGA,EAAO,sBAAsB,EACjE,sBAAuB,KAAK,IAAI,EAAGA,EAAO,qBAAqB,EAC/D,eAAgB,KAAK,IAAI,EAAGA,EAAO,cAAc,EACjD,aAAc,KAAK,IAAI,EAAGA,EAAO,YAAY,EAC7C,iBAAkB,KAAK,IAAI,EAAGA,EAAO,gBAAgB,EACrD,wBAAyB,KAAK,IAAI,EAAGA,EAAO,uBAAuB,EACnE,yBAA0B,KAAK,IAAI,EAAGA,EAAO,wBAAwB,EACrE,yBAA0B,KAAK,IAAI,EAAGA,EAAO,wBAAwB,EACrE,yBAA0B,KAAK,IAAI,EAAGA,EAAO,wBAAwB,CACvE,CACF,CAEQ,QAAQuB,EAAeuB,EAAWlD,EAA0B,CAClE,GAAIA,EAAI,OAAO,QAAQ,IAAM,eAC3B,OAAO2B,EAGT,IAAMwB,EADUnD,EAAI,OAAO,iBAAiBkD,CAAC,EACpB,MAAQ,KAAK,IAAI,EAAGlD,EAAI,aAAa,EAC9D,OAAO2B,EAAQwB,CACjB,CAEQ,aAAaC,EAAyBC,EAAkC,CAC9E,OAAO,KAAK,UAAUD,CAAC,IAAM,KAAK,UAAUC,CAAC,CAC/C,CAEQ,wBACNvD,EACAC,EACAC,EACAI,EACM,CAEN,IAAMkD,GADUlD,EAAO,cAAgB,SAClB,MAAM,GAAG,EAAE,CAAC,EAAE,KAAK,EAAE,YAAY,EAChDmD,EAAaC,GAA+B,IAAIF,CAAI,EACpDG,EAAUzD,EAAI,OAAO,qBAAqB,EAEhD,GAAI,CAACuD,GAAc,CAACE,GAAW,CAACA,EAAQ,SAASF,CAAU,EAAG,CAI5D,GAAI,EAFF1D,EAAsB,kBAAkB,IAAIE,CAAM,GAClDF,EAAsB,iBAAiB,IAAIE,CAAM,GACjC,OAElB,IAAM2D,EAAW7D,EAAsB,kBAAkB,IAAIE,CAAM,EAC/D2D,IACFA,EAAS,QAAQ,EACjB7D,EAAsB,kBAAkB,OAAOE,CAAM,GAEvDF,EAAsB,iBAAiB,OAAOE,CAAM,EACnDA,EAAO,OAAe,cAAc,KAAM,CAAE,OAAQ,GAAM,OAAQ,EAAK,CAAC,EACzE,MACF,CAGA,GADiBF,EAAsB,iBAAiB,IAAIE,CAAM,IACjDuD,EAAM,CACrB,IAAMI,EAAW7D,EAAsB,kBAAkB,IAAIE,CAAM,EAC/D2D,GAAUA,EAAS,QAAQ,EAE/B,IAAMrC,EAAQ,iBAAiBvB,CAAE,EAC3B6D,EAAkBF,EAAQ,qBAAqBF,EAAYzD,EAAIuB,CAAK,EACpEuC,EAAWH,EAAQ,OAAOF,EAAYI,CAAe,EAC3D9D,EAAsB,kBAAkB,IAAIE,EAAQ6D,CAAQ,EAC5D/D,EAAsB,iBAAiB,IAAIE,EAAQuD,CAAI,EAEvD,IAAMO,EAAWD,EAAS,SACpBE,EAAW,CAAC,CAACD,GAAU,iBACvBE,EAAchE,EAAO,OAC3BgE,EAAO,cAAcF,EAAU,CAAE,OAAQ,GAAM,OAAQ,EAAM,CAAC,EAC9DE,EAAO,cAAcD,EAAWD,EAAW,KAAM,CAAE,OAAQ,GAAO,OAAQ,EAAK,CAAC,CAClF,CACF,CAEQ,qBAAqB/D,EAAiBC,EAAwBC,EAAwB,CAC5F,IAAMyD,EAAUzD,EAAI,OAAO,qBAAqB,EAChD,GAAI,CAACyD,EAAS,OAEd,IAAMpC,EAAQ,iBAAiBvB,CAAE,EAE3BkE,EAASC,GAAa,CAC1B,IAAMV,EAAaU,GAAK,UAAU,WAClC,GAAI,CAACV,GAAY,SAAU,OAE3B,IAAMW,EAAST,EAAQ,qBAAqBF,EAAYzD,EAAIuB,CAAK,EAEjE,OAAW,CAAC8C,EAAKxC,CAAK,IAAK,OAAO,QAAQuC,CAAM,EAAG,CACjD,IAAME,EAAMb,EAAW,WAAWY,CAAG,EACrC,GAAI,CAACC,EAAK,SAEV,IAAMC,EAAaZ,EAAgB,qBAAqB,KAAKA,CAAO,EAC9Da,EAAYD,EAAYA,EAAUD,EAAI,KAAMzC,CAAK,EAAIA,EAEvDsC,EAAI,UAAU,QAAQ,WAAWE,CAAG,EACtCF,EAAI,SAAS,OAAO,SAASE,CAAG,EAAE,MAAQG,EACjCL,EAAI,UAAU,iBAAiBE,CAAG,EAC3CF,EAAI,SAAS,eAAeE,CAAG,EAAE,MAAQG,EAChCL,EAAI,WAAWE,CAAG,IAC3BF,EAAI,SAASE,CAAG,EAAE,MAAQG,EAE9B,CACF,EAEIvE,EAAO,OAAO,UAChBA,EAAO,OAAO,SAAUwE,GAAe,EACjCA,EAAM,QAAUA,EAAM,YACN,MAAM,QAAQA,EAAM,QAAQ,EAAIA,EAAM,SAAW,CAACA,EAAM,QAAQ,GACxE,QAAQP,CAAK,CAE3B,CAAC,CAEL,CACF,EAlaanE,EACI,WAAa,IAAI2E,EADrB3E,EAEI,WAA4D,IAAI,QAFpEA,EAGI,SAA4C,IAAI,QAHpDA,EAII,iBAAoD,IAAI,QAJ5DA,EAKI,kBAAgE,IAAI,QAL9E,IAAM4E,GAAN5E,ECxDA,IAAM6E,GAAN,KAA2B,CAIhC,OAAe,aAAaC,EAAsB,CAChD,OAAOA,EAAK,KAAK,EAAE,YAAY,CACjC,CAEA,OAAO,SAASA,EAAcC,EAAmB,CAC/C,IAAMC,EAAaF,EAAK,KAAK,EACxBE,GACL,KAAK,MAAM,IAAI,KAAK,aAAaA,CAAU,EAAG,CAAE,KAAMA,EAAY,IAAAD,CAAI,CAAC,CACzE,CAEA,OAAO,WAAWD,EAAoB,CACpC,IAAME,EAAaF,EAAK,KAAK,EACxBE,IACL,KAAK,YAAc,KAAK,aAAaA,CAAU,EACjD,CAEA,OAAO,IAAIF,EAA6C,CACtD,OAAO,KAAK,MAAM,IAAI,KAAK,aAAaA,CAAI,CAAC,CAC/C,CAEA,OAAO,MAA4B,CACjC,OAAO,MAAM,KAAK,KAAK,MAAM,OAAO,CAAC,CACvC,CAEA,OAAO,kBAAkBG,EAA8C,CACrE,GAAI,CAACA,EACH,OAAO,KAAK,WAAW,EAGzB,IAAMC,EAAWD,EACd,MAAM,GAAG,EACT,IAAKE,GAAUA,EAAM,KAAK,EAAE,QAAQ,eAAgB,EAAE,CAAC,EACvD,OAAO,OAAO,EAEjB,QAAWC,KAAUF,EAAU,CAC7B,IAAMG,EAAQ,KAAK,MAAM,IAAI,KAAK,aAAaD,CAAM,CAAC,EACtD,GAAIC,EAAO,OAAOA,CACpB,CAEA,OAAO,KAAK,WAAW,CACzB,CAEA,OAAe,YAAuC,CACpD,OAAK,KAAK,aACH,KAAK,MAAM,IAAI,KAAK,WAAW,GAAK,IAC7C,CACF,EAlDaR,GACI,MAAwC,IAAI,IADhDA,GAEI,YAA6B,KCe9C,IAAIS,GAAuC,KACvCC,GAAsB,KAEtBC,GAAoC,KACpCC,GAAmB,KAEvB,eAAeC,IAA6B,CAC1C,OAAIH,KAICD,KACHA,IAAmB,SACb,OAAO,OAAW,KAAgB,OAAe,UACnDC,GAAkB,OAAe,SAC1BA,IAGF,IAAI,QAAQ,CAACI,EAASC,IAAW,CACtC,GAAI,OAAO,SAAa,IAAa,CACnCA,EAAO,IAAI,MAAM,oEAAoE,CAAC,EACtF,MACF,CACA,IAAMC,EAAS,SAAS,cAAc,QAAQ,EAC9CA,EAAO,IAAM,sEACbA,EAAO,OAAS,IAAM,CACpBN,GAAkB,OAAe,SACjCI,EAAQJ,EAAc,CACxB,EACAM,EAAO,QAAU,IAAMD,EAAO,IAAI,MAAM,4CAA4C,CAAC,EACrF,SAAS,KAAK,YAAYC,CAAM,CAClC,CAAC,GACA,GAEEP,GACT,CAEA,eAAeQ,IAAiC,CAC9C,OAAIL,KAICD,KACHA,IAAgB,SACV,OAAO,OAAW,KAAgB,OAAe,QAAQ,YAC3DC,GAAe,OAAe,OACvBA,IAGF,IAAI,QAAQ,CAACE,EAASC,IAAW,CACtC,GAAI,OAAO,SAAa,IAAa,CACnCA,EAAO,IAAI,MAAM,sEAAsE,CAAC,EACxF,MACF,CACA,IAAMC,EAAS,SAAS,cAAc,QAAQ,EAC9CA,EAAO,IAAM,yEACbA,EAAO,OAAS,IAAM,CACpB,IAAIE,EAAW,EACTC,EAAc,IACdC,EAAa,IAAM,CACvBF,IACA,IAAMG,EAAM,OACRA,EAAI,QAAQ,YACdT,GAAcS,EAAI,OAClBP,EAAQF,EAAW,GACVM,GAAYC,EACrBJ,EAAO,IAAI,MAAM,sDAAsD,CAAC,EAExE,WAAWK,EAAY,EAAE,CAE7B,EACAA,EAAW,CACb,EACAJ,EAAO,QAAU,IAAM,CACrBD,EAAO,IAAI,MAAM,8CAA8C,CAAC,CAClE,EACA,SAAS,KAAK,YAAYC,CAAM,CAClC,CAAC,GACA,GAEEL,GACT,CAEA,eAAeW,GAAgBC,EAA2C,CACxE,IAAMC,EAAQ,MAAMP,GAAiB,EAC/BQ,EAAa,IAAI,WAAWF,CAAM,EAClCG,EAAcF,EAAM,WAAWC,CAAU,EAE/C,GAAIC,aAAuB,WAAY,CACrC,IAAMC,EAAY,IAAI,YAAYD,EAAY,MAAM,EAEpD,OADiB,IAAI,WAAWC,CAAS,EAChC,IAAID,CAAW,EACjBC,CACT,CAEA,OAAOD,EAAY,MACrB,CAEA,SAASE,GAAQL,EAA8B,CAE7C,OADa,IAAI,SAASA,CAAM,EACpB,UAAU,EAAG,EAAK,IAAM,UACtC,CAOO,IAAMM,GAAN,KAAoB,CAIzB,aAAa,KAAKC,EAAuC,CACvD,IAAMC,EAAW,OAAOD,GAAW,SAAWA,EAAS,UAAY,KAAK,IAAI,EAEtEE,EAAS,KAAK,MAAM,IAAID,CAAQ,EACtC,GAAIC,EAAQ,OAAOA,EAEnB,IAAMC,EAAU,KAAK,gBAAgB,IAAIF,CAAQ,EACjD,GAAIE,EAAS,OAAOA,EAEpB,IAAMC,EAAU,KAAK,OAAOJ,EAAQC,CAAQ,EAC5C,KAAK,gBAAgB,IAAIA,EAAUG,CAAO,EAE1C,GAAI,CACF,IAAMC,EAAS,MAAMD,EACrB,YAAK,MAAM,IAAIH,EAAUI,CAAM,EACxBA,CACT,QAAE,CACA,KAAK,gBAAgB,OAAOJ,CAAQ,CACtC,CACF,CAEA,aAAqB,OAAOD,EAAoBC,EAAqC,CACnF,IAAMK,EAAW,MAAMC,GAAa,EAEhCC,EAEJ,GAAI,OAAOR,GAAW,SAEpBQ,EAAS,MADQ,MAAM,MAAMR,CAAM,GACX,YAAY,UAC3BA,aAAkB,YAC3BQ,EAASR,UACAA,aAAkB,WAC3BQ,EAASR,EAAO,WAEhB,OAAM,IAAI,MAAM,qCAAqC,EAGnDS,GAAQD,CAAM,IAChBA,EAAS,MAAME,GAAgBF,CAAM,GAGvC,IAAMG,EAAOL,EAAS,MAAME,CAAM,EAElC,GAAI,CAACG,EACH,MAAM,IAAI,MAAM,sCAAsC,EAGxD,OAAO,KAAK,kBAAkBA,CAAI,CACpC,CAEA,OAAe,kBAAkBA,EAAqB,CACpD,IAAMC,EAAQ,IAAOD,EAAK,WAEpBE,EAAoC,CAAC,EAErCC,EAAOH,EAAK,QAAQ,MAAM,cAChC,GAAIG,GAAQ,OAAOA,GAAS,SAC1B,OAAW,CAACC,EAASC,CAAU,IAAK,OAAO,QAAQF,CAAI,EAAG,CACxD,IAAMG,EAAO,OAAOF,CAAO,EAC3B,GAAI,CAAC,OAAO,SAASE,CAAI,EAAG,SAC5B,IAAMC,EAAQP,EAAK,OAAO,IAAIK,CAAoB,EAClD,GAAI,CAACE,EAAO,SAEZ,IAAMC,EAAOD,EAAM,QAAQ,EAAG,EAAGP,EAAK,UAAU,EAC1CS,EAAU,KAAK,cAAcD,EAAMP,CAAK,EACxCS,EAAeH,EAAM,cAAgBA,EAAM,MAAQP,EAAK,WAAa,GACrEW,EAAO,OAAO,aAAaL,CAAI,EACjCJ,EAAOS,CAAI,IACfT,EAAOS,CAAI,EAAI,CACb,GAAI,KAAK,MAAMD,EAAeT,CAAK,EACnC,MAAOM,EAAM,OAAS,OAAY,KAAK,MAAMA,EAAM,KAAON,CAAK,EAAI,EACnE,MAAOM,EAAM,OAAS,OAAY,KAAK,MAAMA,EAAM,KAAON,CAAK,EAAI,EACnE,EAAGQ,CACL,EACF,KAEA,SAASG,EAAI,EAAGA,EAAIZ,EAAK,OAAO,OAAQY,IAAK,CAC3C,IAAML,EAAQP,EAAK,OAAO,IAAIY,CAAC,EACzBC,EAAgB,MAAM,QAAQN,EAAM,QAAQ,EAC9CA,EAAM,SACNA,EAAM,QACN,CAACA,EAAM,OAAO,EACd,CAAC,EACL,GAAIM,EAAc,SAAW,EAAG,SAEhC,IAAML,EAAOD,EAAM,QAAQ,EAAG,EAAGP,EAAK,UAAU,EAC1CS,EAAU,KAAK,cAAcD,EAAMP,CAAK,EACxCS,EAAeH,EAAM,cAAgBA,EAAM,MAAQP,EAAK,WAAa,GAE3Ea,EAAc,QAASP,GAAiB,CACtC,GAAI,CAAC,OAAO,SAASA,CAAI,EAAG,OAC5B,IAAMK,EAAO,OAAO,aAAaL,CAAI,EACjCJ,EAAOS,CAAI,IACfT,EAAOS,CAAI,EAAI,CACb,GAAI,KAAK,MAAMD,EAAeT,CAAK,EACnC,MAAOM,EAAM,OAAS,OAAY,KAAK,MAAMA,EAAM,KAAON,CAAK,EAAI,EACnE,MAAOM,EAAM,OAAS,OAAY,KAAK,MAAMA,EAAM,KAAON,CAAK,EAAI,EACnE,EAAGQ,CACL,EACF,CAAC,CACH,CAGF,GAAI,CAACP,EAAO,GAAG,EAAG,CAChB,IAAMY,EAAad,EAAK,YAAY,GAAG,EACvCE,EAAO,GAAG,EAAI,CACZ,GAAI,KAAK,OAAOY,GAAY,cAAgBd,EAAK,WAAa,KAAQC,CAAK,EAC3E,MAAO,EACP,MAAO,EACP,EAAG,EACL,CACF,CAEA,MAAO,CACL,OAAAC,EACA,WAAYF,EAAK,MAAM,YAAY,IAAMA,EAAK,MAAM,UAAU,IAAM,UACpE,SAAU,KAAK,MAAMA,EAAK,SAAWC,CAAK,EAC1C,UAAW,KAAK,MAAMD,EAAK,UAAYC,CAAK,EAC5C,kBAAmB,KAAK,OAAOD,EAAK,OAAO,MAAM,mBAAqB,MAAQC,CAAK,EACnF,mBAAoB,KAAK,OAAOD,EAAK,OAAO,MAAM,oBAAsB,IAAMC,CAAK,EACnF,YAAa,CACX,KAAM,KAAK,OAAOD,EAAK,OAAO,MAAM,MAAQ,GAAKC,CAAK,EACtD,KAAM,KAAK,OAAOD,EAAK,OAAO,MAAM,MAAQ,KAAQC,CAAK,EACzD,KAAM,KAAK,OAAOD,EAAK,OAAO,MAAM,MAAQ,MAAQC,CAAK,EACzD,KAAM,KAAK,OAAOD,EAAK,OAAO,MAAM,MAAQ,KAAOC,CAAK,CAC1D,EACA,WAAY,IACZ,eAAgBD,EAAK,gBAAkBA,EAAK,eAAiB,IAAI,SAAS,EAC1E,0BAA2B,CACzB,OAAQ,EACR,UAAWA,EAAK,MAAM,WAAW,IAAM,GACvC,WAAYA,EAAK,MAAM,YAAY,IAAM,GACzC,cAAeA,EAAK,MAAM,eAAe,IAAM,GAC/C,SAAUA,EAAK,MAAM,UAAU,IAAM,GACrC,SAAUA,EAAK,MAAM,UAAU,IAAM,GACrC,QAASA,EAAK,MAAM,SAAS,IAAM,GACnC,eAAgBA,EAAK,MAAM,gBAAgB,IAAM,EACnD,CACF,CACF,CAEA,OAAe,cAAcQ,EAAWP,EAAuB,CAC7D,IAAMc,EAAqB,CAAC,EAE5B,QAAWC,KAAOR,EAAK,SACrB,OAAQQ,EAAI,KAAM,CAChB,IAAK,IACHD,EAAS,KAAK,KAAK,KAAK,MAAMC,EAAI,EAAIf,CAAK,CAAC,IAAI,KAAK,MAAMe,EAAI,EAAIf,CAAK,CAAC,EAAE,EAC3E,MACF,IAAK,IACHc,EAAS,KAAK,KAAK,KAAK,MAAMC,EAAI,EAAIf,CAAK,CAAC,IAAI,KAAK,MAAMe,EAAI,EAAIf,CAAK,CAAC,EAAE,EAC3E,MACF,IAAK,IACHc,EAAS,KACP,KAAK,KAAK,MAAMC,EAAI,GAAKf,CAAK,CAAC,IAAI,KAAK,MAAMe,EAAI,GAAKf,CAAK,CAAC,IAAI,KAAK,MACpEe,EAAI,EAAIf,CACV,CAAC,IAAI,KAAK,MAAMe,EAAI,EAAIf,CAAK,CAAC,EAChC,EACA,MACF,IAAK,IACHc,EAAS,KACP,KAAK,KAAK,MAAMC,EAAI,GAAKf,CAAK,CAAC,IAAI,KAAK,MAAMe,EAAI,GAAKf,CAAK,CAAC,IAAI,KAAK,MACpEe,EAAI,GAAKf,CACX,CAAC,IAAI,KAAK,MAAMe,EAAI,GAAKf,CAAK,CAAC,IAAI,KAAK,MAAMe,EAAI,EAAIf,CAAK,CAAC,IAAI,KAAK,MACnEe,EAAI,EAAIf,CACV,CAAC,EACH,EACA,MACF,IAAK,IACHc,EAAS,KAAK,GAAG,EACjB,KACJ,CAGF,OAAOA,EAAS,KAAK,GAAG,CAC1B,CAEA,OAAe,MAAME,EAAuB,CAC1C,OAAO,KAAK,MAAMA,EAAQ,GAAK,EAAI,GACrC,CAEA,OAAO,eAAeC,EAAsB,CAC1C,IAAMC,EAAQD,EAAI,YAAY,EAC9B,OAAOC,EAAM,SAAS,OAAO,GAAKA,EAAM,SAAS,UAAU,CAC7D,CAEA,OAAO,WAAWD,EAAsB,CACtC,IAAMC,EAAQD,EAAI,YAAY,EAI9B,MAFI,GADmB,4BACJ,KAAKC,CAAK,GACzBA,EAAM,SAAS,mBAAmB,GAClCA,EAAM,SAAS,SAAS,GAAK,CAACA,EAAM,SAAS,OAAO,EAE1D,CAEA,OAAO,YAAmB,CACxB,KAAK,MAAM,MAAM,CACnB,CACF,EA1Ma/B,GACI,MAA+B,IAAI,IADvCA,GAEI,gBAAkD,IAAI,IC7HvE,IAAMgC,GAAa,KAAK,GAAK,IAI7B,IAAMC,GAAqB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,EA8BdC,EAAN,MAAMA,CAAuD,CAalE,OAAe,sBAAsBC,EAAiBC,EAA8B,CAClF,IAAIC,EAAM,KAAK,mBAAmB,IAAIF,CAAO,EACxCE,IACHA,EAAM,IAAI,IACV,KAAK,mBAAmB,IAAIF,EAASE,CAAG,GAE1CA,EAAI,IAAID,CAAM,CAChB,CAEA,OAAe,uBAAuBD,EAAiBC,EAA8B,CACnF,IAAMC,EAAM,KAAK,mBAAmB,IAAIF,CAAO,EAC3CE,GACFA,EAAI,OAAOD,CAAM,CAErB,CAEA,OAAe,yBAAyBD,EAAuB,CAC7D,IAAME,EAAM,KAAK,mBAAmB,IAAIF,CAAO,EAC3CE,IACFA,EAAI,QAASC,GAAQ,CACnB,KAAK,aAAa,OAAOA,CAAG,CAC9B,CAAC,EACDD,EAAI,MAAM,EAEd,CAEA,OAAe,2BAAkC,CAC/C,GAAI,KAAK,qBAAuB,OAAO,SAAa,IAAa,OAEjE,IAAME,EAAQ,SAAS,cAAc,OAAO,EAC5CA,EAAM,aAAa,gBAAiB,aAAa,EACjDA,EAAM,YAAcN,GACpB,SAAS,KAAK,YAAYM,CAAK,EAC/B,KAAK,oBAAsB,EAC7B,CAEA,OAAe,oBAAoBC,EAAuB,CACxD,IAAMC,EAAcD,EAAG,aAAe,GAElCA,EAAG,QAAQ,eAAiBC,IAC9BD,EAAG,QAAQ,aAAeC,GAG5B,IAAMC,EAAW,iBAAiBF,CAAE,EAChCE,EAAS,WAAa,WACxBF,EAAG,MAAM,SAAW,YAGtB,IAAMG,EAAKD,EAAS,iBAAiB,YAAY,EAAE,KAAK,GAAK,IACvDE,EAAKF,EAAS,iBAAiB,YAAY,EAAE,KAAK,GAAK,IACvDG,EAAKH,EAAS,iBAAiB,YAAY,EAAE,KAAK,GAAK,IACvDI,EAAKJ,EAAS,iBAAiB,eAAe,EAAE,KAAK,GAAK,MAC1DK,EAAKL,EAAS,iBAAiB,eAAe,EAAE,KAAK,GAAK,MAC1DM,EAAKN,EAAS,iBAAiB,eAAe,EAAE,KAAK,GAAK,MAC1DO,EAAIP,EAAS,iBAAiB,SAAS,EAAE,KAAK,GAAK,IAEnDQ,EAAY,CAChBJ,IAAO,OAASA,IAAO,IAAM,cAAcA,CAAE,IAAM,GACnDC,IAAO,OAASA,IAAO,IAAM,cAAcA,CAAE,IAAM,GACnDC,IAAO,OAASA,IAAO,IAAM,cAAcA,CAAE,IAAM,GACnDL,IAAO,IAAM,WAAWA,CAAE,OAAS,GACnCC,IAAO,IAAM,WAAWA,CAAE,OAAS,GACnCC,IAAO,IAAM,WAAWA,CAAE,OAAS,GACnCI,IAAM,IAAM,SAASA,CAAC,IAAM,EAC9B,EACG,OAAO,OAAO,EACd,KAAK,GAAG,EAEXT,EAAG,MAAM,YAAY,uBAAwBU,GAAa,MAAM,CAClE,CAEA,OAAe,qBAAqBV,EAAiBJ,EAA8B,CACjF,GAAI,KAAK,iBAAiB,IAAII,CAAE,EAAG,OAEnC,IAAIW,EAAcX,EAAG,aAAe,GAE9BY,EAAW,IAAI,iBAAkBC,GAAc,CACnD,IAAMC,EAAiBd,EAAG,aAAe,GACzC,GAAIc,IAAmBH,EACrB,OAGFA,EAAcG,EAGd,IAAMC,EADY,OAAe,cAAc,UAAU,cAAc,GACvC,OAAO,sBAAsBf,CAAE,EAE3De,IACF,KAAK,aAAa,OAAOA,CAAa,EACtC,KAAK,YAAY,WAAWf,CAAE,EAE1BA,EAAG,QAAQ,eAAiBc,IAC9Bd,EAAG,QAAQ,aAAec,GAGhC,CAAC,EAEDF,EAAS,QAAQZ,EAAI,CACnB,cAAe,GACf,UAAW,GACX,QAAS,EACX,CAAC,EAED,KAAK,iBAAiB,IAAIA,EAAIY,CAAQ,CACxC,CAEA,OAAe,uBAAuBZ,EAAuB,CAC3D,IAAMY,EAAW,KAAK,iBAAiB,IAAIZ,CAAE,EACzCY,IACFA,EAAS,WAAW,EACpB,KAAK,iBAAiB,OAAOZ,CAAE,EAEnC,CAEA,KAAKA,EAAiBJ,EAAwBoB,EAAkBC,EAAsB,CACpFvB,EAAiB,0BAA0B,EAC3CA,EAAiB,oBAAoBM,CAAE,EACvCN,EAAiB,qBAAqBM,EAAIJ,CAAM,EAEhD,GAAM,CAAE,KAAAsB,EAAM,MAAOC,EAAe,OAAQC,CAAe,EAAI,KAAK,WAAWpB,EAAIgB,CAAG,EAChFK,EAAS,KAAK,gBAAgBrB,EAAIgB,CAAG,EAErC,CACJ,WAAAM,EACA,SAAAC,EACA,QAAAC,EACA,QAAAC,EACA,QAAAC,EACA,UAAAC,EACA,QAAAC,EACA,MAAAC,EACA,UAAAC,EACA,UAAAC,EACA,SAAAC,EACA,WAAAC,EACA,cAAAC,EACA,aAAAC,EACA,WAAAC,EACA,SAAAC,EACA,cAAAC,EACA,UAAAC,EACA,kBAAAC,EACA,aAAAC,EACA,UAAAC,EACA,eAAAC,EACA,YAAAC,EACA,cAAAC,EACA,QAAAC,CACF,EAAIzB,EAEE0B,EAAgB7B,EAAK,KAAOA,EAAK,MAAQ,GACzC8B,EAAgB9B,EAAK,IAAMA,EAAK,OAAS,GAE/C,GAAIF,EAAI,OAAO,QAAQ,IAAM,eAC3BpB,EAAO,OAAO,SAAS,IACrBmD,EAAgB/B,EAAI,cAAgB,EACpC,EAAEgC,EAAgBhC,EAAI,eAAiB,GACvCM,CACF,MACK,CACL,IAAM2B,EAAUjC,EAAI,OAAO,iBAAiBM,CAAU,EAChD4B,EAAcH,EAAgB/B,EAAI,cAClCmC,GAAcH,EAAgBhC,EAAI,eACxCpB,EAAO,OAAO,SAAS,KACpBsD,EAAc,IAAOD,EAAQ,MAC9B,EAAEE,GAAc,IAAOF,EAAQ,OAC/B3B,CACF,CACF,CAEA1B,EAAO,OAAO,SAAS,EAAI,CAAC4B,EAAU4B,GACtCxD,EAAO,OAAO,SAAS,EAAI6B,EAAU2B,GACrCxD,EAAO,OAAO,SAAS,EAAI,CAAC8B,EAAU0B,GACtCxD,EAAO,OAAO,SAAS,MAAQ,MAE/BA,EAAO,OAAO,SAAS,EAAI,CAAC8B,EAAU0B,GACtCxD,EAAO,OAAO,SAAS,MAAQ,MAE/B,IAAMyD,EAAS,KAAK,uBAAuBrD,EAAIsC,CAAa,EACtDrC,EAAcoD,EAAO,IAAKC,GAAMA,EAAE,IAAI,EAAE,KAAK,EAAE,EAC/CC,EAAgB,EAAQT,EAExBU,EAAO,KAAK,YAAY5D,CAAM,EACpC,GAAI,CAAC4D,EACH,MAAO,CAAE,MAAOjC,GAAYN,GAAY,OAAS,EAAG,EAGtD,GAAIoC,EAAO,SAAW,EACpB,OAAAG,EAAK,QAAU,GACR,CAAE,MAAOjC,GAAYN,GAAY,OAAS,EAAG,EAGtD,GAAIW,IAAY,EACd,OAAAhC,EAAO,OAAO,QAAU,GACjB,CAAE,MAAO2B,GAAYN,GAAY,OAAS,EAAG,EAEtDrB,EAAO,OAAO,QAAU,GAExB4D,EAAK,QAAU,GAEf,IAAMC,EAAYC,GAAqB,kBAAkBtB,GAAc,EAAE,EACzE,GAAI,CAACqB,EACH,OAAK/D,EAAiB,oBACpBA,EAAiB,kBAAoB,IAEhC,CAAE,MAAO6B,GAAYN,GAAY,OAAS,EAAG,EAGtD,GAAI,CAACD,EAAI,OAAO,UAAY,CAACA,EAAI,OAAO,mBACtC,OAAKtB,EAAiB,sBACpBA,EAAiB,oBAAsB,IAElC,CAAE,MAAO6B,GAAYN,GAAY,OAAS,EAAG,EAGtD,IAAMtB,EAAU8D,EAAU,IACtBE,EAAOjE,EAAiB,UAAU,IAAIC,CAAO,EACjD,GAAI,CAACgE,EAAM,CAET,GADAjE,EAAiB,sBAAsBC,EAASC,CAAM,EAClD,CAACF,EAAiB,aAAa,IAAIC,CAAO,EAAG,CAC/C,IAAMiE,EAAU5C,EAAI,OAAO,SAASrB,CAAO,EAAE,KAAMkE,IAC7CA,IACFnE,EAAiB,UAAU,IAAIC,EAASkE,CAAM,EAC9CnE,EAAiB,yBAAyBC,CAAO,GAE5CkE,EACR,EACDnE,EAAiB,aAAa,IAAIC,EAASiE,CAAO,CACpD,CACA,OAAAJ,EAAK,QAAU,GACR,CAAE,MAAOjC,GAAYN,GAAY,OAAS,EAAG,CACtD,CAEAvB,EAAiB,uBAAuBC,EAASC,CAAM,EAEvD,IAAMkE,EACJT,EAAO,OAAS,EACZ,GAAGA,EAAO,MAAM,IAAIA,EAAO,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC,IAAIA,EAAO,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC,IAAIA,EACtEA,EAAO,OAAS,CAClB,EAAE,EAAE,QAAQ,CAAC,CAAC,IAAIA,EAAOA,EAAO,OAAS,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC,GACxD,QAEAU,EAAM,CACV9D,EACAoC,EAAS,QAAQ,CAAC,EAClBS,GAAW,GACX5B,EAAK,MAAM,QAAQ,CAAC,EACpBA,EAAK,OAAO,QAAQ,CAAC,EACrB4C,EACAvB,EAAU,QAAQ,CAAC,EACnBC,EAAkB,QAAQ,CAAC,EAC3BC,EAAe,IAAM,IACrBC,EAAU,QAAQ,CAAC,EACnBC,EAAe,QAAQ,CAAC,EACxBC,EAAY,QAAQ,CAAC,EACrBC,EAAc,QAAQ,CAAC,CACzB,EAAE,KAAK,GAAG,EAGV,GADgBnD,EAAiB,aAAa,IAAIE,CAAM,IACxCmE,EAAK,CACnB,IAAMC,EAAWhD,EAAI,OAAO,mBAAmBf,EAAa0D,EAAM,CAChE,KAAMtB,EACN,OAAQE,EACR,cAAe,KAAK,IAAI,EAAG,KAAK,MAAMC,CAAiB,CAAC,EACxD,aAAAC,EACA,eAAAE,EACA,UAAAD,EACA,YAAAE,EACA,cAAe,KAAK,IAAI,EAAG,KAAK,MAAMC,CAAa,CAAC,EACpD,WAAY,EACZ,cAAe,EACf,MAAO,OACP,OAAAQ,EACA,aAAcnC,EAAK,MACnB,cAAeA,EAAK,MACtB,CAAC,EAEG8C,IACFA,EAAS,mBAAmB,EACxBR,EAAK,UACPA,EAAK,SAAS,UAAU,EAE1BA,EAAK,SAAWQ,EAChBpE,EAAO,SAAWoE,EAClBtE,EAAiB,aAAa,IAAIE,EAAQmE,CAAG,EAEjD,CAEA,IAAME,GAAchD,GAAY,OAAS,EACnCiD,GACJlD,EAAI,OAAO,QAAQ,IAAM,eACrB,EACAA,EAAI,OAAO,YAAYM,EAAYN,EAAI,cAAc,EAErDmD,GAAc5C,EAAW0C,GAAcC,GAEvCE,GAASD,GAAcxC,EAC7B/B,EAAO,OAAO,MAAM,IAAIuE,GAAaA,GAAaC,EAAM,EAExD,IAAMC,GAAe,CAAClD,EAAgB,GAChCmD,GAAelD,EAAiB,GAEtCoC,EAAK,SAAS,IAAIa,GAAcC,GAAc,CAAC,EAE/C,IAAMC,GAAmB7E,EAAiB,iBAAiB,IAAIE,CAAM,EACrE,OAAI2E,KAAqB,QAAaA,KAAqBpC,GACrDnB,EAAI,OAAUA,EAAI,MAAc,2BAClC,sBAAsB,IAAM,CACtBA,EAAI,OAAUA,EAAI,MAAc,2BACjCA,EAAI,MAAc,0BAA0BpB,EAAQI,CAAE,CAE3D,CAAC,EAILN,EAAiB,iBAAiB,IAAIE,EAAQuC,CAAY,EAE1DqC,GAAiB,iBAAiBxE,EAAIJ,EAAQ,CAC5C,QAAAgC,EACA,MAAOC,GAASA,IAAU,OAASA,EAAQ,OAC3C,UAAW,OAAO,SAASC,CAAS,EAAIA,EAAY,OACpD,UAAW,OAAO,SAASC,CAAS,EAAIA,EAAY,OACpD,SAAUC,GAAYA,IAAa,OAASA,EAAW,OACvD,WAAAC,EACA,cAAAC,CACF,CAAC,EAED,KAAK,qBAAqBlC,EAAIJ,EAAQoB,CAAG,EAElC,CAAE,MAAOmD,EAAY,CAC9B,CAEA,QAAQnE,EAAiBJ,EAA8B,CACrDF,EAAiB,uBAAuBM,CAAE,EAC1CN,EAAiB,aAAa,OAAOE,CAAM,CAC7C,CAEQ,uBACNI,EACAU,EAQC,CACD,IAAM2C,EAOD,CAAC,EACN,GAAI,OAAO,SAAa,KAAe,CAAC,SAAS,YAAa,OAAOA,EAErE,IAAMoB,EAAQ,SAAS,YAAY,EAC7BC,EAAS1E,EAAG,sBAAsB,EAClC2E,EAAS,SAAS,iBAAiB3E,EAAI,WAAW,SAAS,EAC7D4E,EAEJ,KAAQA,EAAOD,EAAO,SAAS,GAAI,CACjC,IAAME,EAAOD,EAAK,aAAe,GACjC,GAAI,GAACC,EAAK,KAAK,GAAKA,IAAS,KAE7B,QAASC,EAAI,EAAGA,EAAID,EAAK,OAAQC,IAAK,CACpC,IAAMC,EAAOF,EAAKC,CAAC,EAGnB,GAFIC,IAAS;AAAA,GAAQA,IAAS,MAE1B,CAACA,EAAK,KAAK,EAAG,SAElBN,EAAM,SAASG,EAAME,CAAC,EACtBL,EAAM,OAAOG,EAAME,EAAI,CAAC,EACxB,IAAME,EAAQP,EAAM,eAAe,EAEnC,GAAIO,EAAM,OAAS,EAAG,CACpB,IAAMC,EAAID,EAAM,CAAC,EACXE,EAAID,EAAE,KAAOP,EAAO,KACpBS,EAAIF,EAAE,IAAMP,EAAO,IAEnBU,EAAc,KAAK,mBAAmBL,EAAMrE,CAAS,EAE3D2C,EAAO,KAAK,CACV,KAAM+B,EACN,EAAAF,EACA,EAAAC,EACA,MAAOF,EAAE,MACT,OAAQA,EAAE,MACZ,CAAC,CACH,CACF,CACF,CACA,OAAO5B,CACT,CAEQ,YAAYzD,EAAoC,CACtD,IAAMyF,EAASzF,EAAO,OACtB,GAAIyF,GAAQ,WAAY,OAAOA,EAAO,WACtC,GAAIA,GAAQ,OAAQ,OAAOA,EAC3B,GAAI,MAAM,QAAQA,GAAQ,QAAQ,EAAG,CACnC,IAAMC,EAAQD,EAAO,SAAS,KAAME,GAAeA,GAAO,MAAM,EAChE,GAAID,EACF,OAAAD,EAAO,WAAaC,EACbA,CAEX,CACA,OAAO,IACT,CAEQ,qBAAqBtF,EAAiBJ,EAAwBoB,EAAwB,CAC5F,IAAMwE,EAAUxE,EAAI,OAAO,qBAAqB,EAChD,GAAI,CAACwE,EAAS,OAEd,IAAMzF,EAAQ,iBAAiBC,CAAE,EAE3ByF,EAASC,GAAa,CAC1B,IAAMC,EAAaD,GAAK,UAAU,WAClC,GAAI,CAACC,GAAY,SAAU,OAE3B,IAAMC,EAASJ,EAAQ,qBAAqBG,EAAY3F,EAAID,CAAK,EACjE,OAAW,CAACgE,EAAK8B,CAAK,IAAK,OAAO,QAAQD,CAAM,EAAG,CACjD,IAAME,EAAMH,EAAW,WAAW5B,CAAG,EACrC,GAAI,CAAC+B,EAAK,SACV,IAAMC,EAAaP,EAAgB,qBAAqB,KAAKA,CAAO,EAC9DQ,EAAYD,EAAYA,EAAUD,EAAI,KAAMD,CAAK,EAAIA,EAEvDH,EAAI,UAAU,QAAQ,WAAW3B,CAAG,EACtC2B,EAAI,SAAS,OAAO,SAAS3B,CAAG,EAAE,MAAQiC,EACjCN,EAAI,UAAU,iBAAiB3B,CAAG,EAC3C2B,EAAI,SAAS,eAAe3B,CAAG,EAAE,MAAQiC,EAChCN,EAAI,WAAW3B,CAAG,IAC3B2B,EAAI,SAAS3B,CAAG,EAAE,MAAQiC,EAE9B,CACF,EAEA,GAAIpG,EAAO,OAAO,SAChBA,EAAO,OAAO,SAAU2F,GAAe,CACjCA,EAAM,SACU,MAAM,QAAQA,EAAM,QAAQ,EAAIA,EAAM,SAAW,CAACA,EAAM,QAAQ,GACxE,QAAQE,CAAK,CAE3B,CAAC,MACI,CACL,IAAMjC,EAAO,KAAK,YAAY5D,CAAM,EACpC,GAAI,CAAC4D,EAAM,QACO,MAAM,QAAQA,EAAK,QAAQ,EAAIA,EAAK,SAAW,CAACA,EAAK,QAAQ,GACrE,QAAQiC,CAAK,CACzB,CACF,CAEQ,gBAAgBzF,EAAiBgB,EAA+B,CACtE,OAAOtB,EAAiB,WAAW,IAAIM,EAAIgB,EAAMhB,GAAO,CACtD,IAAMiG,EAAYjG,EAAW,mBAAmB,EAC1CD,EAAQ,iBAAiBC,CAAE,EAE3BkG,EAAa,CAACC,EAAcC,IAA6B,CAC7D,IAAMC,EAAWJ,GAAU,MAAME,CAAI,EACrC,GAA8BE,GAAa,KAAM,CAC/C,IAAMC,EACJ,OAAOD,GAAa,UAAY,UAAYA,EACvCA,EAAiB,MAClBA,EACAE,EAAM,OAAOD,GAAQ,SAAWA,EAAM,OAAO,WAAW,OAAOA,CAAG,CAAC,EACzE,GAAI,CAAC,OAAO,MAAMC,CAAG,EAAG,OAAOA,CACjC,CACA,IAAMC,EAAMzG,EAAM,iBAAiBoG,CAAI,EACjCI,EAAM,OAAO,WAAWC,CAAG,EACjC,OAAO,OAAO,MAAMD,CAAG,EAAIH,EAAWG,CACxC,EAEME,EAAcN,GAAyB,CAC3C,IAAME,EAAWJ,GAAU,MAAME,CAAI,EAC/BG,EACJD,GAAY,OAAOA,GAAa,UAAY,UAAYA,EACnDA,EAAiB,MAClBA,EACN,OAAI,OAAOC,GAAQ,SAAiBA,EAAI,KAAK,EACtCvG,EAAM,iBAAiBoG,CAAI,EAAE,KAAK,CAC3C,EAEMO,EAAW,CAACP,EAAcC,EAAW,KAAmB,CAC5D,IAAMI,EAAMC,EAAWN,CAAI,EAC3B,GAAI,CAACK,EAAK,OAAOJ,EACjB,IAAMO,EAAOH,EAAI,YAAY,EAC7B,OAAOG,IAAS,QAAUA,IAAS,KAAOA,IAAS,MAC/C,GACAA,IAAS,SAAWA,IAAS,KAAOA,IAAS,KAC7C,GACAP,CACN,EAEMQ,EAAWH,EAAW,kBAAkB,EACxC5E,EAAQ+E,GAAYA,IAAa,OAASA,EAAW7G,EAAM,MAAM,KAAK,EAEtEsC,GAAY,IAAM,CACtB,IAAMmE,EAAMzG,EAAM,UAAY,GACxB8G,EAAS,OAAO,WAAWL,CAAG,EACpC,OAAO,OAAO,SAASK,CAAM,EAAIA,EAAS,EAC5C,GAAG,EAEGC,GAAc,IAAM,CACxB,IAAMN,EAAMzG,EAAM,YAAc,GAChC,GAAI,CAACyG,GAAOA,IAAQ,SAAU,OAAOnE,EAAW,IAChD,IAAMwE,EAAS,OAAO,WAAWL,CAAG,EACpC,OAAK,OAAO,SAASK,CAAM,EACpBL,EAAI,SAAS,IAAI,EAAIK,EAASA,EAASxE,EADTA,EAAW,GAElD,GAAG,EAEG0E,GAAiB,IAAM,CAC3B,IAAMP,EAAMzG,EAAM,eAAiB,GACnC,GAAI,CAACyG,GAAOA,IAAQ,SAAU,MAAO,GACrC,IAAMK,EAAS,OAAO,WAAWL,CAAG,EACpC,OAAO,OAAO,SAASK,CAAM,EAAIA,EAAS,CAC5C,GAAG,EAEGG,EAAMP,EAAW,YAAY,GAAK,OAElCQ,EAAWf,EAAW,eAAgB,GAAG,EACzCgB,EAAQ,OAAO,SAASD,CAAQ,EAAIA,EAAW,KAAK,IAAI,EAAG5E,EAAW,EAAG,EAEzEK,EAAYwD,EAAW,oBAAqB,CAAC,EAC7CvD,EAAiBuD,EAAW,yBAA0B,CAAC,EACvDtD,EAAcsD,EAAW,sBAAuB,CAAC,EACjDrD,EAAgBqD,EAAW,qBAAsB,CAAC,EAElDiB,GAAYpH,EAAM,WAAa,QAAQ,YAAY,EACnDqH,EACJD,IAAa,SACT,SACAA,IAAa,SAAWA,IAAa,MACrC,QACA,OAEArE,EAAU/C,EAAM,MAAM,KAAK,EAC3BsH,EACJvE,GAAWA,EAAQ,OAAS,EACxBA,EACA,CACE/C,EAAM,WAAa,SACnBA,EAAM,YAAc,SACpB,GAAGA,EAAM,UAAY,MAAM,IAAIA,EAAM,YAAc,QAAQ,GAC3DA,EAAM,YAAc,YACtB,EAAE,KAAK,GAAG,EAEhB,MAAO,CACL,WAAYmG,EAAW,gBAAiB,CAAC,EACzC,SAAUA,EAAW,UAAW,CAAC,EACjC,QAASA,EAAW,aAAc,CAAC,EACnC,QAASA,EAAW,aAAc,CAAC,EACnC,QAASA,EAAW,aAAc,CAAC,EACnC,UAAWA,EAAW,YAAa,CAAC,EACpC,QAASA,EAAW,YAAa,GAAG,EACpC,MAAArE,EACA,UAAWqE,EAAW,uBAAwB,GAAG,EACjD,UAAWA,EAAW,uBAAwB,GAAG,EACjD,SAAUO,EAAW,qBAAqB,EAC1C,WAAYC,EAAS,gBAAiB,EAAK,EAC3C,cAAeA,EAAS,mBAAoB,EAAK,EACjD,aAAcD,EAAW,kBAAmB,OAAO,EAAE,MAAM,GAAG,EAAE,CAAC,GAAK,QACtE,WAAY1G,EAAM,YAAc,GAChC,QAASsH,EACT,SAAAhF,EACA,WAAAyE,EACA,cAAAC,EACA,UAAWK,EACX,eAAgBrH,EAAM,eAAiB,IAAI,YAAY,EACvD,UAAWmH,EACX,kBAAmBhB,EAAW,wBAAyB,CAAC,EACxD,aAAcxD,EAAY,GAAKC,EAAiB,EAChD,UAAAD,EACA,eAAAC,EACA,YAAAC,EACA,cAAAC,EACA,QAASmE,IAAQ,SAAWA,IAAQ,OAASA,EAAM,SACrD,CACF,CAAC,CACH,CAEQ,mBAAmBnC,EAAcnE,EAA2B,CAClE,MAAI,CAACA,GAAaA,IAAc,OAAemE,EAC3CnE,IAAc,YAAoBmE,EAAK,YAAY,EACnDnE,IAAc,YAAoBmE,EAAK,YAAY,EACnDnE,IAAc,aACTmE,EAAK,QAAQ,cAAgByC,GAAUA,EAAM,YAAY,CAAC,EAE5DzC,CACT,CAEQ,WAAW7E,EAAiBgB,EAAgC,CAClE,IAAMuG,EAAUvH,EAAW,cAC3B,OAAIuH,GAIG7H,EAAiB,YAAY,IAAIM,EAAIgB,EAAMhB,GAAO,CACvD,IAAMkB,EAAOlB,EAAG,sBAAsB,EACtC,MAAO,CAAE,KAAAkB,EAAM,MAAOA,EAAK,MAAO,OAAQA,EAAK,MAAO,CACxD,CAAC,CACH,CACF,EAvmBaxB,EACI,WAAa,IAAI8H,EADrB9H,EAEI,YAAc,IAAI8H,EAFtB9H,EAGI,aAAgD,IAAI,QAHxDA,EAII,iBAAoD,IAAI,QAJ5DA,EAKI,UAA8B,IAAI,IALtCA,EAMI,aAA0C,IAAI,IANlDA,EAOI,mBAAuD,IAAI,IAP/DA,EAQI,iBAA2D,IAAI,QARnEA,EASI,kBAAoB,GATxBA,EAUI,oBAAsB,GAV1BA,EAWI,oBAAsB,GAXhC,IAAM+H,GAAN/H,EC/BA,IAAMgI,GAAN,KAA2B,CAKhC,YACSC,EACAC,EACAC,EACAC,EACP,CAJO,YAAAH,EACA,mBAAAC,EACA,oBAAAC,EACA,YAAAC,EART,KAAQ,WAAsD,IAAI,IAClE,KAAQ,oBAAsB,EAC9B,KAAQ,qBAAuB,EAQ7B,KAAK,WAAW,IAAI,MAAO,IAAIC,EAAkB,EACjD,KAAK,WAAW,IAAI,SAAU,IAAIA,EAAkB,EACpD,KAAK,WAAW,IAAI,QAAS,IAAIA,EAAkB,EACnD,KAAK,WAAW,IAAI,WAAY,IAAIA,EAAkB,EACtD,KAAK,WAAW,IAAI,QAAS,IAAIA,EAAkB,EACnD,KAAK,WAAW,IAAI,QAAS,IAAIC,EAAmB,EACpD,KAAK,WAAW,IAAI,aAAc,IAAIC,EAAmB,EACzD,KAAK,WAAW,IAAI,eAAgB,IAAIA,EAAmB,EAC3D,KAAK,WAAW,IAAI,mBAAoB,IAAIA,EAAmB,EAC/D,KAAK,WAAW,IAAI,YAAa,IAAIA,EAAmB,EACxD,KAAK,WAAW,IAAI,kBAAmB,IAAIA,EAAmB,EAC9D,KAAK,WAAW,IAAI,YAAa,IAAIC,EAAuB,EAC5D,KAAK,WAAW,IAAI,OAAQ,IAAIC,EAAkB,CACpD,CAEO,YACLC,EACAC,EACAC,EACAC,EACK,CACL,IAAMC,EAAW,KAAK,WAAW,IAAIH,EAAO,IAAI,EAChD,OAAKG,EAIEA,EAAS,KACdJ,EACAC,EACA,CACE,OAAQ,KAAK,OACb,cAAe,KAAK,cACpB,eAAgB,KAAK,eACrB,OAAQ,KAAK,OACb,SAAUE,GAAO,SACjB,UAAWA,GAAO,UAClB,oBAAqB,KAAK,oBAC1B,qBAAsB,KAAK,oBAC7B,EACAD,CACF,EAjBS,IAkBX,CAEO,eAAeG,EAGb,CACP,KAAK,oBAAsB,KAAK,IAAI,EAAGA,EAAQ,qBAAuB,CAAC,EACvE,KAAK,qBAAuB,KAAK,IAAI,EAAGA,EAAQ,sBAAwB,CAAC,CAC3E,CAEO,mBAAmBC,EAAeC,EAAsB,CAC7D,KAAK,cAAgBD,EACrB,KAAK,eAAiBC,CACxB,CAEO,eAAeP,EAAiBC,EAA8B,CACnE,IAAMG,EAAW,KAAK,WAAW,IAAIH,EAAO,IAAI,EAC5CG,GAAU,SACZA,EAAS,QAAQJ,EAAIC,CAAM,CAE/B,CACF,ECjFO,IAAMO,GAAN,KAAuB,CAU5B,YAAYC,EAA2B,CARvC,KAAiB,kBAAoB,IAAM,KAAK,aAAa,EAC7D,KAAQ,cAAkC,IAAI,IAC9C,KAAQ,iBAAqC,IAAI,IACjD,KAAQ,eAAwC,KAChD,KAAQ,iBAA4C,KACpD,KAAQ,QAAU,GAClB,KAAQ,WAAa,EAGnB,KAAK,gBAAkBA,CACzB,CAEA,QAAe,CACT,KAAK,UACT,KAAK,QAAU,GACf,KAAK,eAAe,EACpB,KAAK,qBAAqB,EAC5B,CAEA,SAAgB,CACT,KAAK,UACV,KAAK,QAAU,GACf,KAAK,sBAAsB,EAC3B,KAAK,gBAAgB,WAAW,EAChC,KAAK,kBAAkB,WAAW,EAClC,KAAK,cAAc,MAAM,EACzB,KAAK,iBAAiB,MAAM,EAC9B,CAEA,eAAeC,EAAuB,CAChC,CAAC,KAAK,SAAW,KAAK,iBAAiB,IAAIA,CAAE,IACjD,KAAK,iBAAiB,IAAIA,CAAE,EAC5B,KAAK,gBAAgB,QAAQA,CAAE,EAC/B,KAAK,kBAAkB,QAAQA,EAAI,CACjC,WAAY,GACZ,gBAAiB,KAAK,eACxB,CAAC,EACH,CAEA,aAAaC,EAAqC,CAC3C,KAAK,SACVA,EAAY,QAASC,GAAQ,KAAK,iBAAiBA,CAAG,CAAC,CACzD,CAEA,UAAUF,EAAuB,CAC1B,KAAK,UACV,KAAK,cAAc,IAAIA,CAAE,EACzB,KAAK,YAAY,EACnB,CAEA,cAAqB,CACd,KAAK,UACV,KAAK,iBAAiB,QAASA,GAAO,KAAK,cAAc,IAAIA,CAAE,CAAC,EAChE,KAAK,YAAY,EACnB,CAEA,aAAuC,CACrC,OAAO,KAAK,QAAU,KAAK,cAAgB,IAC7C,CAEA,YAAmB,CACjB,KAAK,cAAc,MAAM,CAC3B,CAEA,YAAqB,CACnB,OAAO,KAAK,UACd,CAEA,WAAqB,CACnB,OAAO,KAAK,OACd,CAEQ,iBAAiBG,EAA8B,CACjDA,EAAO,cAAc,aACvB,KAAK,eAAeA,EAAO,EAAE,EAE/BA,EAAO,SAAS,QAASC,GAAU,KAAK,iBAAiBA,CAAK,CAAC,CACjE,CAEQ,cAAqB,CAC3B,KAAK,aAAa,CACpB,CAEQ,gBAAuB,CACzB,OAAO,eAAmB,MAC5B,KAAK,eAAiB,IAAI,eAAgBC,GAAY,CACpDA,EAAQ,QAASC,GAAU,CACrBA,EAAM,kBAAkB,aAC1B,KAAK,UAAUA,EAAM,MAAM,CAE/B,CAAC,CACH,CAAC,GAGC,OAAO,iBAAqB,MAC9B,KAAK,iBAAmB,IAAI,iBAAkBC,GAAc,CAC1DA,EAAU,QAASC,GAAa,CAC1BA,EAAS,kBAAkB,aAC7B,KAAK,UAAUA,EAAS,MAAM,CAElC,CAAC,CACH,CAAC,EAEL,CAEQ,sBAA6B,CACnC,OAAO,iBAAiB,SAAU,KAAK,kBAAmB,CAAE,QAAS,EAAK,CAAC,EAC3E,OAAO,iBAAiB,SAAU,KAAK,kBAAmB,CAAE,QAAS,EAAK,CAAC,EACvE,OAAO,iBACT,OAAO,eAAe,iBAAiB,SAAU,KAAK,kBAAmB,CAAE,QAAS,EAAK,CAAC,EAC1F,OAAO,eAAe,iBAAiB,SAAU,KAAK,kBAAmB,CAAE,QAAS,EAAK,CAAC,EAE9F,CAEQ,uBAA8B,CACpC,OAAO,oBAAoB,SAAU,KAAK,iBAAiB,EAC3D,OAAO,oBAAoB,SAAU,KAAK,iBAAiB,EACvD,OAAO,iBACT,OAAO,eAAe,oBAAoB,SAAU,KAAK,iBAAiB,EAC1E,OAAO,eAAe,oBAAoB,SAAU,KAAK,iBAAiB,EAE9E,CAEQ,aAAoB,CAC1B,KAAK,YAAc,CACrB,CACF,ECvGO,IAAMC,GAAN,KAAuB,CAI5B,YAAoBC,EAAyD,CAAzD,kBAAAA,EAHpB,KAAQ,aAA4D,IAAI,QACxE,KAAQ,eAA+C,IAAI,OAEmB,CAE9E,eACEC,EACAC,EACAC,EACAC,EACwB,CACxB,IAAMC,EAAkC,CAAC,EACnCC,EAAQC,GAA8B,CAC1C,IAAMC,EAAKD,EAAI,GACf,GAAIC,EAAI,CACN,IAAMC,EAAY,KAAK,aAAa,IAAID,CAAE,GAAG,YAAc,GACrDE,EAAkB,CAACP,GAAgB,CAACC,GAAYA,EAAS,IAAII,CAAE,GAAKC,EACpEE,EAAQ,KAAK,gBAAgBH,EAAIN,EAAKQ,CAAe,EAC3D,GAAIC,GAASA,EAAM,OAAS,EAAG,CAC7B,IAAMC,EAAQ,CAACT,GAAgB,CAACC,GAAYA,EAAS,IAAII,CAAE,GAAKC,EAC1DI,EACJ,KAAK,aAAa,IAAIL,CAAE,GAAG,YAAc,KAAK,qBAAqBG,CAAK,EAC1EN,EAAQ,KAAK,CACX,OAAQE,EACR,QAASI,EACT,WAAAE,EACA,MAAAD,CACF,CAAC,EACD,MACF,CACF,CACAL,EAAI,SAAS,QAASO,GAAUR,EAAKQ,CAAK,CAAC,CAC7C,EACA,OAAAb,EAAY,QAASM,GAAQD,EAAKC,CAAG,CAAC,EAC/BF,CACT,CAEA,OAAc,CACZ,KAAK,aAAe,IAAI,QACxB,KAAK,eAAiB,IAAI,OAC5B,CAEQ,gBACNG,EACAN,EACAQ,EAC4B,CAC5B,IAAMK,EAAW,KAAK,aAAa,IAAIP,CAAE,EACzC,GAAI,CAACE,GAAmBK,EACtB,OAAIA,EAAS,UACJ,KAAK,iBAAiBA,EAAUb,CAAG,EAErCa,EAAS,QAGlB,IAAMC,EAAMC,GAAcT,CAAE,EAC5B,GAAI,CAACQ,GAAOA,IAAQ,OAAQ,CAC1B,GAAID,EAAU,CACZ,GAAIA,EAAS,WAAaA,EAAS,gBAAiB,CAClD,IAAMG,EAAU,KAAK,iBAAiBH,EAAUb,CAAG,EACnD,OAAKa,EAAS,UAIPG,GAHL,KAAK,aAAa,OAAOV,CAAE,EACpB,KAGX,CACA,GAAI,CAAE,SAAAW,EAAU,MAAAC,EAAO,OAAAC,CAAO,EAAI,KAAK,oBAAoBb,CAAE,EAM7D,GALIW,GAAY,GAAKJ,EAAS,aAAe,IAC3CI,EAAWJ,EAAS,aACpBK,EAAQL,EAAS,UACjBM,EAASN,EAAS,YAEhBI,EAAW,EAAG,CAChB,IAAMG,EAAO,KAAK,cAAcP,EAAS,OAAO,EAChD,OAAAA,EAAS,KAAOA,EAAS,QACzBA,EAAS,GAAKO,EACdP,EAAS,UAAYb,EAAMkB,EAC3BL,EAAS,SAAWI,EACpBJ,EAAS,OAASM,EAClBN,EAAS,UAAY,GACrBA,EAAS,gBAAkB,GAC3BA,EAAS,aAAeI,EACxBJ,EAAS,UAAYK,EACrBL,EAAS,WAAaM,EACf,KAAK,iBAAiBN,EAAUb,CAAG,CAC5C,CACF,CACA,YAAK,aAAa,OAAOM,CAAE,EACpB,IACT,CAEA,GAAM,CAAE,QAAAe,EAAS,SAAAC,CAAS,EAAI,KAAK,iBAAiBR,CAAG,EAEvD,GADA,KAAK,iBAAiBR,EAAIQ,EAAKQ,CAAQ,EACnCD,EAAQ,SAAW,EAAG,OAAO,KAEjC,IAAME,EAAQ,KAAK,aAAa,IAAIjB,CAAE,EACtC,GAAI,CAACiB,EAAO,CACV,GAAM,CAAE,SAAAN,EAAU,MAAAC,EAAO,OAAAC,CAAO,EAAI,KAAK,oBAAoBb,CAAE,EAC/D,GAAIW,EAAW,EAAG,CAChB,IAAMG,EAAO,KAAK,cAAcC,CAAO,EACjCG,EAAkC,CACtC,IAAAV,EACA,QAAAO,EACA,UAAW,GACX,KAAMD,EACN,GAAIC,EACJ,UAAWrB,EAAMkB,EACjB,SAAAD,EACA,OAAAE,EACA,gBAAiB,GACjB,aAAcF,EACd,UAAWC,EACX,WAAYC,CACd,EACA,OAAAK,EAAS,WAAa,KAAK,qBAAqBH,CAAO,EACvD,KAAK,aAAa,IAAIf,EAAIkB,CAAQ,EAC3B,KAAK,iBAAiBA,EAAUxB,CAAG,CAC5C,CACA,YAAK,aAAa,IAAIM,EAAI,CACxB,IAAAQ,EACA,QAAAO,EACA,UAAW,GACX,KAAMA,EACN,GAAIA,EACJ,UAAW,EACX,SAAU,EACV,OAASI,GAAMA,EACf,gBAAiB,GACjB,aAAc,EACd,UAAW,EACX,WAAaA,GAAMA,EACnB,WAAY,KAAK,qBAAqBJ,CAAO,CAC/C,CAAC,EACMA,CACT,CAEA,GAAIE,EAAM,MAAQT,EAAK,CACrB,GAAIS,EAAM,UAAW,CACnB,IAAMP,EAAU,KAAK,iBAAiBO,EAAOvB,CAAG,EAChD,MAAI,CAACuB,EAAM,WAAaA,EAAM,iBAC5B,KAAK,aAAa,OAAOjB,CAAE,EACpB,MAEFU,CACT,CACA,OAAOO,EAAM,OACf,CAEAA,EAAM,eAAiB,OACvBA,EAAM,WAAa,OAEnB,GAAI,CAAE,SAAAN,EAAU,MAAAC,EAAO,OAAAC,CAAO,EAAI,KAAK,oBAAoBb,CAAE,EAM7D,GALIW,GAAY,GAAKM,EAAM,aAAe,IACxCN,EAAWM,EAAM,aACjBL,EAAQK,EAAM,UACdJ,EAASI,EAAM,YAEbN,EAAW,EAAG,CAChB,IAAMS,EAAW,KAAK,eAAeH,EAAM,QAASF,CAAO,EACrDL,EAAUO,EAAM,UAAY,KAAK,gBAAgBA,EAAOvB,CAAG,EAAIuB,EAAM,QAC3E,GAAI,CAACG,GAAY,KAAK,YAAYL,CAAO,EACvC,OAAAE,EAAM,WAAaT,EACnBS,EAAM,eAAiBF,EACvBE,EAAM,IAAMT,EACZS,EAAM,QAAUP,EAChBO,EAAM,KAAOP,EACbO,EAAM,GAAK,KAAK,cAAcP,CAAO,EACrCO,EAAM,UAAYvB,EAAMkB,EACxBK,EAAM,SAAWN,EACjBM,EAAM,OAASJ,EACfI,EAAM,UAAY,GAClBA,EAAM,gBAAkB,GACxBA,EAAM,aAAeN,EACrBM,EAAM,UAAYL,EAClBK,EAAM,WAAaJ,EACnBI,EAAM,WAAa,KAAK,qBAAqBF,CAAO,EAC7C,KAAK,iBAAiBE,EAAOvB,CAAG,EAGzC,IAAM2B,EAAYD,EAAWV,EAAU,KAAK,cAAcK,CAAO,EACjE,OAAAE,EAAM,IAAMT,EACZS,EAAM,QAAUF,EAChBE,EAAM,KAAOI,EACbJ,EAAM,GAAKF,EACXE,EAAM,UAAYvB,EAAMkB,EACxBK,EAAM,SAAWN,EACjBM,EAAM,OAASJ,EACfI,EAAM,UAAY,GAClBA,EAAM,gBAAkB,GACxBA,EAAM,aAAeN,EACrBM,EAAM,UAAYL,EAClBK,EAAM,WAAaJ,EACnBI,EAAM,WAAa,KAAK,qBAAqBF,CAAO,EAC7C,KAAK,iBAAiBE,EAAOvB,CAAG,CACzC,CAEA,OAAAuB,EAAM,IAAMT,EACZS,EAAM,QAAUF,EAChBE,EAAM,UAAY,GAClBA,EAAM,gBAAkB,GACxBA,EAAM,WAAa,KAAK,qBAAqBF,CAAO,EAC7CA,CACT,CAEQ,iBAAiBf,EAAiBQ,EAAaQ,EAA0B,CAC3EA,EAAS,SAAW,GACR,KAAK,eAAe,IAAIhB,CAAE,IAC1BQ,GAChB,KAAK,eAAe,IAAIR,EAAIQ,CAAG,CACjC,CAEQ,iBAAiBA,EAAmE,CAC1F,IAAMQ,EAAqB,CAAC,EACtBD,EAA+B,CAAC,EAEhCO,EAAeC,GAAiC,CAEpD,IAAMC,EADUD,EAAM,KAAK,EAAE,YAAY,EACnB,MAAM,sBAAsB,EAClD,GAAI,CAACC,EAAO,OAAO,KACnB,IAAMC,EAAM,OAAO,WAAWD,EAAM,CAAC,CAAC,EACtC,OAAO,OAAO,SAASC,CAAG,EAAIA,EAAM,IACtC,EAEMC,EAAcH,GAAiC,CACnD,IAAMI,EAAUJ,EAAM,KAAK,EAAE,YAAY,EACzC,GAAI,CAACI,EAAS,OAAO,KACrB,GAAIA,EAAQ,SAAS,GAAG,EAAG,CACzB,IAAMF,EAAM,OAAO,WAAWE,EAAQ,MAAM,EAAG,EAAE,CAAC,EAClD,OAAO,OAAO,SAASF,CAAG,EAAIA,EAAM,IAAM,IAC5C,CACA,IAAMA,EAAM,OAAO,WAAWE,CAAO,EACrC,OAAO,OAAO,SAASF,CAAG,EAAIA,EAAM,IACtC,EAEMG,EAAcL,GAAiC,CACnD,IAAMI,EAAUJ,EAAM,KAAK,EAAE,YAAY,EACzC,GAAI,CAACI,EAAS,OAAO,KACrB,GAAIA,EAAQ,SAAS,KAAK,EAAG,CAC3B,IAAMF,EAAM,OAAO,WAAWE,EAAQ,MAAM,EAAG,EAAE,CAAC,EAClD,OAAO,OAAO,SAASF,CAAG,EAAIA,EAAM,IACtC,CACA,IAAMI,EAAWF,EAAQ,SAAS,KAAK,EAAIA,EAAQ,MAAM,EAAG,EAAE,EAAIA,EAC5DF,EAAM,OAAO,WAAWI,CAAQ,EACtC,OAAO,OAAO,SAASJ,CAAG,EAAKA,EAAM,KAAK,GAAM,IAAM,IACxD,EAEMK,EAAcP,GAAmE,CACrF,IAAMQ,EAAQR,EAAM,MAAM,GAAG,EAAE,IAAKS,GAASA,EAAK,KAAK,CAAC,EAClDC,EAAYX,EAAYS,EAAM,CAAC,GAAK,EAAE,EAC5C,GAAIE,IAAc,KAAM,OAAO,KAC/B,IAAMC,EAAYH,EAAM,CAAC,EAAIL,EAAWK,EAAM,CAAC,CAAC,EAAI,KACpD,MAAO,CACL,UAAW,KAAK,IAAI,EAAGE,CAAS,EAChC,UAAWC,IAAc,KAAO,GAAM,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGA,CAAS,CAAC,CAC1E,CACF,EAEMC,EAAc,CAACZ,EAAea,EAAcC,EAAY,KAAyB,CACrF,IAAMC,EAAShB,EAAYC,CAAK,EAChC,OAAIe,IAAW,MACbtB,EAAS,KAAK,sBAAsBoB,CAAI,WAAWb,CAAK,IAAI,EACrD,MAEL,CAACc,GAAaC,GAAU,GAC1BtB,EAAS,KAAK,cAAcoB,CAAI,eAAe,EACxC,MAEFE,CACT,EAEMC,EAAmB,CAAChB,EAAea,IAAgC,CACvE,IAAME,EAASZ,EAAWH,CAAK,EAC/B,OAAIe,IAAW,MACbtB,EAAS,KAAK,sBAAsBoB,CAAI,WAAWb,CAAK,IAAI,EACrD,MAEFe,CACT,EAEME,EAAK,2BACPhB,EACJ,KAAQA,EAAQgB,EAAG,KAAKhC,CAAG,GAAI,CAC7B,IAAM4B,EAAOZ,EAAM,CAAC,EAAE,YAAY,EAC5BiB,GAAQjB,EAAM,CAAC,GAAK,IAAI,KAAK,EAEnC,GAAIY,IAAS,OAAQ,CACnB,IAAME,EAASH,EAAYM,EAAM,OAAQ,EAAI,EACzCH,IAAW,MAAMvB,EAAQ,KAAK,CAAE,KAAM,OAAQ,OAAAuB,CAAO,CAAC,CAC5D,SAAWF,IAAS,SAAWA,IAAS,WAAY,CAClD,IAAMM,EAAOP,EAAYM,EAAM,QAAS,EAAI,EACxCC,IAAS,MAAM3B,EAAQ,KAAK,CAAE,KAAM,QAAS,KAAA2B,CAAK,CAAC,CACzD,SAAWN,IAAS,QAAS,CAC3B,IAAMO,EAAQb,EAAWW,CAAI,EACzBE,EAAO5B,EAAQ,KAAK,CAAE,KAAM,QAAS,GAAG4B,CAAM,CAAC,EAC9C3B,EAAS,KAAK,mCAAmCyB,CAAI,IAAI,CAChE,SAAWL,IAAS,aAAc,CAChC,IAAME,EAASC,EAAiBE,EAAM,YAAY,EAC9CH,IAAW,MAAMvB,EAAQ,KAAK,CAAE,KAAM,aAAc,OAAQ,KAAK,IAAI,EAAGuB,CAAM,CAAE,CAAC,CACvF,SAAWF,IAAS,WAAY,CAC9B,IAAME,EAASC,EAAiBE,EAAM,UAAU,EAC5CH,IAAW,MAAMvB,EAAQ,KAAK,CAAE,KAAM,WAAY,OAAQ,KAAK,IAAI,EAAGuB,CAAM,CAAE,CAAC,CACrF,SAAWF,IAAS,WAAY,CAC9B,IAAME,EAASC,EAAiBE,EAAM,UAAU,EAC5CH,IAAW,MAAMvB,EAAQ,KAAK,CAAE,KAAM,WAAY,OAAQ,KAAK,IAAI,EAAGuB,CAAM,CAAE,CAAC,CACrF,SAAWF,IAAS,YAAa,CAC/B,IAAME,EAASC,EAAiBE,EAAM,WAAW,EAC7CH,IAAW,MACbvB,EAAQ,KAAK,CAAE,KAAM,YAAa,OAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGuB,CAAM,CAAC,CAAE,CAAC,CAChF,SAAWF,IAAS,QAAS,CAC3B,IAAME,EAASC,EAAiBE,EAAM,OAAO,EACzCH,IAAW,MACbvB,EAAQ,KAAK,CAAE,KAAM,QAAS,OAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGuB,CAAM,CAAC,CAAE,CAAC,CAC5E,SAAWF,IAAS,SAAU,CAC5B,IAAME,EAASC,EAAiBE,EAAM,QAAQ,EAC1CH,IAAW,MACbvB,EAAQ,KAAK,CAAE,KAAM,SAAU,OAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGuB,CAAM,CAAC,CAAE,CAAC,CAC7E,SAAWF,IAAS,aAAc,CAChC,IAAMQ,EAAQhB,EAAWa,CAAI,EACzBG,IAAU,KAAM7B,EAAQ,KAAK,CAAE,KAAM,aAAc,MAAA6B,CAAM,CAAC,EACzD5B,EAAS,KAAK,wCAAwCyB,CAAI,IAAI,CACrE,SAAWL,EAAM,CACf,IAAMS,EAASC,GAA6B,IAAIV,CAAI,EACpD,GAAIS,EAAQ,CACV,IAAME,EAASF,EAAO,MAAQA,EAAO,MAAMJ,CAAI,EAAI,CAAC,EAChDM,IAAW,KACb/B,EAAS,KAAK,qCAAqCoB,CAAI,WAAWK,CAAI,IAAI,EAE1E1B,EAAQ,KAAK,CAAE,KAAM,SAAU,KAAAqB,EAAM,SAAUW,CAAO,CAAC,CAE3D,MACE/B,EAAS,KAAK,8BAA8BoB,CAAI,IAAI,CAExD,CACF,CAEA,OAAIrB,EAAQ,SAAW,GACrBC,EAAS,KAAK,mDAAmD,EAG5D,CAAE,QAAAD,EAAS,SAAAC,CAAS,CAC7B,CAEQ,oBAAoBhB,EAI1B,CACA,IAAMgD,EAAQ,iBAAiBhD,CAAE,EAC3BiD,EAAa,KAAK,oBAAoBD,EAAM,kBAAkB,EAC9DE,EAAY,KAAK,oBAAoBF,EAAM,kBAAkB,EAC7DG,EAAS,KAAK,oBAAoBH,EAAM,eAAe,EACvDI,EAAU,KAAK,oBAAoBJ,EAAM,wBAAwB,EAEjEK,EAAQ,KAAK,oBAAoBJ,EAAY,UAAU,EAC7D,GAAII,IAAU,GAAI,CAChB,IAAMC,EAAY,KAAK,yBAAyBN,EAAM,UAAU,EAC1DO,EAAWD,EAAU,IAAI,UAAU,GAAKA,EAAU,IAAI,KAAK,EACjE,OAAIC,GAGG,CAAE,SAAU,EAAG,MAAO,EAAG,OAASpC,GAAMA,CAAE,CACnD,CAEA,IAAMR,EAAW,KAAK,UAAUuC,EAAUG,CAAK,GAAKH,EAAUA,EAAU,OAAS,CAAC,GAAK,IAAI,EACrFtC,EAAQ,KAAK,UAAUuC,EAAOE,CAAK,GAAKF,EAAOA,EAAO,OAAS,CAAC,GAAK,IAAI,EACzEK,EAAYJ,EAAQC,CAAK,GAAKD,EAAQA,EAAQ,OAAS,CAAC,GAAK,SACnE,MAAO,CAAE,SAAAzC,EAAU,MAAAC,EAAO,OAAQ,KAAK,YAAY4C,CAAS,CAAE,CAChE,CAEQ,oBAAoBjC,EAAyB,CACnD,IAAMkC,EAAmB,CAAC,EACtB/C,EAAU,GACVgD,EAAQ,EACZ,QAASC,EAAI,EAAGA,EAAIpC,EAAM,OAAQoC,GAAK,EAAG,CACxC,IAAMC,EAAKrC,EAAMoC,CAAC,EACdC,IAAO,MAAKF,GAAS,GACrBE,IAAO,MAAKF,EAAQ,KAAK,IAAI,EAAGA,EAAQ,CAAC,GACzCE,IAAO,KAAOF,IAAU,GAC1BD,EAAO,KAAK/C,EAAQ,KAAK,CAAC,EAC1BA,EAAU,IAEVA,GAAWkD,CAEf,CACA,OAAIlD,EAAQ,KAAK,GAAG+C,EAAO,KAAK/C,EAAQ,KAAK,CAAC,EACvC+C,EAAO,OAAS,EAAIA,EAAS,CAAC,KAAK,CAC5C,CAEQ,oBAAoBR,EAAsBb,EAAsB,CACtE,IAAMyB,EAAaZ,EAAW,IAAKa,GAASA,EAAK,KAAK,EAAE,YAAY,CAAC,EACjET,EAAQQ,EAAW,QAAQzB,CAAI,EACnC,OAAIiB,IAAU,KACZA,EAAQQ,EAAW,QAAQ,KAAK,GAE3BR,CACT,CAEQ,UAAU9B,EAAuB,CACvC,IAAMf,EAAMe,EAAM,KAAK,EAAE,YAAY,EACrC,GAAIf,EAAI,SAAS,IAAI,EAAG,CACtB,IAAMiB,EAAM,OAAO,WAAWjB,EAAI,MAAM,EAAG,EAAE,CAAC,EAC9C,OAAO,OAAO,SAASiB,CAAG,EAAIA,EAAM,CACtC,CACA,GAAIjB,EAAI,SAAS,GAAG,EAAG,CACrB,IAAMiB,EAAM,OAAO,WAAWjB,EAAI,MAAM,EAAG,EAAE,CAAC,EAC9C,OAAO,OAAO,SAASiB,CAAG,EAAIA,EAAM,IAAO,CAC7C,CACA,IAAMA,EAAM,OAAO,WAAWjB,CAAG,EACjC,OAAO,OAAO,SAASiB,CAAG,EAAIA,EAAM,CACtC,CAEQ,yBACNF,EACiF,CACjF,IAAMwC,EAAM,IAAI,IAKhB,OADc,KAAK,oBAAoBxC,CAAK,EACtC,QAASS,GAAS,CACtB,GAAI,CAACA,EAAM,OACX,IAAMgC,EAAShC,EAAK,KAAK,EAAE,MAAM,kBAAkB,EAC/C8B,EAAO,GACPnD,EAAW,GACXC,EAAQ,GACRC,EAAS,GACbmD,EAAO,QAASC,GAAU,CACxB,IAAMC,EAAQD,EAAM,YAAY,EAC5BC,EAAM,SAAS,IAAI,GAAKA,EAAM,SAAS,GAAG,GAAK,YAAY,KAAKA,CAAK,EAClEvD,EACKC,IAAOA,EAAQsD,GADVvD,EAAWuD,EAG1BA,EAAM,WAAW,cAAc,GAC/BA,EAAM,WAAW,OAAO,GACxBA,IAAU,UACVA,IAAU,QACVA,IAAU,WACVA,IAAU,YACVA,IAAU,cAEVrD,EAASoD,EACCH,IACVA,EAAOG,EAEX,CAAC,EACIH,GACLC,EAAI,IAAID,EAAK,KAAK,EAAE,YAAY,EAAG,CACjC,SAAU,KAAK,UAAUnD,GAAY,IAAI,EACzC,MAAO,KAAK,UAAUC,GAAS,IAAI,EACnC,OAAQ,KAAK,YAAYC,GAAU,QAAQ,CAC7C,CAAC,CACH,CAAC,EACMkD,CACT,CAEQ,YAAYxC,EAAsC,CACxD,IAAMf,EAAMe,EAAM,KAAK,EACvB,GAAI,CAACf,EAAK,OAAQW,GAAMA,EACxB,GAAI,CAAC,KAAK,aAAc,OAAQA,GAAMA,EACtC,GAAI,CACF,IAAMgD,EAAK,KAAK,aAAa3D,CAAG,EAChC,OAAO,OAAO2D,GAAO,WAAaA,EAAMhD,GAAMA,CAChD,MAAQ,CACN,OAAQA,GAAMA,CAChB,CACF,CAEQ,eAAeiD,EAA2BC,EAAkC,CAClF,OAAID,EAAK,SAAWC,EAAG,OAAe,GAC/BD,EAAK,MAAM,CAACE,EAAQjB,IAAU,CACnC,IAAMkB,EAAQF,EAAGhB,CAAK,EACtB,GAAIiB,EAAO,OAASC,EAAM,KAAM,MAAO,GACvC,GAAID,EAAO,OAAS,UAAYC,EAAM,OAAS,SAAU,CACvD,GAAID,EAAO,OAASC,EAAM,KAAM,MAAO,GACvC,IAAMC,EAAO,OAAO,KAAKF,EAAO,UAAY,CAAC,CAAC,EACxCG,EAAY,OAAO,KAAKF,EAAM,UAAY,CAAC,CAAC,EAClD,OAAIC,EAAK,SAAWC,EAAU,OAAe,GACtCD,EAAK,MACTE,GAAQA,KAAQH,EAAM,UAAY,CAAC,IAAM,KAAK,UAAUD,EAAO,WAAWI,CAAG,CAAC,CACjF,CACF,CACA,MAAO,EACT,CAAC,CACH,CAEQ,cAAcvE,EAAiD,CACrE,OAAOA,EAAM,IAAKmE,GAAW,CAC3B,OAAQA,EAAO,KAAM,CACnB,IAAK,OACH,MAAO,CAAE,KAAM,OAAQ,OAAQ,CAAE,EACnC,IAAK,QACH,MAAO,CAAE,KAAM,QAAS,KAAM,CAAE,EAClC,IAAK,QACH,MAAO,CAAE,KAAM,QAAS,UAAW,EAAG,UAAWA,EAAO,SAAU,EACpE,IAAK,aACH,MAAO,CAAE,KAAM,aAAc,OAAQ,CAAE,EACzC,IAAK,WACH,MAAO,CAAE,KAAM,WAAY,OAAQ,CAAE,EACvC,IAAK,WACH,MAAO,CAAE,KAAM,WAAY,OAAQ,CAAE,EACvC,IAAK,YACH,MAAO,CAAE,KAAM,YAAa,OAAQ,CAAE,EACxC,IAAK,QACH,MAAO,CAAE,KAAM,QAAS,OAAQ,CAAE,EACpC,IAAK,SACH,MAAO,CAAE,KAAM,SAAU,OAAQ,CAAE,EACrC,IAAK,aACH,MAAO,CAAE,KAAM,aAAc,MAAO,CAAE,EACxC,IAAK,SAAU,CACb,IAAMK,EAAgC,CAAC,EACvC,cAAO,QAAQL,EAAO,UAAY,CAAC,CAAC,EAAE,QAAQ,CAAC,CAACI,EAAKnD,CAAK,IAAM,CAC9DoD,EAASD,CAAG,EAAI,KAAK,UAAUnD,CAAK,EAAI,EAAIA,CAC9C,CAAC,EACM,CAAE,KAAM,SAAU,KAAM+C,EAAO,KAAM,SAAAK,CAAS,CACvD,CACA,QACE,OAAOL,CACX,CACF,CAAC,CACH,CAEQ,iBAAiBrD,EAA8BvB,EAAkC,CACvF,GAAI,CAACuB,EAAM,UAAW,OAAOA,EAAM,QACnC,GAAIvB,EAAMuB,EAAM,UACd,OAAOA,EAAM,KAEf,IAAM2D,EAAUlF,EAAMuB,EAAM,UACtBN,EAAW,KAAK,IAAI,EAAGM,EAAM,QAAQ,EACrCE,EAAI,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGyD,EAAUjE,CAAQ,CAAC,EAC/CkE,EAAQ5D,EAAM,OAAOE,CAAC,EACtB2D,EAAe,KAAK,iBAAiB7D,EAAM,KAAMA,EAAM,GAAI4D,CAAK,EACtE,OAAI1D,GAAK,IACPF,EAAM,UAAY,GAClBA,EAAM,KAAOA,EAAM,GACfA,EAAM,gBAAkBA,EAAM,aAAeA,EAAM,KACrDA,EAAM,QAAUA,EAAM,eACtBA,EAAM,IAAMA,EAAM,YAAcA,EAAM,IACtCA,EAAM,eAAiB,OACvBA,EAAM,WAAa,QACVA,EAAM,iBACfA,EAAM,eAAiB,OACvBA,EAAM,WAAa,SAGhB6D,CACT,CAEQ,gBAAgB7D,EAA8BvB,EAAkC,CACtF,GAAI,CAACuB,EAAM,UAAW,OAAOA,EAAM,QACnC,GAAIvB,EAAMuB,EAAM,UAAW,OAAOA,EAAM,KACxC,IAAM2D,EAAUlF,EAAMuB,EAAM,UACtBN,EAAW,KAAK,IAAI,EAAGM,EAAM,QAAQ,EACrCE,EAAI,KAAK,IAAI,EAAG,KAAK,IAAI,EAAGyD,EAAUjE,CAAQ,CAAC,EAC/CkE,EAAQ5D,EAAM,OAAOE,CAAC,EAC5B,OAAO,KAAK,iBAAiBF,EAAM,KAAMA,EAAM,GAAI4D,CAAK,CAC1D,CAEQ,iBACNT,EACAC,EACAlD,EACqB,CACrB,OAAK,KAAK,eAAeiD,EAAMC,CAAE,EAC1BD,EAAK,IAAI,CAACE,EAAQjB,IAAU,KAAK,kBAAkBiB,EAAQD,EAAGhB,CAAK,EAAGlC,CAAC,CAAC,EADpCkD,CAE7C,CAEQ,kBACND,EACAC,EACAlD,EACsB,CACtB,IAAM4D,EAAO,CAACC,EAAWC,IAAcD,GAAKC,EAAID,GAAK7D,EACrD,GAAIiD,EAAK,OAAS,QAAUC,EAAG,OAAS,OACtC,MAAO,CAAE,KAAM,OAAQ,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAE9D,GAAID,EAAK,OAAS,SAAWC,EAAG,OAAS,QACvC,MAAO,CAAE,KAAM,QAAS,KAAMU,EAAKX,EAAK,KAAMC,EAAG,IAAI,CAAE,EAEzD,GAAID,EAAK,OAAS,SAAWC,EAAG,OAAS,QACvC,MAAO,CACL,KAAM,QACN,UAAWU,EAAKX,EAAK,UAAWC,EAAG,SAAS,EAC5C,UAAWU,EAAKX,EAAK,UAAWC,EAAG,SAAS,CAC9C,EAEF,GAAID,EAAK,OAAS,cAAgBC,EAAG,OAAS,aAC5C,MAAO,CAAE,KAAM,aAAc,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAEpE,GAAID,EAAK,OAAS,YAAcC,EAAG,OAAS,WAC1C,MAAO,CAAE,KAAM,WAAY,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAElE,GAAID,EAAK,OAAS,YAAcC,EAAG,OAAS,WAC1C,MAAO,CAAE,KAAM,WAAY,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAElE,GAAID,EAAK,OAAS,aAAeC,EAAG,OAAS,YAC3C,MAAO,CAAE,KAAM,YAAa,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAEnE,GAAID,EAAK,OAAS,SAAWC,EAAG,OAAS,QACvC,MAAO,CAAE,KAAM,QAAS,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAE/D,GAAID,EAAK,OAAS,UAAYC,EAAG,OAAS,SACxC,MAAO,CAAE,KAAM,SAAU,OAAQU,EAAKX,EAAK,OAAQC,EAAG,MAAM,CAAE,EAEhE,GAAID,EAAK,OAAS,cAAgBC,EAAG,OAAS,aAC5C,MAAO,CAAE,KAAM,aAAc,MAAOU,EAAKX,EAAK,MAAOC,EAAG,KAAK,CAAE,EAEjE,GAAID,EAAK,OAAS,UAAYC,EAAG,OAAS,UAAYD,EAAK,OAASC,EAAG,KAAM,CAC3E,IAAMM,EAAgC,CAAC,EACvC,cAAO,QAAQN,EAAG,UAAY,CAAC,CAAC,EAAE,QAAQ,CAAC,CAACK,EAAKnD,CAAK,IAAM,CAC1D,IAAM2D,EAAYd,EAAK,WAAWM,CAAG,EACjC,KAAK,UAAUQ,CAAS,GAAK,KAAK,UAAU3D,CAAK,EACnDoD,EAASD,CAAG,EAAIK,EAAKG,EAAW3D,CAAK,EAErCoD,EAASD,CAAG,EAAInD,CAEpB,CAAC,EACM,CAAE,KAAM,SAAU,KAAM8C,EAAG,KAAM,SAAAM,CAAS,CACnD,CACA,OAAON,CACT,CAEQ,qBAAqBlE,EAAoC,CAqB/D,OApBcA,EAAM,IAAKmE,GAAW,CAClC,GAAIA,EAAO,OAAS,OAAQ,MAAO,QAAQA,EAAO,MAAM,GACxD,GAAIA,EAAO,OAAS,QAAS,MAAO,SAASA,EAAO,IAAI,GACxD,GAAIA,EAAO,OAAS,QAAS,MAAO,SAASA,EAAO,SAAS,IAAIA,EAAO,SAAS,GACjF,GAAIA,EAAO,OAAS,aAAc,MAAO,cAAcA,EAAO,MAAM,GACpE,GAAIA,EAAO,OAAS,WAAY,MAAO,YAAYA,EAAO,MAAM,GAChE,GAAIA,EAAO,OAAS,WAAY,MAAO,YAAYA,EAAO,MAAM,GAChE,GAAIA,EAAO,OAAS,YAAa,MAAO,aAAaA,EAAO,MAAM,GAClE,GAAIA,EAAO,OAAS,QAAS,MAAO,SAASA,EAAO,MAAM,GAC1D,GAAIA,EAAO,OAAS,SAAU,MAAO,UAAUA,EAAO,MAAM,GAC5D,GAAIA,EAAO,OAAS,aAAc,MAAO,cAAcA,EAAO,KAAK,GACnE,GAAIA,EAAO,OAAS,SAAU,CAC5B,IAAMK,EAAW,OAAO,KAAKL,EAAO,UAAY,CAAC,CAAC,EAC/C,KAAK,EACL,IAAKI,GAAQ,GAAGA,CAAG,IAAKJ,EAAO,SAAiBI,CAAG,CAAC,EAAE,EACtD,KAAK,GAAG,EACX,MAAO,UAAUJ,EAAO,IAAI,IAAIK,CAAQ,EAC1C,CACA,MAAO,SACT,CAAC,EACY,KAAK,GAAG,CACvB,CAEQ,UAAUpD,EAAiC,CACjD,OAAO,OAAOA,GAAU,UAAY,OAAO,SAASA,CAAK,CAC3D,CAEQ,YAAYpB,EAAqC,CACvD,OAAOA,EAAM,MAAOmE,GAAW,CAC7B,OAAQA,EAAO,KAAM,CACnB,IAAK,OACH,OAAOA,EAAO,QAAU,EAC1B,IAAK,QACH,OAAOA,EAAO,MAAQ,EACxB,IAAK,QACH,OAAOA,EAAO,WAAa,EAC7B,IAAK,aACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,WACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,WACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,YACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,QACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,SACH,OAAOA,EAAO,SAAW,EAC3B,IAAK,aACH,OAAOA,EAAO,QAAU,EAC1B,IAAK,SACH,MAAO,GACT,QACE,MAAO,EACX,CACF,CAAC,CACH,CACF,EpBvqBO,IAAMa,GAAN,MAAMA,WAAiBC,EAAa,CAyCzC,YAAYC,EAAwB,CAClC,MAAMA,CAAO,EAtCf,KAAQ,SAAoC,KAC5C,KAAQ,OAAgC,KACxC,KAAQ,OAA+B,KACvC,KAAQ,aAA4C,KACpD,KAAQ,OAA2B,KACnC,KAAQ,gBAAsC,KAC9C,KAAQ,UAAkC,IAAI,IAE9C,KAAQ,aAAe,GAEvB,KAAQ,aAA2D,IAAI,QAEvE,KAAQ,mBAAqB,GA2B3B,KAAK,QAAU,KACf,KAAK,QAAU,KAAK,yBAAyB,EAC7C,KAAK,iBAAmB,IAAIC,GAAiB,CAC3C,QACA,QACA,YACA,sBACA,uBACF,CAAC,EACD,KAAK,iBAAmB,IAAIC,GAAkBC,GAC5C,KAAK,MAAM,eAAe,QAAQ,CAAE,OAAQA,CAAM,CAAC,CACrD,EAEA,KAAK,gBAAkB,CACrB,GAAG,KAAK,gBACR,CAAE,IAAK,KAAM,KAAM,SAAU,SAAU,KAAM,EAC7C,CAAE,IAAK,WAAY,KAAM,SAAU,SAAU,EAAG,EAChD,CAAE,IAAK,cAAe,KAAM,SAAU,SAAU,EAAG,EACnD,CAAE,IAAK,oBAAqB,KAAM,SAAU,SAAU,EAAG,EACzD,CAAE,IAAK,qBAAsB,KAAM,SAAU,SAAU,EAAG,EAC1D,CAAE,IAAK,kBAAmB,KAAM,SAAU,SAAU,EAAG,EACvD,CAAE,IAAK,iBAAkB,KAAM,SAAU,SAAU,CAAE,EACrD,CAAE,IAAK,kBAAmB,KAAM,UAAW,SAAU,EAAM,EAC3D,CAAE,IAAK,eAAgB,KAAM,SAAU,SAAU,SAAU,CAC7D,EAEAL,GAAS,UAAY,IACvB,CApDA,OAAc,aAA+B,CAC3C,OAAOA,GAAS,SAClB,CAEA,IAAW,OAA8B,CACvC,OAAO,KAAK,MACd,CAEA,OAAc,YAAYM,EAAmC,CAC3DN,GAAS,SAAWM,CACtB,CAEA,OAAc,aAAaC,EAAcC,EAAaC,EAAiC,CAAC,EAAS,CAC/FC,GAAqB,SAASH,EAAMC,CAAG,EACnCC,EAAQ,SACVC,GAAqB,WAAWH,CAAI,CAExC,CAEA,OAAc,eAAeA,EAAoB,CAC/CG,GAAqB,WAAWH,CAAI,CACtC,CAiCS,WAAWI,EAA+B,CACjD,OAAO,MAAM,WAAWA,CAAM,CAChC,CAES,iBACPC,EACAD,EACAE,EACAC,EACM,CACN,MAAM,iBAAiBF,EAAUD,EAAQE,EAASC,CAAU,EAE5DH,EAAO,YAAY,WAAY,IAAI,EACnC,IAAMI,EAAgBF,EAAQ,eAAe,QAC3C,qBACF,EACA,GAAIE,EAAe,CACjB,IAAMC,EAAWD,EAAc,aAAa,WAAW,EACnDC,IACFL,EAAO,YAAY,WAAYK,CAAQ,EACvCL,EAAO,YAAY,SAAUI,CAAa,EAE9C,CACF,CAES,UAAiB,CACpB,KAAK,UAAY,KAAK,QAAU,KAAK,eACvC,KAAK,SAAS,OAAO,KAAK,MAAM,EAChC,KAAK,aAAa,mBAAmB,KAAK,SAAS,MAAO,KAAK,SAAS,MAAM,EAC9E,KAAK,OAAO,gBAAgB,EACxB,KAAK,cACP,KAAK,iBAAiB,aAAa,EAGzC,CAES,QAAe,CAEtB,GADA,KAAK,QAAU,KAAK,yBAAyB,EACzC,CAACf,GAAS,SACZ,OAGF,KAAK,OAASA,GAAS,SAAS,UAAU,EAC1C,KAAK,gBAAkB,KAAK,qBAAqB,EACjD,KAAK,wBAAwB,EAC7B,KAAK,UAAU,EACf,KAAK,aAAe,CAAC,CAAC,KAAK,QAAQ,aAC/B,KAAK,cACP,KAAK,iBAAiB,OAAO,EAG/B,KAAK,SAAW,IAAIiB,GAAiB,KAAK,gBAAiB,KAAK,MAAM,EACtE,KAAK,SAAS,OAAO,EAErB,KAAK,OAAS,IAAIC,GAAe,KAAK,OAAQ,cAAc,EAC5D,KAAK,OAAO,YAAY,EAAG,EAAG,GAAI,EAClC,KAAK,OAAO,OAAO,KAAK,SAAS,MAAO,KAAK,SAAS,MAAM,EAE5D,IAAMC,EAAc,KAAK,mBAAmB,EACtCC,EAAqB,KAAK,0BAA0B,EAC1D,KAAK,OAAS,IAAIC,GAAc,KAAK,OAAQ,CAC3C,YAAAF,EACA,mBAAAC,CACF,CAAC,EACD,KAAK,OAAO,SAAS,EAAE,IAAI,KAAK,OAAO,MAAM,EAE7C,KAAK,aAAe,IAAIE,GACtB,KAAK,OACL,KAAK,SAAS,MACd,KAAK,SAAS,OACd,KAAK,MACP,EACA,KAAK,aAAa,eAAe,CAC/B,oBAAqB,KAAK,QAAQ,oBAClC,qBAAsB,KAAK,QAAQ,oBACrC,CAAC,EAED,KAAK,OAAO,gBAAgB,KAAK,YAAY,CAC/C,CAES,kBAAyB,CAChC,KAAK,QAAU,KAAK,yBAAyB,EAC7C,IAAMC,EAAqB,CAAC,CAAC,KAAK,QAAQ,aACtCA,GAAsB,CAAC,KAAK,cAC9B,KAAK,aAAe,GACpB,KAAK,iBAAiB,OAAO,EACzB,KAAK,QACP,KAAK,iBAAiB,aAAa,KAAK,OAAO,WAAW,EAE5D,KAAK,iBAAiB,aAAa,GAC1B,CAACA,GAAsB,KAAK,eACrC,KAAK,aAAe,GACpB,KAAK,iBAAiB,QAAQ,GAGhC,KAAK,cAAc,eAAe,CAChC,oBAAqB,KAAK,QAAQ,oBAClC,qBAAsB,KAAK,QAAQ,oBACrC,CAAC,CACH,CAEQ,0BAA4C,CAClD,MAAO,CACL,SAAU,KAAK,gBAAgB,WAAY,EAAK,EAChD,UAAW,KAAK,gBAAgB,YAAa,MAAS,EACtD,OAAQ,KAAK,gBAAgB,SAAU,CAAC,EACxC,gBAAiB,KAAK,gBAAgB,kBAAmB,MAAS,EAClE,YAAa,KAAK,gBAAgB,cAAe,MAAS,EAC1D,mBAAoB,KAAK,gBAAgB,qBAAsB,MAAS,EACxE,aAAc,KAAK,gBAAgB,eAAgB,EAAK,EACxD,oBAAqB,KAAK,gBAAgB,sBAAuB,CAAC,EAClE,qBAAsB,KAAK,gBAAgB,uBAAwB,CAAC,CACtE,CACF,CAEQ,gBAAmBC,EAAaC,EAAgB,CACtD,MAAI,CAAC,KAAK,UAAY,EAAED,KAAO,KAAK,UAAkBC,EAC/C,KAAK,SAASD,CAAG,CAC1B,CAEQ,oBAAiD,CACvD,GAAK,KAAK,OACV,IAAI,KAAK,QAAQ,YAAa,OAAO,KAAK,QAAQ,YAClD,GAAI,MAAK,QAAQ,oBACb,KAAK,QAAQ,gBACf,GAAI,CACF,OAAO,KAAK,OAAO,kBAAkB,KAAK,QAAQ,eAAe,CACnE,MAAgB,CAAC,EAGrB,CAEQ,2BAEM,CACZ,GAAK,KAAK,OACV,IAAI,KAAK,QAAQ,mBAAoB,OAAO,KAAK,QAAQ,mBACzD,GAAI,KAAK,QAAQ,gBACf,MAAO,CAACE,EAAmBC,IAAkB,CAC3C,IAAMC,EAAaD,GAAQ,KAAK,QAAQ,gBACxC,GAAI,CAACC,EACH,MAAM,IAAI,MAAM,2CAA2C,EAE7D,OAAOF,EAAO,kBAAkBE,CAAU,CAC5C,EAGJ,CAEQ,sBAAoC,CAC1C,GAAI,KAAK,QAAQ,qBAAqB,YACpC,YAAK,qBAAqB,KAAK,QAAQ,SAAS,EACzC,KAAK,QAAQ,UAGtB,GAAI,OAAO,KAAK,QAAQ,WAAc,SAAU,CAC9C,IAAMC,EAAW,SAAS,eAAe,KAAK,QAAQ,SAAS,EAC/D,GAAIA,EACF,YAAK,qBAAqBA,CAAQ,EAC3BA,CAEX,CAEA,IAAMC,EAAY,SAAS,cAAc,KAAK,EAC9C,OAAAA,EAAU,GAAK,mBACf,KAAK,qBAAqBA,CAAS,EACnC,SAAS,KAAK,aAAaA,EAAW,SAAS,KAAK,UAAU,EACvDA,CACT,CAEQ,qBAAqBC,EAAuB,CAClD,OAAO,OAAOA,EAAG,MAAO,CACtB,SAAU,QACV,KAAM,IACN,IAAK,IACL,MAAO,QACP,OAAQ,SACR,OAAQ,OAAO,KAAK,QAAQ,MAAM,EAClC,cAAe,MACjB,CAAC,CACH,CAES,kBAAkBpB,EAA4B,CACjD,KAAK,UAAU,IAAIA,EAAO,EAAE,GAAK,CAAC,KAAK,SAG3C,KAAK,UAAU,IAAIA,EAAO,GAAI,EAAI,EAElC,KAAK,OAAO,kBAAkBA,CAAM,EAEhC,KAAK,cAAgBA,EAAO,cAC9B,KAAK,iBAAiB,eAAeA,EAAO,WAAW,EACvD,KAAK,iBAAiB,UAAUA,EAAO,WAAW,GAGhD,KAAK,QAAQ,UAAYA,EAAO,cAClCA,EAAO,YAAY,MAAM,QAAU,IACnCA,EAAO,YAAY,MAAM,cAAgB,QAE7C,CAES,QAAQqB,EAAwB,CACvC,GAAI,CAAC,KAAK,UAAY,CAAC,KAAK,QAAU,CAAC,KAAK,QAAU,CAAC,KAAK,aAAc,OAEtE,KAAK,qBACP,KAAK,mBAAqB,GAC1B,KAAK,SAAS,OAAO,KAAK,MAAM,EAChC,KAAK,aAAa,mBAAmB,KAAK,SAAS,MAAO,KAAK,SAAS,MAAM,GAGhF,IAAMC,EAAW,KAAK,aAAe,KAAK,iBAAiB,YAAY,EAAI,KACrEC,EAAY,CAACD,GAAYA,EAAS,OAAS,EAEjD,KAAK,iBAAiB,KAAK,OAAO,YAAaC,EAAWD,CAAQ,EAElE,KAAK,OAAO,YAAY,QAASE,GAAQ,CACvC,KAAK,cAAcA,EAAI,GAAIA,EAAK,CAAE,MAAO,CAAE,EAAGD,EAAWD,CAAQ,CACnE,CAAC,EAED,IAAMG,EAAgB,KAAK,iBAAiB,eAC1C,KAAK,OAAO,YACZ,YAAY,IAAI,EAChB,KAAK,aACLH,CACF,EACA,KAAK,SAAU,OAAO,KAAK,OAAS,KAAK,OAASG,CAAa,EAE3D,KAAK,cACP,KAAK,iBAAiB,WAAW,CAErC,CAEQ,iBACNC,EACAH,EACAD,EACM,CACN,IAAMK,EAAQH,GAA8B,CAC1C,GAAIA,EAAI,KACaD,GAAa,CAACD,GAAYA,EAAS,IAAIE,EAAI,EAAE,GAChD,CACd,IAAMI,EAAOJ,EAAI,GAAG,sBAAsB,EACpCK,EAAQL,EAAI,GAAG,aAAeI,EAAK,MACnCE,EAASN,EAAI,GAAG,cAAgBI,EAAK,OAC1CJ,EAAI,GAAW,cAAgB,CAAE,KAAAI,EAAM,MAAAC,EAAO,OAAAC,CAAO,CACxD,CAEFN,EAAI,SAAS,QAAQG,CAAI,CAC3B,EACAD,EAAY,QAAQC,CAAI,CAC1B,CAEQ,cACNP,EACApB,EACA+B,EACAR,EACAD,EACM,CACN,GAAI,CAAC,KAAK,cAAgB,CAACF,EAAI,OAC/B,IAAMY,EACJhC,EAAO,OAAS,aAChBA,EAAO,OAAS,QAChBuB,GACA,CAACD,GACDA,EAAS,IAAIF,CAAE,EACba,EAAiBF,EAErB,GAAIC,EAAY,CACd,IAAMX,EAAO,KAAK,aAAa,YAAYD,EAAIpB,EAAQ+B,EAAY,CACjE,SAAAT,EACA,UAAAC,CACF,CAAC,EACGF,GAAQ,OAAOA,EAAK,OAAU,WAChC,KAAK,aAAa,IAAIrB,EAAQqB,CAAI,EAClCY,EAAiBZ,EAErB,KAAO,CACL,IAAMa,EAAS,KAAK,aAAa,IAAIlC,CAAM,EACvCkC,IACFD,EAAiBC,EAErB,CAEA,IAAMC,EAAgBZ,GAAaS,EACnChC,EAAO,SAAS,QAASoC,GACvB,KAAK,cAAcA,EAAM,GAAIA,EAAOH,EAAgBE,EAAeb,CAAQ,CAC7E,CACF,CAEQ,WAAkB,CACxB,GAAI,SAAS,eAAe,kBAAkB,EAAG,OAEjD,IAAMe,EAAQ,SAAS,cAAc,OAAO,EAC5CA,EAAM,GAAK,mBACXA,EAAM,YAAc;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,MAyGpB,SAAS,KAAK,YAAYA,CAAK,CACjC,CAEQ,yBAAgC,CACtC,IAAMC,EAAO,WAAmB,IAChC,GAAI,CAACA,GAAK,iBAAkB,OAEiC,CAC3D,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,aAAc,aAAc,GAAI,EACxC,CAAE,KAAM,aAAc,aAAc,GAAI,EACxC,CAAE,KAAM,aAAc,aAAc,GAAI,EACxC,CAAE,KAAM,UAAW,aAAc,GAAI,EACrC,CAAE,KAAM,YAAa,aAAc,GAAI,EACvC,CAAE,KAAM,YAAa,aAAc,GAAI,EACvC,CAAE,KAAM,YAAa,aAAc,GAAI,EACvC,CAAE,KAAM,YAAa,aAAc,GAAI,EACvC,CAAE,KAAM,WAAY,aAAc,MAAO,EACzC,CAAE,KAAM,kBAAmB,aAAc,OAAQ,EACjD,CAAE,KAAM,mBAAoB,aAAc,SAAU,EACpD,CAAE,KAAM,uBAAwB,aAAc,GAAI,EAClD,CAAE,KAAM,uBAAwB,aAAc,GAAI,EAClD,CAAE,KAAM,sBAAuB,aAAc,SAAU,EACvD,CAAE,KAAM,cAAe,aAAc,SAAU,EAC/C,CAAE,KAAM,cAAe,aAAc,KAAM,EAC3C,CAAE,KAAM,iBAAkB,aAAc,GAAI,EAC5C,CAAE,KAAM,gBAAiB,aAAc,KAAM,EAC7C,CAAE,KAAM,gBAAiB,aAAc,MAAO,EAC9C,CAAE,KAAM,mBAAoB,aAAc,MAAO,EACjD,CAAE,KAAM,sBAAuB,aAAc,MAAO,EACpD,CAAE,KAAM,sBAAuB,aAAc,MAAO,EACpD,CAAE,KAAM,eAAgB,aAAc,MAAO,EAC7C,CAAE,KAAM,gBAAiB,aAAc,SAAU,EACjD,CAAE,KAAM,oBAAqB,aAAc,GAAI,EAC/C,CAAE,KAAM,mBAAoB,aAAc,MAAO,EACjD,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,gBAAiB,aAAc,QAAS,EAChD,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,uBAAwB,aAAc,SAAU,EACxD,CAAE,KAAM,iBAAkB,aAAc,MAAO,EAC/C,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,gBAAiB,aAAc,GAAI,EAC3C,CAAE,KAAM,oBAAqB,aAAc,KAAM,EACjD,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,wBAAyB,aAAc,MAAO,EACtD,CAAE,KAAM,mBAAoB,aAAc,SAAU,EACpD,CAAE,KAAM,oBAAqB,aAAc,KAAM,EACjD,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,oBAAqB,aAAc,SAAU,EACrD,CAAE,KAAM,sBAAuB,aAAc,GAAI,EACjD,CAAE,KAAM,qBAAsB,aAAc,KAAM,EAClD,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,oBAAqB,aAAc,QAAS,EACpD,CAAE,KAAM,kBAAmB,aAAc,GAAI,EAC7C,CAAE,KAAM,oBAAqB,aAAc,MAAO,EAClD,CAAE,KAAM,2BAA4B,aAAc,MAAO,EACzD,CAAE,KAAM,yBAA0B,aAAc,MAAO,EACvD,CAAE,KAAM,mBAAoB,aAAc,MAAO,EACjD,CAAE,KAAM,0BAA2B,aAAc,MAAO,EACxD,CAAE,KAAM,wBAAyB,aAAc,MAAO,EACtD,CAAE,KAAM,cAAe,aAAc,IAAK,EAC1C,CAAE,KAAM,eAAgB,aAAc,GAAI,EAC1C,CAAE,KAAM,kBAAmB,aAAc,KAAM,EAC/C,CAAE,KAAM,mBAAoB,aAAc,IAAK,EAC/C,CAAE,KAAM,uBAAwB,aAAc,OAAQ,EACtD,CAAE,KAAM,qBAAsB,aAAc,SAAU,EACtD,CAAE,KAAM,kBAAmB,aAAc,KAAM,EAC/C,CAAE,KAAM,4BAA6B,aAAc,KAAM,EACzD,CAAE,KAAM,6BAA8B,aAAc,KAAM,EAC1D,CAAE,KAAM,mBAAoB,aAAc,QAAS,EACnD,CAAE,KAAM,mBAAoB,aAAc,GAAI,EAC9C,CAAE,KAAM,6BAA8B,aAAc,KAAM,EAC1D,CAAE,KAAM,4BAA6B,aAAc,KAAM,EACzD,CAAE,KAAM,oBAAqB,aAAc,KAAM,EACjD,CAAE,KAAM,kBAAmB,aAAc,KAAM,EAC/C,CAAE,KAAM,sBAAuB,aAAc,GAAI,EACjD,CAAE,KAAM,qBAAsB,aAAc,GAAI,EAChD,CAAE,KAAM,uBAAwB,aAAc,GAAI,EAClD,CAAE,KAAM,uBAAwB,aAAc,GAAI,EAClD,CAAE,KAAM,uBAAwB,aAAc,GAAI,EAClD,CAAE,KAAM,eAAgB,aAAc,GAAI,EAC1C,CAAE,KAAM,wBAAyB,aAAc,GAAI,EACnD,CAAE,KAAM,oBAAqB,aAAc,GAAI,EAC/C,CAAE,KAAM,yBAA0B,aAAc,GAAI,EACpD,CAAE,KAAM,sBAAuB,aAAc,GAAI,EACjD,CAAE,KAAM,qBAAsB,aAAc,GAAI,EAChD,CAAE,KAAM,aAAc,aAAc,SAAU,CAChD,EAEM,QAAQ,CAAC,CAAE,KAAA1C,EAAM,aAAA2C,CAAa,IAAM,CACxC,GAAI,CACFD,EAAI,iBAAiB,CACnB,KAAA1C,EACA,OACEA,IAAS,YACTA,IAAS,kBACTA,EAAK,WAAW,YAAY,GAC5BA,IAAS,mBACTA,IAAS,oBACTA,IAAS,qBACTA,IAAS,qBACTA,IAAS,4BACTA,IAAS,0BACTA,IAAS,oBACTA,IAAS,2BACTA,IAAS,yBACTA,IAAS,wBACTA,IAAS,sBACTA,IAAS,oBACTA,IAAS,aACL,IACAA,EAAK,SAAS,OAAO,GAAKA,EAAK,SAAS,UAAU,EAClD,UACA,WACN,SAAU,GACV,aAAA2C,CACF,CAAC,CACH,MAAQ,CAAC,CACX,CAAC,CACH,CAES,SAAgB,CACvB,KAAK,UAAU,QAAQ,EACvB,KAAK,QAAQ,QAAQ,EACrB,KAAK,UAAU,MAAM,EACrB,KAAK,iBAAiB,QAAQ,EAC9B,KAAK,iBAAiB,MAAM,EAC5B,KAAK,aAAe,IAAI,QAER,SAAS,eAAe,kBAAkB,GACjD,OAAO,EAEZ,KAAK,iBAAiB,KAAO,oBAC/B,KAAK,gBAAgB,OAAO,EAG9B,MAAM,QAAQ,CAChB,CACF,EArmBalD,GACI,SAAqC,KADzCA,GAEI,UAA6B,KAFvC,IAAMmD,GAANnD,GqBrBA,IAAMoD,GAAN,KAAyD,CAK9D,YAAYC,EAAY,CAFxB,KAAQ,aAAiC,IAAI,IAG3C,KAAK,MAAQA,EACb,KAAK,cAAgB,IAAIA,EAAM,aACjC,CAEA,SAASC,EAAuD,CAC9D,MAAO,EACT,CAEA,OACEA,EACAC,EACmB,CACnB,IAAMC,EAAW,KAAK,cAAcF,EAAYC,CAAe,EAE3DE,EAEJ,OAAIH,EAAW,UAAY,UAAa,CAACA,EAAW,SAAWA,EAAW,aACxEG,EAAW,KAAK,qBAAqBH,EAAYE,CAAQ,EAEzDC,EAAW,KAAK,uBAAuBH,EAAYE,CAAQ,EAG7D,KAAK,wBAAwBC,EAAUH,CAAU,EAU1C,CAAE,SAAAG,EAAU,WAAAH,EAAY,OARfI,GAAqC,CACnD,KAAK,eAAeD,EAAUH,EAAYI,CAAW,CACvD,EAMuC,QAJvB,IAAM,CACpBD,EAAS,QAAQ,CACnB,CAE+C,CACjD,CAEA,qBACEH,EACAK,EACAC,EACqB,CACrB,OAAOC,GAAuBP,EAAYK,EAASC,CAAK,CAC1D,CAEQ,cACNN,EACAQ,EACgC,CAChC,IAAMC,EAAyC,CAAC,EAEhD,GAAIT,EAAW,SACb,OAAW,CAACU,EAAKC,CAAG,IAAK,OAAO,QAAQX,EAAW,QAAQ,EAAG,CAC5D,IAAIY,EAAQJ,IAAgBE,CAAG,GAAKC,EAAI,MACxCC,EAAQ,KAAK,oBAAoBD,EAAI,KAAMC,CAAK,EAChDH,EAAOC,CAAG,EAAI,CAAE,MAAAE,CAAM,CACxB,CAGF,OAAOH,CACT,CAEQ,oBAAoBI,EAAcD,EAAiB,CACzD,OAAQC,EAAM,CACZ,IAAK,OACH,OAAI,MAAM,QAAQD,CAAK,EACd,IAAI,KAAK,MAAM,QAAQA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAE3CA,EACT,IAAK,OACH,OAAI,MAAM,QAAQA,CAAK,EACd,IAAI,KAAK,MAAM,QAAQA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAErDA,EACT,IAAK,OACH,OAAI,MAAM,QAAQA,CAAK,EACd,IAAI,KAAK,MAAM,QAAQA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAE/DA,EACT,IAAK,QACH,OAAI,MAAM,QAAQA,CAAK,EACd,IAAI,KAAK,MAAM,MAAMA,EAAM,CAAC,EAAGA,EAAM,CAAC,EAAGA,EAAM,CAAC,CAAC,EAEtD,OAAOA,GAAU,SACZ,IAAI,KAAK,MAAM,MAAMA,CAAK,EAE5BA,EACT,IAAK,UACH,OAAI,OAAOA,GAAU,UAAYA,EACxB,KAAK,YAAYA,CAAK,EAExBA,EACT,QACE,OAAOA,CACX,CACF,CAEQ,YAAYE,EAAkB,CACpC,GAAI,KAAK,aAAa,IAAIA,CAAG,EAC3B,OAAO,KAAK,aAAa,IAAIA,CAAG,EAElC,IAAMC,EAAU,KAAK,cAAc,KAAKD,CAAG,EAC3C,YAAK,aAAa,IAAIA,EAAKC,CAAO,EAC3BA,CACT,CAEQ,qBACNf,EACAE,EACK,CACL,IAAMC,EAAW,IAAI,KAAK,MAAM,eAAe,CAC7C,SAAAD,EACA,aAAcF,EAAW,cAAgB,KAAK,uBAAuB,EACrE,eAAgBA,EAAW,gBAAkB,KAAK,yBAAyB,EAC3E,OAAQA,EAAW,QAAU,GAC7B,YAAaA,EAAW,YAAY,aAAe,EACrD,CAAC,EACD,OAAAG,EAAS,SAAS,eAAiBD,EACnCC,EAAS,SAAS,WAAaH,EACxBG,CACT,CAEQ,uBACNH,EACAE,EACK,CACL,IAAMc,EAAWhB,EAAW,SAAW,WACnCiB,EAEJ,OAAQD,EAAU,CAChB,IAAK,QACHC,EAAe,KAAK,MAAM,kBAC1B,MACF,IAAK,WACHA,EAAe,KAAK,MAAM,qBAC1B,MACF,IAAK,WACL,QACEA,EAAe,KAAK,MAAM,qBAC1B,KACJ,CAEA,IAAMd,EAAW,IAAIc,EAAa,CAChC,YAAajB,EAAW,YAAY,aAAe,EACrD,CAAC,EAED,GAAIA,EAAW,YAAcA,EAAW,WAAW,OAAS,EAAG,CAC7D,IAAMkB,EAAeC,GAAgBnB,EAAW,UAAU,EAE1DG,EAAS,gBAAmBiB,GAAgB,CAC1C,OAAO,OAAOA,EAAO,SAAUlB,CAAQ,EAEvCkB,EAAO,aAAe,KAAK,mBAAmBA,EAAO,aAAcF,EAAchB,CAAQ,EACzFkB,EAAO,eAAiB,KAAK,qBAC3BA,EAAO,eACPF,EACAhB,CACF,EAEAC,EAAS,SAAS,OAASiB,CAC7B,CACF,CAEA,OAAAjB,EAAS,SAAS,eAAiBD,EACnCC,EAAS,SAAS,WAAaH,EAExBG,CACT,CAEQ,mBACNiB,EACAC,EACAnB,EACQ,CACR,IAAIO,EAASW,EAEPE,EAAOD,EAAW,IAAI,aAAa,EACrCC,IACFb,EAASA,EAAO,QAAQ,oBAAqB;AAAA,EAAsBa,CAAI,EAAE,GAG3E,IAAMC,EAASF,EAAW,IAAI,eAAe,EAC7C,GAAIE,EAAQ,CACV,IAAMC,EAAsB,KAAK,4BAA4BtB,CAAQ,EACrEO,EAASA,EAAO,QAAQ,gBAAiB,GAAGe,CAAmB;AAAA,EAAKD,CAAM;AAAA,cAAiB,CAC7F,CAEA,IAAME,EAAYJ,EAAW,IAAI,kBAAkB,EAC/CI,IACFhB,EAASA,EAAO,QAAQ,0BAA2B;AAAA,EAA4BgB,CAAS,EAAE,GAG5F,IAAMC,EAASL,EAAW,IAAI,eAAe,EAC7C,OAAIK,IACFjB,EAASA,EAAO,QAAQ,4BAA6B,GAAGiB,CAAM;AAAA,0BAA6B,GAGtFjB,CACT,CAEQ,qBACNW,EACAC,EACAnB,EACQ,CACR,IAAIO,EAASW,EAEPE,EAAOD,EAAW,IAAI,eAAe,EACvCC,IACFb,EAASA,EAAO,QAAQ,oBAAqB;AAAA,EAAsBa,CAAI,EAAE,GAG3E,IAAMC,EAASF,EAAW,IAAI,iBAAiB,EAC/C,GAAIE,EAAQ,CACV,IAAMC,EAAsB,KAAK,4BAA4BtB,CAAQ,EACrEO,EAASA,EAAO,QAAQ,gBAAiB,GAAGe,CAAmB;AAAA,EAAKD,CAAM;AAAA,cAAiB,CAC7F,CAEA,IAAMI,EAAQN,EAAW,IAAI,gBAAgB,EACzCM,IACFlB,EAASA,EAAO,QAAQ,4BAA6B;AAAA,EAA8BkB,CAAK,EAAE,GAG5F,IAAMC,EAASP,EAAW,IAAI,iBAAiB,EAC3CO,IACFnB,EAASA,EAAO,QACd,kCACA;AAAA,EAAoCmB,CAAM,EAC5C,GAGF,IAAMC,EAAYR,EAAW,IAAI,oBAAoB,EACjDQ,IACFpB,EAASA,EAAO,QACd,mCACA;AAAA,EAAqCoB,CAAS,EAChD,GAGF,IAAMC,EAAYT,EAAW,IAAI,oBAAoB,EACjDS,IACFrB,EAASA,EAAO,QACd,mCACA;AAAA,EAAqCqB,CAAS,EAChD,GAGF,IAAMC,EAAKV,EAAW,IAAI,aAAa,EACnCU,IACFtB,EAASA,EAAO,QAAQ,4BAA6B;AAAA,EAA8BsB,CAAE,EAAE,GAGzF,IAAMC,EAAeX,EAAW,IAAI,uBAAuB,EACvDW,IACFvB,EAASA,EAAO,QACd,mCACA;AAAA,EAAqCuB,CAAY,EACnD,GAGF,IAAMC,EAASZ,EAAW,IAAI,iBAAiB,EAC3CY,IACFxB,EAASA,EAAO,QACd,sCACA;AAAA,EAAwCwB,CAAM,EAChD,GAGF,IAAMC,EAAWb,EAAW,IAAI,mBAAmB,EAC/Ca,IACFzB,EAASA,EAAO,QACd,kCACA;AAAA,EAAoCyB,CAAQ,EAC9C,GAGF,IAAMR,EAASL,EAAW,IAAI,iBAAiB,EAC/C,OAAIK,IACFjB,EAASA,EAAO,QACd,gCACA,GAAGiB,CAAM;AAAA,8BACX,GAGKjB,CACT,CAEQ,4BAA4BP,EAAkD,CACpF,IAAMiC,EAAkB,CAAC,EAEzB,OAAW,CAACC,EAAMC,CAAO,IAAK,OAAO,QAAQnC,CAAQ,EAAG,CACtD,IAAMW,EAAO,KAAK,cAAcwB,EAAQ,KAAK,EAC7CF,EAAM,KAAK,WAAWtB,CAAI,IAAIuB,CAAI,GAAG,CACvC,CAEA,OAAOD,EAAM,KAAK;AAAA,CAAI,CACxB,CAEQ,cAAcvB,EAAoB,CACxC,OAAI,OAAOA,GAAU,SAAiB,QAClC,OAAOA,GAAU,UAAkB,OACnCA,aAAiB,KAAK,MAAM,QAAgB,OAC5CA,aAAiB,KAAK,MAAM,QAAgB,OAC5CA,aAAiB,KAAK,MAAM,QAAgB,OAC5CA,aAAiB,KAAK,MAAM,MAAc,OAC1CA,aAAiB,KAAK,MAAM,QAAgB,OAC5CA,aAAiB,KAAK,MAAM,QAAgB,OAC5CA,GAAO,UAAkB,YACtB,OACT,CAEQ,wBACNT,EACAH,EACM,CACN,IAAMsC,EAAQtC,EAAW,WACzB,GAAKsC,EAML,IAJIA,EAAM,cAAgB,SACxBnC,EAAS,YAAcmC,EAAM,aAG3BA,EAAM,OAAS,OACjB,OAAQA,EAAM,KAAM,CAClB,IAAK,QACHnC,EAAS,KAAO,KAAK,MAAM,UAC3B,MACF,IAAK,OACHA,EAAS,KAAO,KAAK,MAAM,SAC3B,MACF,IAAK,SACHA,EAAS,KAAO,KAAK,MAAM,WAC3B,KACJ,CAWF,GARImC,EAAM,aAAe,SACvBnC,EAAS,WAAamC,EAAM,YAG1BA,EAAM,YAAc,SACtBnC,EAAS,UAAYmC,EAAM,WAGzBA,EAAM,WAAa,OACrB,OAAQA,EAAM,SAAU,CACtB,IAAK,WACHnC,EAAS,SAAW,KAAK,MAAM,iBAC/B,MACF,IAAK,cACHA,EAAS,SAAW,KAAK,MAAM,oBAC/B,MACF,IAAK,WACHA,EAAS,SAAW,KAAK,MAAM,iBAC/B,MACF,QACEA,EAAS,SAAW,KAAK,MAAM,cACnC,CAGEmC,EAAM,YAAc,SACtBnC,EAAS,UAAYmC,EAAM,WAE/B,CAEQ,eACNnC,EACAH,EACAuC,EACM,CACN,IAAMnB,EAASjB,EAAS,UAAU,OAC5BqC,EAAiBrC,EAAS,UAAU,eAE1C,GAAIiB,GAAQ,SACV,OAAW,CAACV,EAAKE,CAAK,IAAK,OAAO,QAAQ2B,CAAS,EAAG,CACpD,IAAME,EAAazC,EAAW,WAAWU,CAAG,EACxC+B,GAAcrB,EAAO,SAASV,CAAG,IACnCU,EAAO,SAASV,CAAG,EAAE,MAAQ,KAAK,oBAAoB+B,EAAW,KAAM7B,CAAK,EAEhF,SACS4B,EACT,OAAW,CAAC9B,EAAKE,CAAK,IAAK,OAAO,QAAQ2B,CAAS,EAAG,CACpD,IAAME,EAAazC,EAAW,WAAWU,CAAG,EACxC+B,GAAcD,EAAe9B,CAAG,IAClC8B,EAAe9B,CAAG,EAAE,MAAQ,KAAK,oBAAoB+B,EAAW,KAAM7B,CAAK,EAE/E,CAGF,GAAIT,EAAS,SACX,OAAW,CAACO,EAAKE,CAAK,IAAK,OAAO,QAAQ2B,CAAS,EAAG,CACpD,IAAME,EAAazC,EAAW,WAAWU,CAAG,EACxC+B,GAActC,EAAS,SAASO,CAAG,IACrCP,EAAS,SAASO,CAAG,EAAE,MAAQ,KAAK,oBAAoB+B,EAAW,KAAM7B,CAAK,EAElF,CAEJ,CAEQ,wBAAiC,CACvC,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAYT,CAEQ,0BAAmC,CACzC,MAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAST,CAEA,SAAgB,CACd,KAAK,aAAa,QAASG,GAAYA,EAAQ,QAAQ,CAAC,EACxD,KAAK,aAAa,MAAM,CAC1B,CACF,EC7ZO,IAAM2B,GAAN,KAAyC,CAU9C,YAAYC,EAAYC,EAA+B,CAAC,EAAG,CAP3D,KAAQ,gBAAiD,KACzD,KAAQ,mBAAuC,IAAI,IACnD,KAAQ,0BAAuD,IAAI,IACnE,KAAQ,UAA8B,IAAI,IAC1C,KAAQ,iBAA8C,IAAI,IAC1D,KAAQ,iBAAqE,IAAI,IAG/E,KAAK,MAAQD,EACb,KAAK,QAAUC,EACf,KAAK,gBAAkB,IAAIC,GAAuBF,CAAK,CACzD,CAEA,oBAA8C,CAC5C,OAAO,KAAK,eACd,CAEA,cAAcG,EAAI,EAAGC,EAAI,EAAGC,EAAI,EAAe,CAC7C,OAAO,IAAI,KAAK,MAAM,QAAQF,EAAGC,EAAGC,CAAC,CACvC,CAEA,cAAcF,EAAI,EAAGC,EAAI,EAAe,CACtC,OAAO,IAAI,KAAK,MAAM,QAAQD,EAAGC,CAAC,CACpC,CAEA,iBAAiBD,EAAI,EAAGC,EAAI,EAAGC,EAAI,EAAGC,EAAI,EAAkB,CAC1D,OAAO,IAAI,KAAK,MAAM,WAAWH,EAAGC,EAAGC,EAAGC,CAAC,CAC7C,CAEA,YAAYH,EAAI,EAAGC,EAAI,EAAGC,EAAI,EAAGE,EAAQ,MAAiB,CACxD,OAAO,IAAI,KAAK,MAAM,MAAMJ,EAAGC,EAAGC,EAAGE,CAAK,CAC5C,CAEA,eAA4B,CAC1B,OAAO,IAAI,KAAK,MAAM,OACxB,CAEA,WAAWC,EAAkBC,EAA2B,CACtD,OAAO,IAAI,KAAK,MAAM,KAAKD,EAAKC,CAAG,CACrC,CAEA,aAAwB,CACtB,OAAO,IAAI,KAAK,MAAM,KACxB,CAEA,eAAeC,EAIC,CACd,IAAMC,EAAW,IAAI,KAAK,MAAM,cAAcD,CAAO,EACrD,OAAAC,EAAS,eAAiB,KAAK,MAAM,aAC9BA,CACT,CAEA,wBAAwBC,EAAM,GAAIC,EAAS,EAAGC,EAAO,GAAKC,EAAM,IAA4B,CAC1F,OAAO,IAAI,KAAK,MAAM,kBAAkBH,EAAKC,EAAQC,EAAMC,CAAG,CAChE,CAEA,yBACEC,EACAC,EACAC,EACAC,EACAL,EAAO,GACPC,EAAM,IACiB,CACvB,OAAO,IAAI,KAAK,MAAM,mBAAmBC,EAAMC,EAAOC,EAAKC,EAAQL,EAAMC,CAAG,CAC9E,CAEA,aAAyB,CACvB,OAAO,IAAI,KAAK,MAAM,KACxB,CAEA,WAAWK,EAAuBC,EAAgC,CAChE,OAAO,IAAI,KAAK,MAAM,KAAKD,EAAUC,CAAQ,CAC/C,CAEA,kBAAkBC,EAAeC,EAAgBC,EAA4B,CAC3E,OAAO,IAAI,KAAK,MAAM,YAAYF,EAAOC,EAAQC,CAAK,CACxD,CAEA,qBAAqBC,EAAgBC,EAAgB,GAAIC,EAAiB,GAAiB,CACzF,OAAO,IAAI,KAAK,MAAM,eAAeF,EAAQC,EAAeC,CAAc,CAC5E,CAEA,oBAAoBL,EAAeC,EAA6B,CAC9D,OAAO,IAAI,KAAK,MAAM,cAAcD,EAAOC,CAAM,CACnD,CAEA,uBACEK,EACAC,EACAN,EACAO,EAAW,GACE,CACb,OAAO,IAAI,KAAK,MAAM,iBAAiBF,EAAWC,EAAcN,EAAQO,CAAQ,CAClF,CAEA,wBAAwBC,EAA2B,CACjD,OAAO,IAAI,KAAK,MAAM,kBAAkBA,CAAM,CAChD,CAEA,2BAA2BA,EAA2B,CACpD,OAAO,IAAI,KAAK,MAAM,qBAAqBA,CAAM,CACnD,CAEA,qBAAqBA,EAA2B,CAC9C,OAAO,IAAI,KAAK,MAAM,eAAeA,CAAM,CAC7C,CACA,iBAAiBC,EAAyBC,EAAY,EAAGC,EAAW,EAAGC,EAAQ,EAAa,CAC1F,OAAO,IAAI,KAAK,MAAM,WAAWH,EAAOC,EAAWC,EAAUC,CAAK,CACpE,CAEA,gBACEH,EACAC,EAAY,EACZC,EAAW,EACXE,EAAQ,KAAK,GAAK,EAClBC,EAAW,EACXF,EAAQ,EACE,CACV,OAAO,IAAI,KAAK,MAAM,UAAUH,EAAOC,EAAWC,EAAUE,EAAOC,EAAUF,CAAK,CACpF,CAEA,sBACEG,EACAC,EACAN,EAAY,EACF,CACV,OAAO,IAAI,KAAK,MAAM,gBAAgBK,EAAUC,EAAaN,CAAS,CACxE,CAEA,mBAAmBD,EAAyBC,EAAY,EAAa,CACnE,OAAO,IAAI,KAAK,MAAM,aAAaD,EAAOC,CAAS,CACrD,CAEA,uBAAuBD,EAAyBC,EAAY,EAAa,CACvE,OAAO,IAAI,KAAK,MAAM,iBAAiBD,EAAOC,CAAS,CACzD,CAEA,qBAAwC,CACtC,OAAO,IAAI,KAAK,MAAM,aACxB,CAEA,kBAAkBO,EAA8B,CAC9C,IAAMC,EAAc,KAAK,QAAQD,CAAI,EACrC,GAAI,CAACC,EACH,MAAM,IAAI,MAAM,iCAAiCD,CAAI,kBAAkB,EAEzE,OAAO,IAAIC,CACb,CAEA,mBAAmBnB,EAAeC,EAAgBb,EAAe,CAAC,EAAoB,CACpF,IAAMgC,EAAW,CACf,UAAW,KAAK,MAAM,aACtB,UAAW,KAAK,MAAM,aACtB,OAAQ,KAAK,MAAM,WACnB,YAAa,GACb,cAAe,EACjB,EACA,OAAO,IAAI,KAAK,MAAM,kBAAkBpB,EAAOC,EAAQ,CAAE,GAAGmB,EAAU,GAAGhC,CAAQ,CAAC,CACpF,CAEA,SAASiC,EAA2B,CAClC,IAAMC,EAAaD,EAAI,KAAK,EAC5B,GAAI,CAACC,GAAcA,IAAe,OAChC,OAAO,QAAQ,QAAQ,IAAI,EAE7B,GAAI,KAAK,UAAU,IAAIA,CAAU,EAC/B,OAAO,QAAQ,QAAQ,KAAK,UAAU,IAAIA,CAAU,CAAC,EAEvD,IAAMC,EAAgB,KAAK,iBAAiB,IAAID,CAAU,EAC1D,GAAIC,EAAe,OAAOA,EAE1B,IAAMC,EAAaC,GAAc,WAAWH,CAAU,EAElDI,EAEJ,OAAIF,EACFE,EAAU,KAAK,sBAAsBJ,CAAU,EAE/CI,EAAU,KAAK,mBAAmBJ,CAAU,EAG9C,KAAK,iBAAiB,IAAIA,EAAYI,CAAO,EACtCA,CACT,CAEA,MAAc,sBAAsBL,EAA2B,CAC7D,GAAI,CACF,IAAMM,EAAW,MAAMF,GAAc,KAAKJ,CAAG,EACvCO,EAAO,KAAK,mBAAmBD,CAAQ,EAC7C,YAAK,UAAU,IAAIN,EAAKO,CAAI,EACrBA,CACT,MAAgB,CACd,OAAO,IACT,CACF,CAEQ,mBAAmBP,EAA2B,CACpD,IAAMF,EAAc,KAAK,QAAQ,MAAQ,KAAK,QAAQ,WACtD,GAAI,CAACA,EACH,OAAO,QAAQ,QAAQ,IAAI,EAG7B,IAAMU,EAAS,IAAIV,EACnB,OAAO,IAAI,QAAcW,GAAY,CACnCD,EAAO,KACLR,EACCO,GAAc,CACb,KAAK,UAAU,IAAIP,EAAKO,CAAI,EAC5BE,EAAQF,CAAI,CACd,EACA,OACA,IAAM,CACJE,EAAQ,IAAI,CACd,CACF,CACF,CAAC,CACH,CAEQ,mBAAmBH,EAAoB,CAC7C,IAAMR,EAAc,KAAK,QAAQ,MAAQ,KAAK,QAAQ,WACtD,GAAIA,GAAeA,EAAY,OAASA,EAAY,MAAM,QAAS,CACjE,IAAMU,EAAS,IAAIV,EACnB,GAAIU,EAAO,MACT,OAAOA,EAAO,MAAMF,CAAQ,CAEhC,CAYA,MAVa,CACX,KAAMA,EACN,OAAQ,GACR,eAAgB,CAACI,EAAcC,IACtB,KAAK,2BAA2BL,EAAUI,EAAMC,EAAM,EAAK,EAEpE,yBAA0B,CAACD,EAAcC,IAChC,KAAK,2BAA2BL,EAAUI,EAAMC,EAAM,EAAI,CAErE,CAEF,CAEQ,2BACNL,EACAI,EACAC,EACAC,EAA6B,GACtB,CACP,IAAMC,EAAgB,CAAC,EACjBC,EAAQH,EAAOL,EAAS,WAExBS,EAAOL,EAAK,CAAC,EACnB,GAAI,CAACK,EAAM,OAAOF,EAElB,IAAMG,EAAQV,EAAS,OAAOS,CAAI,EAClC,GAAI,CAACC,GAAS,CAACA,EAAM,EAAG,OAAOH,EAE/B,IAAII,EAAU,EACVL,IAEFK,EAAU,CADG,KAAK,eAAeD,EAAM,CAAC,EACtBF,GAGpB,IAAMI,EAAa,KAAK,qBAAqBF,EAAM,EAAGF,EAAOG,EAASX,GAAU,aAAa,EAC7F,OAAAO,EAAO,KAAK,GAAGK,CAAU,EAElBL,CACT,CAEQ,eAAeM,EAAyB,CAC9C,IAAMC,EAAWD,EAAQ,MAAM,GAAG,EAC9BE,EAAO,IACPC,EAAI,EAER,KAAOA,EAAIF,EAAS,QAElB,OADYA,EAASE,CAAC,EACT,CACX,IAAK,IACL,IAAK,IACHD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDD,EAAO,KAAK,IAAIA,EAAM,WAAWD,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,QACEA,IACA,KACJ,CAGF,OAAOD,IAAS,IAAW,EAAIA,CACjC,CAEQ,eAAeF,EAAyB,CAC9C,IAAMC,EAAWD,EAAQ,MAAM,GAAG,EAC9BI,EAAO,KACPD,EAAI,EAER,KAAOA,EAAIF,EAAS,QAElB,OADYA,EAASE,CAAC,EACT,CACX,IAAK,IACL,IAAK,IACHC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDC,EAAO,KAAK,IAAIA,EAAM,WAAWH,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,QACEA,IACA,KACJ,CAGF,OAAOC,IAAS,KAAY,EAAIA,CAClC,CAEQ,eAAeJ,EAAyB,CAC9C,IAAMC,EAAWD,EAAQ,MAAM,GAAG,EAC9BK,EAAO,IACPF,EAAI,EAER,KAAOA,EAAIF,EAAS,QAElB,OADYA,EAASE,CAAC,EACT,CACX,IAAK,IACL,IAAK,IACHE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,IAAK,IACHE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDE,EAAO,KAAK,IAAIA,EAAM,WAAWJ,EAASE,EAAI,CAAC,CAAC,GAAK,CAAC,EACtDA,GAAK,EACL,MACF,QACEA,IACA,KACJ,CAGF,OAAOE,IAAS,IAAW,EAAIA,CACjC,CAEQ,eACNC,EACAC,EACAC,EACS,CACT,IAAIC,EAAS,GACb,QAASN,EAAI,EAAGO,EAAIF,EAAQ,OAAS,EAAGL,EAAIK,EAAQ,OAAQE,EAAIP,IAAK,CACnE,IAAMQ,EAAKH,EAAQL,CAAC,EAAE,EAChBS,EAAKJ,EAAQL,CAAC,EAAE,EAChBU,EAAKL,EAAQE,CAAC,EAAE,EAChBI,EAAKN,EAAQE,CAAC,EAAE,EAElBE,EAAKL,GAAOO,EAAKP,GAAMD,GAAOO,EAAKF,IAAOJ,EAAKK,IAAQE,EAAKF,GAAMD,IACpEF,EAAS,CAACA,EAEd,CACA,OAAOA,CACT,CAEQ,iBAAiBM,EAAWC,EAAqB,GAAqC,CAC5F,OAAKD,GAAM,UACJA,EAAK,UAAUC,CAAU,EAAE,IAAKC,IAAY,CAAE,EAAGA,EAAE,EAAG,EAAGA,EAAE,CAAE,EAAE,EADzC,CAAC,CAEhC,CAEQ,eAAeC,EAMrB,CACA,GAAIA,EAAO,SAAW,EACpB,MAAO,CAAE,KAAM,EAAG,KAAM,EAAG,KAAM,EAAG,KAAM,EAAG,KAAM,CAAE,EAEvD,IAAIhB,EAAO,IACPE,EAAO,KACPC,EAAO,IACPc,EAAO,KACX,QAAWF,KAAKC,EACVD,EAAE,EAAIf,IAAMA,EAAOe,EAAE,GACrBA,EAAE,EAAIb,IAAMA,EAAOa,EAAE,GACrBA,EAAE,EAAIZ,IAAMA,EAAOY,EAAE,GACrBA,EAAE,EAAIE,IAAMA,EAAOF,EAAE,GAE3B,MAAO,CAAE,KAAAf,EAAM,KAAAE,EAAM,KAAAC,EAAM,KAAAc,EAAM,MAAOf,EAAOF,IAASiB,EAAOd,EAAM,CACvE,CAEQ,iBAAiBa,EAAmE,CAC1F,GAAIA,EAAO,OAAS,EAAG,OAAOA,EAAO,CAAC,GAAK,CAAE,EAAG,EAAG,EAAG,CAAE,EACxD,IAAME,EAAUF,EAAO,IAAKD,GAAM,IAAI,KAAK,MAAM,QAAQA,EAAE,EAAGA,EAAE,CAAC,CAAC,EAC5DI,EAAY,KAAK,MAAM,WAAW,iBAAiBD,EAAS,CAAC,CAAC,EACpE,QAAWE,KAAOD,EAAW,CAC3B,IAAME,EAAIH,EAAQE,EAAI,CAAC,CAAC,EAClBE,EAAIJ,EAAQE,EAAI,CAAC,CAAC,EAClBG,EAAIL,EAAQE,EAAI,CAAC,CAAC,EAClBI,GAAMH,EAAE,EAAIC,EAAE,EAAIC,EAAE,GAAK,EACzBE,GAAMJ,EAAE,EAAIC,EAAE,EAAIC,EAAE,GAAK,EAC/B,GAAI,KAAK,eAAeC,EAAIC,EAAIT,CAAM,EACpC,MAAO,CAAE,EAAGQ,EAAI,EAAGC,CAAG,CAE1B,CACA,OAAOT,EAAO,CAAC,CACjB,CAEQ,qBACNlB,EACAL,EACAiC,EAAkB,EAClBC,EACO,CACP,GAAI,CAAC7B,EAAS,MAAO,CAAC,EAEtB,IAAM8B,EAAY,IAAI,KAAK,MAAM,UAC3B7B,EAAWD,EAAQ,MAAM,GAAG,EAC9BG,EAAI,EAER,KAAOA,EAAIF,EAAS,QAElB,OADYA,EAASE,CAAC,EACT,CACX,IAAK,IACH,CACE,IAAM4B,EAAK,WAAW9B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EAC3CI,EAAK,CAAC,WAAW/B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC1CmC,EAAU,OAAOC,EAAIC,CAAE,EACvB7B,GAAK,CACP,CACA,MACF,IAAK,IACH,CACE,IAAM8B,EAAK,WAAWhC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EAC3CM,EAAK,CAAC,WAAWjC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC1CmC,EAAU,OAAOG,EAAIC,CAAE,EACvB/B,GAAK,CACP,CACA,MACF,IAAK,IACH,CACE,IAAMgC,EAAK,WAAWlC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EAC3CQ,EAAK,CAAC,WAAWnC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC1CmC,EAAU,iBACR,WAAW7B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EACtC,CAAC,WAAW3B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC/BwC,EACAC,CACF,EACAjC,GAAK,CACP,CACA,MACF,IAAK,IACH,CACE,IAAMkC,EAAK,WAAWpC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EAC3CU,EAAK,CAAC,WAAWrC,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC1CmC,EAAU,cACR,WAAW7B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EACtC,CAAC,WAAW3B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC/B,WAAWM,EAASE,EAAI,CAAC,CAAC,EAAIR,EAAQiC,EACtC,CAAC,WAAW3B,EAASE,EAAI,CAAC,CAAC,EAAIR,EAC/B0C,EACAC,CACF,EACAnC,GAAK,CACP,CACA,MACF,IAAK,IAEG,OAAO2B,EAAU,WAAc,WACjCA,EAAU,UAAU,EAEpBA,EAAU,aACV,OAAOA,EAAU,YAAY,WAAc,YAE3CA,EAAU,YAAY,UAAU,EAElC3B,GAAK,EAEP,MACF,QACEA,IACA,KACJ,CAGF,IAAMoC,EAAWT,EAAU,SAC3B,GAAI,CAACS,GAAYA,EAAS,SAAW,EAAG,MAAO,CAAC,EAEhD,IAAMC,EAAQD,EAAS,IAAKE,GAAY,CACtC,IAAMvB,EAASuB,EAAG,UAAU,EACtBC,EAAO,KAAK,MAAM,WAAW,KAAKxB,CAAM,EACxCyB,EAAO,KAAK,eAAezB,EAAO,IAAKD,IAAY,CAAE,EAAGA,EAAE,EAAG,EAAGA,EAAE,CAAE,EAAE,CAAC,EAC7E,MAAO,CACL,KAAMwB,EACN,OAAAvB,EACA,KAAM,KAAK,IAAIwB,CAAI,EACnB,WAAYA,EACZ,KAAAC,CACF,CACF,CAAC,EAEDH,EAAM,KAAK,CAACjB,EAAQC,IAAWA,EAAE,KAAOD,EAAE,IAAI,EAE9C,IAAMqB,EAAqB,CAAC,EACtBC,EAAO,IAAI,IAEjB,QAAS1C,EAAI,EAAGA,EAAIqC,EAAM,OAAQrC,IAAK,CACrC,GAAI0C,EAAK,IAAI1C,CAAC,EAAG,SAEjB,IAAM2C,EAAYN,EAAMrC,CAAC,EACnB4C,EAAQ,IAAI,KAAK,MAAM,MAAMD,EAAU,MAAM,EACnDD,EAAK,IAAI1C,CAAC,EAEV,QAASO,EAAI,EAAGA,EAAI8B,EAAM,OAAQ9B,IAAK,CACrC,GAAImC,EAAK,IAAInC,CAAC,GAAKP,IAAMO,EAAG,SAE5B,IAAMsC,EAAYR,EAAM9B,CAAC,EAEzB,GACEsC,EAAU,KAAK,KAAOF,EAAU,KAAK,MACrCE,EAAU,KAAK,KAAOF,EAAU,KAAK,MACrCE,EAAU,KAAK,KAAOF,EAAU,KAAK,MACrCE,EAAU,KAAK,KAAOF,EAAU,KAAK,KAErC,SAGF,IAAIG,EAAkB,GAChBC,EAAa,CACjBF,EAAU,OAAO,CAAC,EAClBA,EAAU,OAAO,KAAK,MAAMA,EAAU,OAAO,OAAS,CAAC,CAAC,CAC1D,EAEA,QAAWG,KAAaD,EACtB,GACE,CAACC,GACD,CAAC,KAAK,eACJA,EAAU,EACVA,EAAU,EACVL,EAAU,OAAO,IAAK7B,IAAY,CAAE,EAAGA,EAAE,EAAG,EAAGA,EAAE,CAAE,EAAE,CACvD,EACA,CACAgC,EAAkB,GAClB,KACF,CAGEA,IACFF,EAAM,MAAM,KAAK,IAAI,KAAK,MAAM,KAAKC,EAAU,MAAM,CAAC,EACtDH,EAAK,IAAInC,CAAC,EAEd,CAEAkC,EAAY,KAAKG,CAAK,CACxB,CAEA,OAAOH,EAAY,OAAS,EAAIA,EAAcd,EAAU,SAAS,EAAI,CACvE,CAEQ,YAAYf,EAAgB,CAClC,IAAMqC,EAAU,IAAI,KAAK,MAAM,KAC/B,GAAI,CAACrC,EAAK,QAAUA,EAAK,OAAO,SAAW,EAAG,OAAOqC,EAErD,IAAMC,EAAYtC,EAAK,OAAOA,EAAK,OAAO,OAAS,CAAC,EAC9CuC,EACJD,EAAU,IAAMA,EAAU,KAAOA,EAAU,SAAWA,EAAU,SAAS,CAAC,EAAI,MAC5EC,GACFF,EAAQ,OAAOE,EAAS,EAAGA,EAAS,CAAC,EAGvC,QAASnD,EAAIY,EAAK,OAAO,OAAS,EAAGZ,GAAK,EAAGA,IAAK,CAChD,IAAMoD,EAAQxC,EAAK,OAAOZ,CAAC,EACvBoD,EAAM,aAAeA,EAAM,OAAS,aAAeA,EAAM,OAAS,aACpEH,EAAQ,OAAOG,EAAM,GAAG,EAAGA,EAAM,GAAG,CAAC,EAErCA,EAAM,wBACNA,EAAM,OAAS,wBACfA,EAAM,OAAS,wBAEfH,EAAQ,iBAAiBG,EAAM,GAAG,EAAGA,EAAM,GAAG,EAAGA,EAAM,GAAG,EAAGA,EAAM,GAAG,CAAC,GAEvEA,EAAM,oBACNA,EAAM,OAAS,oBACfA,EAAM,OAAS,sBAEfH,EAAQ,cACNG,EAAM,GAAG,EACTA,EAAM,GAAG,EACTA,EAAM,GAAG,EACTA,EAAM,GAAG,EACTA,EAAM,GAAG,EACTA,EAAM,GAAG,CACX,CAEJ,CAEA,OAAOH,CACT,CAEA,mBAAmB7D,EAAcH,EAAWxC,EAAkC,CAC5E,GAAI,CAAC2C,GAAQ,CAACH,EAAM,OAAO,KAE3B,IAAMI,EAAO,KAAK,IAAI,KAAO5C,EAAQ,MAAQ,EAAE,EACzCa,EAAS,KAAK,IAAI,EAAGb,EAAQ,QAAU,CAAC,EACxC4G,EAAa,KAAK,IAAI,KAAO5G,EAAQ,YAAc4C,EAAO,GAAG,EAC7DiE,EAAgB,OAAO,SAAS7G,EAAQ,aAAa,EAAIA,EAAQ,cAAgB,EACjF8G,EAAQ9G,EAAQ,OAAS,OACzB+G,EAAe,CAAC,CAAC/G,EAAQ,aACzBgH,EAAiB,KAAK,IAAI,EAAGhH,EAAQ,gBAAkB,CAAC,EACxDiH,EAAY,KAAK,IAAI,EAAGjH,EAAQ,WAAa,CAAC,EAC9CkH,EAAclH,EAAQ,aAAe,EACrCmH,EAAgB,KAAK,IAAI,EAAGnH,EAAQ,eAAiB,CAAC,EACtDoH,EAAgB,KAAK,IAAI,EAAG,KAAK,MAAMpH,EAAQ,eAAiB,CAAC,CAAC,EAElEqH,EAAQ,OAAO1E,CAAI,EAAE,MAAM,OAAO,EAClCG,EAAgB,CAAC,EAEjBP,EAAWC,GAAM,KACjB8E,EAAa/E,GAAU,YAAc,IAC3C,GAAIvC,EAAQ,QAAUA,EAAQ,OAAO,OAAS,EAAG,CAC/C,IAAMuH,EAAehF,GAAU,UAAY+E,EAAa,GAClDE,EAAgBjF,GAAU,WAAa,CAAC+E,EAAa,GACrDG,EAAeF,EAAeC,EAC9BE,EAAgBH,EAAeE,EAE/BE,EAAe3H,EAAQ,cAAgB,EACvC4H,EAAgB5H,EAAQ,eAAiB,EACzC6H,EAAgB,EAChBC,EAAgB,EAEtB9H,EAAQ,OAAO,QAAS+H,GAAc,CACpC,IAAM5E,EAAaX,EAAK,eAAeuF,EAAK,KAAMnF,CAAI,EAEhDoC,EAAU+C,EAAK,EAAIF,EAGnBG,GADaD,EAAK,QAAUnF,GACG8E,EAC/BO,EAAU,EAAEF,EAAK,EAAID,GAAiBE,EAE5C7E,EAAW,QAASgD,GAAe,CACjC,IAAI+B,EAAa,KAAK,eAAe/B,EAAOnB,EAASiD,CAAO,EACxDF,EAAK,OAASA,EAAK,QAAU,IAC/BG,EAAa,KAAK,WAAWA,EAAYH,EAAK,KAAK,GAErDjF,EAAO,KAAKoF,CAAU,CACxB,CAAC,CACH,CAAC,CACH,MACEb,EAAM,QAAQ,CAACc,EAAMC,IAAU,CAC7B,GAAM,CAAE,OAAQC,EAAY,MAAAzH,CAAM,EAAI,KAAK,gBAAgBuH,EAAM3F,EAAMI,EAAMiE,CAAa,EACtF7B,EAAU,EACV8B,IAAU,SACZ9B,EAAU,CAACpE,EAAQ,GACVkG,IAAU,UACnB9B,EAAU,CAACpE,GAEb,IAAMqH,EAAU,CAACG,EAAQxB,EACzByB,EAAW,QAASlC,GAAU,CAC5BrD,EAAO,KAAK,KAAK,eAAeqD,EAAOnB,EAASiD,CAAO,CAAC,CAC1D,CAAC,CACH,CAAC,EAGH,GAAI,CAACnF,EAAO,OACV,OAAO,KAGT,IAAMpC,EAAW,IAAI,KAAK,MAAM,gBAAgBoC,EAAQ,CACtD,MAAOjC,EACP,cAAAuG,EACA,aAAAL,EACA,eAAAC,EACA,UAAAC,EACA,YAAAC,EACA,cAAAC,CACF,CAAC,EACD,OAAAzG,EAAS,mBAAmB,EACrBA,CACT,CAEQ,gBACNyH,EACA3F,EACAI,EACAiE,EACkC,CAClC,IAAM/D,EAAgB,CAAC,EACnBrD,EAAI,EACF6I,EAAQ,MAAM,KAAKH,CAAI,EAE7B,OAAAG,EAAM,QAAQ,CAACtF,EAAMoF,IAAU,CACV5F,EAAK,eAAeQ,EAAMJ,CAAI,EACtC,QAASuD,GAAe,CACjC,IAAMoC,EAAa,KAAK,eAAepC,EAAO1G,EAAG,CAAC,EAClDqD,EAAO,KAAKyF,CAAU,CACxB,CAAC,EACD,IAAMC,EAAU,KAAK,gBAAgBhG,EAAMQ,EAAMJ,CAAI,EAErDnD,GAAK+I,EACD3B,IAAkB,GAAKuB,EAAQE,EAAM,OAAS,IAChD7I,GAAKoH,EAET,CAAC,EAEM,CAAE,OAAA/D,EAAQ,MAAOrD,CAAE,CAC5B,CAEQ,gBAAgB+C,EAAWQ,EAAcJ,EAAsB,CACrE,IAAM6F,EAAOjG,GAAM,KACbkG,EAASD,GAAM,QAAU,CAAC,EAE1BE,GADQD,EAAO1F,CAAI,GAAK0F,EAAO1F,EAAK,WAAW,CAAC,CAAC,GAAK0F,EAAO,GAAG,IACpD,IAAMD,GAAM,GACxBnB,EAAamB,GAAM,YAAc,IACvC,OAAI,OAAOE,GAAO,SACRA,EAAKrB,EAAc1E,EAEtBA,EAAO,EAChB,CAEQ,eAAeuD,EAAY1G,EAAWC,EAAgB,CAC5D,GAAI,CAACyG,GAAU,CAAC1G,GAAK,CAACC,EAAI,OAAOyG,EACjC,GAAI,OAAOA,EAAM,WAAc,WAC7B,OAAAA,EAAM,UAAU1G,EAAGC,CAAC,EACbyG,EAET,GAAI,OAAOA,EAAM,cAAiB,WAAY,CAC5C,IAAMyC,EAAS,IAAI,KAAK,MAAM,QAAQ,EAAE,gBAAgBnJ,EAAGC,EAAG,CAAC,EAC/D,OAAAyG,EAAM,aAAayC,CAAM,EAClBzC,CACT,CACA,GAAI,OAAOA,EAAM,eAAkB,WAAY,CAC7C,GAAM,CAAE,MAAO7B,EAAQ,MAAAuE,CAAM,EAAI1C,EAAM,cAAc,EAAE,EACjD2C,EAAUC,GAAY,IAAI,KAAK,MAAM,SAASA,EAAG,GAAK,GAAKtJ,GAAIsJ,EAAG,GAAK,GAAKrJ,CAAC,EAC7EsJ,EAAW,IAAI,KAAK,MAAM,MAAM1E,EAAO,IAAIwE,CAAM,CAAC,EACxD,OAAI,MAAM,QAAQD,CAAK,GACrBA,EAAM,QAASI,GAAgB,CAC7B,IAAMC,EAAW,IAAI,KAAK,MAAM,KAChCA,EAAS,cAAcD,EAAK,IAAIH,CAAM,CAAC,EACvCE,EAAS,MAAM,KAAKE,CAAQ,CAC9B,CAAC,EAEIF,CACT,CACA,OAAO7C,CACT,CAEQ,WAAWA,EAAYgD,EAAgB,CAC7C,GAAIA,IAAM,EAAG,OAAOhD,EACpB,GAAI,OAAOA,EAAM,OAAU,WACzB,OAAAA,EAAM,MAAMgD,EAAGA,CAAC,EACThD,EAET,GAAI,OAAOA,EAAM,cAAiB,WAAY,CAC5C,IAAMyC,EAAS,IAAI,KAAK,MAAM,QAAQ,EAAE,UAAUO,EAAGA,EAAG,CAAC,EACzD,OAAAhD,EAAM,aAAayC,CAAM,EAClBzC,CACT,CAEA,GAAI,OAAOA,EAAM,eAAkB,WAAY,CAC7C,GAAM,CAAE,MAAO7B,EAAQ,MAAAuE,CAAM,EAAI1C,EAAM,cAAc,EAAE,EACjD2C,EAAUC,GAAY,IAAI,KAAK,MAAM,SAASA,EAAG,GAAK,GAAKI,GAAIJ,EAAG,GAAK,GAAKI,CAAC,EAC7EH,EAAW,IAAI,KAAK,MAAM,MAAM1E,EAAO,IAAIwE,CAAM,CAAC,EACxD,OAAI,MAAM,QAAQD,CAAK,GACrBA,EAAM,QAASI,GAAgB,CAC7B,IAAMC,EAAW,IAAI,KAAK,MAAM,KAChCA,EAAS,cAAcD,EAAK,IAAIH,CAAM,CAAC,EACvCE,EAAS,MAAM,KAAKE,CAAQ,CAC9B,CAAC,EAEIF,CACT,CACA,OAAO7C,CACT,CAEQ,6BACNiD,EACAC,EACAC,EACqB,CACrB,IAAMrH,EAAMmH,EAAS,KAAK,EAC1B,GAAI,CAACnH,GAAOA,IAAQ,OAClB,OAAO,QAAQ,QAAQ,IAAI,EAG7B,IAAMsH,EACJF,GAAcA,IAAe,OACzBA,EACA,KAAK,QAAQ,KACb,OACA,OAAO,KAAK,KAAK,OAAO,EAAE,CAAC,EACjC,GAAI,CAACE,EACH,OAAO,QAAQ,QAAQ,IAAI,EAG7B,IAAMC,GAAWF,GAAY,IAAI,KAAK,EAChCG,EAAW,GAAGF,CAAgB,IAAItH,CAAG,IAAIuH,CAAO,GACtD,GAAI,KAAK,mBAAmB,IAAIC,CAAQ,EACtC,OAAO,QAAQ,QAAQ,KAAK,mBAAmB,IAAIA,CAAQ,CAAC,EAE9D,IAAMtH,EAAgB,KAAK,0BAA0B,IAAIsH,CAAQ,EACjE,GAAItH,EACF,OAAOA,EAGT,IAAMG,EAAU,IAAI,QAAqBI,GAAY,CACnD,IAAID,EAAgC,KACpC,GAAI,CACFA,EAAS,KAAK,kBAAkB8G,CAAgB,CAClD,MAAgB,CACd7G,EAAQ,IAAI,EACZ,MACF,CAEAD,EAAO,KACLR,EACCyH,GAAc,CACb,IAAMC,EAAOD,GAAM,OAASA,GAAM,QAAUA,EAC5C,GAAI,CAACC,EAAM,CACTjH,EAAQ,IAAI,EACZ,MACF,CACA,IAAIkH,EAAY,KAChB,GAAIJ,EAAS,CACX,GAAIG,EAAK,gBAAiB,CACxB,IAAME,EAAQF,EAAK,gBAAgBH,CAAO,EACtCK,GAAO,SAAQD,EAAOC,EAC5B,CACI,CAACD,GAAQD,EAAK,UAChBA,EAAK,SAAUG,GAAe,CACxBF,GACAE,GAAO,QAAUA,GAAO,OAASN,IACnCI,EAAOE,EAEX,CAAC,CAEL,CACKF,IACCD,EAAK,OACPC,EAAOD,EACEA,EAAK,UACdA,EAAK,SAAUG,GAAe,CACxB,CAACF,GAAQE,GAAO,SAClBF,EAAOE,EAEX,CAAC,GAIL,IAAMpJ,EAAWkJ,GAAM,UAAY,KACnC,GAAI,CAAClJ,EAAU,CACbgC,EAAQ,IAAI,EACZ,MACF,CACA,KAAK,mBAAmB,IAAI+G,EAAU/I,CAAQ,EAC9CgC,EAAQhC,CAAQ,CAClB,EACA,OACA,IAAM,CACJgC,EAAQ,IAAI,CACd,CACF,CACF,CAAC,EAED,YAAK,0BAA0B,IAAI+G,EAAUnH,CAAO,EAC7CA,CACT,CAEA,qBAAqByH,EAAiD,CACpE,IAAMzK,EAAQ,KAAK,MACb0K,EAAS,KAETC,EAAWC,GAAiB,CAChC,IAAIf,EAAI,KAAK,IAAI,EAAGe,EAAO,CAAC,EAC5B,MAAO,KACLf,GAAKA,GAAK,GACVA,GAAKA,GAAK,GACVA,GAAKA,GAAK,GACDA,IAAM,GAAK,IAAU,IAElC,EAEA,MAAMgB,UAAuB7K,EAAM,QAAS,CAoC1C,YAAY8K,EAA2B,CACrC,MAAM,EAnCR,KAAQ,IAAMH,EAAQF,EAAO,IAAI,EACjC,KAAQ,OAAc,KACtB,KAAQ,UAAiB,KACzB,KAAQ,UAA0B,IAAI,aAAa,CAAC,EACpD,KAAQ,WAA2B,IAAI,aAAa,CAAC,EACrD,KAAQ,KAAqB,IAAI,aAAa,CAAC,EAC/C,KAAQ,OAAuB,IAAI,aAAa,CAAC,EACjD,KAAQ,YAA4B,IAAI,aAAa,CAAC,EACtD,KAAQ,MAAQ,EAChB,KAAQ,cAAgB,EACxB,KAAQ,aAAe,EACvB,KAAQ,cAA8B,IAAI,aAAa,CAAC,EACxD,KAAQ,WAA2B,IAAI,aAAa,CAAC,EACrD,KAAQ,WAA2B,IAAI,aAAa,CAAC,EACrD,KAAQ,UAA0B,IAAI,aAAa,CAAC,EACpD,KAAQ,QAAU,EAClB,KAAQ,cAAqB,KAC7B,KAAQ,SAAW,GACnB,KAAQ,4BAA8B,GACtC,KAAQ,qBAA4B,KACpC,KAAQ,gBAAkB,GAC1B,KAAQ,iBAAwB,KAChC,KAAQ,0BAAiC,KACzC,KAAQ,uBAA8B,KACtC,KAAQ,yBAAgC,KACxC,KAAQ,oBAAsB,EAC9B,KAAQ,mBAAqB,EAC7B,KAAQ,gBAAkB,GAC1B,KAAQ,wBAAwC,IAAI,aAAa,CAAC,EAClE,KAAQ,sBAAsC,IAAI,aAAa,CAAC,EAChE,KAAQ,kBAAoB,GAC5B,KAAQ,qBAAuB,GAC/B,KAAQ,wBAA0B,GAIhC,KAAK,IAAM,CAAE,GAAGK,CAAI,EACpB,KAAK,qBAAqB,EAC1B,KAAK,QAAQ,CACf,CAEA,UAAUL,EAAoC,CAC5C,IAAMM,EAAO,KAAK,IAClB,KAAK,IAAM,CAAE,GAAGN,CAAO,EACvB,IAAMO,EACJ,KAAK,IAAI,OAAS,YACjBD,EAAK,WAAa,KAAK,IAAI,UAC1BA,EAAK,YAAc,KAAK,IAAI,WAC5BA,EAAK,eAAiB,KAAK,IAAI,cAC/BA,EAAK,gBAAkB,KAAK,IAAI,eAChC,CAAC,KAAK,YAAYA,EAAK,kBAAmB,KAAK,IAAI,iBAAiB,GACpE,CAAC,KAAK,YAAYA,EAAK,gBAAiB,KAAK,IAAI,eAAe,GAChEA,EAAK,eAAiB,KAAK,IAAI,cAC/BA,EAAK,wBAA0B,KAAK,IAAI,uBACxCA,EAAK,yBAA2B,KAAK,IAAI,wBACzCA,EAAK,QAAU,KAAK,IAAI,OAgB5B,GAdEA,EAAK,OAAS,KAAK,IAAI,MACvBA,EAAK,QAAU,KAAK,IAAI,OACxBA,EAAK,OAAS,KAAK,IAAI,MACvBA,EAAK,SAAW,KAAK,IAAI,QACzBA,EAAK,gBAAkB,KAAK,IAAI,eAChCA,EAAK,mBAAqB,KAAK,IAAI,kBACnCA,EAAK,sBAAwB,KAAK,IAAI,qBACtCA,EAAK,oBAAsB,KAAK,IAAI,mBACpCA,EAAK,gBAAkB,KAAK,IAAI,eAChCA,EAAK,mBAAqB,KAAK,IAAI,kBACnCA,EAAK,sBAAwB,KAAK,IAAI,qBACtCA,EAAK,oBAAsB,KAAK,IAAI,mBACpCA,EAAK,gBAAkB,KAAK,IAAI,eAChCA,EAAK,yBAA2B,KAAK,IAAI,uBACzB,CAChB,IAAME,EACJ,KAAK,IAAI,OAAS,aAClB,KAAK,WACL,KAAK,IAAI,wBAA0B,IAClCF,EAAK,mBAAqB,KAAK,IAAI,kBAClCA,EAAK,sBAAwB,KAAK,IAAI,qBACtCA,EAAK,oBAAsB,KAAK,IAAI,mBACpCA,EAAK,gBAAkB,KAAK,IAAI,eAE9BG,EACJ,KAAK,IAAI,OAAS,aAClB,KAAK,WACL,KAAK,IAAI,wBAA0B,IAClCH,EAAK,mBAAqB,KAAK,IAAI,kBAClCA,EAAK,sBAAwB,KAAK,IAAI,qBACtCA,EAAK,oBAAsB,KAAK,IAAI,mBACpCA,EAAK,gBAAkB,KAAK,IAAI,eAEhCE,GAAyBC,EAC3B,KAAK,qBAAqB,GAE1B,KAAK,qBAAqB,EAC1B,KAAK,4BAA4B,EACjC,KAAK,QAAQ,GAEf,MACF,CAIA,GAHIF,GACF,KAAK,aAAa,EAEhB,KAAK,OAAQ,CACf,IAAMG,EAAW,KAAK,OAAO,SAAS,SAClCA,IACEA,EAAS,WACXA,EAAS,SAAS,MAAQ,KAAK,IAAI,SAEjCA,EAAS,QACXA,EAAS,MAAM,MAAQ,KAAK,IAAI,MAE9BA,EAAS,WACXA,EAAS,SAAS,MAAQ,KAAK,IAAI,uBAEjCA,EAAS,aACXA,EAAS,WAAW,MAAQ,KAAK,IAAI,MAG3C,CACI,KAAK,YACP,KAAK,UAAU,SAAS,QAAU,KAAK,IAAI,QAC3C,KAAK,UAAU,SAAS,MAAQ,IAAInL,EAAM,MAAM,KAAK,IAAI,KAAK,GAEhE,KAAK,aAAe,KAAK,IAAI,SAC/B,CAEQ,sBAA6B,CACnC,KAAK,wBAA0B,IAAI,aAAa,KAAK,aAAa,EAClE,KAAK,mBAAqB,KAAK,IAAI,wBAEnC,IAAM2C,EAAM,KAAK,IAAI,kBAAkB,KAAK,EACtCyI,EAAM,GAAG,KAAK,IAAI,mBAAmB,IAAIzI,CAAG,IAAI,KAAK,IAAI,iBAAiB,GAChF,KAAK,kBAAoB,GACzB,KAAK,qBAAuByI,EAE5B,KAAK,qBAAqB,EAC1B,KAAK,yCAAyC,CAChD,CAEQ,0CAAiD,CACvD,GAAI,KAAK,IAAI,gBAAkB,QAAS,CACtC,KAAK,qBAAqB,EAC1B,MACF,CACA,IAAMzI,EAAM,KAAK,IAAI,kBAAkB,KAAK,EAC5C,GAAI,CAACA,GAAOA,IAAQ,OAAQ,CAC1B,KAAK,qBAAqB,EAC1B,MACF,CACA,IAAMyI,EAAM,GAAG,KAAK,IAAI,mBAAmB,IAAIzI,CAAG,IAAI,KAAK,IAAI,iBAAiB,GAEhF,GAAI,KAAK,kBAAoByI,GAAO,KAAK,qBAAsB,CAC7D,KAAK,qBAAqB,EAC1B,MACF,CAEA,KAAK,gBAAkBA,EACvBV,EACG,6BACC/H,EACA,KAAK,IAAI,oBACT,KAAK,IAAI,iBACX,EACC,KAAMvB,GAAa,CACbA,GACD,KAAK,kBAAoBgK,IACzB,CAAC,KAAK,mBAAqB,KAAK,uBAAyBA,IAE7D,KAAK,qBAAuBhK,EAC5B,KAAK,qBAAqB,GAC5B,CAAC,CACL,CAEQ,sBAA6B,CACnC,KAAK,kBAAoB,GACzB,KAAK,qBAAuB,GAE5B,IAAMiK,EAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,KAAK,EAIxC,GAHA,KAAK,sBAAwB,IAAI,aAAaA,EAAQ,CAAC,EAEtC,KAAK,IAAI,gBAAkB,SAAW,KAAK,qBAE1D,KAAK,qBAAqBA,EAAO,KAAK,qBAAsB,KAAK,qBAAqB,MAEtF,SAASpH,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EACJ,KAAK,IAAI,gBAAkB,MACvB,KAAK,YAAY,KAAK,IAAI,MAAM,EAChC,KAAK,eAAe,KAAK,IAAI,MAAM,EACzC,KAAK,sBAAsB,IAAIA,EAAKrH,EAAI,CAAC,CAC3C,CAGF,KAAK,oBAAsB,KAAK,QAChC,KAAK,gBAAkB,EACzB,CAEQ,iBAAwB,CAC9B,KAAK,gBAAkB,GACvB,KAAK,kBAAoB,GACzB,KAAK,qBAAuB,GAC5B,KAAK,wBAA0B,IAAI,aAAa,CAAC,EACjD,KAAK,sBAAwB,IAAI,aAAa,CAAC,CACjD,CAEQ,kBAAyB,CAC/B,GAAI,CAAC,KAAK,gBAAiB,OAE3B,IAAMsH,EAAU,KAAK,QAAU,KAAK,oBAC9BC,EAAW,KAAK,IAAI,EAAGD,EAAU,KAAK,kBAAkB,EAExDE,EACJD,EAAW,GAAM,EAAIA,EAAWA,EAAW,EAAI,KAAK,IAAI,GAAKA,EAAW,EAAG,CAAC,EAAI,EAE5EH,EAAQ,KAAK,IACjB,KAAK,wBAAwB,OAAS,EACtC,KAAK,sBAAsB,OAAS,EACpC,KAAK,cAAc,OAAS,CAC9B,EAEA,QAASpH,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMyH,EAAKzH,EAAI,EACf,KAAK,cAAcyH,CAAE,EACnB,KAAK,wBAAwBA,CAAE,GAC9B,KAAK,sBAAsBA,CAAE,EAAI,KAAK,wBAAwBA,CAAE,GAAKD,EACxE,KAAK,cAAcC,EAAK,CAAC,EACvB,KAAK,wBAAwBA,EAAK,CAAC,GAClC,KAAK,sBAAsBA,EAAK,CAAC,EAAI,KAAK,wBAAwBA,EAAK,CAAC,GAAKD,EAChF,KAAK,cAAcC,EAAK,CAAC,EACvB,KAAK,wBAAwBA,EAAK,CAAC,GAClC,KAAK,sBAAsBA,EAAK,CAAC,EAAI,KAAK,wBAAwBA,EAAK,CAAC,GAAKD,CAClF,CAEA,GAAID,GAAY,EAAG,CACjB,QAASvH,EAAI,EAAGA,EAAIoH,EAAQ,EAAGpH,GAAK,EAClC,KAAK,cAAcA,CAAC,EAAI,KAAK,sBAAsBA,CAAC,EAEtD,KAAK,gBAAgB,CACvB,CACF,CAEQ,qBAAqBoH,EAAejK,EAAeuK,EAAiC,CAC1F,IAAMC,EAAOxK,GAAU,YAAY,SACnC,GAAI,CAACwK,GAAM,OAASA,EAAK,SAAW,EAAG,CACrC,QAAS3H,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EAAM,KAAK,eAAe,KAAK,IAAI,MAAM,EAC/CK,EAAY,IAAIL,EAAKrH,EAAI,CAAC,CAC5B,CACA,MACF,CAEA,IAAM4H,EAAQD,EAAK,MACbE,EAAWF,EAAK,SAChBG,EAAc,KAAK,MAAMF,EAAM,OAASC,CAAQ,EACtD,GAAIC,GAAe,EACjB,OAGF,IAAMC,EAAa5K,GAAU,OAAO,MAC9B6K,EACF,KAAK,MADaD,EACPA,EAAW,OAAS,EACpBD,EAAc,CADO,EAEpC,GAAIE,GAAiB,EACnB,OAGF,IAAIjI,EAAO,IACPG,EAAO,IACP+H,EAAO,IACPhI,EAAO,KACPe,EAAO,KACPkH,EAAO,KACX,QAASlI,EAAI,EAAGA,EAAI8H,EAAa9H,GAAK,EAAG,CACvC,IAAMmI,EAAMnI,EAAI6H,EACV3L,EAAI0L,EAAMO,CAAG,EACbhM,EAAIyL,EAAMO,EAAM,CAAC,EACjB/L,EAAIwL,EAAMO,EAAM,CAAC,EACvBpI,EAAO,KAAK,IAAIA,EAAM7D,CAAC,EACvBgE,EAAO,KAAK,IAAIA,EAAM/D,CAAC,EACvB8L,EAAO,KAAK,IAAIA,EAAM7L,CAAC,EACvB6D,EAAO,KAAK,IAAIA,EAAM/D,CAAC,EACvB8E,EAAO,KAAK,IAAIA,EAAM7E,CAAC,EACvB+L,EAAO,KAAK,IAAIA,EAAM9L,CAAC,CACzB,CACA,IAAMgM,EAAQ,KAAK,IAAI,KAAMnI,EAAOF,CAAI,EAClCsI,EAAQ,KAAK,IAAI,KAAMrH,EAAOd,CAAI,EAClCoI,EAAQ,KAAK,IAAI,KAAMJ,EAAOD,CAAI,EAClCM,GAAW,KAAK,IAAI,QAAU,EAAI,KAAK,IAAI,QAAU,KAAK,IAAI,QAAU,EACxEC,GAAW,KAAK,IAAI,QAAU,EAAI,KAAK,IAAI,QAAU,KAAK,IAAI,QAAU,EACxEC,EAASF,EAAU,EAAIA,EAAUH,EAAQ,EACzCM,EAASF,EAAU,EAAIA,EAAUH,EAAQ,EACzC7I,EAAQ,KAAK,IAAIiJ,EAAQC,CAAM,EAC/BC,GAAW5I,EAAOE,GAAQ,GAC1B2I,GAAW1I,EAAOc,GAAQ,GAC1B6H,GAAWZ,EAAOC,GAAQ,GAE1BY,EAAkB,IAAI,aAAad,CAAa,EAClDe,EAAY,EAChB,QAAS/I,EAAI,EAAGA,EAAIgI,EAAehI,GAAK,EAAG,CACzC,IAAMgJ,EAAOhJ,EAAI,EACXiJ,EAAKlB,EAAaA,EAAWiB,CAAI,EAAIA,EACrCE,EAAKnB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChDG,EAAKpB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChD5H,EAAI6H,EAAKpB,EACTxG,EAAI6H,EAAKrB,EACTvG,EAAI6H,EAAKtB,EACTuB,EAAKxB,EAAMxG,CAAC,EACZiI,EAAKzB,EAAMxG,EAAI,CAAC,EAChBkI,GAAK1B,EAAMxG,EAAI,CAAC,EAChBc,GAAK0F,EAAMvG,CAAC,EACZc,GAAKyF,EAAMvG,EAAI,CAAC,EAChBkI,GAAK3B,EAAMvG,EAAI,CAAC,EAChBE,GAAKqG,EAAMtG,CAAC,EACZE,GAAKoG,EAAMtG,EAAI,CAAC,EAChBkI,GAAK5B,EAAMtG,EAAI,CAAC,EAChBmI,EAAMvH,GAAKkH,EACXM,EAAMvH,GAAKkH,EACXM,GAAMJ,GAAKD,GACXM,GAAMrI,GAAK6H,EACXS,GAAMrI,GAAK6H,EACXS,EAAMN,GAAKF,GACXS,GAASL,EAAMI,EAAMH,GAAME,GAC3BG,GAASL,GAAMC,GAAMH,EAAMK,EAC3BG,GAASR,EAAMI,GAAMH,EAAME,GAC3BrH,GAAO,KAAK,KAAKwH,GAASA,GAASC,GAASA,GAASC,GAASA,EAAM,EAAI,GAC9ElB,GAAaxG,GACbuG,EAAgB9I,CAAC,EAAI+I,CACvB,CACA,GAAIA,GAAa,EAAG,CAClB,QAAS/I,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EAAM,KAAK,eAAe,KAAK,IAAI,MAAM,EAC/CK,EAAY,IAAIL,EAAKrH,EAAI,CAAC,CAC5B,CACA,MACF,CAEA,QAASA,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMkK,EAAI,KAAK,IAAI,EAAInB,EACnBoB,EAAK,EACLC,EAAKpC,EAAgB,EACzB,KAAOmC,EAAKC,GAAI,CACd,IAAMC,GAAM,KAAK,OAAOF,EAAKC,GAAM,CAAC,EAChCF,GAAKpB,EAAgBuB,EAAG,EAC1BD,EAAKC,GAELF,EAAKE,GAAM,CAEf,CACA,IAAMrB,EAAOmB,EAAK,EACZlB,EAAKlB,EAAaA,EAAWiB,CAAI,EAAIA,EACrCE,EAAKnB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChDG,EAAKpB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChD5H,EAAI6H,EAAKpB,EACTxG,EAAI6H,EAAKrB,EACTvG,GAAI6H,EAAKtB,EACTuB,GAAKxB,EAAMxG,CAAC,EACZiI,GAAKzB,EAAMxG,EAAI,CAAC,EAChBkI,GAAK1B,EAAMxG,EAAI,CAAC,EAChBc,GAAK0F,EAAMvG,CAAC,EACZc,GAAKyF,EAAMvG,EAAI,CAAC,EAChBkI,GAAK3B,EAAMvG,EAAI,CAAC,EAChBE,EAAKqG,EAAMtG,EAAC,EACZE,EAAKoG,EAAMtG,GAAI,CAAC,EAChBkI,GAAK5B,EAAMtG,GAAI,CAAC,EAChBgJ,GAAI,KAAK,IAAI,EACbC,GAAI,KAAK,IAAI,EACbC,EAAK,KAAK,KAAKF,EAAC,EAChBG,GAAK,EAAID,EACTE,GAAKF,GAAM,EAAID,IACfI,GAAKH,EAAKD,GACVrO,IAAKkN,GAAKqB,GAAKvI,GAAKwI,GAAKnJ,EAAKoJ,GAAKhC,GAAWnJ,EAC9CrD,IAAKkN,GAAKoB,GAAKtI,GAAKuI,GAAKlJ,EAAKmJ,GAAK/B,GAAWpJ,EAC9CpD,IAAKkN,GAAKmB,GAAKlB,GAAKmB,GAAKlB,GAAKmB,GAAK9B,GAAWrJ,EACpDkI,EAAY1H,EAAI,CAAC,EAAI9D,GACrBwL,EAAY1H,EAAI,EAAI,CAAC,EAAI7D,GACzBuL,EAAY1H,EAAI,EAAI,CAAC,EAAI5D,EAC3B,CACF,CAEA,OAAOwO,EAAkB,CACnBA,GAAM,IACV,KAAK,SAAWA,EAEhB,KAAK,iBAAiB,EAElB,KAAK,IAAI,OAAS,UACpB,KAAK,cAAcA,CAAE,EAErB,KAAK,gBAAgB,KAAK,OAAO,EAErC,CAEA,SAAgB,CACd,KAAK,gBAAgB,EACjB,KAAK,SACP,KAAK,OAAO,SAAS,QAAQ,EAC7B,KAAK,OAAO,SAAS,QAAQ,GAE3B,KAAK,YACF,KAAK,6BACR,KAAK,UAAU,SAAS,QAAQ,EAElC,KAAK,UAAU,SAAS,QAAQ,EAEpC,CAEQ,SAAgB,CAiBtB,GAhBI,KAAK,SACP,KAAK,OAAO,KAAK,MAAM,EACvB,KAAK,OAAO,SAAS,QAAQ,EAC7B,KAAK,OAAO,SAAS,QAAQ,EAC7B,KAAK,OAAS,MAEZ,KAAK,YACP,KAAK,OAAO,KAAK,SAAS,EACrB,KAAK,6BACR,KAAK,UAAU,SAAS,QAAQ,EAElC,KAAK,UAAU,SAAS,QAAQ,EAChC,KAAK,UAAY,MAEnB,KAAK,QAAU,EAEX,KAAK,IAAI,OAAS,UACpB,KAAK,aAAa,MACb,CACL,IAAMC,EAAa,KAAK,IAAI,gBAAkB,QACxCC,EAAW,KAAK,uBAAyB,KAC/C,GAAID,GAAc,CAACC,EAAU,CAC3B,KAAK,wBAA0B,GAC/B,KAAK,4BAA4B,EACjC,MACF,CACA,KAAK,wBAA0B,GAC/B,KAAK,4BAA4B,EACjC,KAAK,eAAe,CACtB,CACA,KAAK,uBAAuB,CAC9B,CAEQ,cAAqB,CAC3B,IAAM1D,EAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,KAAK,EACxC,KAAK,UAAY,IAAI,aAAaA,EAAQ,CAAC,EAC3C,KAAK,WAAa,IAAI,aAAaA,EAAQ,CAAC,EAC5C,KAAK,KAAO,IAAI,aAAaA,CAAK,EAClC,KAAK,OAAS,IAAI,aAAaA,EAAQ,CAAC,EACxC,KAAK,YAAc,IAAI,aAAaA,CAAK,EACzC,IAAM2D,EAAO,IACb,QAAS/K,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMyH,EAAKzH,EAAI,EACf,KAAK,UAAUyH,CAAE,EAAIsD,EACrB,KAAK,UAAUtD,EAAK,CAAC,EAAIsD,EACzB,KAAK,UAAUtD,EAAK,CAAC,EAAIsD,CAC3B,CACA,KAAK,MAAQ,EACb,KAAK,cAAgB,EACrB,KAAK,aAAe,KAAK,IAAI,UAE7B,IAAM5N,EAAW,IAAIpB,EAAM,eAC3BoB,EAAS,aAAa,WAAY,IAAIpB,EAAM,gBAAgB,KAAK,UAAW,CAAC,CAAC,EAC9EoB,EAAS,aAAa,QAAS,IAAIpB,EAAM,gBAAgB,KAAK,OAAQ,CAAC,CAAC,EACxEoB,EAAS,aAAa,aAAc,IAAIpB,EAAM,gBAAgB,KAAK,YAAa,CAAC,CAAC,EAClF,IAAMqB,EAAW,IAAIrB,EAAM,eAAe,CACxC,YAAa,KAAK,IAAI,QAAU,EAChC,WAAY,GACZ,SAAU,CACR,SAAU,CAAE,MAAO,KAAK,IAAI,OAAQ,EACpC,MAAO,CAAE,MAAO,KAAK,IAAI,IAAK,EAC9B,SAAU,CAAE,MAAO,KAAK,IAAI,qBAAsB,CACpD,EACA,aAAc;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,YAad,eAAgB;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,WASlB,CAAC,EACD,KAAK,OAAS,IAAIA,EAAM,OAAOoB,EAAUC,CAAQ,EACjD,KAAK,uBAAyBA,EAC9B,KAAK,IAAI,KAAK,MAAM,CACtB,CAEQ,gBAAuB,CAC7B,IAAMgK,EAAQ,KAAK,IAAI,EAAG,KAAK,IAAI,KAAK,EAClC4D,EAAoB,KAAK,IAAI,gBAAkB,SAAW,KAAK,cAC/D7N,EACJ,KAAK,IAAI,gBAAkB,SAAW,KAAK,cACvC,KAAK,cACL,KAAK,IAAI,gBAAkB,MAC3B,IAAIpB,EAAM,YAAY,EAAG,EAAG,CAAC,EAC7B,IAAIA,EAAM,eAAe,GAAK,EAAG,CAAC,EACxC,KAAK,4BAA8BiP,EACnC,IAAM5N,EAAW,IAAIrB,EAAM,qBAAqB,CAC9C,MAAO,IAAIA,EAAM,MAAM,KAAK,IAAI,KAAK,EACrC,YAAa,KAAK,IAAI,QAAU,EAChC,QAAS,KAAK,IAAI,OACpB,CAAC,EACD,KAAK,yBAA2BqB,EAChC,KAAK,UAAY,IAAIrB,EAAM,cAAcoB,EAAUC,EAAUgK,CAAK,EAClE,KAAK,cAAgB,IAAI,aAAaA,EAAQ,CAAC,EAC/C,KAAK,WAAa,IAAI,aAAaA,CAAK,EACxC,KAAK,WAAa,IAAI,aAAaA,EAAQ,CAAC,EAC5C,KAAK,UAAY,IAAI,aAAaA,CAAK,EACvC,KAAK,kBAAkBA,CAAK,EAC5B,KAAK,yBAAyB,CAAC,EAC/B,KAAK,IAAI,KAAK,SAAS,CACzB,CAEA,YACEhK,EACAX,EAAkD,CAAC,EAC7C,CACN,IAAMwO,EAAYxO,EAAQ,QAAU,IAClBA,EAAQ,QAAU,MAElC,KAAK,iBAAmBW,GAEtB6N,IACF,KAAK,0BAA4B7N,GAEnC,KAAK,uBAAuB,CAC9B,CAEQ,cAAcwN,EAAkB,CACtC,IAAMxD,EAAQ,KAAK,IAAI,MACjB8D,EAAM,KAAK,UAAU,KAAK,IAAI,iBAAiB,EAC/CC,EAAU,KAAK,IAAI,gBACnBC,EAAO,KAAK,IAAI,EAAG,KAAK,IAAI,EAAG,KAAK,IAAI,YAAY,CAAC,EAErDC,EADW,KAAK,IAAI,SACKT,EAAK,KAAK,cACnCU,EAAY,KAAK,MAAMD,CAAW,EACxC,KAAK,cAAgBA,EAAcC,EACnC,IAAIC,EAAa,GACXR,EAAO,IAEb,QAAS/K,EAAI,EAAGA,EAAIsL,EAAWtL,GAAK,EAClC,KAAK,cAAckL,CAAG,EAExB,KAAO,KAAK,aAAe,GACzB,KAAK,cAAcA,CAAG,EACtB,KAAK,cAAgB,EAGvB,QAASlL,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,GAAI,KAAK,KAAKA,CAAC,GAAK,EAAG,SAEvB,GADA,KAAK,KAAKA,CAAC,GAAK4K,EACZ,KAAK,KAAK5K,CAAC,GAAK,EAAG,CACrB,KAAK,KAAKA,CAAC,EAAI,EACf,IAAMyH,EAAKzH,EAAI,EACf,KAAK,UAAUyH,CAAE,EAAIsD,EACrB,KAAK,UAAUtD,EAAK,CAAC,EAAIsD,EACzB,KAAK,UAAUtD,EAAK,CAAC,EAAIsD,EACzB,KAAK,OAAOtD,CAAE,EAAI,EAClB,KAAK,OAAOA,EAAK,CAAC,EAAI,EACtB,KAAK,OAAOA,EAAK,CAAC,EAAI,EACtB8D,EAAa,GACb,QACF,CACA,IAAMpD,EAAMnI,EAAI,EAChB,KAAK,WAAWmI,CAAG,GAAKgD,EAAQ,CAAC,EAAIP,EACrC,KAAK,WAAWzC,EAAM,CAAC,GAAKgD,EAAQ,CAAC,EAAIP,EACzC,KAAK,WAAWzC,EAAM,CAAC,GAAKgD,EAAQ,CAAC,EAAIP,EACzC,KAAK,WAAWzC,CAAG,GAAK,EAAIiD,EAAOR,EACnC,KAAK,WAAWzC,EAAM,CAAC,GAAK,EAAIiD,EAAOR,EACvC,KAAK,WAAWzC,EAAM,CAAC,GAAK,EAAIiD,EAAOR,EACvC,KAAK,UAAUzC,CAAG,GAAK,KAAK,WAAWA,CAAG,EAAIyC,EAC9C,KAAK,UAAUzC,EAAM,CAAC,GAAK,KAAK,WAAWA,EAAM,CAAC,EAAIyC,EACtD,KAAK,UAAUzC,EAAM,CAAC,GAAK,KAAK,WAAWA,EAAM,CAAC,EAAIyC,CACxD,CAEI,KAAK,SACP,KAAK,OAAO,SAAS,WAAW,SAAS,YAAc,GACnDW,IACF,KAAK,OAAO,SAAS,WAAW,MAAM,YAAc,IAG1D,CAEQ,cAAcL,EAAqC,CACzD,IAAM9D,EAAQ,KAAK,IAAI,MACnBe,EAAM,GACV,QAASnI,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAC9B,GAAI,KAAK,KAAKA,CAAC,GAAK,EAAG,CACrBmI,EAAMnI,EACN,KACF,CAEF,GAAImI,IAAQ,GAAI,OAEhB,IAAMd,EAAM,KAAK,eAAe,KAAK,IAAI,MAAM,EACzCmE,EACJ,KAAK,IAAI,eACR,EAAI,KAAK,IAAI,sBAAwB,KAAK,IAAI,EAAI,KAAK,IAAI,uBACxDC,EAAM,CACVP,EAAI,CAAC,EAAIM,GAAS,KAAK,IAAI,EAAI,IAAOA,EAAQ,GAC9CN,EAAI,CAAC,EAAIM,GAAS,KAAK,IAAI,EAAI,IAAOA,EAAQ,GAC9CN,EAAI,CAAC,EAAIM,GAAS,KAAK,IAAI,EAAI,IAAOA,EAAQ,EAChD,EAEM/D,EAAKU,EAAM,EACjB,KAAK,UAAU,IAAId,EAAKI,CAAE,EAC1B,KAAK,WAAW,IAAIgE,EAAKhE,CAAE,EAC3B,KAAK,KAAKU,CAAG,EAAI,KAAK,IAAI,aAC1B,KAAK,YAAYA,CAAG,EAAI,KAAK,IAAI,EAEjC,IAAMpK,EAAQ,IAAIhC,EAAM,MAAM,KAAK,IAAI,KAAK,EACxC,KAAK,IAAI,uBAAyB,GACpCgC,EAAM,WAAW,KAAK,IAAI,EAAI,IAAO,KAAK,IAAI,uBAAwB,EAAG,CAAC,EAE5E,KAAK,OAAO0J,CAAE,EAAI1J,EAAM,EACxB,KAAK,OAAO0J,EAAK,CAAC,EAAI1J,EAAM,EAC5B,KAAK,OAAO0J,EAAK,CAAC,EAAI1J,EAAM,EACxB,KAAK,SACP,KAAK,OAAO,SAAS,WAAW,MAAM,YAAc,GACpD,KAAK,OAAO,SAAS,WAAW,WAAW,YAAc,GAE7D,CAEQ,gBAAgB2N,EAAoB,CAC1C,KAAK,yBAAyBA,CAAI,EAC9B,KAAK,YACP,KAAK,UAAU,eAAe,YAAc,GAEhD,CAEQ,yBAAyBA,EAAoB,CACnD,GAAI,CAAC,KAAK,UAAW,OACrB,IAAMtE,EAAQ,KAAK,IAAI,MACjBuE,EAAS,KAAK,IAAI,eAClBC,EAAO,KAAK,IAAI,aAChBC,EAAW,KAAK,IAAI,EAAG,KAAK,IAAI,gBAAgB,EAChDC,EAAU,KAAK,IAAI,EAAG,KAAK,IAAI,uBAAuB,EACtDC,EACJ,KAAK,IAAI,yBAA2B,EAAI,KAAK,IAAI,yBAA2BD,EACxEE,EACJ,KAAK,IAAI,yBAA2B,EAAI,KAAK,IAAI,yBAA2BF,EACxEG,EACJ,KAAK,IAAI,yBAA2B,EAAI,KAAK,IAAI,yBAA2BH,EACxEI,EAAW,KAAK,IAAI,sBACpBC,EAAO,IAAIpQ,EAAM,SACvB,QAASiE,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMyH,EAAKzH,EAAI,EACToM,EAAQ,KAAK,cAAc3E,CAAE,EAC7B4E,EAAQ,KAAK,cAAc5E,EAAK,CAAC,EACjC6E,EAAQ,KAAK,cAAc7E,EAAK,CAAC,EACjC8E,EAAQ,KAAK,UAAUvM,CAAC,EACxBwM,EAAS,KAAK,KAAKH,EAAQX,EAAO,KAAO,GAAMa,CAAK,EAAIX,EAAO,KAAK,IAAI,OACxEa,EAAS,KAAK,KAAKL,EAAQV,EAAO,KAAO,GAAMa,CAAK,EAAIX,EAAO,KAAK,IAAI,OACxEc,EAAS,KAAK,KAAKJ,EAAQZ,EAAO,KAAO,GAAMa,CAAK,EAAIX,EAAO,KAAK,IAAI,OACxEe,EAAU,KAAK,IAAIjB,EAAO,IAAMa,EAAQ,KAAK,WAAW9E,CAAE,EAAI,GAAG,EAAIkE,EACrEiB,EAAU,KAAK,IAAIlB,EAAO,IAAMa,EAAQ,KAAK,WAAW9E,EAAK,CAAC,EAAI,GAAG,EAAIkE,EACzEkB,EAAU,KAAK,IAAInB,EAAO,IAAMa,EAAQ,KAAK,WAAW9E,EAAK,CAAC,EAAI,GAAG,EAAIkE,EACzEmB,EAAY,EAAIjB,EAChBkB,EAAO,KAAK,WAAWtF,CAAE,EACzBuF,EAAO,KAAK,WAAWvF,EAAK,CAAC,EAC7BwF,EAAO,KAAK,WAAWxF,EAAK,CAAC,EAC7ByF,EAAS,KAAK,KAAKH,EAAOA,EAAOC,EAAOA,EAAOC,EAAOA,CAAI,GAAK,EAC/DE,EAAetB,EAAW,KAAK,IAAI,OACnCuB,EAAkBL,EAAOG,EAAUnB,EAAWoB,EAC9CE,EAAkBL,EAAOE,EAAUlB,EAAWmB,EAC9CG,EAAkBL,EAAOC,EAAUjB,EAAWkB,EACpDhB,EAAK,SAAS,IACZC,EAAQU,EAAYM,EAAiBZ,EAASG,EAC9CN,EAAQS,EAAYO,EAAiBZ,EAASG,EAC9CN,EAAQQ,EAAYQ,EAAiBZ,EAASG,CAChD,EACAV,EAAK,SAAS,IACZ,KAAK,WAAW1E,CAAE,EAAI,GACtBiE,EAAOQ,EAAWlM,EAAI,GACtB,KAAK,WAAWyH,EAAK,CAAC,EAAI,EAC5B,EACA,IAAMjI,EAAQ,KAAK,WAAWQ,CAAC,EAAI,KAAK,IAAI,KAC5CmM,EAAK,MAAM,IAAI3M,EAAOA,EAAOA,CAAK,EAClC2M,EAAK,aAAa,EAClB,KAAK,UAAU,YAAYnM,EAAGmM,EAAK,MAAM,CAC3C,CACF,CAEQ,wBAA+B,CACrC,GAAI,KAAK,OAAQ,CACf,IAAMoB,EAAO,KAAK,2BAA6B,KAAK,uBAChDA,GAAQ,KAAK,OAAO,WAAaA,IACnC,KAAK,OAAO,SAAWA,EACvB,KAAK,oBAAoBA,CAAI,EAEjC,CACA,GAAI,KAAK,UAAW,CAClB,IAAMA,EAAO,KAAK,kBAAoB,KAAK,yBACvCA,GAAQ,KAAK,UAAU,WAAaA,IACtC,KAAK,UAAU,SAAWA,EAE9B,CACF,CAEQ,oBAAoBnQ,EAAqB,CAC1CA,GAAU,mBACVA,EAAS,WACZA,EAAS,SAAW,CAAC,GAElBA,EAAS,SAAS,aACrBA,EAAS,SAAS,WAAa,CAAE,MAAO,KAAK,IAAI,IAAK,GAEnDA,EAAS,SAAS,WACrBA,EAAS,SAAS,SAAW,CAAE,MAAO,KAAK,IAAI,OAAQ,GAEpDA,EAAS,aAAa,SAAS,cAAc,IAC3CA,EAAS,aAAa,SAAS,YAAY,IAC9CA,EAAS,aAAe;AAAA,EAA8BA,EAAS,YAAY,IAE7EA,EAAS,aAAeA,EAAS,aAAa,QAC5C,gCACA,8CACF,EACAA,EAAS,YAAc,IAE3B,CAEQ,sBAA6B,CACnC,GAAI,KAAK,IAAI,gBAAkB,QAAS,CACtC,KAAK,cAAgB,KACrB,KAAK,SAAW,GAChB,MACF,CACA,IAAMsB,EAAM,KAAK,IAAI,kBAAkB,KAAK,EAC5C,GAAI,CAACA,GAAOA,IAAQ,OAAQ,CAC1B,KAAK,cAAgB,KACrB,KAAK,SAAW,GAChB,MACF,CACA,IAAMyI,EAAM,GAAG,KAAK,IAAI,mBAAmB,IAAIzI,CAAG,IAAI,KAAK,IAAI,iBAAiB,GAC5E,KAAK,WAAayI,GAAO,KAAK,gBAGlC,KAAK,SAAWA,EAChBV,EACG,6BACC/H,EACA,KAAK,IAAI,oBACT,KAAK,IAAI,iBACX,EACC,KAAMvB,GAAa,CACbA,GACD,KAAK,WAAagK,IACtB,KAAK,cAAgBhK,EACjB,KAAK,IAAI,OAAS,aAAe,KAAK,IAAI,gBAAkB,SAC9D,KAAK,QAAQ,EAEjB,CAAC,EACL,CAEQ,6BAAoC,CAC1C,GAAI,KAAK,IAAI,gBAAkB,QAAS,CACtC,KAAK,qBAAuB,KAC5B,KAAK,gBAAkB,GACvB,MACF,CACA,IAAMuB,EAAM,KAAK,IAAI,kBAAkB,KAAK,EAC5C,GAAI,CAACA,GAAOA,IAAQ,OAAQ,CAC1B,KAAK,qBAAuB,KAC5B,KAAK,gBAAkB,GACvB,MACF,CACA,IAAMyI,EAAM,GAAG,KAAK,IAAI,mBAAmB,IAAIzI,CAAG,IAAI,KAAK,IAAI,iBAAiB,GAC5E,KAAK,kBAAoByI,GAAO,KAAK,uBAGzC,KAAK,gBAAkBA,EACvBV,EACG,6BACC/H,EACA,KAAK,IAAI,oBACT,KAAK,IAAI,iBACX,EACC,KAAMvB,GAAa,CACbA,GACD,KAAK,kBAAoBgK,IAC7B,KAAK,qBAAuBhK,EACxB,KAAK,IAAI,OAAS,aAAe,KAAK,IAAI,gBAAkB,UAC1D,KAAK,yBACP,KAAK,wBAA0B,GAC/B,KAAK,eAAe,EACpB,KAAK,uBAAuB,GAE5B,KAAK,QAAQ,GAGnB,CAAC,EACL,CAEQ,kBAAkBiK,EAAqB,CAE7C,GADiB,KAAK,IAAI,gBAAkB,SAAW,KAAK,qBAE1D,KAAK,cAAcA,EAAO,KAAK,oBAAoB,MAEnD,SAASpH,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EACJ,KAAK,IAAI,gBAAkB,MACvB,KAAK,YAAY,KAAK,IAAI,MAAM,EAChC,KAAK,eAAe,KAAK,IAAI,MAAM,EACzC,KAAK,cAAc,IAAIA,EAAKrH,EAAI,CAAC,CACnC,CAGF,QAASA,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMyH,EAAKzH,EAAI,EACf,KAAK,WAAWyH,CAAE,EAAI,KAAK,IAAI,EAAI,EAAI,EACvC,KAAK,WAAWA,EAAK,CAAC,EAAI,KAAK,IAAI,EAAI,EAAI,EAC3C,KAAK,WAAWA,EAAK,CAAC,EAAI,KAAK,IAAI,EAAI,EAAI,EAC3C,KAAK,UAAUzH,CAAC,EAAI,KAAK,IAAI,EAAI,KAAK,GAAK,EAC3C,IAAMR,EACJ,KAAK,IAAI,eACR,EAAI,KAAK,IAAI,uBAAyB,KAAK,IAAI,EAAI,KAAK,IAAI,wBAC/D,KAAK,WAAWQ,CAAC,EAAIR,CACvB,CACF,CAEQ,cAAc4H,EAAejK,EAAqB,CACxD,IAAMwK,EAAOxK,GAAU,YAAY,SACnC,GAAI,CAACwK,GAAM,OAASA,EAAK,SAAW,EAAG,CACrC,QAAS3H,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EAAM,KAAK,eAAe,KAAK,IAAI,MAAM,EAC/C,KAAK,cAAc,IAAIA,EAAKrH,EAAI,CAAC,CACnC,CACA,MACF,CAEA,IAAM4H,EAAQD,EAAK,MACbE,EAAWF,EAAK,SAChBG,EAAc,KAAK,MAAMF,EAAM,OAASC,CAAQ,EACtD,GAAIC,GAAe,EACjB,OAGF,IAAMC,EAAa5K,GAAU,OAAO,MAC9B6K,EACF,KAAK,MADaD,EACPA,EAAW,OAAS,EACpBD,EAAc,CADO,EAEpC,GAAIE,GAAiB,EACnB,OAGF,IAAIjI,EAAO,IACPG,EAAO,IACP+H,EAAO,IACPhI,EAAO,KACPe,EAAO,KACPkH,EAAO,KACX,QAASlI,EAAI,EAAGA,EAAI8H,EAAa9H,GAAK,EAAG,CACvC,IAAMmI,EAAMnI,EAAI6H,EACV3L,EAAI0L,EAAMO,CAAG,EACbhM,EAAIyL,EAAMO,EAAM,CAAC,EACjB/L,EAAIwL,EAAMO,EAAM,CAAC,EACvBpI,EAAO,KAAK,IAAIA,EAAM7D,CAAC,EACvBgE,EAAO,KAAK,IAAIA,EAAM/D,CAAC,EACvB8L,EAAO,KAAK,IAAIA,EAAM7L,CAAC,EACvB6D,EAAO,KAAK,IAAIA,EAAM/D,CAAC,EACvB8E,EAAO,KAAK,IAAIA,EAAM7E,CAAC,EACvB+L,EAAO,KAAK,IAAIA,EAAM9L,CAAC,CACzB,CACA,IAAMgM,EAAQ,KAAK,IAAI,KAAMnI,EAAOF,CAAI,EAClCsI,EAAQ,KAAK,IAAI,KAAMrH,EAAOd,CAAI,EAClCoI,EAAQ,KAAK,IAAI,KAAMJ,EAAOD,CAAI,EAClCM,GAAW,KAAK,IAAI,QAAU,EAAI,KAAK,IAAI,QAAU,KAAK,IAAI,QAAU,EACxEC,GAAW,KAAK,IAAI,QAAU,EAAI,KAAK,IAAI,QAAU,KAAK,IAAI,QAAU,EACxEC,EAASF,EAAU,EAAIA,EAAUH,EAAQ,EACzCM,EAASF,EAAU,EAAIA,EAAUH,EAAQ,EACzC7I,EAAQ,KAAK,IAAIiJ,EAAQC,CAAM,EAC/BC,GAAW5I,EAAOE,GAAQ,GAC1B2I,GAAW1I,EAAOc,GAAQ,GAC1B6H,GAAWZ,EAAOC,GAAQ,GAE1BY,EAAkB,IAAI,aAAad,CAAa,EAClDe,EAAY,EAChB,QAAS/I,EAAI,EAAGA,EAAIgI,EAAehI,GAAK,EAAG,CACzC,IAAMgJ,EAAOhJ,EAAI,EACXiJ,EAAKlB,EAAaA,EAAWiB,CAAI,EAAIA,EACrCE,EAAKnB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChDG,EAAKpB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChD5H,EAAI6H,EAAKpB,EACTxG,EAAI6H,EAAKrB,EACTvG,EAAI6H,EAAKtB,EACTuB,EAAKxB,EAAMxG,CAAC,EACZiI,EAAKzB,EAAMxG,EAAI,CAAC,EAChBkI,EAAK1B,EAAMxG,EAAI,CAAC,EAChBc,GAAK0F,EAAMvG,CAAC,EACZc,GAAKyF,EAAMvG,EAAI,CAAC,EAChBkI,GAAK3B,EAAMvG,EAAI,CAAC,EAChBE,GAAKqG,EAAMtG,CAAC,EACZE,GAAKoG,EAAMtG,EAAI,CAAC,EAChBkI,GAAK5B,EAAMtG,EAAI,CAAC,EAChBmI,GAAMvH,GAAKkH,EACXM,EAAMvH,GAAKkH,EACXM,EAAMJ,GAAKD,EACXM,GAAMrI,GAAK6H,EACXS,GAAMrI,GAAK6H,EACXS,GAAMN,GAAKF,EACXS,EAASL,EAAMI,GAAMH,EAAME,GAC3BG,GAASL,EAAMC,GAAMH,GAAMK,GAC3BG,GAASR,GAAMI,GAAMH,EAAME,GAC3BrH,GAAO,KAAK,KAAKwH,EAASA,EAASC,GAASA,GAASC,GAASA,EAAM,EAAI,GAC9ElB,GAAaxG,GACbuG,EAAgB9I,CAAC,EAAI+I,CACvB,CACA,GAAIA,GAAa,EAAG,CAClB,QAAS/I,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMqH,EAAM,KAAK,eAAe,KAAK,IAAI,MAAM,EAC/C,KAAK,cAAc,IAAIA,EAAKrH,EAAI,CAAC,CACnC,CACA,MACF,CAEA,QAASA,EAAI,EAAGA,EAAIoH,EAAOpH,GAAK,EAAG,CACjC,IAAMkK,EAAI,KAAK,IAAI,EAAInB,EACnBoB,EAAK,EACLC,EAAKpC,EAAgB,EACzB,KAAOmC,EAAKC,GAAI,CACd,IAAMC,GAAM,KAAK,OAAOF,EAAKC,GAAM,CAAC,EAChCF,GAAKpB,EAAgBuB,EAAG,EAC1BD,EAAKC,GAELF,EAAKE,GAAM,CAEf,CACA,IAAMrB,EAAOmB,EAAK,EACZlB,EAAKlB,EAAaA,EAAWiB,CAAI,EAAIA,EACrCE,EAAKnB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChDG,EAAKpB,EAAaA,EAAWiB,EAAO,CAAC,EAAIA,EAAO,EAChD5H,EAAI6H,EAAKpB,EACTxG,EAAI6H,EAAKrB,EACTvG,EAAI6H,EAAKtB,EACTuB,GAAKxB,EAAMxG,CAAC,EACZiI,GAAKzB,EAAMxG,EAAI,CAAC,EAChBkI,GAAK1B,EAAMxG,EAAI,CAAC,EAChBc,GAAK0F,EAAMvG,CAAC,EACZc,GAAKyF,EAAMvG,EAAI,CAAC,EAChBkI,GAAK3B,EAAMvG,EAAI,CAAC,EAChBE,GAAKqG,EAAMtG,CAAC,EACZE,EAAKoG,EAAMtG,EAAI,CAAC,EAChBkI,EAAK5B,EAAMtG,EAAI,CAAC,EAChBgJ,GAAI,KAAK,IAAI,EACbC,GAAI,KAAK,IAAI,EACbC,GAAK,KAAK,KAAKF,EAAC,EAChBG,EAAK,EAAID,GACTE,GAAKF,IAAM,EAAID,IACfI,GAAKH,GAAKD,GACVrO,IAAKkN,GAAKqB,EAAKvI,GAAKwI,GAAKnJ,GAAKoJ,GAAKhC,GAAWnJ,EAC9CrD,IAAKkN,GAAKoB,EAAKtI,GAAKuI,GAAKlJ,EAAKmJ,GAAK/B,GAAWpJ,EAC9CpD,IAAKkN,GAAKmB,EAAKlB,GAAKmB,GAAKlB,EAAKmB,GAAK9B,GAAWrJ,EACpD,KAAK,cAAcQ,EAAI,CAAC,EAAI9D,GAC5B,KAAK,cAAc8D,EAAI,EAAI,CAAC,EAAI7D,GAChC,KAAK,cAAc6D,EAAI,EAAI,CAAC,EAAI5D,EAClC,CACF,CAEQ,cAAqB,CAC3B,GAAI,CAAC,KAAK,OAAQ,OAClB,IAAM2O,EAAO,IACb,QAAS/K,EAAI,EAAGA,EAAI,KAAK,UAAU,OAAQA,GAAK,EAC9C,KAAK,UAAUA,CAAC,EAAI+K,EACpB,KAAK,UAAU/K,EAAI,CAAC,EAAI+K,EACxB,KAAK,UAAU/K,EAAI,CAAC,EAAI+K,EAE1B,KAAK,WAAW,KAAK,CAAC,EACtB,KAAK,KAAK,KAAK,CAAC,EAChB,KAAK,OAAO,KAAK,CAAC,EAClB,KAAK,YAAY,KAAK,CAAC,EACvB,KAAK,MAAQ,EACb,KAAK,cAAgB,EACrB,KAAK,aAAe,KAAK,IAAI,UAC7B,KAAK,OAAO,SAAS,WAAW,SAAS,YAAc,GACvD,KAAK,OAAO,SAAS,WAAW,MAAM,YAAc,GACpD,KAAK,OAAO,SAAS,WAAW,WAAW,YAAc,EAC3D,CAEQ,UAAUyC,EAAyD,CACzE,IAAMC,EAAM,KAAK,KAAKD,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAIA,EAAI,CAAC,EAAIA,EAAI,CAAC,CAAC,GAAK,EAC9E,MAAO,CAACA,EAAI,CAAC,EAAIC,EAAKD,EAAI,CAAC,EAAIC,EAAKD,EAAI,CAAC,EAAIC,CAAG,CAClD,CAEQ,YAAYrM,EAA6BC,EAAsC,CACrF,OAAOD,EAAE,CAAC,IAAMC,EAAE,CAAC,GAAKD,EAAE,CAAC,IAAMC,EAAE,CAAC,GAAKD,EAAE,CAAC,IAAMC,EAAE,CAAC,CACvD,CAEQ,eAAe7D,EAA0C,CAC/D,IAAM8M,EAAI,KAAK,IAAI,EACbC,EAAI,KAAK,IAAI,EACbmD,EAAQpD,EAAI,KAAK,GAAK,EACtBqD,EAAM,KAAK,KAAK,EAAIpD,EAAI,CAAC,EACzBL,EAAI,KAAK,KAAK,KAAK,IAAI,CAAC,EAAI1M,EAClC,MAAO,CACL0M,EAAI,KAAK,IAAIyD,CAAG,EAAI,KAAK,IAAID,CAAK,EAClCxD,EAAI,KAAK,IAAIyD,CAAG,EAAI,KAAK,IAAID,CAAK,EAClCxD,EAAI,KAAK,IAAIyD,CAAG,CAClB,CACF,CAEQ,YAAYtO,EAAwC,CAC1D,IAAMuO,EAAOvO,EAAO,GACpB,MAAO,EACJ,KAAK,IAAI,EAAI,EAAI,GAAKuO,GACtB,KAAK,IAAI,EAAI,EAAI,GAAKA,GACtB,KAAK,IAAI,EAAI,EAAI,GAAKA,CACzB,CACF,CACF,CAEA,OAAO,IAAIhH,EAAeJ,CAAM,CAClC,CAEA,iBAAiBrJ,EAAuB0Q,EAAqC,CAC3E,IAAMC,EAAY,KAAK,OAAe,iBACtC,GAAI,CAACA,EAAU,OAAO,KACtB,IAAMC,EAAe5Q,EACfiK,EAAQ2G,GAAS,YAAY,UAAU,MAC7C,GAAI,CAAC,OAAO,SAAS3G,CAAK,EAAG,OAAO,KACpC,IAAM4G,EAAU,KAAK,IAAI,IAAM,KAAK,IAAI,EAAGH,CAAO,CAAC,EAC7CI,EAAS,KAAK,IAAI,EAAG,KAAK,MAAM7G,EAAQ4G,CAAO,CAAC,EACtD,GAAIC,GAAU7G,EAAO,OAAOjK,EAC5B,GAAI,CAEF,OADiB,IAAI2Q,EAAS,EACd,OAAOC,EAASE,CAAM,CACxC,MAAQ,CACN,OAAO,IACT,CACF,CAEA,SAASC,EAAyB,CAChC,OAAO,KAAK,MAAM,UAAU,SAASA,CAAO,CAC9C,CAEA,SAASC,EAAyB,CAChC,OAAO,KAAK,MAAM,UAAU,SAASA,CAAO,CAC9C,CAEA,8BAA8BC,EAA4B,CACxD,IAAMC,EAAc,IAAI,KAAK,MAAM,KAC/BC,EAAS,GAEb,OAAIF,EAAO,UACTA,EAAO,SAAU7H,GAAe,CAC9B,GAAKA,EAAM,SACPA,EAAM,SAAU,CACd,OAAOA,EAAM,SAAS,oBAAuB,YAC/CA,EAAM,SAAS,mBAAmB,EAEpC,IAAMgI,EAAMhI,EAAM,SAAS,YAC3B,GAAIgI,EAAK,CACP,IAAMC,EAAWD,EAAI,MAAM,EAAE,aAAahI,EAAM,WAAW,EAC3D8H,EAAY,MAAMG,CAAQ,EAC1BF,EAAS,EACX,CACF,CACF,CAAC,EAGIA,EAASD,EAAc,IAAI,KAAK,MAAM,IAC/C,CACF,EAEaI,GAAN,KAAmD,CAGxD,YAAY1S,EAAYC,EAA+B,CAAC,EAAG,CACzD,KAAK,OAAS,IAAIF,GAAcC,EAAOC,CAAO,CAChD,CAEA,WAAuB,CACrB,OAAO,KAAK,MACd,CAEA,SAAkB,CAChB,MAAO,UACT,CACF","names":["StringModule","String3DCamera","engine","mode","fov","near","far","width","height","ortho","x","y","z","screenX","screenY","normalizedX","normalizedY","distance","viewportHeight","roundedZ","scale","String3DCustomFilterRegistry","definition","name","RenderTargetPool","create","width","height","target","String3DFilterPipeline","engine","renderer","geometry","w","h","scale","next","input","effects","quality","current","locals","releaseLocal","idx","acquire","effect","radius","first","second","output","intensity","blurRadius","extracted","blur1","blur2","combined","mode","amount","material","uniforms","clear","key","value","base","bloom","object","anyObj","name","type","params","normalized","def","String3DCustomFilterRegistry","String3DRenderer","container","engine","width","height","rendererAny","scene","camera","filterTargets","pipeline","allObjects","visibility","obj","anyObj","filteredSet","target","prevAutoClear","originalVisible","lights","supportsLayers","cache","effects","allowed","restoreLayers","restoreCameraMask","subtree","input","output","entry","existing","String3DFilterPipeline","object","set","child","visible","el","cached","rect","cx","cy","clamp","value","effect","center","changed","next","uniforms","filterCount","now","dt","fps","countScale","targetScale","maxAge","key","objects","layer","restoredMap","apply","setMode","light","mask","entries","prev","String3DObject","id","type","object","engine","options","child","originalScale","matrix","pos","quat","scale","position","quaternion","euler","value","mat","texture","material","geometry","result","walk","obj","anyObj","childMat","StyleReader","el","prop","fallback","mapValue","val","num","raw","value","norm","readNumberStyle","parsed","stripQuotes","readStringStyle","style","readBooleanStyle","normalized","readFilterRaw","styleMap","String3DCustomMaterialRegistry","definition","name","css","uniforms","def","cssVar","syntax","type","parseUniformValue","def","cssValue","trimmed","num","parts","s","n","parseColorValue","match","value","hex","r","g","b","rgbMatch","collectUniformsFromCSS","definition","element","style","result","parsed","key","mergeInjections","injections","grouped","injection","list","point","sorted","i","String3DScene","engine","options","synchronizer","id","element","el","result","walk","obj","child","root","object","type","onAdd","added3DObject","parentId","group","String3DObject","kind","colorRaw","readStringStyle","color","intensity","readNumberStyle","light","distance","decay","angle","penumbra","groundRaw","groundColor","readBooleanStyle","bias","mapSize","mesh","castShadow","receiveShadow","geometry","material","quality","widthSegments","heightSegments","segments","modelPath","loaderType","loader","shouldCenter","gltf","overrideMaterial","config","system","bbox","center","box","style","getCSS","prop","resolve","cssProp","parser","defaultValue","cssVal","parseNumber","v","parseColor","parseUrl","match","customMaterial","opacity","metalness","roughness","emissive","params","mapSrc","normalMapSrc","roughnessMapSrc","metalnessMapSrc","aoMapSrc","flipY","colorSpace","hasMaps","finalType","definition","String3DCustomMaterialRegistry","factory","initialUniforms","instance","objectId","uniforms","oldInstance","stringObject","newMaterial","src","texture","value","normalized","hasStyle","val","baseRaw","base","mappingRaw","mapping","manager","url","mapped","StyleBundleCache","el","ctx","reader","cached","now","interval","metaData","bundle","DEG_TO_RAD","_GroupSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","styles","StyleReader","StyleBundleCache","GroupSynchronizer","_LightSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","light","targetEl","tCached","tRect","tTranslateZ","StyleReader","tScreenCenterX","tScreenCenterY","x","z","styles","groundColor","targetId","offsetRaw","offset","value","parts","part","num","StyleBundleCache","LightSynchronizer","DEG_TO_RAD","_MeshSynchronizer","el","object","props","prev","castShadow","receiveShadow","opacity","applyMaterialProps","mat","child","mesh","ctx","parentData","rect","originalWidth","originalHeight","bundle","translateZ","cssScale","rotateX","rotateY","rotateZ","cssScaleZ","color","metalness","roughness","emissive","geometryQuality","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","targetWidth","targetHeight","parentScale","baseScaleZ","minTargetSize","scaleX","scaleY","scaleZ","uniformSize","bbox","size","fitMode","modelScale","finalModelScale","scaleW","scaleH","uniformScale","fallbackSize","quality","engine","simplify","normalized","applyToMesh","userData","original","key","simplified","factory","style","apply","definition","values","value","def","converter","converted","styleMap","readNumber","prop","fallback","mapValue","val","num","readString","readBool","raw","norm","cached","width","height","StyleBundleCache","MeshSynchronizer","DEG_TO_RAD","DEFAULT_CONFIG","_ParticlesSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","parentScale","scale","config","prev","now","last","dt","styles","StyleReader","mode","property","style","properties","durations","index","shorthand","match","value","result","current","depth","i","ch","name","normalized","prop","raw","num","map","part","tokens","duration","token","lower","fallback","parts","fitMultiplier","spread","spreadX","spreadY","z","perPixel","a","b","type","definition","String3DCustomMaterialRegistry","factory","existing","initialUniforms","instance","material","isShader","system","apply","mat","values","key","def","converter","converted","child","StyleBundleCache","ParticlesSynchronizer","String3DFontRegistry","name","url","normalized","fontFamily","families","value","family","entry","opentypePromise","opentypeModule","woff2Promise","woff2Module","loadOpentype","resolve","reject","script","loadWoff2Decoder","attempts","maxAttempts","checkReady","win","decompressWoff2","buffer","woff2","inputArray","outputArray","newBuffer","isWoff2","FontConverter","source","cacheKey","cached","loading","promise","result","opentype","loadOpentype","buffer","isWoff2","decompressWoff2","font","scale","glyphs","cmap","codeStr","glyphIndex","code","glyph","path","outline","advanceWidth","char","i","unicodeValues","spaceGlyph","commands","cmd","value","url","lower","DEG_TO_RAD","PSEUDO_ELEMENT_CSS","_TextSynchronizer","fontUrl","object","set","obj","style","el","textContent","computed","rx","ry","rz","tx","ty","tz","s","transform","lastContent","observer","mutations","currentContent","currentObject","ctx","parentData","rect","originalWidth","originalHeight","bundle","translateZ","cssScale","rotateX","rotateY","rotateZ","cssScaleZ","opacity","color","metalness","roughness","emissive","castShadow","receiveShadow","materialType","fontFamily","fontSize","textTransform","textDepth","textCurveSegments","bevelEnabled","bevelSize","bevelThickness","bevelOffset","bevelSegments","fontCss","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","DEG_TO_RAD","layout","l","useCanvasText","mesh","fontEntry","String3DFontRegistry","font","promise","loaded","layoutSig","key","geometry","parentScale","perPixel","scaleFactor","scaleZ","localOffsetX","localOffsetY","prevMaterialType","MeshSynchronizer","range","elRect","walker","node","text","i","char","rects","r","x","y","visibleChar","anyObj","found","child","factory","apply","mat","definition","values","value","def","converter","converted","styleMap","readNumber","prop","fallback","mapValue","val","num","raw","readString","readBool","norm","colorVar","parsed","lineHeight","letterSpacing","fit","depthRaw","depth","alignRaw","align","computedFont","match","cached","StyleBundleCache","TextSynchronizer","String3DSynchronizer","camera","viewportWidth","viewportHeight","engine","MeshSynchronizer","GroupSynchronizer","LightSynchronizer","ParticlesSynchronizer","TextSynchronizer","el","object","parentData","hints","strategy","options","width","height","DirtySyncManager","attributeFilter","el","rootObjects","obj","object","child","entries","entry","mutations","mutation","FilterController","easingParser","rootObjects","now","useDirtySync","dirtySet","targets","walk","obj","el","animating","shouldReadStyle","chain","dirty","effectsKey","child","existing","raw","readFilterRaw","current","duration","delay","easing","zero","effects","warnings","state","newState","t","canTween","fromChain","parseNumber","value","match","num","parseRatio","cleaned","parseAngle","stripped","parseBloom","parts","part","intensity","threshold","parseAmount","name","allowZero","amount","parseRatioAmount","re","args","size","bloom","angle","custom","String3DCustomFilterRegistry","parsed","style","properties","durations","delays","timings","index","shorthand","fallback","easingRaw","result","depth","i","ch","normalized","prop","map","tokens","token","lower","fn","from","to","effect","other","keys","otherKeys","key","uniforms","elapsed","eased","interpolated","lerp","a","b","fromValue","_String3D","StringModule","context","DirtySyncManager","FilterController","value","provider","name","url","options","String3DFontRegistry","object","globalId","element","attributes","parentElement","parentId","String3DRenderer","String3DCamera","modelLoader","modelLoaderFactory","String3DScene","String3DSynchronizer","shouldUseDirtySync","key","fallback","engine","type","loaderType","existing","container","el","data","dirtySet","forceSync","obj","filterTargets","rootObjects","walk","rect","width","height","parentData","shouldSync","nextParentData","cached","forceChildren","child","style","css","initialValue","String3D","ThreeJSMaterialFactory","THREE","definition","initialUniforms","uniforms","material","newUniforms","element","style","collectUniformsFromCSS","initialValues","result","key","def","value","type","url","texture","baseType","BaseMaterial","injectionMap","mergeInjections","shader","injections","pars","header","uniformDeclarations","transform","output","color","normal","roughness","metalness","ao","transmission","lights","emissive","lines","name","uniform","props","newValues","customUniforms","uniformDef","ThreeJSEngine","THREE","loaders","ThreeJSMaterialFactory","x","y","z","w","order","min","max","options","renderer","fov","aspect","near","far","left","right","top","bottom","geometry","material","width","height","depth","radius","widthSegments","heightSegments","radiusTop","radiusBottom","segments","params","color","intensity","distance","decay","angle","penumbra","skyColor","groundColor","type","LoaderClass","defaults","url","normalized","cachedPromise","isFontFile","FontConverter","promise","fontData","font","loader","resolve","text","size","normalizePosition","shapes","scale","char","glyph","xOffset","charShapes","outline","commands","minX","i","maxX","minY","px","py","polygon","inside","j","xi","yi","xj","yj","path","numSamples","p","points","maxY","contour","triangles","tri","a","b","c","cx","cy","offsetX","outlineFormat","shapePath","mx","my","lx","ly","qx","qy","bx","by","subPaths","paths","sp","area","bbox","finalShapes","used","outerPath","shape","innerPath","allPointsInside","testPoints","testPoint","newPath","lastCurve","endPoint","curve","lineHeight","letterSpacing","align","bevelEnabled","bevelThickness","bevelSize","bevelOffset","bevelSegments","curveSegments","lines","resolution","fontAscender","fontDescender","fontEmHeight","baselineRatio","elementWidth","elementHeight","centerOffsetX","centerOffsetY","item","baselineFromTop","offsetY","finalShape","line","index","lineShapes","chars","translated","advance","data","glyphs","ha","matrix","holes","toVec2","pt","newShape","hole","holePath","s","modelUrl","loaderType","nodeName","normalizedLoader","nodeKey","cacheKey","gltf","root","mesh","found","child","config","engine","makeRng","seed","ParticleSystem","cfg","prev","emitterReset","isParticleModelChange","isInstanceModelChange","uniforms","key","count","pos","elapsed","progress","eased","i3","targetArray","attr","array","itemSize","vertexCount","indexArray","triangleCount","minZ","maxZ","idx","sizeX","sizeY","sizeZ","targetX","targetY","scaleX","scaleY","centerX","centerY","centerZ","cumulativeAreas","totalArea","base","ia","ib","ic","ax","ay","az","bz","cz","abx","aby","abz","acx","acy","acz","crossX","crossY","crossZ","r","lo","hi","mid","u","v","su","w1","w2","w3","dt","needsModel","hasModel","hide","useSharedGeometry","setPoints","dir","gravity","drag","totalToEmit","emitCount","colorDirty","speed","vel","time","jitter","flow","disperse","scatter","scatterX","scatterY","scatterZ","rotSpeed","temp","baseX","baseY","baseZ","phase","driftX","driftY","driftZ","jitterX","jitterY","jitterZ","dispersal","dirX","dirY","dirZ","dirLen","scatterScale","scatterOffsetX","scatterOffsetY","scatterOffsetZ","next","vec","len","theta","phi","half","quality","Modifier","anyGeom","clamped","target","degrees","radians","object","boundingBox","hasBox","box","childBox","ThreeJSProvider"]}
1
+ {"version":3,"sources":["../src/modules/String3D.ts","../src/core/String3DCamera.ts","../src/core/abstractions/engineCapabilities.ts","../src/core/filters/String3DCustomFilter.ts","../src/core/filters/String3DFilterPipeline.ts","../src/core/String3DRenderer.ts","../src/core/String3DObject.ts","../src/modules/string3d/styleUtils.ts","../src/core/materials/String3DCustomMaterial.ts","../src/core/materials/MaterialFactory.ts","../src/core/String3DScene.ts","../src/core/synchronizer/StyleBundleCache.ts","../src/core/synchronizer/GroupSynchronizer.ts","../src/core/synchronizer/LightSynchronizer.ts","../src/core/synchronizer/MeshSynchronizer.ts","../src/core/synchronizer/ParticlesSynchronizer.ts","../src/core/text/String3DFontRegistry.ts","../src/core/text/FontConverter.ts","../src/core/synchronizer/TextSynchronizer.ts","../src/core/svg/SVGParser.ts","../src/core/synchronizer/SVGSynchronizer.ts","../src/core/synchronizer/String3DSynchronizer.ts","../src/modules/string3d/DirtySyncManager.ts","../src/modules/string3d/FilterController.ts","../src/adapters/ThreeJSMaterialFactory.ts","../src/adapters/ThreePostProcessPipeline.ts","../src/adapters/ThreeJSProvider.ts"],"sourcesContent":["import { StringContext, StringModule, StringObject, StringData } from \"@fiddle-digital/string-tune\";\r\n\r\nimport { String3DCamera } from \"../core/String3DCamera\";\r\nimport { String3DRenderer } from \"../core/String3DRenderer\";\r\nimport { String3DScene } from \"../core/String3DScene\";\r\nimport { String3DSynchronizer } from \"../core/synchronizer/String3DSynchronizer\";\r\nimport { I3DEngineProvider } from \"../core/abstractions/I3DEngineProvider\";\r\nimport { I3DEngine, I3DModelLoader } from \"../core/abstractions/I3DEngine\";\r\nimport { String3DObject } from \"../core/String3DObject\";\r\nimport { DirtySyncManager } from \"./string3d/DirtySyncManager\";\r\nimport { FilterController } from \"./string3d/FilterController\";\r\nimport { StyleReader } from \"./string3d/styleUtils\";\r\nimport { String3DFontRegistry } from \"../core/text\";\r\n\r\nexport interface String3DOptions {\r\n hideHTML?: boolean;\r\n container?: string | HTMLElement;\r\n zIndex?: number;\r\n modelLoaderType?: string;\r\n modelLoader?: I3DModelLoader;\r\n modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n useDirtySync?: boolean;\r\n styleReadIntervalMs?: number;\r\n layoutReadIntervalMs?: number;\r\n}\r\n\r\nexport class String3D extends StringModule {\r\n private static provider: I3DEngineProvider | null = null;\r\n private static _instance: String3D | null = null;\r\n\r\n private renderer: String3DRenderer | null = null;\r\n private camera: String3DCamera | null = null;\r\n private _scene: String3DScene | null = null;\r\n private synchronizer: String3DSynchronizer | null = null;\r\n private engine: I3DEngine | null = null;\r\n private canvasContainer: HTMLElement | null = null;\r\n private isLoading: Map<string, boolean> = new Map();\r\n private options: String3DOptions;\r\n private useDirtySync = false;\r\n private dirtySyncManager: DirtySyncManager;\r\n private lastSyncData: WeakMap<String3DObject, { scale: number }> = new WeakMap();\r\n private filterController: FilterController;\r\n private needsInitialResize = true;\r\n private providerBootstrapped = false;\r\n private pendingConnectedObjects: Map<string, StringObject> = new Map();\r\n\r\n public static getInstance(): String3D | null {\r\n return String3D._instance;\r\n }\r\n\r\n public get scene(): String3DScene | null {\r\n return this._scene;\r\n }\r\n\r\n public static setProvider(provider: I3DEngineProvider): void {\r\n String3D.provider = provider;\r\n }\r\n\r\n public static registerFont(name: string, url: string, options: { default?: boolean } = {}): void {\r\n String3DFontRegistry.register(name, url);\r\n if (options.default) {\r\n String3DFontRegistry.setDefault(name);\r\n }\r\n }\r\n\r\n public static setDefaultFont(name: string): void {\r\n String3DFontRegistry.setDefault(name);\r\n }\r\n\r\n constructor(context: StringContext) {\r\n super(context);\r\n this.htmlKey = \"3d\";\r\n this.options = this.buildOptionsFromSettings();\r\n this.dirtySyncManager = new DirtySyncManager([\r\n \"style\",\r\n \"class\",\r\n \"string-3d\",\r\n \"string-3d-model-fit\",\r\n \"string-3d-model-scale\",\r\n ]);\r\n this.filterController = new FilterController((value) =>\r\n this.tools.easingFunction.process({ easing: value }),\r\n );\r\n\r\n this.attributesToMap = [\r\n ...this.attributesToMap,\r\n { key: \"3d\", type: \"string\", fallback: \"box\" },\r\n { key: \"3d-model\", type: \"string\", fallback: \"\" },\r\n { key: \"3d-segments\", type: \"number\", fallback: 32 },\r\n { key: \"3d-segments-width\", type: \"number\", fallback: 32 },\r\n { key: \"3d-segments-height\", type: \"number\", fallback: 32 },\r\n { key: \"3d-model-loader\", type: \"string\", fallback: \"\" },\r\n { key: \"3d-model-scale\", type: \"number\", fallback: 1 },\r\n { key: \"3d-model-center\", type: \"boolean\", fallback: false },\r\n { key: \"3d-model-fit\", type: \"string\", fallback: \"contain\" },\r\n ];\r\n\r\n String3D._instance = this;\r\n }\r\n\r\n canConnect(object: StringObject): boolean {\r\n return super.canConnect(object);\r\n }\r\n\r\n initializeObject(\r\n globalId: number,\r\n object: StringObject,\r\n element: HTMLElement,\r\n attributes: Record<string, any>,\r\n ): void {\r\n super.initializeObject(globalId, object, element, attributes);\r\n\r\n object.setProperty(\"parentId\", null);\r\n const parentElement = element.parentElement?.closest(\r\n '[string-3d=\"group\"]',\r\n ) as HTMLElement | null;\r\n if (parentElement) {\r\n const parentId = parentElement.getAttribute(\"string-id\");\r\n if (parentId) {\r\n object.setProperty(\"parentId\", parentId);\r\n object.setProperty(\"parent\", parentElement);\r\n }\r\n }\r\n }\r\n\r\n onResize(): void {\r\n if (this.renderer && this.camera && this.synchronizer) {\r\n this.renderer.resize(this.camera);\r\n this.synchronizer.updateViewportSize(this.renderer.width, this.renderer.height);\r\n this.camera.clearScaleCache();\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.markAllDirty();\r\n }\r\n }\r\n }\r\n\r\n onInit(): void {\r\n this.options = this.buildOptionsFromSettings();\r\n if (!String3D.provider) {\r\n return;\r\n }\r\n this.registerTypedProperties();\r\n this.injectCSS();\r\n this.useDirtySync = !!this.options.useDirtySync;\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.enable();\r\n }\r\n\r\n const provider = String3D.provider;\r\n const initResult = provider.initialize?.();\r\n if (initResult && typeof (initResult as Promise<void>).then === \"function\") {\r\n (initResult as Promise<void>)\r\n .then(() => {\r\n this.bootstrapProvider(provider);\r\n })\r\n .catch(() => {});\r\n return;\r\n }\r\n\r\n this.bootstrapProvider(provider);\r\n }\r\n\r\n private bootstrapProvider(provider: I3DEngineProvider): void {\r\n if (this.providerBootstrapped) {\r\n return;\r\n }\r\n\r\n this.engine = provider.getEngine();\r\n this.filterController.setCustomFilterRegistry(this.engine.getCustomFilterRegistry?.());\r\n this.canvasContainer = this.createOrGetContainer();\r\n\r\n this.renderer = new String3DRenderer(this.canvasContainer, this.engine);\r\n this.renderer.attach();\r\n\r\n this.camera = new String3DCamera(this.engine, \"orthographic\");\r\n this.camera.setPosition(0, 0, 1000);\r\n this.camera.lookAt(0, 0, 0);\r\n this.camera.resize(this.renderer.width, this.renderer.height);\r\n\r\n const modelLoader = this.resolveModelLoader();\r\n const modelLoaderFactory = this.resolveModelLoaderFactory();\r\n this._scene = new String3DScene(this.engine, {\r\n modelLoader,\r\n modelLoaderFactory,\r\n });\r\n this._scene.getScene().add(this.camera.camera);\r\n\r\n this.synchronizer = new String3DSynchronizer(\r\n this.camera,\r\n this.renderer.width,\r\n this.renderer.height,\r\n this.engine,\r\n );\r\n this.synchronizer.setScene(this._scene);\r\n this.synchronizer.setSyncOptions({\r\n styleReadIntervalMs: this.options.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.options.layoutReadIntervalMs,\r\n });\r\n\r\n this._scene.setSynchronizer(this.synchronizer);\r\n this.providerBootstrapped = true;\r\n this.flushPendingConnections();\r\n }\r\n\r\n private flushPendingConnections(): void {\r\n const pending = Array.from(this.pendingConnectedObjects.values());\r\n this.pendingConnectedObjects.clear();\r\n pending.forEach((object) => this.onObjectConnected(object));\r\n }\r\n\r\n onSettingsChange(): void {\r\n this.options = this.buildOptionsFromSettings();\r\n const shouldUseDirtySync = !!this.options.useDirtySync;\r\n if (shouldUseDirtySync && !this.useDirtySync) {\r\n this.useDirtySync = true;\r\n this.dirtySyncManager.enable();\r\n if (this._scene) {\r\n this.dirtySyncManager.observeScene(this._scene.rootObjects);\r\n }\r\n this.dirtySyncManager.markAllDirty();\r\n } else if (!shouldUseDirtySync && this.useDirtySync) {\r\n this.useDirtySync = false;\r\n this.dirtySyncManager.disable();\r\n }\r\n\r\n this.synchronizer?.setSyncOptions({\r\n styleReadIntervalMs: this.options.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.options.layoutReadIntervalMs,\r\n });\r\n }\r\n\r\n private buildOptionsFromSettings(): String3DOptions {\r\n return {\r\n hideHTML: this.getSettingValue(\"hideHTML\", false),\r\n container: this.getSettingValue(\"container\", undefined),\r\n zIndex: this.getSettingValue(\"zIndex\", 1),\r\n modelLoaderType: this.getSettingValue(\"modelLoaderType\", undefined),\r\n modelLoader: this.getSettingValue(\"modelLoader\", undefined),\r\n modelLoaderFactory: this.getSettingValue(\"modelLoaderFactory\", undefined),\r\n useDirtySync: this.getSettingValue(\"useDirtySync\", false),\r\n styleReadIntervalMs: this.getSettingValue(\"styleReadIntervalMs\", 0),\r\n layoutReadIntervalMs: this.getSettingValue(\"layoutReadIntervalMs\", 0),\r\n };\r\n }\r\n\r\n private getSettingValue<T>(key: string, fallback: T): T {\r\n if (!this.settings || !(key in this.settings)) return fallback;\r\n return this.settings[key] as T;\r\n }\r\n\r\n private resolveModelLoader(): I3DModelLoader | undefined {\r\n if (!this.engine) return undefined;\r\n if (this.options.modelLoader) return this.options.modelLoader;\r\n if (this.options.modelLoaderFactory) return undefined;\r\n if (this.options.modelLoaderType) {\r\n try {\r\n return this.engine.createModelLoader(this.options.modelLoaderType);\r\n } catch (error) {}\r\n }\r\n return undefined;\r\n }\r\n\r\n private resolveModelLoaderFactory():\r\n | ((engine: I3DEngine, type?: string) => I3DModelLoader)\r\n | undefined {\r\n if (!this.engine) return undefined;\r\n if (this.options.modelLoaderFactory) return this.options.modelLoaderFactory;\r\n if (this.options.modelLoaderType) {\r\n return (engine: I3DEngine, type?: string) => {\r\n const loaderType = type || this.options.modelLoaderType;\r\n if (!loaderType) {\r\n throw new Error(\"[String3D] Model loader type not provided\");\r\n }\r\n return engine.createModelLoader(loaderType);\r\n };\r\n }\r\n return undefined;\r\n }\r\n\r\n private createOrGetContainer(): HTMLElement {\r\n if (this.options.container instanceof HTMLElement) {\r\n this.applyContainerStyles(this.options.container);\r\n return this.options.container;\r\n }\r\n\r\n if (typeof this.options.container === \"string\") {\r\n const existing = document.getElementById(this.options.container);\r\n if (existing) {\r\n this.applyContainerStyles(existing);\r\n return existing;\r\n }\r\n }\r\n\r\n const container = document.createElement(\"div\");\r\n container.id = \"string-3d-canvas\";\r\n this.applyContainerStyles(container);\r\n document.body.insertBefore(container, document.body.firstChild);\r\n return container;\r\n }\r\n\r\n private applyContainerStyles(el: HTMLElement): void {\r\n Object.assign(el.style, {\r\n position: \"fixed\",\r\n left: \"0\",\r\n top: \"0\",\r\n width: \"100vw\",\r\n height: \"100lvh\",\r\n zIndex: String(this.options.zIndex),\r\n pointerEvents: \"none\",\r\n });\r\n }\r\n\r\n onObjectConnected(object: StringObject): void {\r\n if (!this._scene) {\r\n this.pendingConnectedObjects.set(object.id, object);\r\n return;\r\n }\r\n this.pendingConnectedObjects.delete(object.id);\r\n\r\n if (this.isLoading.has(object.id)) {\r\n return;\r\n }\r\n this.isLoading.set(object.id, true);\r\n\r\n this._scene.createFromElement(object);\r\n\r\n if (this.useDirtySync && object.htmlElement) {\r\n this.dirtySyncManager.observeElement(object.htmlElement);\r\n this.dirtySyncManager.markDirty(object.htmlElement);\r\n }\r\n\r\n if (this.options.hideHTML && object.htmlElement) {\r\n const nodeType = object.htmlElement.getAttribute(\"string-3d\");\r\n object.htmlElement.style.color = \"transparent\";\r\n object.htmlElement.style.setProperty(\"-webkit-text-fill-color\", \"transparent\");\r\n }\r\n }\r\n\r\n onFrame(data: StringData): void {\r\n if (!this.renderer || !this._scene || !this.camera || !this.synchronizer) return;\r\n\r\n if (this.needsInitialResize) {\r\n this.needsInitialResize = false;\r\n this.renderer.resize(this.camera);\r\n this.synchronizer.updateViewportSize(this.renderer.width, this.renderer.height);\r\n }\r\n\r\n const dirtySet = this.useDirtySync ? this.dirtySyncManager.getDirtySet() : null;\r\n const forceSync = !dirtySet || dirtySet.size === 0;\r\n\r\n this.batchReadLayouts(this._scene.rootObjects, forceSync, dirtySet);\r\n\r\n this._scene.rootObjects.forEach((obj) => {\r\n this.syncRecursive(obj.el, obj, { scale: 1 }, forceSync, dirtySet);\r\n });\r\n\r\n const filterTargets = this.filterController.collectTargets(\r\n this._scene.rootObjects,\r\n performance.now(),\r\n this.useDirtySync,\r\n dirtySet,\r\n );\r\n this.renderer!.render(this._scene!, this.camera!, filterTargets);\r\n\r\n if (this.useDirtySync) {\r\n this.dirtySyncManager.clearDirty();\r\n }\r\n }\r\n\r\n private batchReadLayouts(\r\n rootObjects: String3DObject[],\r\n forceSync: boolean,\r\n dirtySet: Set<HTMLElement> | null,\r\n ): void {\r\n const walk = (obj: String3DObject): void => {\r\n if (obj.el) {\r\n const shouldSync = forceSync || !dirtySet || dirtySet.has(obj.el);\r\n if (shouldSync) {\r\n const rect = obj.el.getBoundingClientRect();\r\n const width = obj.el.offsetWidth || rect.width;\r\n const height = obj.el.offsetHeight || rect.height;\r\n (obj.el as any).__layoutCache = { rect, width, height };\r\n }\r\n }\r\n obj.children.forEach(walk);\r\n };\r\n rootObjects.forEach(walk);\r\n }\r\n\r\n private syncRecursive(\r\n el: HTMLElement | undefined,\r\n object: String3DObject,\r\n parentData: any,\r\n forceSync: boolean,\r\n dirtySet: Set<HTMLElement> | null,\r\n ): void {\r\n if (!this.synchronizer || !el) return;\r\n const shouldSync =\r\n object.type === \"particles\" ||\r\n object.type === \"text\" ||\r\n forceSync ||\r\n !dirtySet ||\r\n dirtySet.has(el);\r\n let nextParentData = parentData;\r\n\r\n if (shouldSync) {\r\n const data = this.synchronizer.syncElement(el, object, parentData, {\r\n dirtySet,\r\n forceSync,\r\n });\r\n if (data && typeof data.scale === \"number\") {\r\n this.lastSyncData.set(object, data);\r\n nextParentData = data;\r\n }\r\n } else {\r\n const cached = this.lastSyncData.get(object);\r\n if (cached) {\r\n nextParentData = cached;\r\n }\r\n }\r\n\r\n const forceChildren = forceSync || shouldSync;\r\n object.children.forEach((child) =>\r\n this.syncRecursive(child.el, child, nextParentData, forceChildren, dirtySet),\r\n );\r\n }\r\n\r\n private injectCSS(): void {\r\n if (document.getElementById(\"string-3d-styles\")) return;\r\n\r\n const style = document.createElement(\"style\");\r\n style.id = \"string-3d-styles\";\r\n style.textContent = `\r\n @property --translate-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --translate-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --translate-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --rotate-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --scale { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-x { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-y { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --scale-z { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --opacity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --filter { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --light-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --light-intensity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --light-distance { syntax: \"<number>\"; inherits: false; initial-value: 1000; }\r\n @property --light-decay { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --light-angle { syntax: \"<number>\"; inherits: false; initial-value: 1.0472; }\r\n @property --light-penumbra { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --light-ground-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --light-target { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --shadow-cast { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-receive { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-bias { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --shadow-map-size { syntax: \"<number>\"; inherits: false; initial-value: 512; }\r\n @property --texture-flip-y { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --texture-color-space { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-mode { syntax: \"*\"; inherits: false; initial-value: emitter; }\r\n @property --particles-count { syntax: \"<number>\"; inherits: false; initial-value: 300; }\r\n @property --particles-size { syntax: \"<number>\"; inherits: false; initial-value: 2; }\r\n @property --particles-color { syntax: \"<color>\"; inherits: false; initial-value: #ffffff; }\r\n @property --particles-opacity { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --particles-spread { syntax: \"<number>\"; inherits: false; initial-value: 120; }\r\n @property --particles-seed { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --particles-shape { syntax: \"*\"; inherits: false; initial-value: sphere; }\r\n @property --particles-fit { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --particles-model { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-model-loader { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --particles-model-node { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model-loader { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --instance-model-node { syntax: \"*\"; inherits: false; initial-value: none; }\r\n @property --emit-rate { syntax: \"<number>\"; inherits: false; initial-value: 30; }\r\n @property --emit-burst { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --particle-life { syntax: \"<number>\"; inherits: false; initial-value: 2.5; }\r\n @property --particle-speed { syntax: \"<number>\"; inherits: false; initial-value: 40; }\r\n @property --particle-direction { syntax: \"*\"; inherits: false; initial-value: 0 1 0; }\r\n @property --particle-gravity { syntax: \"*\"; inherits: false; initial-value: 0 -30 0; }\r\n @property --particle-drag { syntax: \"<number>\"; inherits: false; initial-value: 0.1; }\r\n @property --particle-size-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.6; }\r\n @property --particle-color-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.2; }\r\n @property --instance-shape { syntax: \"*\"; inherits: false; initial-value: sphere; }\r\n @property --instance-scale { syntax: \"<number>\"; inherits: false; initial-value: 1; }\r\n @property --instance-scale-variation { syntax: \"<number>\"; inherits: false; initial-value: 0.5; }\r\n @property --instance-rotation-speed { syntax: \"<number>\"; inherits: false; initial-value: 0.4; }\r\n @property --instance-jitter { syntax: \"<number>\"; inherits: false; initial-value: 0.2; }\r\n @property --instance-flow { syntax: \"<number>\"; inherits: false; initial-value: 0.3; }\r\n @property --instance-disperse { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-x { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-y { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --instance-scatter-z { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-depth { syntax: \"<number>\"; inherits: false; initial-value: 8; }\r\n @property --text-curve-segments { syntax: \"<number>\"; inherits: false; initial-value: 8; }\r\n @property --text-bevel-size { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-thickness { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-offset { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-bevel-steps { syntax: \"<number>\"; inherits: false; initial-value: 0; }\r\n @property --text-fit { syntax: \"*\"; inherits: false; initial-value: contain; }\r\n\r\n :where([string-3d]) {\r\n --translate-x: 0; --translate-y: 0; --translate-z: 0;\r\n --rotate-x: 0; --rotate-y: 0; --rotate-z: 0;\r\n --scale: 1; --scale-x: 1; --scale-y: 1; --scale-z: 1; --opacity: 1; --filter: none;\r\n --light-color: #ffffff; --light-intensity: 1; --light-distance: 1000; --light-decay: 0;\r\n --light-angle: 1.0472; --light-penumbra: 0; --light-ground-color: #ffffff; --light-target: none;\r\n --shadow-cast: 0; --shadow-receive: 0; --shadow-bias: 0; --shadow-map-size: 512;\r\n --texture-flip-y: 1; --texture-color-space: none;\r\n --particles-mode: emitter; --particles-count: 300; --particles-size: 2; --particles-color: #ffffff;\r\n --particles-opacity: 1; --particles-spread: 120; --particles-seed: 1; --particles-shape: sphere;\r\n --particles-fit: 0;\r\n --particles-model: none; --particles-model-loader: none; --particles-model-node: none;\r\n --instance-model: none; --instance-model-loader: none; --instance-model-node: none;\r\n --emit-rate: 30; --emit-burst: 0; --particle-life: 2.5; --particle-speed: 40;\r\n --particle-direction: 0 1 0; --particle-gravity: 0 -30 0; --particle-drag: 0.1;\r\n --particle-size-variation: 0.6; --particle-color-variation: 0.2;\r\n --instance-shape: sphere; --instance-scale: 1; --instance-scale-variation: 0.5;\r\n --instance-rotation-speed: 0.4; --instance-jitter: 0.2; --instance-flow: 0.3;\r\n --instance-disperse: 0;\r\n --instance-scatter: 0;\r\n --instance-scatter-x: 0; --instance-scatter-y: 0; --instance-scatter-z: 0;\r\n --text-depth: 8; --text-curve-segments: 8; --text-bevel-size: 0; --text-bevel-thickness: 0;\r\n --text-bevel-offset: 0; --text-bevel-steps: 0; --text-fit: contain;\r\n transform-style: preserve-3d;\r\n }\r\n\r\n [string-3d-visual=\"true\"] {\r\n transform:\r\n translate3d(calc(var(--translate-x) * 1px), calc(var(--translate-y) * 1px), calc(var(--translate-z) * 1px))\r\n rotateX(calc(var(--rotate-x) * 1deg))\r\n rotateY(calc(var(--rotate-y) * 1deg))\r\n rotateZ(calc(var(--rotate-z) * 1deg))\r\n scale3d(calc(var(--scale) * var(--scale-x)), calc(var(--scale) * var(--scale-y)), calc(var(--scale) * var(--scale-z)));\r\n }\r\n `;\r\n document.head.appendChild(style);\r\n }\r\n\r\n private registerTypedProperties(): void {\r\n const css = (globalThis as any).CSS;\r\n if (!css?.registerProperty) return;\r\n\r\n const props: Array<{ name: string; initialValue: string }> = [\r\n { name: \"--translate-x\", initialValue: \"0\" },\r\n { name: \"--translate-y\", initialValue: \"0\" },\r\n { name: \"--translate-z\", initialValue: \"0\" },\r\n { name: \"--rotate-x\", initialValue: \"0\" },\r\n { name: \"--rotate-y\", initialValue: \"0\" },\r\n { name: \"--rotate-z\", initialValue: \"0\" },\r\n { name: \"--scale\", initialValue: \"1\" },\r\n { name: \"--scale-x\", initialValue: \"1\" },\r\n { name: \"--scale-y\", initialValue: \"1\" },\r\n { name: \"--scale-z\", initialValue: \"1\" },\r\n { name: \"--opacity\", initialValue: \"1\" },\r\n { name: \"--filter\", initialValue: \"none\" },\r\n { name: \"--material-type\", initialValue: \"basic\" },\r\n { name: \"--material-color\", initialValue: \"#ffffff\" },\r\n { name: \"--material-metalness\", initialValue: \"0\" },\r\n { name: \"--material-roughness\", initialValue: \"1\" },\r\n { name: \"--material-emissive\", initialValue: \"#000000\" },\r\n { name: \"--rim-color\", initialValue: \"#00c8ff\" },\r\n { name: \"--rim-power\", initialValue: \"1.5\" },\r\n { name: \"--rim-strength\", initialValue: \"1\" },\r\n { name: \"--uv-strength\", initialValue: \"0.7\" },\r\n { name: \"--texture-map\", initialValue: \"none\" },\r\n { name: \"--texture-normal\", initialValue: \"none\" },\r\n { name: \"--texture-roughness\", initialValue: \"none\" },\r\n { name: \"--texture-metalness\", initialValue: \"none\" },\r\n { name: \"--texture-ao\", initialValue: \"none\" },\r\n { name: \"--light-color\", initialValue: \"#ffffff\" },\r\n { name: \"--light-intensity\", initialValue: \"1\" },\r\n { name: \"--light-distance\", initialValue: \"1000\" },\r\n { name: \"--light-decay\", initialValue: \"0\" },\r\n { name: \"--light-angle\", initialValue: \"1.0472\" },\r\n { name: \"--light-penumbra\", initialValue: \"0\" },\r\n { name: \"--light-ground-color\", initialValue: \"#ffffff\" },\r\n { name: \"--light-target\", initialValue: \"none\" },\r\n { name: \"--shadow-cast\", initialValue: \"0\" },\r\n { name: \"--shadow-receive\", initialValue: \"0\" },\r\n { name: \"--shadow-bias\", initialValue: \"0\" },\r\n { name: \"--shadow-map-size\", initialValue: \"512\" },\r\n { name: \"--texture-flip-y\", initialValue: \"1\" },\r\n { name: \"--texture-color-space\", initialValue: \"none\" },\r\n { name: \"--particles-mode\", initialValue: \"emitter\" },\r\n { name: \"--particles-count\", initialValue: \"300\" },\r\n { name: \"--particles-size\", initialValue: \"2\" },\r\n { name: \"--particles-color\", initialValue: \"#ffffff\" },\r\n { name: \"--particles-opacity\", initialValue: \"1\" },\r\n { name: \"--particles-spread\", initialValue: \"120\" },\r\n { name: \"--particles-seed\", initialValue: \"1\" },\r\n { name: \"--particles-shape\", initialValue: \"sphere\" },\r\n { name: \"--particles-fit\", initialValue: \"0\" },\r\n { name: \"--particles-model\", initialValue: \"none\" },\r\n { name: \"--particles-model-loader\", initialValue: \"none\" },\r\n { name: \"--particles-model-node\", initialValue: \"none\" },\r\n { name: \"--instance-model\", initialValue: \"none\" },\r\n { name: \"--instance-model-loader\", initialValue: \"none\" },\r\n { name: \"--instance-model-node\", initialValue: \"none\" },\r\n { name: \"--emit-rate\", initialValue: \"30\" },\r\n { name: \"--emit-burst\", initialValue: \"0\" },\r\n { name: \"--particle-life\", initialValue: \"2.5\" },\r\n { name: \"--particle-speed\", initialValue: \"40\" },\r\n { name: \"--particle-direction\", initialValue: \"0 1 0\" },\r\n { name: \"--particle-gravity\", initialValue: \"0 -30 0\" },\r\n { name: \"--particle-drag\", initialValue: \"0.1\" },\r\n { name: \"--particle-size-variation\", initialValue: \"0.6\" },\r\n { name: \"--particle-color-variation\", initialValue: \"0.2\" },\r\n { name: \"--instance-shape\", initialValue: \"sphere\" },\r\n { name: \"--instance-scale\", initialValue: \"1\" },\r\n { name: \"--instance-scale-variation\", initialValue: \"0.5\" },\r\n { name: \"--instance-rotation-speed\", initialValue: \"0.4\" },\r\n { name: \"--instance-jitter\", initialValue: \"0.2\" },\r\n { name: \"--instance-flow\", initialValue: \"0.3\" },\r\n { name: \"--instance-disperse\", initialValue: \"0\" },\r\n { name: \"--instance-scatter\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-x\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-y\", initialValue: \"0\" },\r\n { name: \"--instance-scatter-z\", initialValue: \"0\" },\r\n { name: \"--text-depth\", initialValue: \"8\" },\r\n { name: \"--text-curve-segments\", initialValue: \"8\" },\r\n { name: \"--text-bevel-size\", initialValue: \"0\" },\r\n { name: \"--text-bevel-thickness\", initialValue: \"0\" },\r\n { name: \"--text-bevel-offset\", initialValue: \"0\" },\r\n { name: \"--text-bevel-steps\", initialValue: \"0\" },\r\n { name: \"--text-fit\", initialValue: \"contain\" },\r\n ];\r\n\r\n props.forEach(({ name, initialValue }) => {\r\n try {\r\n css.registerProperty({\r\n name,\r\n syntax:\r\n name === \"--filter\" ||\r\n name === \"--light-target\" ||\r\n name.startsWith(\"--texture-\") ||\r\n name === \"--material-type\" ||\r\n name === \"--particles-mode\" ||\r\n name === \"--particles-shape\" ||\r\n name === \"--particles-model\" ||\r\n name === \"--particles-model-loader\" ||\r\n name === \"--particles-model-node\" ||\r\n name === \"--instance-model\" ||\r\n name === \"--instance-model-loader\" ||\r\n name === \"--instance-model-node\" ||\r\n name === \"--particle-direction\" ||\r\n name === \"--particle-gravity\" ||\r\n name === \"--instance-shape\" ||\r\n name === \"--text-fit\"\r\n ? \"*\"\r\n : name.includes(\"color\") || name.includes(\"emissive\")\r\n ? \"<color>\"\r\n : \"<number>\",\r\n inherits: false,\r\n initialValue,\r\n });\r\n } catch {}\r\n });\r\n }\r\n\r\n destroy(): void {\r\n this.renderer?.destroy();\r\n this._scene?.destroy();\r\n this.isLoading.clear();\r\n this.dirtySyncManager.disable();\r\n this.filterController.clear();\r\n this.lastSyncData = new WeakMap();\r\n this.pendingConnectedObjects.clear();\r\n this.providerBootstrapped = false;\r\n\r\n const styleEl = document.getElementById(\"string-3d-styles\");\r\n styleEl?.remove();\r\n\r\n if (this.canvasContainer?.id === \"string-3d-canvas\") {\r\n this.canvasContainer.remove();\r\n }\r\n\r\n super.destroy();\r\n }\r\n}\r\n","import { I3DEngine, I3DVector3, I3DCamera } from \"./abstractions/I3DEngine\";\r\n\r\nexport type CameraMode = \"orthographic\" | \"perspective\";\r\n\r\nexport class String3DCamera {\r\n private scaleCache = new Map<number, number>();\r\n private _camera: I3DCamera;\r\n private _position: I3DVector3;\r\n private _width = 1;\r\n private _height = 1;\r\n private engine: I3DEngine;\r\n private mode: CameraMode;\r\n private perspectiveFov: number;\r\n\r\n constructor(\r\n engine: I3DEngine,\r\n mode: CameraMode = \"perspective\",\r\n fov = 50,\r\n near = 0.1,\r\n far = 10000\r\n ) {\r\n this.engine = engine;\r\n this.mode = mode;\r\n this.perspectiveFov = fov;\r\n\r\n if (mode === \"orthographic\") {\r\n this._camera = engine.createOrthographicCamera(-1, 1, 1, -1, near, far);\r\n } else {\r\n this._camera = engine.createPerspectiveCamera(fov, 1, near, far);\r\n }\r\n\r\n this._position = engine.createVector3(0, 0, 1000);\r\n this.update();\r\n }\r\n\r\n public get camera(): I3DCamera {\r\n return this._camera;\r\n }\r\n\r\n public resize(width: number, height: number): void {\r\n this._width = width;\r\n this._height = height;\r\n\r\n if (this.mode === \"orthographic\") {\r\n const ortho = this._camera as any;\r\n ortho.left = -width / 2;\r\n ortho.right = width / 2;\r\n ortho.top = height / 2;\r\n ortho.bottom = -height / 2;\r\n } else {\r\n this._camera.aspect = width / height;\r\n }\r\n\r\n this.update();\r\n }\r\n\r\n public setPosition(x: number, y: number, z: number): void {\r\n this._position.set(x, y, z);\r\n this._camera.position.copy(this._position);\r\n this.update();\r\n }\r\n\r\n public lookAt(x: number, y: number, z: number): void {\r\n this._camera.lookAt(x, y, z);\r\n this.update();\r\n }\r\n\r\n public update(): void {\r\n this._camera.updateProjectionMatrix();\r\n (this._camera as any).updateMatrixWorld?.();\r\n }\r\n\r\n public screenToWorld(screenX: number, screenY: number, z = 0): I3DVector3 {\r\n if (this.mode === \"orthographic\") {\r\n const x = screenX - this._width / 2;\r\n const y = -(screenY - this._height / 2);\r\n return this.engine.createVector3(x, y, z);\r\n } else {\r\n const { width, height } = this.getFrustumSizeAt(z);\r\n const normalizedX = screenX / this._width;\r\n const normalizedY = screenY / this._height;\r\n const x = (normalizedX - 0.5) * width;\r\n const y = -(normalizedY - 0.5) * height;\r\n return this.engine.createVector3(x, y, z);\r\n }\r\n }\r\n\r\n public getFrustumSizeAt(z: number): { width: number; height: number } {\r\n if (this.mode === \"orthographic\") {\r\n return { width: this._width, height: this._height };\r\n }\r\n\r\n const fov = this.engine.degToRad(this.perspectiveFov);\r\n const distance = Math.abs(z - this._camera.position.z);\r\n const height = 2 * Math.tan(fov / 2) * distance;\r\n const width = height * this._camera.aspect;\r\n return { width, height };\r\n }\r\n\r\n public getScaleAtZ(z: number, viewportHeight: number): number {\r\n if (this.mode === \"orthographic\") {\r\n return 1;\r\n }\r\n\r\n const roundedZ = Math.round(z * 1000) / 1000;\r\n if (this.scaleCache.has(roundedZ)) {\r\n return this.scaleCache.get(roundedZ)!;\r\n }\r\n\r\n const { height } = this.getFrustumSizeAt(z);\r\n const scale = height / viewportHeight;\r\n this.scaleCache.set(roundedZ, scale);\r\n return scale;\r\n }\r\n\r\n public clearScaleCache(): void {\r\n this.scaleCache.clear();\r\n }\r\n\r\n public getMode(): CameraMode {\r\n return this.mode;\r\n }\r\n\r\n public getPerspectiveFov(): number {\r\n return this.perspectiveFov;\r\n }\r\n\r\n public getPositionZ(): number {\r\n return this._position.z;\r\n }\r\n}\r\n","import { I3DEngine, I3DEngineCapabilities, I3DPostProcessRuntime, I3DRenderer } from \"./I3DEngine\";\r\n\r\nconst DEFAULT_CAPABILITIES: I3DEngineCapabilities = {\r\n renderTargets: false,\r\n shaderMaterials: false,\r\n postProcess: false,\r\n customMaterialFactory: false,\r\n particles: false,\r\n text: false,\r\n geometrySimplify: false,\r\n};\r\n\r\nexport function resolveEngineCapabilities(engine: I3DEngine): I3DEngineCapabilities {\r\n const reported = engine.getCapabilities?.();\r\n if (reported) {\r\n return {\r\n ...DEFAULT_CAPABILITIES,\r\n ...reported,\r\n };\r\n }\r\n\r\n const inferred: I3DEngineCapabilities = {\r\n renderTargets: typeof engine.createRenderTarget === \"function\",\r\n shaderMaterials: typeof engine.createShaderMaterial === \"function\",\r\n postProcess:\r\n typeof engine.createRenderTarget === \"function\" &&\r\n typeof engine.createShaderMaterial === \"function\",\r\n customMaterialFactory: typeof engine.getMaterialFactory === \"function\",\r\n particles: typeof engine.createParticleSystem === \"function\",\r\n text: typeof engine.createTextGeometry === \"function\" || typeof engine.loadFont === \"function\",\r\n geometrySimplify: typeof engine.simplifyGeometry === \"function\",\r\n };\r\n\r\n return inferred;\r\n}\r\n\r\nexport function canUsePostProcessing(engine: I3DEngine, renderer: I3DRenderer): boolean {\r\n return !!resolvePostProcessRuntime(engine, renderer);\r\n}\r\n\r\nexport function resolvePostProcessRuntime(\r\n engine: I3DEngine,\r\n renderer: I3DRenderer,\r\n): I3DPostProcessRuntime | null {\r\n const explicit = engine.getPostProcessRuntime?.();\r\n if (explicit && explicit.isSupported(renderer)) {\r\n return explicit;\r\n }\r\n\r\n const capabilities = resolveEngineCapabilities(engine);\r\n if (!capabilities.postProcess || !capabilities.renderTargets || !capabilities.shaderMaterials) {\r\n return null;\r\n }\r\n\r\n if (\r\n typeof engine.createRenderTarget !== \"function\" ||\r\n typeof engine.createShaderMaterial !== \"function\" ||\r\n typeof renderer.setRenderTarget !== \"function\"\r\n ) {\r\n return null;\r\n }\r\n\r\n return {\r\n isSupported: () => true,\r\n createRenderTarget: (width: number, height: number, options?: any) =>\r\n engine.createRenderTarget!(width, height, options),\r\n createShaderMaterial: (params?: any) => engine.createShaderMaterial!(params),\r\n setRenderTarget: (activeRenderer: I3DRenderer, target: any) => {\r\n activeRenderer.setRenderTarget?.(target);\r\n },\r\n clear: (activeRenderer: I3DRenderer, color = true, depth = true, stencil = true) => {\r\n activeRenderer.clear?.(color, depth, stencil);\r\n },\r\n };\r\n}\r\n","import type { I3DBackend } from \"../abstractions/I3DEngine\";\n\nexport type String3DCustomFilterImplementation = {\n kind: \"shader\";\n language: \"glsl\" | \"wgsl\" | \"custom\";\n stage?: \"fragment\" | \"pipeline\";\n code: string;\n vertexCode?: string;\n entryPoint?: string;\n metadata?: Record<string, any>;\n};\n\nexport type String3DCustomFilterDefinition = {\n name: string;\n implementations?: Partial<Record<I3DBackend, String3DCustomFilterImplementation>>;\n /**\n * @deprecated Use `implementations.webgl` instead.\n */\n fragmentShader?: string;\n uniforms?: Record<string, any>;\n parse?: (args: string) => Record<string, any> | null;\n};\n\nexport class String3DCustomFilterRegistry {\n private static filters: Map<string, String3DCustomFilterDefinition> = new Map();\n\n static register(definition: String3DCustomFilterDefinition): void {\n const name = definition.name.trim().toLowerCase();\n if (!name) {\n throw new Error(\"[String3D] Custom filter name is required.\");\n }\n this.filters.set(name, { ...definition, name });\n }\n\n static get(name: string): String3DCustomFilterDefinition | undefined {\n return this.filters.get(name.trim().toLowerCase());\n }\n\n static has(name: string): boolean {\n return this.filters.has(name.trim().toLowerCase());\n }\n\n static list(): String3DCustomFilterDefinition[] {\n return Array.from(this.filters.values());\n }\n\n static getImplementation(\n name: string,\n backend: I3DBackend,\n ): String3DCustomFilterImplementation | undefined {\n const def = this.get(name);\n if (!def) return undefined;\n const impl = def.implementations?.[backend] || def.implementations?.custom;\n if (impl) return impl;\n if (def.fragmentShader && backend === \"webgl\") {\n return {\n kind: \"shader\",\n language: \"glsl\",\n stage: \"fragment\",\n code: def.fragmentShader,\n };\n }\n return undefined;\n }\n}\n","import {\n I3DCustomFilterRegistryRuntime,\n I3DEngine,\n I3DPostProcessPipelineRuntime,\n I3DPostProcessRuntime,\n I3DRenderer,\n I3DRenderTarget,\n} from \"../abstractions/I3DEngine\";\nimport type { String3DFilterChain } from \"./String3DFilterTypes\";\nimport { String3DCustomFilterRegistry } from \"./String3DCustomFilter\";\n\nexport class String3DFilterPipeline {\n private readonly pipeline: I3DPostProcessPipelineRuntime | null;\n\n constructor(\n engine: I3DEngine,\n renderer: I3DRenderer,\n runtime: I3DPostProcessRuntime,\n width: number,\n height: number,\n ) {\n const customFilterRegistry: I3DCustomFilterRegistryRuntime =\n engine.getCustomFilterRegistry?.() || String3DCustomFilterRegistry;\n this.pipeline =\n runtime.createPipeline?.({\n engine,\n renderer,\n width,\n height,\n customFilterRegistry,\n }) || null;\n }\n\n public isSupported(): boolean {\n return this.pipeline?.isSupported() ?? false;\n }\n\n public resize(width: number, height: number): void {\n this.pipeline?.resize(width, height);\n }\n\n public setScale(scale: number): void {\n this.pipeline?.setScale(scale);\n }\n\n public applyFilters(\n input: I3DRenderTarget,\n effects: String3DFilterChain,\n quality = 1,\n ): I3DRenderTarget {\n return this.pipeline?.applyFilters(input, effects, quality) || input;\n }\n\n public acquireTarget(): I3DRenderTarget {\n if (!this.pipeline) {\n throw new Error(\"[String3D] Post-process pipeline runtime is not available.\");\n }\n return this.pipeline.acquireTarget();\n }\n\n public releaseTarget(target: I3DRenderTarget): void {\n this.pipeline?.releaseTarget(target);\n }\n\n public renderToScreen(input: I3DRenderTarget): void {\n this.pipeline?.renderToScreen(input);\n }\n\n public dispose(): void {\n this.pipeline?.dispose();\n }\n}\n","import {\r\n I3DEngine,\r\n I3DLayerIsolationState,\r\n I3DRenderer,\r\n I3DObject,\r\n I3DPostProcessRuntime,\r\n I3DRenderTarget,\r\n} from \"./abstractions/I3DEngine\";\r\nimport { resolvePostProcessRuntime } from \"./abstractions/engineCapabilities\";\r\nimport { String3DCamera } from \"./String3DCamera\";\r\nimport { String3DScene } from \"./String3DScene\";\r\nimport { String3DFilterPipeline } from \"./filters/String3DFilterPipeline\";\r\nimport type { String3DFilterTarget } from \"./filters/String3DFilterTypes\";\r\nimport type { String3DFilterEffect } from \"./filters/String3DFilterTypes\";\r\n\r\ntype FilterCacheEntry = {\r\n target: I3DRenderTarget;\r\n effectsKey: string;\r\n lastUsedFrame: number;\r\n qualityScale: number;\r\n};\r\n\r\nexport class String3DRenderer {\r\n private _container: HTMLElement;\r\n private _renderer: I3DRenderer;\r\n private _width: number;\r\n private _height: number;\r\n private engine: I3DEngine;\r\n private postProcessRuntime: I3DPostProcessRuntime | null;\r\n private filterPipeline: String3DFilterPipeline | null = null;\r\n private filterCache: Map<string, FilterCacheEntry> = new Map();\r\n private frameId = 0;\r\n private lastFrameTime = performance.now();\r\n private avgFrameMs = 16.7;\r\n private qualityScale = 1;\r\n private lastQualityChange = 0;\r\n private filterLayer = 1;\r\n\r\n constructor(container: HTMLElement, engine: I3DEngine) {\r\n this.engine = engine;\r\n this._container = container;\r\n const { width, height } = container.getBoundingClientRect();\r\n this._width = width;\r\n this._height = height;\r\n\r\n this._renderer = engine.createRenderer({\r\n antialias: true,\r\n alpha: true,\r\n logarithmicDepthBuffer: true,\r\n });\r\n const configuredPixelRatio = this.engine.getRecommendedPixelRatio?.();\r\n const pixelRatio =\r\n typeof configuredPixelRatio === \"number\" && Number.isFinite(configuredPixelRatio)\r\n ? Math.max(0.1, configuredPixelRatio)\r\n : 1;\r\n this._renderer.setPixelRatio(pixelRatio);\r\n this._renderer.setSize(width, height);\r\n this.engine.configureRenderer?.(this._renderer, {\r\n width,\r\n height,\r\n pixelRatio,\r\n container: this._container,\r\n });\r\n\r\n this.postProcessRuntime = resolvePostProcessRuntime(this.engine, this._renderer);\r\n }\r\n\r\n public attach(): void {\r\n this._container.appendChild(this._renderer.domElement);\r\n }\r\n\r\n public render(\r\n scene: String3DScene,\r\n camera: String3DCamera,\r\n filterTargets: String3DFilterTarget[] = [],\r\n ): void {\r\n if (filterTargets.length === 0) {\r\n this._renderer.render(scene.getScene(), camera.camera);\r\n return;\r\n }\r\n\r\n const pipeline = this.ensureFilterPipeline();\r\n if (!pipeline?.isSupported()) {\r\n this._renderer.render(scene.getScene(), camera.camera);\r\n return;\r\n }\r\n\r\n this.frameId += 1;\r\n this.updateQuality(filterTargets.length, pipeline);\r\n\r\n const allObjects = scene.getAllObjects();\r\n const visibility = new Map<I3DObject, boolean | undefined>();\r\n allObjects.forEach((obj) => {\r\n const anyObj = obj.object as any;\r\n if (\"visible\" in anyObj) {\r\n visibility.set(obj.object, anyObj.visible);\r\n }\r\n });\r\n\r\n const filteredSet = new Set<I3DObject>();\r\n filterTargets.forEach((target) => {\r\n this.collectSubtreeObjects(target.object, filteredSet);\r\n });\r\n\r\n allObjects.forEach((obj) => {\r\n if (filteredSet.has(obj.object)) {\r\n this.setVisible(obj.object, false);\r\n }\r\n });\r\n\r\n const rendererAny = this._renderer as any;\r\n const prevAutoClear = rendererAny.autoClear;\r\n rendererAny.autoClear = true;\r\n this.postProcessRuntime?.setRenderTarget(this._renderer, null);\r\n this.postProcessRuntime?.clear(this._renderer, true, true, true);\r\n this._renderer.render(scene.getScene(), camera.camera);\r\n\r\n rendererAny.autoClear = false;\r\n\r\n allObjects.forEach((obj) => {\r\n const originalVisible = visibility.get(obj.object);\r\n if (typeof originalVisible !== \"undefined\") {\r\n this.setVisible(obj.object, originalVisible);\r\n }\r\n });\r\n\r\n const lights = allObjects.filter((obj) => obj.type.endsWith(\"Light\"));\r\n const supportsLayerIsolation =\r\n this.engine.supportsObjectLayerIsolation?.(\r\n camera.camera,\r\n allObjects.map((entry) => entry.object),\r\n ) === true &&\r\n typeof this.engine.beginObjectLayerIsolation === \"function\" &&\r\n typeof this.engine.endObjectLayerIsolation === \"function\";\r\n let usedVisibilityFallback = false;\r\n\r\n filterTargets.forEach((target) => {\r\n const cache = this.filterCache.get(target.object.id);\r\n const canUseCache =\r\n !target.dirty &&\r\n cache &&\r\n cache.effectsKey === target.effectsKey &&\r\n cache.qualityScale === this.qualityScale;\r\n\r\n if (canUseCache) {\r\n cache.lastUsedFrame = this.frameId;\r\n pipeline.renderToScreen(cache.target);\r\n return;\r\n }\r\n\r\n const effects = this.injectEffectContext(\r\n target.object.el as HTMLElement | undefined,\r\n target.effects,\r\n );\r\n\r\n const allowed = new Set<I3DObject>();\r\n this.collectSubtreeObjects(target.object, allowed);\r\n\r\n let isolationState: I3DLayerIsolationState | null = null;\r\n if (supportsLayerIsolation) {\r\n const subtree = target.object.getSubtreeObjects();\r\n isolationState =\r\n this.engine.beginObjectLayerIsolation?.(\r\n camera.camera,\r\n subtree,\r\n lights.map((entry) => entry.object),\r\n this.filterLayer,\r\n ) || null;\r\n }\r\n\r\n if (!isolationState) {\r\n usedVisibilityFallback = true;\r\n allObjects.forEach((obj) => {\r\n const originalVisible = visibility.get(obj.object);\r\n if (originalVisible === false) {\r\n this.setVisible(obj.object, false);\r\n return;\r\n }\r\n\r\n if (obj.type.endsWith(\"Light\")) {\r\n this.setVisible(obj.object, true);\r\n return;\r\n }\r\n\r\n this.setVisible(obj.object, allowed.has(obj.object));\r\n });\r\n }\r\n\r\n const input = pipeline.acquireTarget();\r\n this.postProcessRuntime?.setRenderTarget(this._renderer, input);\r\n this.postProcessRuntime?.clear(this._renderer, true, true, true);\r\n this._renderer.render(scene.getScene(), camera.camera);\r\n\r\n const output = pipeline.applyFilters(input, effects, this.qualityScale);\r\n this.postProcessRuntime?.setRenderTarget(this._renderer, null);\r\n pipeline.renderToScreen(output);\r\n\r\n if (isolationState) {\r\n this.engine.endObjectLayerIsolation?.(camera.camera, isolationState);\r\n }\r\n\r\n if (output !== input) {\r\n pipeline.releaseTarget(input);\r\n }\r\n\r\n const entry: FilterCacheEntry = {\r\n target: output,\r\n effectsKey: target.effectsKey,\r\n lastUsedFrame: this.frameId,\r\n qualityScale: this.qualityScale,\r\n };\r\n const existing = this.filterCache.get(target.object.id);\r\n if (existing && existing.target !== output) {\r\n pipeline.releaseTarget(existing.target);\r\n }\r\n this.filterCache.set(target.object.id, entry);\r\n });\r\n\r\n if (usedVisibilityFallback) {\r\n allObjects.forEach((obj) => {\r\n const originalVisible = visibility.get(obj.object);\r\n if (typeof originalVisible !== \"undefined\") {\r\n this.setVisible(obj.object, originalVisible);\r\n }\r\n });\r\n }\r\n\r\n rendererAny.autoClear = prevAutoClear;\r\n\r\n this.evictCache();\r\n }\r\n\r\n public resize(camera: String3DCamera): void {\r\n const { width, height } = this._container.getBoundingClientRect();\r\n this._width = width;\r\n this._height = height;\r\n this._renderer.setSize(width, height);\r\n camera.resize(width, height);\r\n this.filterPipeline?.resize(width, height);\r\n this.invalidateFilterCache();\r\n }\r\n\r\n public get width(): number {\r\n return this._width;\r\n }\r\n\r\n public get height(): number {\r\n return this._height;\r\n }\r\n\r\n public get renderer(): I3DRenderer {\r\n return this._renderer;\r\n }\r\n\r\n public destroy(): void {\r\n this._renderer.dispose();\r\n this.filterPipeline?.dispose();\r\n this.filterCache.clear();\r\n }\r\n\r\n private ensureFilterPipeline(): String3DFilterPipeline | null {\r\n const runtime = this.postProcessRuntime;\r\n if (!runtime || !this.canCreateFilterPipeline()) {\r\n return null;\r\n }\r\n if (!this.filterPipeline) {\r\n this.filterPipeline = new String3DFilterPipeline(\r\n this.engine,\r\n this._renderer,\r\n runtime,\r\n this._width,\r\n this._height,\r\n );\r\n this.filterPipeline.setScale(this.qualityScale);\r\n }\r\n return this.filterPipeline;\r\n }\r\n\r\n private canCreateFilterPipeline(): boolean {\r\n return !!this.postProcessRuntime;\r\n }\r\n\r\n private collectSubtreeObjects(\r\n object: import(\"./String3DObject\").String3DObject,\r\n set: Set<I3DObject>,\r\n ): void {\r\n set.add(object.object);\r\n object.children.forEach((child) => this.collectSubtreeObjects(child, set));\r\n }\r\n\r\n private setVisible(object: I3DObject, visible: boolean): void {\r\n const anyObj = object as any;\r\n if (\"visible\" in anyObj) {\r\n anyObj.visible = visible;\r\n }\r\n }\r\n\r\n private getFilterCenter(el: HTMLElement | undefined): [number, number] {\r\n if (!el || !this._width || !this._height) return [0.5, 0.5];\r\n const cached = (el as any).__layoutCache;\r\n const rect = cached ? cached.rect : el.getBoundingClientRect();\r\n const cx = (rect.left + rect.width / 2) / this._width;\r\n const cy = 1 - (rect.top + rect.height / 2) / this._height;\r\n const clamp = (value: number) => Math.max(0, Math.min(1, value));\r\n return [clamp(cx), clamp(cy)];\r\n }\r\n\r\n private injectEffectContext(\r\n el: HTMLElement | undefined,\r\n effects: String3DFilterEffect[],\r\n ): String3DFilterEffect[] {\r\n if (!effects.some((effect) => effect.type === \"custom\")) {\r\n return effects;\r\n }\r\n const center = this.getFilterCenter(el);\r\n let changed = false;\r\n const next = effects.map((effect) => {\r\n if (effect.type !== \"custom\") return effect;\r\n if (effect.uniforms && \"uCenter\" in effect.uniforms) return effect;\r\n const uniforms = { ...(effect.uniforms || {}), uCenter: center };\r\n changed = true;\r\n return { ...effect, uniforms };\r\n });\r\n return changed ? next : effects;\r\n }\r\n\r\n private updateQuality(filterCount: number, pipeline: String3DFilterPipeline): void {\r\n const now = performance.now();\r\n const dt = Math.max(0.1, now - this.lastFrameTime);\r\n this.lastFrameTime = now;\r\n this.avgFrameMs = this.avgFrameMs * 0.9 + dt * 0.1;\r\n\r\n const fps = 1000 / this.avgFrameMs;\r\n const countScale = Math.max(0.75, 1 - Math.min(0.4, filterCount * 0.03));\r\n let targetScale = countScale;\r\n\r\n if (fps < 48) targetScale = Math.max(0.75, countScale - 0.1);\r\n if (fps < 40) targetScale = Math.max(0.75, countScale - 0.2);\r\n if (fps > 58) targetScale = Math.min(1, countScale + 0.05);\r\n\r\n if (Math.abs(targetScale - this.qualityScale) >= 0.05 && now - this.lastQualityChange > 300) {\r\n this.qualityScale = targetScale;\r\n this.lastQualityChange = now;\r\n pipeline.setScale(this.qualityScale);\r\n this.invalidateFilterCache();\r\n }\r\n }\r\n\r\n private invalidateFilterCache(): void {\r\n if (!this.filterPipeline) return;\r\n this.filterCache.forEach((entry) => {\r\n this.filterPipeline?.releaseTarget(entry.target);\r\n });\r\n this.filterCache.clear();\r\n }\r\n\r\n private evictCache(): void {\r\n if (!this.filterPipeline) return;\r\n const maxAge = 120;\r\n this.filterCache.forEach((entry, key) => {\r\n if (this.frameId - entry.lastUsedFrame > maxAge) {\r\n this.filterPipeline?.releaseTarget(entry.target);\r\n this.filterCache.delete(key);\r\n }\r\n });\r\n }\r\n}\r\n","import {\r\n I3DEngine,\r\n I3DObject,\r\n I3DMaterial,\r\n I3DGeometry,\r\n I3DQuaternion,\r\n I3DVector3,\r\n I3DEuler,\r\n I3DMatrix4,\r\n I3DBox3,\r\n} from \"./abstractions/I3DEngine\";\r\n\r\nexport class String3DObject {\n public id: string;\n public type: string;\n private _object: I3DObject;\n private _material?: I3DMaterial;\n private _geometry?: I3DGeometry;\n private _texture?: any;\n private _uniforms: Record<string, { value: any }> = {};\r\n private _originalBoundingBox?: I3DBox3 | null;\r\n private _quaternion: I3DQuaternion;\r\n private _originalSize: I3DVector3;\r\n private _bbox: I3DBox3;\r\n public el: any;\r\n private _children: String3DObject[] = [];\n private _flatObjectsCache: I3DObject[] | null = null;\n private _subtreeCache: I3DObject[] | null = null;\n private engine: I3DEngine;\r\n\r\n public get children(): String3DObject[] {\r\n return this._children;\r\n }\r\n\r\n constructor(\n id: string,\n type: string,\n object: I3DObject,\n engine: I3DEngine,\n options: { material?: I3DMaterial; geometry?: I3DGeometry; texture?: any } = {}\n ) {\n this.id = id;\n this.type = type;\n this._object = object;\n this.engine = engine;\n this._material = options.material;\n this._geometry = options.geometry;\n this._texture = options.texture;\n this._quaternion = engine.createQuaternion();\n this._originalSize = engine.createVector3();\n this._bbox = engine.createBox3();\n this.updateBoundingBox();\n }\n\r\n public get object(): I3DObject {\r\n return this._object;\r\n }\r\n\r\n public get material(): I3DMaterial | undefined {\r\n return this._material;\r\n }\r\n\r\n public get originalSize(): I3DVector3 {\r\n return this._originalSize.clone();\r\n }\r\n\r\n public get boundingBox(): I3DBox3 {\r\n return this._bbox.clone();\r\n }\r\n\r\n public addChild(child: String3DObject): void {\n this._children.push(child);\n this.object.add(child.object);\n this.invalidateFlatCache();\n this.invalidateSubtreeCache();\n }\n\r\n public getWorldMatrix(): I3DMatrix4 {\r\n return this._object.matrixWorld.clone();\r\n }\r\n\r\n public getWorldPosition(): I3DVector3 {\r\n return this.engine.createVector3().setFromMatrixPosition(this._object.matrixWorld);\r\n }\r\n\r\n public getOriginalBoundingBox(): I3DBox3 {\r\n if (!this._originalBoundingBox) {\r\n const originalScale = this.object.scale.clone();\r\n this.object.scale.set(1, 1, 1);\r\n this.object.updateMatrixWorld(true);\r\n this._originalBoundingBox = this.engine.computeBoundingBoxRecursively(this.object);\r\n this.object.scale.copy(originalScale);\r\n this.object.updateMatrixWorld(true);\r\n }\r\n return this._originalBoundingBox!.clone();\r\n }\r\n\r\n public syncTransformFromMatrix(matrix: I3DMatrix4): void {\r\n const pos = this.engine.createVector3();\r\n const quat = this.engine.createQuaternion();\r\n const scale = this.engine.createVector3();\r\n matrix.decompose(pos, quat, scale);\r\n this._object.position.copy(pos);\r\n this._object.quaternion.copy(quat);\r\n this._object.scale.copy(scale);\r\n this._object.updateMatrix();\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public applyWorldTransform(\r\n position: I3DVector3,\r\n quaternion: I3DQuaternion,\r\n scale: I3DVector3\r\n ): void {\r\n this._object.position.copy(position);\r\n this._object.quaternion.copy(quaternion);\r\n this._object.scale.copy(scale);\r\n this._object.updateMatrix();\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public set quaternion(quaternion: I3DQuaternion) {\r\n this._quaternion.copy(quaternion);\r\n this._object.quaternion.copy(this._quaternion);\r\n this._object.updateMatrixWorld();\r\n }\r\n\r\n public set position(position: I3DVector3) {\r\n this._object.position.copy(position);\r\n }\r\n\r\n public set scale(scale: I3DVector3) {\r\n this._object.scale.copy(scale);\r\n }\r\n\r\n public set rotation(euler: I3DEuler) {\r\n this._object.rotation.copy(euler);\r\n }\r\n\r\n public set opacity(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"opacity\" in mat.material) {\r\n mat.material.opacity = value;\r\n }\r\n }\r\n\r\n public set metalness(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"metalness\" in mat.material) {\r\n mat.material.metalness = value;\r\n }\r\n }\r\n\r\n public set roughness(value: number) {\r\n const mat = this._object as any;\r\n if (mat.material && \"roughness\" in mat.material) {\r\n mat.material.roughness = value;\r\n }\r\n }\r\n\r\n public set texture(texture: any) {\n this._texture = texture;\n if ((this._object as any).isMesh && texture?.applyTexture) {\n texture.applyTexture(this._object);\n }\n }\n\n public set material(material: I3DMaterial | undefined) {\n this._material = material;\n }\n\n public set geometry(geometry: I3DGeometry | undefined) {\n this._geometry = geometry;\n }\n\n public updateBoundingBox(): void {\n this._bbox.setFromObject(this._object);\n this._bbox.getSize(this._originalSize);\n }\n\n public destroy(): void {\n this.disposeObjectResources(this._object);\n this._texture?.dispose?.();\n this._material?.dispose();\n this._geometry?.dispose();\n this._subtreeCache = null;\n }\n\n public getFlatObjects(): I3DObject[] {\n if (this._flatObjectsCache) return this._flatObjectsCache;\n const result: I3DObject[] = [];\n const walk = (obj: String3DObject): void => {\n result.push(obj.object);\n obj.children.forEach((child) => walk(child));\n };\n walk(this);\n this._flatObjectsCache = result;\n return result;\n }\n\n public getSubtreeObjects(): I3DObject[] {\n if (this._subtreeCache) return this._subtreeCache;\n const result: I3DObject[] = [];\n const anyObj = this._object as any;\n result.push(this._object);\n if (typeof anyObj.traverse === \"function\") {\n anyObj.traverse((child: any) => {\n if (child && child !== this._object) {\n result.push(child as I3DObject);\n }\n });\n }\n this._subtreeCache = result;\n return result;\n }\n\n private invalidateFlatCache(): void {\n this._flatObjectsCache = null;\n }\n\n private invalidateSubtreeCache(): void {\n this._subtreeCache = null;\n }\n\n private disposeObjectResources(object: I3DObject): void {\n const anyObj = object as any;\n if (anyObj?.geometry?.dispose) {\n anyObj.geometry.dispose();\n }\n const material = anyObj?.material;\n if (Array.isArray(material)) {\n material.forEach((mat) => mat?.dispose?.());\n } else if (material?.dispose) {\n material.dispose();\n }\n if (typeof anyObj?.traverse === \"function\") {\n anyObj.traverse((child: any) => {\n if (child?.geometry?.dispose) {\n child.geometry.dispose();\n }\n const childMat = child?.material;\n if (Array.isArray(childMat)) {\n childMat.forEach((mat: any) => mat?.dispose?.());\n } else if (childMat?.dispose) {\n childMat.dispose();\n }\n });\n }\n }\n}\n","export class StyleReader {\r\n private styleMap: any;\r\n private style: CSSStyleDeclaration;\r\n\r\n constructor(el: HTMLElement) {\r\n this.styleMap = (el as any).computedStyleMap?.();\r\n this.style = getComputedStyle(el);\r\n }\r\n\r\n readNumber(prop: string, fallback: number): number {\r\n const mapValue = this.styleMap?.get?.(prop);\r\n if (mapValue !== undefined && mapValue !== null) {\r\n const val = typeof mapValue === \"object\" ? (mapValue as any).value : mapValue;\r\n const num = typeof val === \"number\" ? val : Number.parseFloat(val);\r\n if (!Number.isNaN(num)) return num;\r\n }\r\n const num = Number.parseFloat(this.style.getPropertyValue(prop));\r\n return Number.isNaN(num) ? fallback : num;\r\n }\r\n\r\n readString(prop: string, fallback = \"\"): string {\r\n const mapValue = this.styleMap?.get?.(prop);\r\n const val = mapValue && typeof mapValue === \"object\" ? (mapValue as any).value : mapValue;\r\n if (typeof val === \"string\") return this.stripQuotes(val.trim()) || fallback;\r\n const raw = this.style.getPropertyValue(prop).trim();\r\n return this.stripQuotes(raw) || fallback;\r\n }\r\n\r\n private stripQuotes(value: string): string {\r\n if (\r\n (value.startsWith(\"'\") && value.endsWith(\"'\")) ||\r\n (value.startsWith('\"') && value.endsWith('\"'))\r\n ) {\r\n return value.slice(1, -1);\r\n }\r\n return value;\r\n }\r\n\r\n readBoolean(prop: string, fallback = false): boolean {\r\n const raw = this.readString(prop, \"\");\r\n if (!raw) return fallback;\r\n const norm = raw.toLowerCase();\r\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\r\n ? true\r\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\r\n ? false\r\n : fallback;\r\n }\r\n}\r\n\r\nexport function readNumberStyle(el: HTMLElement, prop: string, fallback: number): number {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const mapValue = styleMap?.get?.(prop);\r\n if (mapValue !== undefined) {\r\n if (typeof mapValue === \"number\") return mapValue;\r\n if (typeof mapValue === \"string\") {\r\n const parsed = Number.parseFloat(mapValue);\r\n if (!Number.isNaN(parsed)) return parsed;\r\n }\r\n if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"number\") return value;\r\n if (typeof value === \"string\") {\r\n const parsed = Number.parseFloat(value);\r\n if (!Number.isNaN(parsed)) return parsed;\r\n }\r\n }\r\n }\r\n\r\n const style = getComputedStyle(el);\r\n const raw = style.getPropertyValue(prop);\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isNaN(parsed) ? fallback : parsed;\r\n}\r\n\r\nfunction stripQuotes(value: string): string {\r\n if (\r\n (value.startsWith(\"'\") && value.endsWith(\"'\")) ||\r\n (value.startsWith('\"') && value.endsWith('\"'))\r\n ) {\r\n return value.slice(1, -1);\r\n }\r\n return value;\r\n}\r\n\r\nexport function readStringStyle(el: HTMLElement, prop: string, fallback = \"\"): string {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const mapValue = styleMap?.get?.(prop);\r\n if (typeof mapValue === \"string\") {\r\n return stripQuotes(mapValue.trim());\r\n }\r\n if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"string\") {\r\n return stripQuotes(value.trim());\r\n }\r\n }\r\n const style = getComputedStyle(el).getPropertyValue(prop);\r\n const result = style ? stripQuotes(style.trim()) : \"\";\r\n return result || fallback;\r\n}\r\n\r\nexport function readBooleanStyle(el: HTMLElement, prop: string, fallback = false): boolean {\r\n const raw = readStringStyle(el, prop, \"\");\r\n if (!raw) return fallback;\r\n const normalized = raw.toLowerCase().trim();\r\n if (normalized === \"true\" || normalized === \"1\" || normalized === \"yes\") return true;\r\n if (normalized === \"false\" || normalized === \"0\" || normalized === \"no\") return false;\r\n return fallback;\r\n}\r\n\r\nexport function readFilterRaw(el: HTMLElement): string {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n let raw = \"\";\r\n const mapValue = styleMap?.get?.(\"--filter\");\r\n if (mapValue !== undefined) {\r\n if (typeof mapValue === \"string\") {\r\n raw = mapValue;\r\n } else if (mapValue && typeof mapValue === \"object\") {\r\n const value = (mapValue as any).value;\r\n if (typeof value === \"string\") raw = value;\r\n }\r\n }\r\n if (!raw) {\r\n raw = getComputedStyle(el).getPropertyValue(\"--filter\") || \"\";\r\n }\r\n raw = raw.trim();\r\n return raw;\r\n}\r\n","export type UniformType =\r\n | \"float\"\r\n | \"int\"\r\n | \"vec2\"\r\n | \"vec3\"\r\n | \"vec4\"\r\n | \"color\"\r\n | \"texture\"\r\n | \"mat3\"\r\n | \"mat4\";\r\n\r\nexport type UniformDefinition = {\r\n type: UniformType;\r\n value: any;\r\n css?: string;\r\n};\r\n\r\nexport type ShaderInjectionPoint =\r\n | \"vertex_pars\"\r\n | \"vertex_header\"\r\n | \"vertex_transform\"\r\n | \"vertex_output\"\r\n | \"fragment_pars\"\r\n | \"fragment_header\"\r\n | \"fragment_color\"\r\n | \"fragment_normal\"\r\n | \"fragment_emissive\"\r\n | \"fragment_roughness\"\r\n | \"fragment_metalness\"\r\n | \"fragment_ao\"\r\n | \"fragment_transmission\"\r\n | \"fragment_lights\"\r\n | \"fragment_output\";\r\n\r\nexport type ShaderInjection = {\r\n point: ShaderInjectionPoint;\r\n code: string;\r\n order?: number;\r\n};\r\n\r\nexport type MaterialBlendMode = \"normal\" | \"additive\" | \"subtractive\" | \"multiply\";\r\nexport type MaterialSide = \"front\" | \"back\" | \"double\";\r\n\r\nexport type String3DCustomMaterialDefinition = {\r\n name: string;\r\n\r\n extends?: \"basic\" | \"standard\" | \"physical\" | \"transmission\" | \"shader\";\r\n\r\n vertexShader?: string;\r\n fragmentShader?: string;\r\n\r\n injections?: ShaderInjection[];\r\n\r\n uniforms?: Record<string, UniformDefinition>;\r\n\r\n properties?: {\r\n transparent?: boolean;\r\n opacity?: number;\r\n side?: MaterialSide;\r\n depthWrite?: boolean;\r\n depthTest?: boolean;\r\n blending?: MaterialBlendMode;\r\n wireframe?: boolean;\r\n color?: string | number;\r\n emissive?: string | number;\r\n metalness?: number;\r\n roughness?: number;\r\n transmission?: number;\r\n thickness?: number;\r\n ior?: number;\r\n reflectivity?: number;\r\n clearcoat?: number;\r\n clearcoatRoughness?: number;\r\n attenuationDistance?: number;\r\n attenuationColor?: string | number;\r\n transmissionSamples?: number;\r\n transmissionSampler?: boolean;\r\n };\r\n\r\n lights?: boolean;\r\n\r\n parse?: (element: HTMLElement, style: CSSStyleDeclaration) => Record<string, any>;\r\n};\r\n\r\nexport class String3DCustomMaterialRegistry {\r\n private static materials: Map<string, String3DCustomMaterialDefinition> = new Map();\r\n private static registeredCssVars: Set<string> = new Set();\r\n\r\n static register(definition: String3DCustomMaterialDefinition): void {\r\n const name = definition.name.trim().toLowerCase();\r\n if (!name) {\r\n throw new Error(\"[String3D] Custom material name is required.\");\r\n }\r\n this.materials.set(name, { ...definition, name });\r\n this.registerCssVarsForMaterial(definition);\r\n }\r\n\r\n private static registerCssVarsForMaterial(definition: String3DCustomMaterialDefinition): void {\r\n const css = (globalThis as any).CSS;\r\n if (!css?.registerProperty) return;\r\n\r\n const uniforms = definition.uniforms || {};\r\n for (const def of Object.values(uniforms)) {\r\n const cssVar = def.css?.trim();\r\n if (!cssVar || !cssVar.startsWith(\"--\")) continue;\r\n if (this.registeredCssVars.has(cssVar)) continue;\r\n\r\n const syntax = this.resolveCssSyntax(def.type);\r\n\r\n try {\r\n css.registerProperty({\r\n name: cssVar,\r\n syntax,\r\n inherits: false,\r\n initialValue: this.defaultCssInitialValue(def),\r\n });\r\n this.registeredCssVars.add(cssVar);\r\n } catch (err) { }\r\n }\r\n }\r\n\r\n private static resolveCssSyntax(type: UniformType): string {\r\n switch (type) {\r\n case \"color\":\r\n return \"<color>\";\r\n case \"float\":\r\n case \"int\":\r\n return \"<number>\";\r\n default:\r\n return \"*\";\r\n }\r\n }\r\n\r\n private static defaultCssInitialValue(def: UniformDefinition): string {\r\n if (def.type === \"color\") {\r\n if (typeof def.value === \"string\") return def.value;\r\n return \"#000000\";\r\n }\r\n if (def.type === \"float\" || def.type === \"int\") {\r\n return typeof def.value === \"number\" ? String(def.value) : \"0\";\r\n }\r\n return \"initial\";\r\n }\r\n\r\n static get(name: string): String3DCustomMaterialDefinition | undefined {\r\n return this.materials.get(name.trim().toLowerCase());\r\n }\r\n\r\n static has(name: string): boolean {\r\n return this.materials.has(name.trim().toLowerCase());\r\n }\r\n\r\n static list(): String3DCustomMaterialDefinition[] {\r\n return Array.from(this.materials.values());\r\n }\r\n\r\n static unregister(name: string): boolean {\r\n return this.materials.delete(name.trim().toLowerCase());\r\n }\r\n}\r\n","import type {\r\n String3DCustomMaterialDefinition,\r\n UniformDefinition,\r\n ShaderInjection,\r\n} from \"./String3DCustomMaterial\";\r\n\r\nexport type MaterialUpdateCallback = (uniforms: Record<string, any>) => void;\r\n\r\nexport interface IMaterialInstance {\r\n material: any;\r\n definition: String3DCustomMaterialDefinition;\r\n update: MaterialUpdateCallback;\r\n dispose: () => void;\r\n}\r\n\r\nexport interface IMaterialFactory {\r\n supports(definition: String3DCustomMaterialDefinition): boolean;\r\n\r\n create(\r\n definition: String3DCustomMaterialDefinition,\r\n initialUniforms?: Record<string, any>,\r\n ): IMaterialInstance;\r\n\r\n parseUniformsFromCSS(\r\n definition: String3DCustomMaterialDefinition,\r\n element: HTMLElement,\r\n style: CSSStyleDeclaration,\r\n ): Record<string, any>;\r\n\r\n getMaterialDefinition?(material: any): String3DCustomMaterialDefinition | null;\r\n\r\n applyUniforms?(\r\n material: any,\r\n definition: String3DCustomMaterialDefinition,\r\n values: Record<string, any>,\r\n ): void;\r\n\r\n isShaderMaterial?(material: any): boolean;\r\n}\r\n\r\nexport function parseUniformValue(\r\n def: UniformDefinition,\r\n cssValue: string | null | undefined,\r\n): any {\r\n if (cssValue === null || cssValue === undefined || cssValue === \"\" || cssValue === \"none\") {\r\n return def.value;\r\n }\r\n\r\n const trimmed = cssValue.trim();\r\n\r\n switch (def.type) {\r\n case \"float\":\r\n case \"int\": {\r\n const num = parseFloat(trimmed);\r\n return isNaN(num) ? def.value : num;\r\n }\r\n case \"vec2\": {\r\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\r\n if (parts.length >= 2 && parts.every((n) => !isNaN(n))) {\r\n return [parts[0], parts[1]];\r\n }\r\n return def.value;\r\n }\r\n case \"vec3\": {\r\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\r\n if (parts.length >= 3 && parts.every((n) => !isNaN(n))) {\r\n return [parts[0], parts[1], parts[2]];\r\n }\r\n return def.value;\r\n }\r\n case \"vec4\": {\r\n const parts = trimmed.split(/[\\s,]+/).map((s) => parseFloat(s.trim()));\r\n if (parts.length >= 4 && parts.every((n) => !isNaN(n))) {\r\n return [parts[0], parts[1], parts[2], parts[3]];\r\n }\r\n return def.value;\r\n }\r\n case \"color\": {\r\n return parseColorValue(trimmed) ?? def.value;\r\n }\r\n case \"texture\": {\r\n const match = trimmed.match(/url\\(['\"]?(.*?)['\"]?\\)/);\r\n return match ? match[1] : trimmed || def.value;\r\n }\r\n default:\r\n return def.value;\r\n }\r\n}\r\n\r\nfunction parseColorValue(value: string): [number, number, number] | null {\r\n if (value.startsWith(\"#\")) {\r\n const hex = value.slice(1);\r\n if (hex.length === 3) {\r\n const r = parseInt(hex[0] + hex[0], 16) / 255;\r\n const g = parseInt(hex[1] + hex[1], 16) / 255;\r\n const b = parseInt(hex[2] + hex[2], 16) / 255;\r\n return [r, g, b];\r\n }\r\n if (hex.length === 6) {\r\n const r = parseInt(hex.slice(0, 2), 16) / 255;\r\n const g = parseInt(hex.slice(2, 4), 16) / 255;\r\n const b = parseInt(hex.slice(4, 6), 16) / 255;\r\n return [r, g, b];\r\n }\r\n }\r\n\r\n const rgbMatch = value.match(/rgba?\\(\\s*(\\d+)\\s*,\\s*(\\d+)\\s*,\\s*(\\d+)/);\r\n if (rgbMatch) {\r\n return [parseInt(rgbMatch[1]) / 255, parseInt(rgbMatch[2]) / 255, parseInt(rgbMatch[3]) / 255];\r\n }\r\n\r\n return null;\r\n}\r\n\r\nexport function collectUniformsFromCSS(\r\n definition: String3DCustomMaterialDefinition,\r\n element: HTMLElement,\r\n style: CSSStyleDeclaration,\r\n): Record<string, any> {\r\n const result: Record<string, any> = {};\r\n\r\n if (definition.parse) {\r\n const parsed = definition.parse(element, style);\r\n Object.assign(result, parsed);\r\n }\r\n\r\n if (definition.uniforms) {\r\n for (const [key, def] of Object.entries(definition.uniforms)) {\r\n if (def.css) {\r\n const cssValue = style.getPropertyValue(def.css).trim();\r\n result[key] = parseUniformValue(def, cssValue);\r\n } else if (!(key in result)) {\r\n result[key] = def.value;\r\n }\r\n }\r\n }\r\n\r\n return result;\r\n}\r\n\r\nexport function mergeInjections(injections: ShaderInjection[]): Map<string, string> {\r\n const grouped = new Map<string, ShaderInjection[]>();\r\n\r\n for (const injection of injections) {\r\n const list = grouped.get(injection.point) || [];\r\n list.push(injection);\r\n grouped.set(injection.point, list);\r\n }\r\n\r\n const result = new Map<string, string>();\r\n\r\n for (const [point, list] of grouped) {\r\n const sorted = list.sort((a, b) => (a.order ?? 0) - (b.order ?? 0));\r\n result.set(point, sorted.map((i) => i.code).join(\"\\n\"));\r\n }\r\n\r\n return result;\r\n}\r\n","import {\r\n I3DCustomMaterialRegistryRuntime,\r\n I3DEngine,\r\n I3DScene,\r\n I3DLight,\r\n I3DMaterial,\r\n I3DModelLoader,\r\n I3DModelLoaderOptions,\r\n I3DVector3,\r\n} from \"./abstractions/I3DEngine\";\r\nimport { String3DObject } from \"./String3DObject\";\r\nimport { readBooleanStyle, readNumberStyle, readStringStyle } from \"../modules/string3d/styleUtils\";\r\nimport { String3DCustomMaterialRegistry, IMaterialInstance } from \"./materials\";\r\nimport type { String3DSynchronizer } from \"./synchronizer/String3DSynchronizer\";\r\n\r\ntype String3DSourceObject = {\r\n id: string;\r\n htmlElement: HTMLElement | null;\r\n getProperty<T>(name: string): T;\r\n};\r\n\r\nexport interface String3DSceneOptions {\r\n modelLoader?: I3DModelLoader;\r\n modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n}\r\n\r\nexport class String3DScene {\r\n private _scene: I3DScene;\r\n private _objects: Map<string, String3DObject> = new Map();\r\n private _rootObjects: String3DObject[] = [];\r\n private _elementMap: Map<string, HTMLElement> = new Map();\r\n private _materialInstances: Map<string, IMaterialInstance> = new Map();\r\n private engine: I3DEngine;\r\n private _modelLoader?: I3DModelLoader;\r\n private _modelLoaderFactory?: (engine: I3DEngine, type?: string) => I3DModelLoader;\r\n private _modelLoaderCache: Map<string, I3DModelLoader> = new Map();\r\n private _synchronizer?: String3DSynchronizer;\r\n private customMaterialRegistry: I3DCustomMaterialRegistryRuntime;\r\n\r\n public get rootObjects(): String3DObject[] {\r\n return this._rootObjects;\r\n }\r\n\r\n constructor(engine: I3DEngine, options: String3DSceneOptions = {}) {\r\n this.engine = engine;\r\n this.customMaterialRegistry =\r\n this.engine.getCustomMaterialRegistry?.() || String3DCustomMaterialRegistry;\r\n this._modelLoader = options.modelLoader;\r\n this._modelLoaderFactory = options.modelLoaderFactory;\r\n this._scene = engine.createScene();\r\n }\r\n\r\n public setSynchronizer(synchronizer: String3DSynchronizer): void {\r\n this._synchronizer = synchronizer;\r\n }\r\n\r\n public getScene(): I3DScene {\r\n return this._scene;\r\n }\r\n\r\n public getObject(id: string): String3DObject | undefined {\r\n return this._objects.get(id);\r\n }\r\n\r\n public getObjectForElement(element: HTMLElement): String3DObject | undefined {\r\n for (const [id, el] of this._elementMap) {\r\n if (el === element) {\r\n return this._objects.get(id);\r\n }\r\n }\r\n return undefined;\r\n }\r\n\r\n public getAllObjects(): String3DObject[] {\r\n const result: String3DObject[] = [];\r\n const walk = (obj: String3DObject): void => {\r\n result.push(obj);\r\n obj.children.forEach((child) => walk(child));\r\n };\r\n this._rootObjects.forEach((obj) => walk(obj));\r\n return result;\r\n }\r\n\r\n public hasObject(id: string): boolean {\r\n return this._objects.has(id);\r\n }\r\n\r\n public deleteObject(id: string): boolean {\r\n const obj = this._objects.get(id);\r\n if (obj) {\r\n const element = this._elementMap.get(id);\r\n if (element && this._synchronizer) {\r\n this._synchronizer.cleanupElement(element, obj);\r\n }\r\n\r\n this._scene.remove(obj.object);\r\n this._objects.delete(id);\r\n this._elementMap.delete(id);\r\n this._rootObjects = this._rootObjects.filter((root) => root !== obj);\r\n obj.destroy();\r\n return true;\r\n }\r\n return false;\r\n }\r\n\r\n public createFromElement(object: String3DSourceObject): void {\r\n const type = object.getProperty<string>(\"3d\");\r\n if (!type) return;\r\n\r\n const element = object.htmlElement;\r\n if (!element) return;\r\n\r\n const onAdd = (added3DObject: String3DObject) => {\r\n if (added3DObject) {\r\n const parentId = object.getProperty<string>(\"parentId\");\r\n if (parentId == null) {\r\n this._scene.add(added3DObject.object);\r\n this._rootObjects.push(added3DObject);\r\n } else {\r\n this._objects.get(parentId)?.addChild(added3DObject);\r\n }\r\n this._objects.set(object.id, added3DObject);\r\n this._elementMap.set(object.id, element);\r\n added3DObject.el = element;\r\n }\r\n };\r\n\r\n try {\r\n switch (type) {\r\n case \"group\":\r\n this.createGroup(object, onAdd);\r\n break;\r\n case \"pointLight\":\r\n this.createLight(object, \"point\", onAdd);\r\n break;\r\n case \"ambientLight\":\r\n this.createLight(object, \"ambient\", onAdd);\r\n break;\r\n case \"directionalLight\":\r\n this.createLight(object, \"directional\", onAdd);\r\n break;\r\n case \"spotLight\":\r\n this.createLight(object, \"spot\", onAdd);\r\n break;\r\n case \"hemisphereLight\":\r\n this.createLight(object, \"hemisphere\", onAdd);\r\n break;\r\n case \"model\":\r\n this.createModel(object, onAdd);\r\n break;\r\n case \"box\":\r\n this.createBox(object, onAdd);\r\n break;\r\n case \"sphere\":\r\n this.createSphere(object, onAdd);\r\n break;\r\n case \"plane\":\r\n this.createPlane(object, onAdd);\r\n break;\r\n case \"cylinder\":\r\n this.createCylinder(object, onAdd);\r\n break;\r\n case \"particles\":\r\n this.createParticles(object, onAdd);\r\n break;\r\n case \"text\":\r\n this.createText(object, onAdd);\r\n break;\r\n case \"svg\":\r\n this.createSVG(object, onAdd);\r\n break;\r\n default:\r\n break;\r\n }\r\n } catch (error) {\r\n\r\n }\r\n }\r\n\r\n private createGroup(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const group = this.engine.createGroup();\r\n const obj = new String3DObject(object.id, \"group\", group, this.engine);\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createLight(\r\n object: String3DSourceObject,\r\n kind: \"point\" | \"ambient\" | \"directional\" | \"spot\" | \"hemisphere\",\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const element = object.htmlElement;\r\n const colorRaw = element ? readStringStyle(element, \"--light-color\", \"#ffffff\") : \"#ffffff\";\r\n const color = colorRaw && colorRaw !== \"none\" ? colorRaw : \"#ffffff\";\r\n const intensity = element ? readNumberStyle(element, \"--light-intensity\", 1) : 1;\r\n\r\n let light: I3DLight;\r\n if (kind === \"point\") {\r\n const distance = element ? readNumberStyle(element, \"--light-distance\", 1000) : 1000;\r\n const decay = element ? readNumberStyle(element, \"--light-decay\", 0) : 0;\r\n light = this.engine.createPointLight(color, intensity, distance, decay);\r\n } else if (kind === \"directional\") {\r\n light = this.engine.createDirectionalLight(color, intensity);\r\n } else if (kind === \"spot\") {\r\n const distance = element ? readNumberStyle(element, \"--light-distance\", 0) : 0;\r\n const angle = element ? readNumberStyle(element, \"--light-angle\", Math.PI / 3) : Math.PI / 3;\r\n const penumbra = element ? readNumberStyle(element, \"--light-penumbra\", 0) : 0;\r\n const decay = element ? readNumberStyle(element, \"--light-decay\", 1) : 1;\r\n light = this.engine.createSpotLight(color, intensity, distance, angle, penumbra, decay);\r\n } else if (kind === \"hemisphere\") {\r\n const groundRaw = element\r\n ? readStringStyle(element, \"--light-ground-color\", \"#ffffff\")\r\n : \"#ffffff\";\r\n const groundColor = groundRaw && groundRaw !== \"none\" ? groundRaw : \"#ffffff\";\r\n light = this.engine.createHemisphereLight(color, groundColor, intensity);\r\n } else {\r\n light = this.engine.createAmbientLight(color, intensity);\r\n }\r\n\r\n const castShadow = element ? readBooleanStyle(element, \"--shadow-cast\", false) : false;\r\n if (castShadow && light.shadow) {\r\n light.castShadow = true;\r\n const bias = element ? readNumberStyle(element, \"--shadow-bias\", 0) : 0;\r\n const mapSize = element ? readNumberStyle(element, \"--shadow-map-size\", 512) : 512;\r\n light.shadow.bias = bias;\r\n light.shadow.mapSize.width = mapSize;\r\n light.shadow.mapSize.height = mapSize;\r\n }\r\n\r\n const obj = new String3DObject(object.id, kind + \"Light\", light, this.engine);\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private applyShadowProps(object: String3DSourceObject, mesh: any): void {\r\n const element = object.htmlElement;\r\n const castShadow = element ? readBooleanStyle(element, \"--shadow-cast\", false) : false;\r\n const receiveShadow = element ? readBooleanStyle(element, \"--shadow-receive\", false) : false;\r\n mesh.castShadow = castShadow;\r\n mesh.receiveShadow = receiveShadow;\r\n }\r\n\r\n private createBox(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const geometry = this.engine.createBoxGeometry(1, 1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"box\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createSphere(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const quality = this.getGeometryQuality(object.htmlElement);\r\n const widthSegments = Math.max(3, Math.round(32 * quality));\r\n const heightSegments = Math.max(2, Math.round(32 * quality));\r\n const geometry = this.engine.createSphereGeometry(0.5, widthSegments, heightSegments);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"sphere\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createPlane(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const geometry = this.engine.createPlaneGeometry(1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"plane\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createCylinder(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): String3DObject {\r\n const quality = this.getGeometryQuality(object.htmlElement);\r\n const segments = Math.max(3, Math.round(32 * quality));\r\n const geometry = this.engine.createCylinderGeometry(0.5, 0.5, 1, segments);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n const obj = new String3DObject(object.id, \"cylinder\", mesh, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n return obj;\r\n }\r\n\r\n private createModel(object: String3DSourceObject, onAdd: (obj: String3DObject) => void): void {\r\n const modelPath = object.getProperty<string>(\"3d-model\");\r\n if (!modelPath) return;\r\n\r\n const loaderType = object.getProperty<string>(\"3d-model-loader\") || undefined;\r\n const loader = this.resolveModelLoader(loaderType);\r\n if (!loader) {\r\n return;\r\n }\r\n\r\n const element = object.htmlElement;\r\n if (element) {\r\n const loaderOptions = this.parseModelLoaderOptions(element);\r\n if (loaderOptions) {\r\n this.engine.configureModelLoader?.(loader, loaderOptions);\r\n }\r\n }\r\n const shouldCenter = object.getProperty<boolean>(\"3d-model-center\") ?? false;\r\n\r\n loader.load(\r\n modelPath,\r\n (loadedModel: any) => {\r\n const root =\r\n this.engine.resolveLoadedModelRoot?.(loadedModel) ||\r\n (loadedModel && typeof loadedModel === \"object\" ? loadedModel : null);\r\n if (!root) {\r\n return;\r\n }\r\n\r\n const overrideMaterial =\r\n element && this.shouldOverrideModelMaterial(element)\r\n ? this.createMaterialFromElement(element, object)\r\n : null;\r\n this.engine.forEachMesh(root, (mesh) => {\r\n if (overrideMaterial) {\r\n (mesh as any).material = overrideMaterial;\r\n }\r\n this.applyShadowProps(object, mesh);\r\n });\r\n\r\n if (shouldCenter) {\r\n this.centerObject(root);\r\n }\r\n const obj = new String3DObject(object.id, \"model\", root, this.engine);\r\n onAdd(obj);\r\n },\r\n undefined,\r\n undefined,\r\n );\r\n }\r\n\r\n private createParticles(\r\n object: String3DSourceObject,\r\n onAdd: (obj: String3DObject) => void,\r\n ): void {\r\n if (!this.engine.createParticleSystem) {\r\n return;\r\n }\r\n\r\n const element = object.htmlElement;\r\n const config: import(\"./abstractions/I3DEngine\").ParticleSystemConfig = {\r\n mode: \"emitter\",\r\n count: 300,\r\n size: 2,\r\n color: \"#ffffff\",\r\n opacity: 1,\r\n spread: 120,\r\n spreadX: 0,\r\n spreadY: 0,\r\n seed: 1,\r\n emitRate: 30,\r\n emitBurst: 0,\r\n particleLife: 2.5,\r\n particleSpeed: 40,\r\n particleDirection: [0, 1, 0] as [number, number, number],\r\n particleGravity: [0, -30, 0] as [number, number, number],\r\n particleDrag: 0.1,\r\n particleSizeVariation: 0.6,\r\n particleColorVariation: 0.2,\r\n particleShape: \"sphere\",\r\n particleModelUrl: \"\",\r\n particleModelLoader: \"\",\r\n particleModelNode: \"\",\r\n instanceShape: \"sphere\",\r\n instanceModelUrl: \"\",\r\n instanceModelLoader: \"\",\r\n instanceModelNode: \"\",\r\n instanceScale: 1,\r\n instanceScaleVariation: 0.5,\r\n instanceRotationSpeed: 0.4,\r\n instanceJitter: 0.2,\r\n instanceFlow: 0.3,\r\n instanceDisperse: 0,\r\n instanceDisperseScatter: 0,\r\n instanceDisperseScatterX: 0,\r\n instanceDisperseScatterY: 0,\r\n instanceDisperseScatterZ: 0,\r\n modelTransitionDuration: 0,\r\n };\r\n\r\n const system = this.engine.createParticleSystem(config);\r\n const obj = new String3DObject(object.id, \"particles\", system, this.engine);\r\n onAdd(obj);\r\n }\r\n\r\n private createText(object: String3DSourceObject, onAdd: (obj: String3DObject) => void): void {\r\n if (!this.engine.createTextGeometry) {\r\n return;\r\n }\r\n\r\n const geometry = this.engine.createBoxGeometry(1, 1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n\r\n const group = this.engine.createGroup();\r\n group.add(mesh);\r\n\r\n const obj = new String3DObject(object.id, \"text\", group, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n }\r\n\r\n private createSVG(object: String3DSourceObject, onAdd: (obj: String3DObject) => void): void {\r\n const geometry = this.engine.createBoxGeometry(1, 1, 1);\r\n const material = this.createMaterialFromObject(object);\r\n const mesh = this.engine.createMesh(geometry, material);\r\n this.applyShadowProps(object, mesh);\r\n\r\n const group = this.engine.createGroup();\r\n group.add(mesh);\r\n\r\n const obj = new String3DObject(object.id, \"svg\", group, this.engine, {\r\n geometry,\r\n material,\r\n });\r\n onAdd(obj);\r\n }\r\n\r\n private getGeometryQuality(element?: HTMLElement | null): number {\r\n if (!element) return 1;\r\n const quality = readNumberStyle(element, \"--geometry-quality\", 1);\r\n if (!Number.isFinite(quality) || quality <= 0) return 1;\r\n return quality;\r\n }\r\n\r\n private resolveModelLoader(type?: string): I3DModelLoader | undefined {\r\n if (type) {\r\n if (this._modelLoaderCache.has(type)) {\r\n return this._modelLoaderCache.get(type);\r\n }\r\n if (!this._modelLoaderFactory) {\r\n return undefined;\r\n }\r\n const loader = this._modelLoaderFactory(this.engine, type);\r\n this._modelLoaderCache.set(type, loader);\r\n return loader;\r\n }\r\n\r\n if (this._modelLoader) {\r\n return this._modelLoader;\r\n }\r\n\r\n if (this._modelLoaderFactory) {\r\n return this._modelLoaderFactory(this.engine);\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private centerObject(object: any): void {\r\n if (!object) return;\r\n const bbox = this.engine.computeBoundingBoxRecursively(object);\r\n const center = this.getBoxCenter(bbox);\r\n if (object.position?.set) {\r\n object.position.set(-center.x, -center.y, -center.z);\r\n }\r\n object.updateMatrixWorld(true);\r\n }\r\n\r\n private getBoxCenter(box: any): I3DVector3 {\r\n const center = this.engine.createVector3();\r\n center.x = (box.min.x + box.max.x) / 2;\r\n center.y = (box.min.y + box.max.y) / 2;\r\n center.z = (box.min.z + box.max.z) / 2;\r\n return center;\r\n }\r\n\r\n private createMaterialFromObject(object: String3DSourceObject): I3DMaterial {\r\n return this.createMaterialFromElement(object.htmlElement, object);\r\n }\r\n\r\n private createMaterialFromElement(\r\n element: HTMLElement | null,\r\n object?: String3DSourceObject,\r\n ): I3DMaterial {\r\n const style = element ? getComputedStyle(element) : null;\r\n const getCSS = (prop: string) => (style ? style.getPropertyValue(prop).trim() : \"\");\r\n\r\n const resolve = <T>(cssProp: string, parser: (v: string) => T, defaultValue: T): T => {\r\n const cssVal = getCSS(cssProp);\r\n if (cssVal && cssVal !== \"none\" && cssVal !== \"\") return parser(cssVal);\r\n return defaultValue;\r\n };\r\n\r\n const parseNumber = (v: string) => parseFloat(v);\r\n const parseColor = (v: string) => v;\r\n const parseUrl = (v: string) => {\r\n const match = v.match(/url\\(['\"]?(.*?)['\"]?\\)/);\r\n return match ? match[1] : v;\r\n };\r\n\r\n const type = resolve(\"--material-type\", (v) => v.split(\"[\")[0] || \"basic\", \"basic\");\r\n\r\n const customMaterial = this.tryCreateCustomMaterial(type, element, style, object);\r\n if (customMaterial) {\r\n return customMaterial;\r\n }\r\n\r\n const color = resolve(\"--material-color\", parseColor, \"#ffffff\");\r\n\r\n const opacity = resolve(\"--opacity\", parseNumber, 1);\r\n const metalness = resolve(\"--material-metalness\", parseNumber, 0);\r\n const roughness = resolve(\"--material-roughness\", parseNumber, 1);\r\n const emissive = resolve(\"--material-emissive\", parseColor, \"#000000\");\r\n\r\n const params: any = {\r\n color,\r\n transparent: opacity < 1,\r\n opacity: opacity,\r\n };\r\n\r\n const mapSrc = resolve(\"--texture-map\", parseUrl, \"\");\r\n const normalMapSrc = resolve(\"--texture-normal\", parseUrl, \"\");\r\n const roughnessMapSrc = resolve(\"--texture-roughness\", parseUrl, \"\");\r\n const metalnessMapSrc = resolve(\"--texture-metalness\", parseUrl, \"\");\r\n const aoMapSrc = resolve(\"--texture-ao\", parseUrl, \"\");\r\n\r\n const flipY = this.parseFlipY(element);\r\n const colorSpace = element ? readStringStyle(element, \"--texture-color-space\", \"\") : \"\";\r\n\r\n const hasMaps = !!(mapSrc || normalMapSrc || roughnessMapSrc || metalnessMapSrc || aoMapSrc);\r\n let finalType = type;\r\n if (finalType !== \"standard\" && hasMaps) {\r\n finalType = \"standard\";\r\n }\r\n\r\n if (finalType === \"standard\") {\r\n if (mapSrc) {\r\n params.map = this.loadTexture(mapSrc, {\r\n flipY,\r\n colorSpace: colorSpace || \"srgb\",\r\n });\r\n }\r\n if (normalMapSrc) params.normalMap = this.loadTexture(normalMapSrc, { flipY });\r\n if (roughnessMapSrc) params.roughnessMap = this.loadTexture(roughnessMapSrc, { flipY });\r\n if (metalnessMapSrc) params.metalnessMap = this.loadTexture(metalnessMapSrc, { flipY });\r\n if (aoMapSrc) params.aoMap = this.loadTexture(aoMapSrc, { flipY });\r\n\r\n params.metalness = metalness;\r\n params.roughness = roughness;\r\n params.emissive = emissive;\r\n\r\n return this.engine.createMeshStandardMaterial(params);\r\n }\r\n\r\n return this.engine.createMeshBasicMaterial(params);\r\n }\r\n\r\n private tryCreateCustomMaterial(\r\n type: string,\r\n element: HTMLElement | null,\r\n style: CSSStyleDeclaration | null,\r\n object?: String3DSourceObject,\r\n ): I3DMaterial | null {\r\n const definition = this.customMaterialRegistry.get(type);\r\n if (!definition) {\r\n return null;\r\n }\r\n\r\n const factory = this.engine.getMaterialFactory?.();\r\n if (!factory) {\r\n return null;\r\n }\r\n if (!factory.supports(definition)) {\r\n return null;\r\n }\r\n\r\n let initialUniforms: Record<string, any> = {};\r\n if (element && style) {\r\n initialUniforms = factory.parseUniformsFromCSS(definition, element, style);\r\n }\r\n\r\n const instance = factory.create(definition, initialUniforms);\r\n\r\n if (object) {\r\n this._materialInstances.set(object.id, instance);\r\n }\r\n\r\n return instance.material;\r\n }\r\n\r\n public updateMaterialUniforms(objectId: string, uniforms: Record<string, any>): void {\r\n const instance = this._materialInstances.get(objectId);\r\n if (instance) {\r\n instance.update(uniforms);\r\n }\r\n }\r\n\r\n public getMaterialInstance(objectId: string): IMaterialInstance | undefined {\r\n return this._materialInstances.get(objectId);\r\n }\r\n\r\n public recreateMaterialForObject(object: String3DObject, element: HTMLElement | null): void {\r\n const oldInstance = this._materialInstances.get(object.id);\r\n if (oldInstance && oldInstance.dispose) {\r\n oldInstance.dispose();\r\n }\r\n this._materialInstances.delete(object.id);\r\n\r\n let stringObject: String3DSourceObject | undefined;\r\n for (const [id, el] of this._elementMap) {\r\n if (id === object.id && el === element) {\r\n stringObject = (el as any).__stringObject || (el as any).stringObject;\r\n break;\r\n }\r\n }\r\n\r\n const newMaterial = this.createMaterialFromElement(element, stringObject);\r\n\r\n this.engine.forEachMesh(object.object, (mesh) => {\r\n const current = (mesh as any).material;\r\n if (Array.isArray(current)) {\r\n current.forEach((mat: any) => mat?.dispose?.());\r\n } else {\r\n current?.dispose?.();\r\n }\r\n (mesh as any).material = newMaterial;\r\n });\r\n\r\n object.material = newMaterial;\r\n }\r\n\r\n private loadTexture(src: string, options: { flipY?: boolean; colorSpace?: string } = {}): any {\r\n const textureLoader = this.engine.createTextureLoader();\r\n const texture = textureLoader.load(src);\r\n if (typeof options.flipY === \"boolean\") {\r\n texture.flipY = options.flipY;\r\n }\r\n const colorSpace = (options.colorSpace || \"\").toLowerCase().trim();\r\n if (colorSpace && \"colorSpace\" in texture) {\r\n texture.colorSpace = colorSpace === \"srgb\" ? \"srgb\" : \"linear\";\r\n }\r\n texture.needsUpdate = true;\r\n return texture;\r\n }\r\n\r\n private parseFlipY(element?: HTMLElement | null): boolean | undefined {\r\n const value = element ? readStringStyle(element, \"--texture-flip-y\", \"\") : \"\";\r\n if (value === undefined || value === null || value === \"\") return undefined;\r\n if (typeof value === \"boolean\") return value;\r\n const normalized = String(value).toLowerCase().trim();\r\n if (normalized === \"false\" || normalized === \"0\" || normalized === \"no\") return false;\r\n if (normalized === \"true\" || normalized === \"1\" || normalized === \"yes\") return true;\r\n return undefined;\r\n }\r\n\r\n private shouldOverrideModelMaterial(element: HTMLElement): boolean {\r\n const style = getComputedStyle(element);\r\n const hasStyle = (prop: string) => {\r\n const val = style.getPropertyValue(prop);\r\n return val && val !== \"0\" && val !== \"none\" && val !== \"\";\r\n };\r\n\r\n if (hasStyle(\"--material-color\") || hasStyle(\"--texture-map\")) return true;\r\n\r\n const cssVars = [\r\n \"--material-type\",\r\n \"--material-metalness\",\r\n \"--material-roughness\",\r\n \"--material-emissive\",\r\n \"--opacity\",\r\n \"--texture-normal\",\r\n \"--texture-roughness\",\r\n \"--texture-metalness\",\r\n \"--texture-ao\",\r\n ];\r\n return cssVars.some((prop) => hasStyle(prop));\r\n }\r\n\r\n private parseModelLoaderOptions(element: HTMLElement): I3DModelLoaderOptions | null {\r\n const baseRaw = (element.getAttribute(\"string-3d-model-texture-base\") || \"\").trim();\r\n const mappingRaw = element.getAttribute(\"string-3d-model-textures\");\r\n const options: I3DModelLoaderOptions = {};\r\n\r\n if (baseRaw) {\r\n options.textureBaseUrl = baseRaw.replace(/\\/?$/, \"/\");\r\n }\r\n\r\n if (mappingRaw) {\r\n try {\r\n const parsed = JSON.parse(mappingRaw);\r\n if (parsed && typeof parsed === \"object\") {\r\n options.textureMap = parsed as Record<string, string>;\r\n }\r\n } catch (error) { }\r\n }\r\n\r\n return options.textureBaseUrl || options.textureMap ? options : null;\r\n }\r\n\r\n public destroy(): void {\r\n this._materialInstances.forEach((instance) => instance.dispose());\r\n this._materialInstances.clear();\r\n this._objects.forEach((obj) => obj.destroy());\r\n this._objects.clear();\r\n this._rootObjects = [];\r\n }\r\n}\r\n","import type { SyncContext } from \"./SyncContext\";\r\n\r\nexport class StyleBundleCache<T> {\r\n private cache: WeakMap<HTMLElement, T> = new WeakMap();\r\n private meta: WeakMap<HTMLElement, { time: number }> = new WeakMap();\r\n\r\n get(el: HTMLElement, ctx: SyncContext, reader: (el: HTMLElement) => T): T {\r\n const isDirty = !!ctx.dirtySet && ctx.dirtySet.has(el);\r\n const canUseCache = !!ctx.dirtySet && ctx.forceSync === false && !isDirty;\r\n if (canUseCache) {\r\n const cached = this.cache.get(el);\r\n if (cached) return cached;\r\n }\r\n\r\n const now = performance.now();\r\n const interval = Math.max(0, ctx.styleReadIntervalMs ?? 0);\r\n if (interval > 0 && !isDirty) {\r\n const metaData = this.meta.get(el);\r\n const cached = this.cache.get(el);\r\n if (metaData && cached && now - metaData.time < interval) {\r\n return cached;\r\n }\r\n }\r\n\r\n const bundle = reader(el);\r\n this.cache.set(el, bundle);\r\n this.meta.set(el, { time: now });\r\n return bundle;\r\n }\r\n\r\n clear(): void {\r\n this.cache = new WeakMap();\r\n this.meta = new WeakMap();\r\n }\r\n\r\n invalidate(el: HTMLElement): void {\r\n this.cache.delete(el);\r\n this.meta.delete(el);\r\n }\r\n}\r\n","import { String3DObject } from \"../String3DObject\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport type { SyncContext } from \"./SyncContext\";\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\n\nconst DEG_TO_RAD = Math.PI / 180;\n\ntype GroupStyleBundle = {\n translateZ: number;\n scale: number;\n rotateX: number;\n rotateY: number;\n rotateZ: number;\n};\n\nexport class GroupSynchronizer implements String3DObjectSyncStrategy {\n private static styleCache = new StyleBundleCache<GroupStyleBundle>();\n\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\n const cached = (el as any).__layoutCache;\n const rect = cached ? cached.rect : el.getBoundingClientRect();\n const bundle = this.readStyleBundle(el, ctx);\n\n const screenCenterX = rect.left + rect.width * 0.5;\n const screenCenterY = rect.top + rect.height * 0.5;\n\n if (ctx.camera.getMode() === \"orthographic\") {\n object.object.position.set(\n screenCenterX - ctx.viewportWidth / 2,\n -(screenCenterY - ctx.viewportHeight / 2),\n bundle.translateZ\n );\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\n const normalizedX = screenCenterX / ctx.viewportWidth;\n const normalizedY = screenCenterY / ctx.viewportHeight;\n object.object.position.set(\n (normalizedX - 0.5) * frustum.width,\n -(normalizedY - 0.5) * frustum.height,\n bundle.translateZ\n );\n }\n\n object.object.scale.set(bundle.scale, bundle.scale, bundle.scale);\n\n object.object.rotation.x = -bundle.rotateX * DEG_TO_RAD;\n object.object.rotation.y = bundle.rotateY * DEG_TO_RAD;\n object.object.rotation.z = -bundle.rotateZ * DEG_TO_RAD;\n object.object.rotation.order = \"XYZ\";\n\n object.object.updateMatrixWorld(true);\n\n return { scale: bundle.scale };\n }\n\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): GroupStyleBundle {\n return GroupSynchronizer.styleCache.get(el, ctx, (el) => {\n const styles = new StyleReader(el);\n return {\n translateZ: styles.readNumber(\"--translate-z\", 0),\n scale: styles.readNumber(\"--scale\", 1),\n rotateX: styles.readNumber(\"--rotate-x\", 0),\n rotateY: styles.readNumber(\"--rotate-y\", 0),\n rotateZ: styles.readNumber(\"--rotate-z\", 0),\n };\n });\n }\n}\n","import { String3DObject } from \"../String3DObject\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\nimport type { SyncContext } from \"./SyncContext\";\r\nimport { I3DLight } from \"../abstractions/I3DEngine\";\r\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\r\nimport { StyleBundleCache } from \"./StyleBundleCache\";\r\n\r\ntype LightStyleBundle = {\r\n translateZ: number;\r\n translateX: number;\r\n translateY: number;\r\n color?: string;\r\n intensity: number;\r\n distance?: number;\r\n decay?: number;\r\n angle?: number;\r\n penumbra?: number;\r\n groundColor?: string;\r\n castShadow: boolean;\r\n shadowBias?: number;\r\n shadowMapSize?: number;\r\n targetId?: string;\r\n targetOffset?: { x: number; y: number; z: number };\r\n};\r\n\r\nexport class LightSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<LightStyleBundle>();\r\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n const cached = (el as any).__layoutCache;\r\n const rect = cached ? cached.rect : el.getBoundingClientRect();\r\n const bundle = this.readStyleBundle(el, ctx, object);\r\n\r\n const screenAnchor = this.resolveScreenAnchor(rect, ctx);\r\n const translateX = screenAnchor.fallbackToViewportCenter ? bundle.translateX : 0;\r\n const translateY = screenAnchor.fallbackToViewportCenter ? bundle.translateY : 0;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n this.setObjectPosition(\r\n ctx,\r\n object.object,\r\n screenAnchor.x - ctx.viewportWidth / 2 + translateX,\r\n -(screenAnchor.y - ctx.viewportHeight / 2) + translateY,\r\n bundle.translateZ,\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\r\n const normalizedX = screenAnchor.x / ctx.viewportWidth;\r\n const normalizedY = screenAnchor.y / ctx.viewportHeight;\r\n this.setObjectPosition(\r\n ctx,\r\n object.object,\r\n (normalizedX - 0.5) * frustum.width + translateX,\r\n -(normalizedY - 0.5) * frustum.height + translateY,\r\n bundle.translateZ,\r\n );\r\n }\r\n\r\n const light = object.object as I3DLight;\r\n\r\n if (\r\n bundle.color &&\r\n bundle.color !== \"none\" &&\r\n light.color &&\r\n typeof light.color.set === \"function\"\r\n ) {\r\n light.color.set(bundle.color);\r\n }\r\n\r\n light.intensity = bundle.intensity;\r\n\r\n if (typeof light.distance !== \"undefined\" && bundle.distance !== undefined) {\r\n light.distance = bundle.distance;\r\n }\r\n if (typeof light.decay !== \"undefined\" && bundle.decay !== undefined) {\r\n light.decay = bundle.decay;\r\n }\r\n\r\n if (typeof light.angle !== \"undefined\" && bundle.angle !== undefined) {\r\n light.angle = bundle.angle;\r\n }\r\n if (typeof light.penumbra !== \"undefined\" && bundle.penumbra !== undefined) {\r\n light.penumbra = bundle.penumbra;\r\n }\r\n\r\n if (\r\n bundle.groundColor &&\r\n bundle.groundColor !== \"none\" &&\r\n (light as any).groundColor &&\r\n typeof (light as any).groundColor.set === \"function\"\r\n ) {\r\n (light as any).groundColor.set(bundle.groundColor);\r\n }\r\n\r\n if (light.castShadow !== bundle.castShadow) {\r\n light.castShadow = bundle.castShadow;\r\n }\r\n if (bundle.castShadow && light.shadow) {\r\n if (bundle.shadowBias !== undefined) {\r\n light.shadow.bias = bundle.shadowBias;\r\n }\r\n if (\r\n bundle.shadowMapSize !== undefined &&\r\n light.shadow.mapSize.width !== bundle.shadowMapSize\r\n ) {\r\n light.shadow.mapSize.width = bundle.shadowMapSize;\r\n light.shadow.mapSize.height = bundle.shadowMapSize;\r\n }\r\n }\r\n\r\n if (bundle.targetId && bundle.targetId !== \"none\" && light.target) {\r\n const targetEl = document.querySelector(`[string-id=\"${bundle.targetId}\"]`);\r\n if (targetEl) {\r\n const tCached = (targetEl as any).__layoutCache;\r\n const tRect = tCached ? tCached.rect : targetEl.getBoundingClientRect();\r\n const tStyles = new StyleReader(targetEl as HTMLElement);\r\n const tTranslateX = tStyles.readNumber(\"--translate-x\", 0);\r\n const tTranslateY = tStyles.readNumber(\"--translate-y\", 0);\r\n const tTranslateZ = tStyles.readNumber(\"--translate-z\", 0);\r\n\r\n const tScreenAnchor = this.resolveScreenAnchor(tRect, ctx);\r\n const tOffsetX = tScreenAnchor.fallbackToViewportCenter ? tTranslateX : 0;\r\n const tOffsetY = tScreenAnchor.fallbackToViewportCenter ? tTranslateY : 0;\r\n\r\n let x: number;\r\n let y: number;\r\n let z: number;\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n x = tScreenAnchor.x - ctx.viewportWidth / 2 + tOffsetX;\r\n y = -(tScreenAnchor.y - ctx.viewportHeight / 2) + tOffsetY;\r\n z = tTranslateZ;\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(tTranslateZ);\r\n const normalizedX = tScreenAnchor.x / ctx.viewportWidth;\r\n const normalizedY = tScreenAnchor.y / ctx.viewportHeight;\r\n x = (normalizedX - 0.5) * frustum.width + tOffsetX;\r\n y = -(normalizedY - 0.5) * frustum.height + tOffsetY;\r\n z = tTranslateZ;\r\n }\r\n\r\n if (bundle.targetOffset) {\r\n x += bundle.targetOffset.x;\r\n y += bundle.targetOffset.y;\r\n z += bundle.targetOffset.z;\r\n }\r\n\r\n this.setObjectPosition(ctx, light.target, x, y, z);\r\n\r\n light.target.updateMatrixWorld(true);\r\n }\r\n }\r\n\r\n return null;\r\n }\r\n\r\n private readStyleBundle(\r\n el: HTMLElement,\r\n ctx: SyncContext,\r\n object: String3DObject,\r\n ): LightStyleBundle {\r\n return LightSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styles = new StyleReader(el);\r\n const light = object.object as I3DLight;\r\n\r\n const bundle: LightStyleBundle = {\r\n translateZ: styles.readNumber(\"--translate-z\", 0),\r\n translateX: styles.readNumber(\"--translate-x\", 0),\r\n translateY: styles.readNumber(\"--translate-y\", 0),\r\n color: styles.readString(\"--light-color\", \"\") || undefined,\r\n intensity: styles.readNumber(\"--light-intensity\", light.intensity ?? 1),\r\n castShadow: styles.readBoolean(\"--shadow-cast\", false),\r\n };\r\n\r\n if (typeof light.distance !== \"undefined\") {\r\n bundle.distance = styles.readNumber(\"--light-distance\", light.distance ?? 0);\r\n }\r\n if (typeof light.decay !== \"undefined\") {\r\n bundle.decay = styles.readNumber(\"--light-decay\", light.decay ?? 1);\r\n }\r\n if (typeof light.angle !== \"undefined\") {\r\n bundle.angle = styles.readNumber(\"--light-angle\", light.angle ?? Math.PI / 3);\r\n }\r\n if (typeof light.penumbra !== \"undefined\") {\r\n bundle.penumbra = styles.readNumber(\"--light-penumbra\", light.penumbra ?? 0);\r\n }\r\n\r\n const groundColor = styles.readString(\"--light-ground-color\", \"\");\r\n if (groundColor) bundle.groundColor = groundColor;\r\n\r\n if (bundle.castShadow && light.shadow) {\r\n bundle.shadowBias = styles.readNumber(\"--shadow-bias\", light.shadow.bias ?? 0);\r\n bundle.shadowMapSize = styles.readNumber(\r\n \"--shadow-map-size\",\r\n light.shadow.mapSize.width ?? 512,\r\n );\r\n }\r\n\r\n const targetId = styles.readString(\"--light-target\", \"\").trim();\r\n if (targetId) bundle.targetId = targetId;\r\n const offsetRaw = styles.readString(\"--light-target-offset\", \"\").trim();\r\n if (offsetRaw) {\r\n const offset = this.parseTargetOffset(offsetRaw);\r\n if (offset) bundle.targetOffset = offset;\r\n }\r\n\r\n return bundle;\r\n });\r\n }\r\n\r\n private parseTargetOffset(value: string): { x: number; y: number; z: number } | null {\r\n const parts = value\r\n .split(/[\\s,]+/)\r\n .map((part) => part.trim())\r\n .filter(Boolean)\r\n .map((part) => Number.parseFloat(part));\r\n if (parts.length < 3 || parts.some((num) => Number.isNaN(num))) return null;\r\n return { x: parts[0], y: parts[1], z: parts[2] };\r\n }\r\n\r\n private resolveScreenAnchor(\r\n rect: DOMRect,\r\n ctx: SyncContext,\r\n ): { x: number; y: number; fallbackToViewportCenter: boolean } {\r\n const hasRenderableArea = rect.width > 1 && rect.height > 1;\r\n if (!hasRenderableArea) {\r\n return {\r\n x: ctx.viewportWidth * 0.5,\r\n y: ctx.viewportHeight * 0.5,\r\n fallbackToViewportCenter: true,\r\n };\r\n }\r\n\r\n return {\r\n x: rect.left + rect.width * 0.5,\r\n y: rect.top + rect.height * 0.5,\r\n fallbackToViewportCenter: false,\r\n };\r\n }\r\n\r\n private setObjectPosition(ctx: SyncContext, target: any, x: number, y: number, z: number): void {\r\n if (ctx.engine.setObjectPosition?.(target, x, y, z)) {\r\n return;\r\n }\r\n\r\n if (target?.position?.set && typeof target.position.set === \"function\") {\r\n target.position.set(x, y, z);\r\n return;\r\n }\r\n\r\n if (typeof target?.setPosition === \"function\") {\r\n target.setPosition(x, y, z);\r\n return;\r\n }\r\n\r\n if (target?.position) {\r\n target.position.x = x;\r\n target.position.y = y;\r\n target.position.z = z;\r\n }\r\n }\r\n}\r\n","import { String3DObject } from \"../String3DObject\";\nimport { I3DEngine, I3DMaterialVisualProps } from \"../abstractions/I3DEngine\";\nimport type { SyncContext } from \"./SyncContext\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\n\r\nconst DEG_TO_RAD = Math.PI / 180;\r\n\r\ntype ParsedRgb = { r: number; g: number; b: number };\r\n\r\nfunction parseCssColorToRgb(value: string): ParsedRgb | null {\r\n const raw = (value || \"\").trim().toLowerCase();\r\n if (!raw) return null;\r\n\r\n if (/^#([0-9a-f]{3}|[0-9a-f]{6})$/i.test(raw)) {\r\n const normalized =\r\n raw.length === 4 ? `#${raw[1]}${raw[1]}${raw[2]}${raw[2]}${raw[3]}${raw[3]}` : raw;\r\n const r = Number.parseInt(normalized.slice(1, 3), 16) / 255;\r\n const g = Number.parseInt(normalized.slice(3, 5), 16) / 255;\r\n const b = Number.parseInt(normalized.slice(5, 7), 16) / 255;\r\n return { r, g, b };\r\n }\r\n\r\n const rgb = raw.match(/rgba?\\(([^)]+)\\)/i);\r\n if (rgb) {\r\n const parts = rgb[1]\r\n .replace(/\\//g, \" \")\r\n .split(/[\\s,]+/)\r\n .map((part) => Number.parseFloat(part.trim()))\r\n .filter((num) => Number.isFinite(num));\r\n if (parts.length >= 3) {\r\n return { r: parts[0] / 255, g: parts[1] / 255, b: parts[2] / 255 };\r\n }\r\n }\r\n\r\n if (raw === \"black\") return { r: 0, g: 0, b: 0 };\r\n if (raw === \"white\") return { r: 1, g: 1, b: 1 };\r\n return null;\r\n}\r\n\r\nfunction isBlackCssColor(value: string): boolean {\r\n const raw = (value || \"\").trim().toLowerCase();\r\n if (!raw) return false;\r\n if (raw === \"black\" || raw === \"#000\" || raw === \"#000000\") return true;\r\n\r\n const parsed = parseCssColorToRgb(raw);\r\n if (!parsed) return false;\r\n return parsed.r === 0 && parsed.g === 0 && parsed.b === 0;\r\n}\r\n\r\nfunction applyColorToTarget(target: any, value: string): boolean {\n if (!target) return false;\n\n if (typeof target.set === \"function\") {\n try {\n target.set(value);\n return true;\n } catch {}\n }\n\n const rgb = parseCssColorToRgb(value);\n if (!rgb) return false;\n\n if (typeof target.setRGB === \"function\") {\n target.setRGB(rgb.r, rgb.g, rgb.b);\n return true;\n }\n\r\n if (\"r\" in target && \"g\" in target && \"b\" in target) {\r\n target.r = rgb.r;\r\n target.g = rgb.g;\r\n target.b = rgb.b;\r\n return true;\r\n }\r\n\r\n return false;\r\n}\r\n\r\nexport class MeshSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<StyleBundle>();\r\n private static layoutCache = new StyleBundleCache<LayoutBundle>();\r\n private static tempVector3: any = null;\r\n private static lastVisualProps: WeakMap<\r\n String3DObject,\r\n {\r\n opacity?: number;\r\n color?: string;\r\n metalness?: number;\r\n roughness?: number;\r\n emissive?: string;\r\n castShadow?: boolean;\r\n receiveShadow?: boolean;\r\n }\r\n > = new WeakMap();\n private static lastGeometryQuality: WeakMap<String3DObject, number> = new WeakMap();\n private static originalGeometryByMesh: WeakMap<object, any> = new WeakMap();\n private static lodGeometryCacheByMesh: WeakMap<object, Map<string, any>> = new WeakMap();\n\r\n static resolveEmissiveValue(el: HTMLElement, emissive?: string): string | undefined {\r\n if (!emissive || emissive === \"none\") return undefined;\r\n\r\n const inlineRaw = el.style.getPropertyValue(\"--material-emissive\").trim();\r\n if (inlineRaw) {\r\n return emissive;\r\n }\r\n\r\n return isBlackCssColor(emissive) ? undefined : emissive;\r\n }\r\n\r\n static applyVisualProps(\n el: HTMLElement,\n object: String3DObject,\n engine: I3DEngine,\n props: {\n opacity?: number;\n color?: string;\n metalness?: number;\r\n roughness?: number;\r\n emissive?: string;\r\n castShadow?: boolean;\r\n receiveShadow?: boolean;\r\n },\r\n ): void {\r\n const prev = MeshSynchronizer.lastVisualProps.get(object);\r\n if (prev) {\r\n if (\r\n prev.opacity === props.opacity &&\r\n prev.color === props.color &&\r\n prev.metalness === props.metalness &&\r\n prev.roughness === props.roughness &&\r\n prev.emissive === props.emissive &&\r\n prev.castShadow === props.castShadow &&\r\n prev.receiveShadow === props.receiveShadow\r\n )\r\n return;\r\n prev.opacity = props.opacity;\r\n prev.color = props.color;\r\n prev.metalness = props.metalness;\r\n prev.roughness = props.roughness;\r\n prev.emissive = props.emissive;\r\n prev.castShadow = props.castShadow;\r\n prev.receiveShadow = props.receiveShadow;\r\n } else {\r\n MeshSynchronizer.lastVisualProps.set(object, {\r\n opacity: props.opacity,\r\n color: props.color,\r\n metalness: props.metalness,\r\n roughness: props.roughness,\r\n emissive: props.emissive,\r\n castShadow: props.castShadow,\r\n receiveShadow: props.receiveShadow,\r\n });\r\n }\r\n\r\n const castShadow = props.castShadow ?? false;\r\n const receiveShadow = props.receiveShadow ?? false;\r\n\r\n const opacity = typeof props.opacity === \"number\" ? props.opacity : NaN;\r\n\r\n const materialProps: I3DMaterialVisualProps = {\n opacity: Number.isFinite(opacity) ? opacity : undefined,\n color: props.color,\n metalness: Number.isFinite(props.metalness as number) ? props.metalness : undefined,\n roughness: Number.isFinite(props.roughness as number) ? props.roughness : undefined,\n emissive: props.emissive,\n };\n\n const applyMaterialProps = (mat: any) => {\n if (!mat) return;\n\n if (engine.applyMaterialProps?.(mat, materialProps)) {\n return;\n }\n\n if (!isNaN(opacity)) {\n mat.opacity = opacity;\n mat.transparent = opacity < 1;\n }\n\n if (props.color && mat.color) {\n applyColorToTarget(mat.color, props.color);\n }\n\n if (typeof props.metalness === \"number\" && \"metalness\" in mat) {\n mat.metalness = props.metalness;\r\n }\r\n\r\n if (typeof props.roughness === \"number\" && \"roughness\" in mat) {\r\n mat.roughness = props.roughness;\r\n }\r\n\r\n if (props.emissive) {\n if (mat.emissive) {\n applyColorToTarget(mat.emissive, props.emissive);\n }\n }\n };\n\r\n engine.forEachMesh(object.object, (mesh) => {\n if (mesh.castShadow !== castShadow) mesh.castShadow = castShadow;\n if (mesh.receiveShadow !== receiveShadow) mesh.receiveShadow = receiveShadow;\n\n const materials = Array.isArray((mesh as any).material)\n ? (mesh as any).material\n : [(mesh as any).material];\n materials.forEach(applyMaterialProps);\n });\n }\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n const { rect, width: originalWidth, height: originalHeight } = this.readLayout(el, ctx);\r\n const bundle = this.readStyleBundle(el, ctx);\r\n const {\r\n translateZ,\r\n cssScale,\r\n rotateX,\r\n rotateY,\r\n rotateZ,\r\n cssScaleZ,\r\n opacity,\r\n color,\r\n metalness,\r\n roughness,\r\n emissive,\r\n castShadow,\r\n receiveShadow,\r\n geometryQuality,\r\n } = bundle;\r\n\r\n const screenCenterX = rect.left + rect.width * 0.5;\r\n const screenCenterY = rect.top + rect.height * 0.5;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n object.object.position.set(\r\n screenCenterX - ctx.viewportWidth / 2,\r\n -(screenCenterY - ctx.viewportHeight / 2),\r\n translateZ,\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(translateZ);\r\n const normalizedX = screenCenterX / ctx.viewportWidth;\r\n const normalizedY = screenCenterY / ctx.viewportHeight;\r\n object.object.position.set(\r\n (normalizedX - 0.5) * frustum.width,\r\n -(normalizedY - 0.5) * frustum.height,\r\n translateZ,\r\n );\r\n }\r\n\r\n object.object.rotation.x = -rotateX * DEG_TO_RAD;\r\n object.object.rotation.y = rotateY * DEG_TO_RAD;\r\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n const targetWidth = originalWidth * cssScale;\r\n const targetHeight = originalHeight * cssScale;\r\n const parentScale = parentData?.scale || 1;\r\n const baseScaleZ = cssScaleZ * parentScale;\r\n const minTargetSize = targetWidth < targetHeight ? targetWidth : targetHeight;\r\n let scaleX: number, scaleY: number, scaleZ: number;\r\n\r\n switch (object.type) {\r\n case \"box\":\r\n case \"sphere\": {\r\n const uniformSize = minTargetSize * parentScale;\r\n scaleX = scaleY = uniformSize;\r\n scaleZ = uniformSize * cssScaleZ;\r\n break;\r\n }\r\n case \"model\": {\r\n const bbox = object.getOriginalBoundingBox();\r\n if (!MeshSynchronizer.tempVector3) {\r\n MeshSynchronizer.tempVector3 = ctx.engine.createVector3();\r\n }\r\n const size = bbox.getSize(MeshSynchronizer.tempVector3);\r\n const fitMode = el.getAttribute(\"string-3d-model-fit\");\r\n const modelScale = parseFloat(el.getAttribute(\"string-3d-model-scale\") || \"1\");\r\n const finalModelScale = Number.isFinite(modelScale)\r\n ? modelScale * parentScale\r\n : parentScale;\r\n\r\n if (size.x > 0 && size.y > 0) {\r\n const scaleW = targetWidth / size.x;\r\n const scaleH = targetHeight / size.y;\r\n const uniformScale =\r\n (fitMode === \"cover\"\r\n ? scaleW > scaleH\r\n ? scaleW\r\n : scaleH\r\n : scaleW < scaleH\r\n ? scaleW\r\n : scaleH) * finalModelScale;\r\n scaleX = scaleY = uniformScale;\r\n scaleZ = uniformScale * cssScaleZ;\r\n } else {\r\n const fallbackSize = minTargetSize * finalModelScale;\r\n scaleX = scaleY = fallbackSize;\r\n scaleZ = fallbackSize * cssScaleZ;\r\n }\r\n break;\r\n }\r\n case \"cylinder\":\r\n scaleX = targetWidth * parentScale;\r\n scaleY = targetHeight * parentScale;\r\n scaleZ = targetWidth * baseScaleZ;\r\n break;\r\n default:\r\n scaleX = targetWidth * parentScale;\r\n scaleY = targetHeight * parentScale;\r\n scaleZ = minTargetSize * 0.5 * baseScaleZ;\r\n break;\r\n }\r\n\r\n object.object.scale.set(scaleX, scaleY, scaleZ);\r\n\r\n MeshSynchronizer.applyVisualProps(el, object, ctx.engine, {\n opacity,\r\n color: color && color !== \"none\" ? color : undefined,\r\n metalness: isNaN(metalness) ? undefined : metalness,\r\n roughness: isNaN(roughness) ? undefined : roughness,\r\n emissive: MeshSynchronizer.resolveEmissiveValue(el, emissive),\r\n castShadow,\r\n receiveShadow,\r\n });\r\n\r\n this.applyGeometryQuality(object, geometryQuality, ctx);\r\n\r\n this.updateCustomUniforms(el, object, ctx);\r\n\r\n return { scale: cssScale * parentScale };\r\n }\r\n\r\n private applyGeometryQuality(object: String3DObject, quality: number, ctx: SyncContext): void {\r\n const simplify = ctx.engine.simplifyGeometry?.bind(ctx.engine);\n if (typeof simplify !== \"function\") return;\n\r\n const normalized = Number.isFinite(quality) && quality > 0 ? quality : 1;\r\n const prev = MeshSynchronizer.lastGeometryQuality.get(object);\r\n if (typeof prev === \"number\" && Math.abs(prev - normalized) < 0.001) return;\r\n MeshSynchronizer.lastGeometryQuality.set(object, normalized);\r\n\r\n const applyToMesh = (mesh: any) => {\n if (!mesh?.geometry) return;\n if (!MeshSynchronizer.originalGeometryByMesh.has(mesh)) {\n MeshSynchronizer.originalGeometryByMesh.set(mesh, mesh.geometry);\n }\n const original = MeshSynchronizer.originalGeometryByMesh.get(mesh);\n if (normalized >= 0.999) {\n mesh.geometry = original;\n return;\n }\n if (!MeshSynchronizer.lodGeometryCacheByMesh.has(mesh)) {\n MeshSynchronizer.lodGeometryCacheByMesh.set(mesh, new Map<string, any>());\n }\n const lodCache = MeshSynchronizer.lodGeometryCacheByMesh.get(mesh)!;\n const key = normalized.toFixed(3);\n if (lodCache.has(key)) {\n mesh.geometry = lodCache.get(key);\n return;\n }\n const simplified = simplify(original, normalized);\n if (simplified) {\n lodCache.set(key, simplified);\n mesh.geometry = simplified;\n }\n };\n ctx.engine.forEachMesh(object.object, applyToMesh);\n }\n\r\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n if (!factory) return;\r\n\r\n const style = getComputedStyle(el);\r\n\r\n const apply = (mat: any) => {\r\n const definition = factory.getMaterialDefinition?.(mat) ?? mat?.userData?.definition;\r\n if (!definition?.uniforms) return;\r\n\r\n const values = factory.parseUniformsFromCSS(definition, el, style);\r\n\r\n if (typeof factory.applyUniforms === \"function\") {\r\n factory.applyUniforms(mat, definition, values);\r\n return;\r\n }\r\n\r\n for (const [key, value] of Object.entries(values)) {\r\n const def = definition.uniforms?.[key];\r\n if (!def) continue;\r\n\r\n const converter = (factory as any).convertUniformValue?.bind(factory);\r\n const converted = converter ? converter(def.type, value) : value;\r\n\r\n if (mat.uniforms?.[key]) {\n mat.uniforms[key].value = converted;\n }\n }\n };\n ctx.engine.forEachMaterial(object.object, apply);\n }\n\r\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): StyleBundle {\r\n return MeshSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const style = getComputedStyle(el);\r\n\r\n const readNumber = (prop: string, fallback: number): number => {\r\n const mapValue = styleMap?.get?.(prop);\r\n if (mapValue !== undefined && mapValue !== null) {\r\n const val =\r\n typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n const num = typeof val === \"number\" ? val : Number.parseFloat(String(val));\r\n if (!Number.isNaN(num)) return num;\r\n }\r\n const num = Number.parseFloat(style.getPropertyValue(prop));\r\n return Number.isNaN(num) ? fallback : num;\r\n };\r\n\r\n const readString = (prop: string): string | undefined => {\r\n const mapValue = styleMap?.get?.(prop);\r\n const val =\r\n mapValue && typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n if (typeof val === \"string\") return val.trim() || undefined;\r\n const raw = style.getPropertyValue(prop).trim();\r\n return raw || undefined;\r\n };\r\n\r\n const readBool = (prop: string, fallback = false): boolean => {\r\n const raw = readString(prop);\r\n if (!raw) return fallback;\r\n const norm = raw.toLowerCase();\r\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\r\n ? true\r\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\r\n ? false\r\n : fallback;\r\n };\r\n\r\n return {\r\n translateZ: readNumber(\"--translate-z\", 0),\r\n cssScale: readNumber(\"--scale\", 1),\r\n rotateX: readNumber(\"--rotate-x\", 0),\r\n rotateY: readNumber(\"--rotate-y\", 0),\r\n rotateZ: readNumber(\"--rotate-z\", 0),\r\n cssScaleZ: readNumber(\"--scale-z\", 1),\r\n opacity: readNumber(\"--opacity\", NaN),\r\n color: readString(\"--material-color\"),\r\n metalness: readNumber(\"--material-metalness\", NaN),\r\n roughness: readNumber(\"--material-roughness\", NaN),\r\n emissive: readString(\"--material-emissive\"),\r\n castShadow: readBool(\"--shadow-cast\", false),\r\n receiveShadow: readBool(\"--shadow-receive\", false),\r\n geometryQuality: readNumber(\"--geometry-quality\", 1),\r\n };\r\n });\r\n }\r\n\r\n private readLayout(el: HTMLElement, ctx: SyncContext): LayoutBundle {\r\n const cached = (el as any).__layoutCache;\r\n if (cached) {\r\n return cached;\r\n }\r\n\r\n return MeshSynchronizer.layoutCache.get(el, ctx, (el) => {\r\n const rect = el.getBoundingClientRect();\r\n const width = el.offsetWidth || rect.width;\r\n const height = el.offsetHeight || rect.height;\r\n return { rect, width, height };\r\n });\r\n }\r\n}\r\n\r\ntype StyleBundle = {\r\n translateZ: number;\r\n cssScale: number;\r\n rotateX: number;\r\n rotateY: number;\r\n rotateZ: number;\r\n cssScaleZ: number;\r\n opacity: number;\r\n color?: string;\r\n metalness: number;\r\n roughness: number;\r\n emissive?: string;\r\n castShadow: boolean;\r\n receiveShadow: boolean;\r\n geometryQuality: number;\r\n};\r\n\r\ntype LayoutBundle = {\r\n rect: DOMRect;\r\n width: number;\r\n height: number;\r\n};\r\n","import { String3DObject } from \"../String3DObject\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\nimport type { SyncContext } from \"./SyncContext\";\r\nimport { StyleReader } from \"../../modules/string3d/styleUtils\";\r\nimport { StyleBundleCache } from \"./StyleBundleCache\";\r\nimport type { ParticleSystemConfig, I3DParticleSystem } from \"../abstractions/I3DEngine\";\nimport { String3DCustomMaterialRegistry } from \"../materials\";\r\nimport type { IMaterialInstance } from \"../materials\";\r\n\r\ntype ParticleStyleBundle = ParticleSystemConfig & {\r\n translateZ: number;\r\n scale: number;\r\n rotateX: number;\r\n rotateY: number;\r\n rotateZ: number;\r\n particlesFit: boolean;\r\n materialType: string;\r\n};\r\n\r\nconst DEG_TO_RAD = Math.PI / 180;\r\n\r\nconst DEFAULT_CONFIG: ParticleSystemConfig = {\r\n mode: \"emitter\",\r\n count: 300,\r\n size: 2,\r\n color: \"#ffffff\",\r\n opacity: 1,\r\n spread: 120,\r\n spreadX: 120,\r\n spreadY: 120,\r\n seed: 1,\r\n emitRate: 30,\r\n emitBurst: 0,\r\n particleLife: 2.5,\r\n particleSpeed: 40,\r\n particleDirection: [0, 1, 0],\r\n particleGravity: [0, -30, 0],\r\n particleDrag: 0.1,\r\n particleSizeVariation: 0.6,\r\n particleColorVariation: 0.2,\r\n particleShape: \"sphere\",\r\n particleModelUrl: \"\",\r\n particleModelLoader: \"\",\r\n particleModelNode: \"\",\r\n instanceShape: \"sphere\",\r\n instanceModelUrl: \"\",\r\n instanceModelLoader: \"\",\r\n instanceModelNode: \"\",\r\n instanceScale: 1,\r\n instanceScaleVariation: 0.5,\r\n instanceRotationSpeed: 0.4,\r\n instanceJitter: 0.2,\r\n instanceFlow: 0.3,\r\n instanceDisperse: 0,\r\n instanceDisperseScatter: 0,\r\n instanceDisperseScatterX: 0,\r\n instanceDisperseScatterY: 0,\r\n instanceDisperseScatterZ: 0,\r\n modelTransitionDuration: 0,\r\n};\r\n\r\nexport class ParticlesSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<ParticleStyleBundle>();\r\n private static lastConfig: WeakMap<String3DObject, ParticleSystemConfig> = new WeakMap();\r\n private static lastTime: WeakMap<String3DObject, number> = new WeakMap();\r\n private static lastMaterialType: WeakMap<String3DObject, string> = new WeakMap();\r\n private static materialInstances: WeakMap<String3DObject, IMaterialInstance> = new WeakMap();\r\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n const cached = (el as any).__layoutCache;\r\n const rect = cached ? cached.rect : el.getBoundingClientRect();\r\n const bundle = this.readStyleBundle(el, ctx);\r\n\r\n const screenCenterX = rect.left + rect.width * 0.5;\r\n const screenCenterY = rect.top + rect.height * 0.5;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n object.object.position.set(\r\n screenCenterX - ctx.viewportWidth / 2,\r\n -(screenCenterY - ctx.viewportHeight / 2),\r\n bundle.translateZ,\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(bundle.translateZ);\r\n const normalizedX = screenCenterX / ctx.viewportWidth;\r\n const normalizedY = screenCenterY / ctx.viewportHeight;\r\n object.object.position.set(\r\n (normalizedX - 0.5) * frustum.width,\r\n -(normalizedY - 0.5) * frustum.height,\r\n bundle.translateZ,\r\n );\r\n }\r\n\r\n const parentScale = parentData?.scale ?? 1;\r\n const scale = bundle.scale * parentScale;\r\n object.object.scale.set(scale, scale, scale);\r\n\r\n object.object.rotation.x = -bundle.rotateX * DEG_TO_RAD;\r\n object.object.rotation.y = bundle.rotateY * DEG_TO_RAD;\r\n object.object.rotation.z = -bundle.rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n const config = this.buildConfig(bundle, rect, ctx, parentData);\n const prev = ParticlesSynchronizer.lastConfig.get(object);\n const particleSystem = object.object as I3DParticleSystem;\n if (!prev || !this.isSameConfig(prev, config)) {\n ParticlesSynchronizer.lastConfig.set(object, config);\n particleSystem.setConfig?.(config);\n }\n\r\n this.updateMaterialOverrides(el, object, ctx, bundle);\r\n this.updateCustomUniforms(el, object, ctx);\r\n\r\n const now = performance.now();\n const last = ParticlesSynchronizer.lastTime.get(object) ?? now;\n const dt = Math.max(0, (now - last) / 1000);\n ParticlesSynchronizer.lastTime.set(object, now);\n particleSystem.update?.(dt);\n\r\n return { scale: parentData?.scale ?? 1 };\r\n }\r\n\r\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): ParticleStyleBundle {\r\n return ParticlesSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styles = new StyleReader(el);\r\n const modeRaw = styles.readString(\"--particles-mode\", DEFAULT_CONFIG.mode).toLowerCase();\r\n const mode = modeRaw === \"instanced\" ? \"instanced\" : \"emitter\";\r\n return {\r\n ...DEFAULT_CONFIG,\r\n translateZ: styles.readNumber(\"--translate-z\", 0),\r\n scale: styles.readNumber(\"--scale\", 1),\r\n rotateX: styles.readNumber(\"--rotate-x\", 0),\r\n rotateY: styles.readNumber(\"--rotate-y\", 0),\r\n rotateZ: styles.readNumber(\"--rotate-z\", 0),\r\n particlesFit: styles.readNumber(\"--particles-fit\", 0) > 0.5,\r\n materialType: styles.readString(\"--material-type\", \"basic\"),\r\n mode,\r\n count: styles.readNumber(\"--particles-count\", DEFAULT_CONFIG.count),\r\n size: styles.readNumber(\"--particles-size\", DEFAULT_CONFIG.size),\r\n color: styles.readString(\"--particles-color\", DEFAULT_CONFIG.color),\r\n opacity: styles.readNumber(\"--particles-opacity\", DEFAULT_CONFIG.opacity),\r\n spread: styles.readNumber(\"--particles-spread\", DEFAULT_CONFIG.spread),\r\n seed: styles.readNumber(\"--particles-seed\", DEFAULT_CONFIG.seed),\r\n emitRate: styles.readNumber(\"--emit-rate\", DEFAULT_CONFIG.emitRate),\r\n emitBurst: styles.readNumber(\"--emit-burst\", DEFAULT_CONFIG.emitBurst),\r\n particleLife: styles.readNumber(\"--particle-life\", DEFAULT_CONFIG.particleLife),\r\n particleSpeed: styles.readNumber(\"--particle-speed\", DEFAULT_CONFIG.particleSpeed),\r\n particleDirection: this.parseVec3(\r\n styles.readString(\"--particle-direction\", \"0 1 0\"),\r\n DEFAULT_CONFIG.particleDirection,\r\n ),\r\n particleGravity: this.parseVec3(\r\n styles.readString(\"--particle-gravity\", \"0 -30 0\"),\r\n DEFAULT_CONFIG.particleGravity,\r\n ),\r\n particleDrag: styles.readNumber(\"--particle-drag\", DEFAULT_CONFIG.particleDrag),\r\n particleSizeVariation: styles.readNumber(\r\n \"--particle-size-variation\",\r\n DEFAULT_CONFIG.particleSizeVariation,\r\n ),\r\n particleColorVariation: styles.readNumber(\r\n \"--particle-color-variation\",\r\n DEFAULT_CONFIG.particleColorVariation,\r\n ),\r\n particleShape: this.parseShape(\r\n styles.readString(\"--particles-shape\", DEFAULT_CONFIG.particleShape),\r\n ),\r\n particleModelUrl: styles.readString(\"--particles-model\", DEFAULT_CONFIG.particleModelUrl),\r\n particleModelLoader: styles.readString(\r\n \"--particles-model-loader\",\r\n DEFAULT_CONFIG.particleModelLoader,\r\n ),\r\n particleModelNode: styles.readString(\r\n \"--particles-model-node\",\r\n DEFAULT_CONFIG.particleModelNode,\r\n ),\r\n instanceShape: this.parseDistribution(\r\n styles.readString(\"--instance-shape\", DEFAULT_CONFIG.instanceShape),\r\n ),\r\n instanceModelUrl: styles.readString(\"--instance-model\", DEFAULT_CONFIG.instanceModelUrl),\r\n instanceModelLoader: styles.readString(\r\n \"--instance-model-loader\",\r\n DEFAULT_CONFIG.instanceModelLoader,\r\n ),\r\n instanceModelNode: styles.readString(\r\n \"--instance-model-node\",\r\n DEFAULT_CONFIG.instanceModelNode,\r\n ),\r\n instanceScale: styles.readNumber(\"--instance-scale\", DEFAULT_CONFIG.instanceScale),\r\n instanceScaleVariation: styles.readNumber(\r\n \"--instance-scale-variation\",\r\n DEFAULT_CONFIG.instanceScaleVariation,\r\n ),\r\n instanceRotationSpeed: styles.readNumber(\r\n \"--instance-rotation-speed\",\r\n DEFAULT_CONFIG.instanceRotationSpeed,\r\n ),\r\n instanceJitter: styles.readNumber(\"--instance-jitter\", DEFAULT_CONFIG.instanceJitter),\r\n instanceFlow: styles.readNumber(\"--instance-flow\", DEFAULT_CONFIG.instanceFlow),\r\n instanceDisperse: styles.readNumber(\"--instance-disperse\", DEFAULT_CONFIG.instanceDisperse),\r\n instanceDisperseScatter: styles.readNumber(\r\n \"--instance-scatter\",\r\n DEFAULT_CONFIG.instanceDisperseScatter,\r\n ),\r\n instanceDisperseScatterX: styles.readNumber(\r\n \"--instance-scatter-x\",\r\n DEFAULT_CONFIG.instanceDisperseScatterX,\r\n ),\r\n instanceDisperseScatterY: styles.readNumber(\r\n \"--instance-scatter-y\",\r\n DEFAULT_CONFIG.instanceDisperseScatterY,\r\n ),\r\n instanceDisperseScatterZ: styles.readNumber(\r\n \"--instance-scatter-z\",\r\n DEFAULT_CONFIG.instanceDisperseScatterZ,\r\n ),\r\n modelTransitionDuration: this.getTransitionDuration(el, \"--instance-model\"),\r\n };\r\n });\r\n }\r\n\r\n private getTransitionDuration(el: HTMLElement, property: string): number {\r\n const style = getComputedStyle(el);\r\n const properties = this.splitTransitionList(style.transitionProperty);\r\n const durations = this.splitTransitionList(style.transitionDuration);\r\n\r\n const index = this.findTransitionIndex(properties, property);\r\n if (index === -1) {\r\n const shorthand = this.parseTransitionShorthand(style.transition);\r\n const match = shorthand.get(property) || shorthand.get(\"all\");\r\n return match ? match.duration : 0;\r\n }\r\n\r\n return this.parseTime(durations[index] || durations[durations.length - 1] || \"0s\");\r\n }\r\n\r\n private splitTransitionList(value: string): string[] {\r\n const result: string[] = [];\r\n let current = \"\";\r\n let depth = 0;\r\n for (let i = 0; i < value.length; i += 1) {\r\n const ch = value[i];\r\n if (ch === \"(\") depth += 1;\r\n if (ch === \")\") depth = Math.max(0, depth - 1);\r\n if (ch === \",\" && depth === 0) {\r\n result.push(current.trim());\r\n current = \"\";\r\n } else {\r\n current += ch;\r\n }\r\n }\r\n if (current.trim()) result.push(current.trim());\r\n return result.length > 0 ? result : [\"all\"];\r\n }\r\n\r\n private findTransitionIndex(properties: string[], name: string): number {\r\n const normalized = properties.map((prop) => prop.trim().toLowerCase());\r\n let index = normalized.indexOf(name);\r\n if (index === -1) {\r\n index = normalized.indexOf(\"all\");\r\n }\r\n return index;\r\n }\r\n\r\n private parseTime(value: string): number {\r\n const raw = value.trim().toLowerCase();\r\n if (raw.endsWith(\"ms\")) {\r\n const num = Number.parseFloat(raw.slice(0, -2));\r\n return Number.isFinite(num) ? num / 1000 : 0;\r\n }\r\n if (raw.endsWith(\"s\")) {\r\n const num = Number.parseFloat(raw.slice(0, -1));\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n const num = Number.parseFloat(raw);\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n\r\n private parseTransitionShorthand(value: string): Map<string, { duration: number }> {\r\n const map = new Map<string, { duration: number }>();\r\n const parts = this.splitTransitionList(value);\r\n parts.forEach((part) => {\r\n if (!part) return;\r\n const tokens = part.trim().split(/\\s+(?![^()]*\\))/g);\r\n let prop = \"\";\r\n let duration = \"\";\r\n tokens.forEach((token) => {\r\n const lower = token.toLowerCase();\r\n if (lower.endsWith(\"ms\") || lower.endsWith(\"s\") || /^[0-9.]+$/.test(lower)) {\r\n if (!duration) duration = lower;\r\n } else if (\r\n lower.startsWith(\"cubic-bezier\") ||\r\n lower.startsWith(\"steps\") ||\r\n lower === \"linear\" ||\r\n lower === \"ease\" ||\r\n lower === \"ease-in\" ||\r\n lower === \"ease-out\" ||\r\n lower === \"ease-in-out\"\r\n ) {\r\n } else if (!prop) {\r\n prop = token;\r\n }\r\n });\r\n if (!prop) return;\r\n map.set(prop.trim().toLowerCase(), {\r\n duration: this.parseTime(duration || \"0s\"),\r\n });\r\n });\r\n return map;\r\n }\r\n\r\n private parseVec3(value: string, fallback: [number, number, number]): [number, number, number] {\r\n const parts = value\r\n .split(/[\\s,]+/)\r\n .map((part) => Number.parseFloat(part))\r\n .filter((num) => !Number.isNaN(num));\r\n if (parts.length >= 3) {\r\n return [parts[0], parts[1], parts[2]];\r\n }\r\n return fallback;\r\n }\r\n\r\n private parseShape(value: string): \"box\" | \"sphere\" | \"model\" {\r\n const normalized = value.trim().toLowerCase();\r\n if (normalized === \"box\") return \"box\";\r\n if (normalized === \"model\") return \"model\";\r\n return \"sphere\";\r\n }\r\n\r\n private parseDistribution(value: string): \"box\" | \"sphere\" | \"model\" {\r\n return this.parseShape(value);\r\n }\r\n\r\n private buildConfig(\r\n bundle: ParticleStyleBundle,\r\n rect: DOMRect,\r\n ctx: SyncContext,\r\n parentData: any,\r\n ): ParticleSystemConfig {\r\n const parentScale = parentData?.scale ?? 1;\r\n const scale = parentScale;\r\n const fitMultiplier = 0.5;\r\n let spread: number;\r\n let spreadX: number;\r\n let spreadY: number;\r\n if (bundle.particlesFit) {\r\n spreadX = this.toWorld(rect.width * fitMultiplier, bundle.translateZ, ctx);\r\n spreadY = this.toWorld(rect.height * fitMultiplier, bundle.translateZ, ctx);\r\n spread = Math.max(spreadX, spreadY);\r\n } else {\r\n spread = this.toWorld(bundle.spread, bundle.translateZ, ctx);\r\n spreadX = spread;\r\n spreadY = spread;\r\n }\r\n return {\r\n ...bundle,\r\n count: Math.max(0, Math.floor(bundle.count)),\r\n size: Math.max(0.1, bundle.size),\r\n opacity: Math.max(0, Math.min(1, bundle.opacity)),\r\n spread: Math.max(0, spread * scale),\r\n spreadX: Math.max(0, spreadX * scale),\r\n spreadY: Math.max(0, spreadY * scale),\r\n seed: Math.max(0, Math.floor(bundle.seed)),\r\n emitRate: Math.max(0, bundle.emitRate),\r\n emitBurst: Math.max(0, bundle.emitBurst),\r\n particleLife: Math.max(0.1, bundle.particleLife),\r\n particleSpeed: Math.max(0, bundle.particleSpeed),\r\n particleDrag: Math.max(0, Math.min(1, bundle.particleDrag)),\r\n particleSizeVariation: Math.max(0, bundle.particleSizeVariation),\r\n particleColorVariation: Math.max(0, bundle.particleColorVariation),\r\n instanceScale: Math.max(0.1, bundle.instanceScale),\r\n instanceScaleVariation: Math.max(0, bundle.instanceScaleVariation),\r\n instanceRotationSpeed: Math.max(0, bundle.instanceRotationSpeed),\r\n instanceJitter: Math.max(0, bundle.instanceJitter),\r\n instanceFlow: Math.max(0, bundle.instanceFlow),\r\n instanceDisperse: Math.max(0, bundle.instanceDisperse),\r\n instanceDisperseScatter: Math.max(0, bundle.instanceDisperseScatter),\r\n instanceDisperseScatterX: Math.max(0, bundle.instanceDisperseScatterX),\r\n instanceDisperseScatterY: Math.max(0, bundle.instanceDisperseScatterY),\r\n instanceDisperseScatterZ: Math.max(0, bundle.instanceDisperseScatterZ),\r\n };\r\n }\r\n\r\n private toWorld(value: number, z: number, ctx: SyncContext): number {\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n return value;\r\n }\r\n const frustum = ctx.camera.getFrustumSizeAt(z);\r\n const perPixel = frustum.width / Math.max(1, ctx.viewportWidth);\r\n return value * perPixel;\r\n }\r\n\r\n private isSameConfig(a: ParticleSystemConfig, b: ParticleSystemConfig): boolean {\r\n return JSON.stringify(a) === JSON.stringify(b);\r\n }\r\n\r\n private updateMaterialOverrides(\n el: HTMLElement,\n object: String3DObject,\n ctx: SyncContext,\n bundle: ParticleStyleBundle,\n ): void {\n const particleSystem = object.object as I3DParticleSystem;\n const typeRaw = bundle.materialType || \"basic\";\n const type = typeRaw.split(\"[\")[0].trim().toLowerCase();\r\n const customMaterialRegistry =\r\n ctx.engine.getCustomMaterialRegistry?.() || String3DCustomMaterialRegistry;\r\n const definition = customMaterialRegistry.get(type);\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n\r\n if (!definition || !factory || !factory.supports(definition)) {\r\n const hasExisting =\r\n ParticlesSynchronizer.materialInstances.has(object) ||\r\n ParticlesSynchronizer.lastMaterialType.has(object);\r\n if (!hasExisting) return;\r\n\r\n const existing = ParticlesSynchronizer.materialInstances.get(object);\r\n if (existing) {\r\n existing.dispose();\r\n ParticlesSynchronizer.materialInstances.delete(object);\r\n }\r\n ParticlesSynchronizer.lastMaterialType.delete(object);\r\n particleSystem.setMaterial?.(null, { points: true, meshes: true });\n return;\n }\n\r\n const lastType = ParticlesSynchronizer.lastMaterialType.get(object);\r\n if (lastType !== type) {\r\n const existing = ParticlesSynchronizer.materialInstances.get(object);\r\n if (existing) existing.dispose();\r\n\r\n const style = getComputedStyle(el);\r\n const initialUniforms = factory.parseUniformsFromCSS(definition, el, style);\r\n const instance = factory.create(definition, initialUniforms);\r\n ParticlesSynchronizer.materialInstances.set(object, instance);\r\n ParticlesSynchronizer.lastMaterialType.set(object, type);\r\n\r\n const material = instance.material;\n const isShader = factory.isShaderMaterial?.(material) ?? !!material?.isShaderMaterial;\n particleSystem.setMaterial?.(material, { meshes: true, points: false });\n particleSystem.setMaterial?.(isShader ? material : null, { meshes: false, points: true });\n }\n }\n\r\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n if (!factory) return;\r\n\r\n const style = getComputedStyle(el);\r\n\r\n const apply = (mat: any) => {\r\n const definition = factory.getMaterialDefinition?.(mat) ?? mat?.userData?.definition;\r\n if (!definition?.uniforms) return;\r\n\r\n const values = factory.parseUniformsFromCSS(definition, el, style);\r\n\r\n if (typeof factory.applyUniforms === \"function\") {\r\n factory.applyUniforms(mat, definition, values);\r\n return;\r\n }\r\n\r\n for (const [key, value] of Object.entries(values)) {\r\n const def = definition.uniforms?.[key];\r\n if (!def) continue;\r\n\r\n const converter = (factory as any).convertUniformValue?.bind(factory);\r\n const converted = converter ? converter(def.type, value) : value;\r\n\r\n if (mat.uniforms?.[key]) {\n mat.uniforms[key].value = converted;\n }\n }\n };\n ctx.engine.forEachMaterial(object.object, apply);\n }\n}\n","export type String3DFontEntry = {\r\n name: string;\r\n url: string;\r\n};\r\n\r\nexport class String3DFontRegistry {\r\n private static fonts: Map<string, String3DFontEntry> = new Map();\r\n private static defaultFont: string | null = null;\r\n\r\n private static normalizeKey(name: string): string {\r\n return name.trim().toLowerCase();\r\n }\r\n\r\n static register(name: string, url: string): void {\r\n const normalized = name.trim();\r\n if (!normalized) return;\r\n this.fonts.set(this.normalizeKey(normalized), { name: normalized, url });\r\n }\r\n\r\n static setDefault(name: string): void {\r\n const normalized = name.trim();\r\n if (!normalized) return;\r\n this.defaultFont = this.normalizeKey(normalized);\r\n }\r\n\r\n static get(name: string): String3DFontEntry | undefined {\r\n return this.fonts.get(this.normalizeKey(name));\r\n }\r\n\r\n static list(): String3DFontEntry[] {\r\n return Array.from(this.fonts.values());\r\n }\r\n\r\n static resolveFontFamily(fontFamily: string): String3DFontEntry | null {\r\n if (!fontFamily) {\r\n return this.getDefault();\r\n }\r\n\r\n const families = fontFamily\r\n .split(\",\")\r\n .map((value) => value.trim().replace(/^[\"']|[\"']$/g, \"\"))\r\n .filter(Boolean);\r\n\r\n for (const family of families) {\r\n const entry = this.fonts.get(this.normalizeKey(family));\r\n if (entry) return entry;\r\n }\r\n\r\n return this.getDefault();\r\n }\r\n\r\n private static getDefault(): String3DFontEntry | null {\r\n if (!this.defaultFont) return null;\r\n return this.fonts.get(this.defaultFont) || null;\r\n }\r\n}\r\n","export interface FontData {\r\n glyphs: Record<string, GlyphData>;\r\n familyName: string;\r\n ascender: number;\r\n descender: number;\r\n underlinePosition: number;\r\n underlineThickness: number;\r\n boundingBox: { xMin: number; xMax: number; yMin: number; yMax: number };\r\n resolution: number;\r\n outlineFormat: string;\r\n original_font_information: Record<string, any>;\r\n}\r\n\r\nexport interface GlyphData {\r\n ha: number;\r\n x_min: number;\r\n x_max: number;\r\n o: string;\r\n}\r\n\r\nexport type FontSource = string | ArrayBuffer | Uint8Array;\r\n\r\nlet opentypePromise: Promise<any> | null = null;\r\nlet opentypeModule: any = null;\r\n\r\nlet woff2Promise: Promise<any> | null = null;\r\nlet woff2Module: any = null;\r\n\r\nasync function loadOpentype(): Promise<any> {\r\n if (opentypeModule) {\r\n return opentypeModule;\r\n }\r\n\r\n if (!opentypePromise) {\r\n opentypePromise = (async () => {\r\n if (typeof window !== \"undefined\" && (window as any).opentype) {\r\n opentypeModule = (window as any).opentype;\r\n return opentypeModule;\r\n }\r\n\r\n return new Promise((resolve, reject) => {\r\n if (typeof document === \"undefined\") {\r\n reject(new Error(\"[FontConverter] Cannot load opentype.js in non-browser environment\"));\r\n return;\r\n }\r\n const script = document.createElement(\"script\");\r\n script.src = \"https://cdn.jsdelivr.net/npm/opentype.js@1.3.4/dist/opentype.min.js\";\r\n script.onload = () => {\r\n opentypeModule = (window as any).opentype;\r\n resolve(opentypeModule);\r\n };\r\n script.onerror = () => reject(new Error(\"[FontConverter] Failed to load opentype.js\"));\r\n document.head.appendChild(script);\r\n });\r\n })();\r\n }\r\n return opentypePromise;\r\n}\r\n\r\nasync function loadWoff2Decoder(): Promise<any> {\r\n if (woff2Module) {\r\n return woff2Module;\r\n }\r\n\r\n if (!woff2Promise) {\r\n woff2Promise = (async () => {\r\n if (typeof window !== \"undefined\" && (window as any).Module?.decompress) {\r\n woff2Module = (window as any).Module;\r\n return woff2Module;\r\n }\r\n\r\n return new Promise((resolve, reject) => {\r\n if (typeof document === \"undefined\") {\r\n reject(new Error(\"[FontConverter] Cannot load woff2 decoder in non-browser environment\"));\r\n return;\r\n }\r\n const script = document.createElement(\"script\");\r\n script.src = \"https://cdn.jsdelivr.net/npm/wawoff2@2.0.1/build/decompress_binding.js\";\r\n script.onload = () => {\r\n let attempts = 0;\r\n const maxAttempts = 500;\r\n const checkReady = () => {\r\n attempts++;\r\n const win = window as any;\r\n if (win.Module?.decompress) {\r\n woff2Module = win.Module;\r\n resolve(woff2Module);\r\n } else if (attempts >= maxAttempts) {\r\n reject(new Error(\"[FontConverter] woff2 decoder initialization timeout\"));\r\n } else {\r\n setTimeout(checkReady, 10);\r\n }\r\n };\r\n checkReady();\r\n };\r\n script.onerror = () => {\r\n reject(new Error(\"[FontConverter] Failed to load woff2 decoder\"));\r\n };\r\n document.head.appendChild(script);\r\n });\r\n })();\r\n }\r\n return woff2Promise;\r\n}\r\n\r\nasync function decompressWoff2(buffer: ArrayBuffer): Promise<ArrayBuffer> {\r\n const woff2 = await loadWoff2Decoder();\r\n const inputArray = new Uint8Array(buffer);\r\n const outputArray = woff2.decompress(inputArray);\r\n\r\n if (outputArray instanceof Uint8Array) {\r\n const newBuffer = new ArrayBuffer(outputArray.length);\r\n const newArray = new Uint8Array(newBuffer);\r\n newArray.set(outputArray);\r\n return newBuffer;\r\n }\r\n\r\n return outputArray.buffer;\r\n}\r\n\r\nfunction isWoff2(buffer: ArrayBuffer): boolean {\r\n const view = new DataView(buffer);\r\n return view.getUint32(0, false) === 0x774f4632;\r\n}\r\n\r\nfunction isWoff(buffer: ArrayBuffer): boolean {\r\n const view = new DataView(buffer);\r\n return view.getUint32(0, false) === 0x774f4646;\r\n}\r\n\r\nexport class FontConverter {\r\n private static cache: Map<string, FontData> = new Map();\r\n private static loadingPromises: Map<string, Promise<FontData>> = new Map();\r\n\r\n static async load(source: FontSource): Promise<FontData> {\r\n const cacheKey = typeof source === \"string\" ? source : \"buffer-\" + Date.now();\r\n\r\n const cached = this.cache.get(cacheKey);\r\n if (cached) return cached;\r\n\r\n const loading = this.loadingPromises.get(cacheKey);\r\n if (loading) return loading;\r\n\r\n const promise = this.doLoad(source, cacheKey);\r\n this.loadingPromises.set(cacheKey, promise);\r\n\r\n try {\r\n const result = await promise;\r\n this.cache.set(cacheKey, result);\r\n return result;\r\n } finally {\r\n this.loadingPromises.delete(cacheKey);\r\n }\r\n }\r\n\r\n private static async doLoad(source: FontSource, cacheKey: string): Promise<FontData> {\r\n const opentype = await loadOpentype();\r\n\r\n let buffer: ArrayBuffer;\r\n\r\n if (typeof source === \"string\") {\r\n const response = await fetch(source);\r\n buffer = await response.arrayBuffer();\r\n } else if (source instanceof ArrayBuffer) {\r\n buffer = source;\r\n } else if (source instanceof Uint8Array) {\r\n buffer = source.buffer as ArrayBuffer;\r\n } else {\r\n throw new Error(\"[FontConverter] Invalid font source\");\r\n }\r\n\r\n if (isWoff2(buffer)) {\r\n buffer = await decompressWoff2(buffer);\r\n }\r\n\r\n const font = opentype.parse(buffer);\r\n\r\n if (!font) {\r\n throw new Error(\"[FontConverter] Failed to parse font\");\r\n }\r\n\r\n return this.convertToTypeFace(font);\r\n }\r\n\r\n private static convertToTypeFace(font: any): FontData {\r\n const scale = 1000 / font.unitsPerEm;\r\n\r\n const glyphs: Record<string, GlyphData> = {};\r\n\r\n const cmap = font.tables?.cmap?.glyphIndexMap;\r\n if (cmap && typeof cmap === \"object\") {\r\n for (const [codeStr, glyphIndex] of Object.entries(cmap)) {\r\n const code = Number(codeStr);\r\n if (!Number.isFinite(code)) continue;\r\n const glyph = font.glyphs.get(glyphIndex as number);\r\n if (!glyph) continue;\r\n\r\n const path = glyph.getPath(0, 0, font.unitsPerEm);\r\n const outline = this.pathToOutline(path, scale);\r\n const advanceWidth = glyph.advanceWidth ?? glyph.xMax ?? font.unitsPerEm * 0.5;\r\n const char = String.fromCharCode(code);\r\n if (glyphs[char]) continue;\r\n glyphs[char] = {\r\n ha: Math.round(advanceWidth * scale),\r\n x_min: glyph.xMin !== undefined ? Math.round(glyph.xMin * scale) : 0,\r\n x_max: glyph.xMax !== undefined ? Math.round(glyph.xMax * scale) : 0,\r\n o: outline,\r\n };\r\n }\r\n } else {\r\n for (let i = 0; i < font.glyphs.length; i++) {\r\n const glyph = font.glyphs.get(i);\r\n const unicodeValues = Array.isArray(glyph.unicodes)\r\n ? glyph.unicodes\r\n : glyph.unicode\r\n ? [glyph.unicode]\r\n : [];\r\n if (unicodeValues.length === 0) continue;\r\n\r\n const path = glyph.getPath(0, 0, font.unitsPerEm);\r\n const outline = this.pathToOutline(path, scale);\r\n const advanceWidth = glyph.advanceWidth ?? glyph.xMax ?? font.unitsPerEm * 0.5;\r\n\r\n unicodeValues.forEach((code: number) => {\r\n if (!Number.isFinite(code)) return;\r\n const char = String.fromCharCode(code);\r\n if (glyphs[char]) return;\r\n glyphs[char] = {\r\n ha: Math.round(advanceWidth * scale),\r\n x_min: glyph.xMin !== undefined ? Math.round(glyph.xMin * scale) : 0,\r\n x_max: glyph.xMax !== undefined ? Math.round(glyph.xMax * scale) : 0,\r\n o: outline,\r\n };\r\n });\r\n }\r\n }\r\n\r\n if (!glyphs[\" \"]) {\r\n const spaceGlyph = font.charToGlyph(\" \");\r\n glyphs[\" \"] = {\r\n ha: Math.round((spaceGlyph?.advanceWidth || font.unitsPerEm * 0.25) * scale),\r\n x_min: 0,\r\n x_max: 0,\r\n o: \"\",\r\n };\r\n }\r\n\r\n return {\r\n glyphs,\r\n familyName: font.names.fontFamily?.en || font.names.fullName?.en || \"Unknown\",\r\n ascender: Math.round(font.ascender * scale),\r\n descender: Math.round(font.descender * scale),\r\n underlinePosition: Math.round((font.tables.post?.underlinePosition || -100) * scale),\r\n underlineThickness: Math.round((font.tables.post?.underlineThickness || 50) * scale),\r\n boundingBox: {\r\n xMin: Math.round((font.tables.head?.xMin || 0) * scale),\r\n xMax: Math.round((font.tables.head?.xMax || 1000) * scale),\r\n yMin: Math.round((font.tables.head?.yMin || -200) * scale),\r\n yMax: Math.round((font.tables.head?.yMax || 800) * scale),\r\n },\r\n resolution: 1000,\r\n outlineFormat: (font.outlinesFormat || font.outlineFormat || \"\").toString(),\r\n original_font_information: {\r\n format: 0,\r\n copyright: font.names.copyright?.en || \"\",\r\n fontFamily: font.names.fontFamily?.en || \"\",\r\n fontSubfamily: font.names.fontSubfamily?.en || \"\",\r\n uniqueID: font.names.uniqueID?.en || \"\",\r\n fullName: font.names.fullName?.en || \"\",\r\n version: font.names.version?.en || \"\",\r\n postScriptName: font.names.postScriptName?.en || \"\",\r\n },\r\n };\r\n }\r\n\r\n private static pathToOutline(path: any, scale: number): string {\r\n const commands: string[] = [];\r\n\r\n for (const cmd of path.commands) {\r\n switch (cmd.type) {\r\n case \"M\":\r\n commands.push(`m ${this.round(cmd.x * scale)} ${this.round(cmd.y * scale)}`);\r\n break;\r\n case \"L\":\r\n commands.push(`l ${this.round(cmd.x * scale)} ${this.round(cmd.y * scale)}`);\r\n break;\r\n case \"Q\":\r\n commands.push(\r\n `q ${this.round(cmd.x1 * scale)} ${this.round(cmd.y1 * scale)} ${this.round(\r\n cmd.x * scale\r\n )} ${this.round(cmd.y * scale)}`\r\n );\r\n break;\r\n case \"C\":\r\n commands.push(\r\n `b ${this.round(cmd.x1 * scale)} ${this.round(cmd.y1 * scale)} ${this.round(\r\n cmd.x2 * scale\r\n )} ${this.round(cmd.y2 * scale)} ${this.round(cmd.x * scale)} ${this.round(\r\n cmd.y * scale\r\n )}`\r\n );\r\n break;\r\n case \"Z\":\r\n commands.push(\"z\");\r\n break;\r\n }\r\n }\r\n\r\n return commands.join(\" \");\r\n }\r\n\r\n private static round(value: number): number {\r\n return Math.round(value * 10000) / 10000;\r\n }\r\n\r\n static isTypefaceJson(url: string): boolean {\r\n const lower = url.toLowerCase();\r\n return lower.endsWith(\".json\") || lower.includes(\"typeface\");\r\n }\r\n\r\n static isFontFile(url: string): boolean {\r\n const lower = url.toLowerCase();\r\n const fontExtensions = /\\.(ttf|otf|woff2?)(\\?|$)/i;\r\n if (fontExtensions.test(lower)) return true;\r\n if (lower.includes(\"fonts.gstatic.com\")) return true;\r\n if (lower.includes(\"/fonts/\") && !lower.endsWith(\".json\")) return true;\r\n return false;\r\n }\r\n\r\n static clearCache(): void {\r\n this.cache.clear();\r\n }\r\n}\r\n","import { String3DObject } from \"../String3DObject\";\r\nimport type { SyncContext } from \"./SyncContext\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\nimport { StyleBundleCache } from \"./StyleBundleCache\";\r\nimport { String3DFontRegistry } from \"../text\";\r\nimport { MeshSynchronizer } from \"./MeshSynchronizer\";\r\n\r\nconst DEG_TO_RAD = Math.PI / 180;\r\n\r\nconst PSEUDO_ELEMENT_CSS = `\r\n[data-string3d-text] {\r\n -webkit-text-fill-color: transparent;\r\n}\r\n\r\n[data-string3d-text]::before {\r\n content: attr(data-string3d-text);\r\n position: absolute;\r\n left: 0;\r\n top: 0;\r\n width: 100%;\r\n height: 100%;\r\n pointer-events: none;\r\n \r\n color: inherit;\r\n -webkit-text-fill-color: initial;\r\n font: inherit;\r\n text-transform: inherit;\r\n letter-spacing: inherit;\r\n line-height: inherit;\r\n text-align: inherit;\r\n white-space: inherit;\r\n word-spacing: inherit;\r\n \r\n transform: var(--string3d-transform, none);\r\n transform-style: preserve-3d;\r\n transform-origin: center center;\r\n}\r\n`;\r\n\r\nexport class TextSynchronizer implements String3DObjectSyncStrategy {\r\n private static styleCache = new StyleBundleCache<StyleBundle>();\r\n private static layoutCache = new StyleBundleCache<LayoutBundle>();\r\n private static geometryKeys: WeakMap<String3DObject, string> = new WeakMap();\r\n private static lastMaterialType: WeakMap<String3DObject, string> = new WeakMap();\r\n private static fontCache: Map<string, any> = new Map();\r\n private static fontPromises: Map<string, Promise<any>> = new Map();\r\n private static pendingFontObjects: Map<string, Set<String3DObject>> = new Map();\r\n private static contentObservers: WeakMap<HTMLElement, MutationObserver> = new WeakMap();\r\n private static warnedMissingFont = false;\r\n private static warnedMissingLoader = false;\r\n private static pseudoStyleInjected = false;\r\n\r\n private static markObjectPendingFont(fontUrl: string, object: String3DObject): void {\r\n let set = this.pendingFontObjects.get(fontUrl);\r\n if (!set) {\r\n set = new Set();\r\n this.pendingFontObjects.set(fontUrl, set);\r\n }\r\n set.add(object);\r\n }\r\n\r\n private static clearObjectPendingFont(fontUrl: string, object: String3DObject): void {\r\n const set = this.pendingFontObjects.get(fontUrl);\r\n if (set) {\r\n set.delete(object);\r\n }\r\n }\r\n\r\n private static invalidatePendingObjects(fontUrl: string): void {\r\n const set = this.pendingFontObjects.get(fontUrl);\r\n if (set) {\r\n set.forEach((obj) => {\r\n this.geometryKeys.delete(obj);\r\n });\r\n set.clear();\r\n }\r\n }\r\n\r\n private static injectPseudoElementStyles(): void {\r\n if (this.pseudoStyleInjected || typeof document === \"undefined\") return;\r\n\r\n const style = document.createElement(\"style\");\r\n style.setAttribute(\"data-string3d\", \"pseudo-text\");\r\n style.textContent = PSEUDO_ELEMENT_CSS;\r\n document.head.appendChild(style);\r\n this.pseudoStyleInjected = true;\r\n }\r\n\r\n private static setupSelectableText(el: HTMLElement): void {\r\n const textContent = el.textContent || \"\";\r\n\r\n if (el.dataset.string3dText !== textContent) {\r\n el.dataset.string3dText = textContent;\r\n }\r\n\r\n const computed = getComputedStyle(el);\r\n if (computed.position === \"static\") {\r\n el.style.position = \"relative\";\r\n }\r\n\r\n const rx = computed.getPropertyValue(\"--rotate-x\").trim() || \"0\";\r\n const ry = computed.getPropertyValue(\"--rotate-y\").trim() || \"0\";\r\n const rz = computed.getPropertyValue(\"--rotate-z\").trim() || \"0\";\r\n const tx = computed.getPropertyValue(\"--translate-x\").trim() || \"0px\";\r\n const ty = computed.getPropertyValue(\"--translate-y\").trim() || \"0px\";\r\n const tz = computed.getPropertyValue(\"--translate-z\").trim() || \"0px\";\r\n const s = computed.getPropertyValue(\"--scale\").trim() || \"1\";\r\n\r\n const transform = [\r\n tx !== \"0px\" && tx !== \"0\" ? `translateX(${tx})` : \"\",\r\n ty !== \"0px\" && ty !== \"0\" ? `translateY(${ty})` : \"\",\r\n tz !== \"0px\" && tz !== \"0\" ? `translateZ(${tz})` : \"\",\r\n rx !== \"0\" ? `rotateX(${rx}deg)` : \"\",\r\n ry !== \"0\" ? `rotateY(${ry}deg)` : \"\",\r\n rz !== \"0\" ? `rotateZ(${rz}deg)` : \"\",\r\n s !== \"1\" ? `scale(${s})` : \"\",\r\n ]\r\n .filter(Boolean)\r\n .join(\" \");\r\n\r\n el.style.setProperty(\"--string3d-transform\", transform || \"none\");\r\n }\r\n\r\n private static setupContentObserver(\r\n el: HTMLElement,\r\n resolveObject: () => String3DObject | undefined,\r\n ): void {\r\n if (this.contentObservers.has(el)) return;\r\n\r\n let lastContent = el.textContent || \"\";\r\n\r\n const observer = new MutationObserver((mutations) => {\r\n const currentContent = el.textContent || \"\";\r\n if (currentContent === lastContent) {\r\n return;\r\n }\r\n\r\n lastContent = currentContent;\r\n\r\n const currentObject = resolveObject();\r\n\r\n if (currentObject) {\r\n this.geometryKeys.delete(currentObject);\r\n this.layoutCache.invalidate(el);\r\n\r\n if (el.dataset.string3dText !== currentContent) {\r\n el.dataset.string3dText = currentContent;\r\n }\r\n }\r\n });\r\n\r\n observer.observe(el, {\r\n characterData: true,\r\n childList: true,\r\n subtree: true,\r\n });\r\n\r\n this.contentObservers.set(el, observer);\r\n }\r\n\r\n private static cleanupContentObserver(el: HTMLElement): void {\r\n const observer = this.contentObservers.get(el);\r\n if (observer) {\r\n observer.disconnect();\r\n this.contentObservers.delete(el);\r\n }\r\n }\r\n\r\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\r\n TextSynchronizer.injectPseudoElementStyles();\r\n TextSynchronizer.setupSelectableText(el);\r\n TextSynchronizer.setupContentObserver(\r\n el,\r\n () => ctx.scene?.getObjectForElement(el) || object,\r\n );\r\n\r\n const { rect, width: originalWidth, height: originalHeight } = this.readLayout(el, ctx);\r\n const bundle = this.readStyleBundle(el, ctx);\r\n\r\n const {\r\n translateZ,\r\n cssScale,\r\n rotateX,\r\n rotateY,\r\n rotateZ,\r\n cssScaleZ,\r\n opacity,\r\n color,\r\n metalness,\r\n roughness,\r\n emissive,\r\n castShadow,\r\n receiveShadow,\r\n materialType,\r\n fontFamily,\r\n fontSize,\r\n textTransform,\r\n textDepth,\r\n textCurveSegments,\r\n bevelEnabled,\r\n bevelSize,\r\n bevelThickness,\r\n bevelOffset,\r\n bevelSegments,\r\n fontCss,\r\n } = bundle;\r\n\r\n const screenCenterX = rect.left + rect.width * 0.5;\r\n const screenCenterY = rect.top + rect.height * 0.5;\r\n\r\n if (ctx.camera.getMode() === \"orthographic\") {\r\n object.object.position.set(\r\n screenCenterX - ctx.viewportWidth / 2,\r\n -(screenCenterY - ctx.viewportHeight / 2),\r\n translateZ,\r\n );\r\n } else {\r\n const frustum = ctx.camera.getFrustumSizeAt(translateZ);\r\n const normalizedX = screenCenterX / ctx.viewportWidth;\r\n const normalizedY = screenCenterY / ctx.viewportHeight;\r\n object.object.position.set(\r\n (normalizedX - 0.5) * frustum.width,\r\n -(normalizedY - 0.5) * frustum.height,\r\n translateZ,\r\n );\r\n }\r\n\r\n object.object.rotation.x = -rotateX * DEG_TO_RAD;\r\n object.object.rotation.y = rotateY * DEG_TO_RAD;\r\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\r\n object.object.rotation.order = \"XYZ\";\r\n\r\n const layout = this.extractCharacterLayout(el, textTransform);\r\n const rawText = this.extractRawText(el, textTransform);\r\n const textContent = rawText || layout.map((l) => l.char).join(\"\");\r\n\r\n const mesh = this.getTextMesh(object, ctx);\r\n if (!mesh) {\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (layout.length === 0) {\r\n mesh.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (opacity === 0) {\r\n object.object.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n object.object.visible = true;\r\n\r\n mesh.visible = true;\r\n\r\n const fontEntry = String3DFontRegistry.resolveFontFamily(fontFamily || \"\");\r\n if (!fontEntry) {\r\n if (!TextSynchronizer.warnedMissingFont) {\r\n TextSynchronizer.warnedMissingFont = true;\r\n }\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n if (!ctx.engine.loadFont || !ctx.engine.createTextGeometry) {\r\n if (!TextSynchronizer.warnedMissingLoader) {\r\n TextSynchronizer.warnedMissingLoader = true;\r\n }\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n const fontUrl = fontEntry.url;\r\n let font = TextSynchronizer.fontCache.get(fontUrl);\r\n if (!font) {\r\n TextSynchronizer.markObjectPendingFont(fontUrl, object);\r\n if (!TextSynchronizer.fontPromises.has(fontUrl)) {\r\n const promise = ctx.engine.loadFont(fontUrl).then((loaded) => {\r\n if (loaded) {\r\n TextSynchronizer.fontCache.set(fontUrl, loaded);\r\n TextSynchronizer.invalidatePendingObjects(fontUrl);\r\n }\r\n return loaded;\r\n });\r\n TextSynchronizer.fontPromises.set(fontUrl, promise);\r\n }\r\n mesh.visible = false;\r\n return { scale: cssScale * (parentData?.scale || 1) };\r\n }\r\n\r\n TextSynchronizer.clearObjectPendingFont(fontUrl, object);\r\n\r\n const layoutSig =\r\n layout.length > 0\r\n ? `${layout.length}:${layout[0].x.toFixed(1)},${layout[0].y.toFixed(1)}:${layout[\r\n layout.length - 1\r\n ].x.toFixed(1)},${layout[layout.length - 1].y.toFixed(1)}`\r\n : \"empty\";\r\n const effectiveLayoutSig =\r\n ctx.engine.getTextGeometryLayoutSignature?.({\r\n text: textContent,\r\n layoutSignature: layoutSig,\r\n layout,\r\n elementWidth: rect.width,\r\n elementHeight: rect.height,\r\n fontSize,\r\n }) || layoutSig;\r\n\r\n const key = [\r\n textContent,\r\n fontSize.toFixed(3),\r\n fontCss || \"\",\r\n rect.width.toFixed(1),\r\n rect.height.toFixed(1),\r\n effectiveLayoutSig,\r\n textDepth.toFixed(3),\r\n textCurveSegments.toFixed(3),\r\n bevelEnabled ? \"1\" : \"0\",\r\n bevelSize.toFixed(3),\r\n bevelThickness.toFixed(3),\r\n bevelOffset.toFixed(3),\r\n bevelSegments.toFixed(3),\r\n ].join(\"|\");\r\n\r\n const prevKey = TextSynchronizer.geometryKeys.get(object);\r\n if (prevKey !== key) {\r\n const geometry = ctx.engine.createTextGeometry(textContent, font, {\r\n size: fontSize,\r\n height: textDepth,\r\n curveSegments: Math.max(1, Math.round(textCurveSegments)),\r\n bevelEnabled,\r\n bevelThickness,\r\n bevelSize,\r\n bevelOffset,\r\n bevelSegments: Math.max(0, Math.round(bevelSegments)),\r\n lineHeight: 0,\r\n letterSpacing: 0,\r\n align: \"left\",\r\n layout,\r\n elementWidth: rect.width,\r\n elementHeight: rect.height,\r\n });\r\n\r\n if (geometry) {\r\n geometry.computeBoundingBox();\r\n const appliedToMesh = ctx.engine.applyTextGeometryToMesh(mesh, geometry);\r\n if (!appliedToMesh) {\r\n if (mesh.geometry) {\r\n mesh.geometry.dispose?.();\r\n }\r\n mesh.geometry = geometry;\r\n }\r\n object.geometry = geometry;\r\n TextSynchronizer.geometryKeys.set(object, key);\r\n }\r\n }\r\n\r\n const parentScale = parentData?.scale || 1;\r\n const perPixel =\r\n ctx.camera.getMode() === \"orthographic\"\r\n ? 1\r\n : ctx.camera.getScaleAtZ(translateZ, ctx.viewportHeight);\r\n\r\n const scaleFactor = cssScale * parentScale * perPixel;\r\n\r\n const scaleZ = scaleFactor * cssScaleZ;\r\n object.object.scale.set(scaleFactor, scaleFactor, scaleZ);\r\n\r\n const localOffsetX = -originalWidth * 0.5;\r\n const localOffsetY = originalHeight * 0.5;\r\n\r\n mesh.position.set(localOffsetX, localOffsetY, 0);\r\n\r\n const prevMaterialType = TextSynchronizer.lastMaterialType.get(object);\r\n if (prevMaterialType !== undefined && prevMaterialType !== materialType) {\r\n const scene = ctx.scene;\r\n if (scene) {\r\n requestAnimationFrame(() => {\r\n scene.recreateMaterialForObject(object, el);\r\n });\r\n }\r\n }\r\n\r\n TextSynchronizer.lastMaterialType.set(object, materialType);\r\n\r\n MeshSynchronizer.applyVisualProps(el, object, ctx.engine, {\r\n opacity,\r\n color: color && color !== \"none\" ? color : undefined,\r\n metalness: Number.isFinite(metalness) ? metalness : undefined,\r\n roughness: Number.isFinite(roughness) ? roughness : undefined,\r\n emissive: MeshSynchronizer.resolveEmissiveValue(el, emissive),\r\n castShadow,\r\n receiveShadow,\r\n });\r\n\r\n this.updateCustomUniforms(el, object, ctx);\r\n\r\n return { scale: scaleFactor };\r\n }\r\n\r\n cleanup(el: HTMLElement, object: String3DObject): void {\r\n TextSynchronizer.cleanupContentObserver(el);\r\n TextSynchronizer.geometryKeys.delete(object);\r\n }\r\n\r\n private extractCharacterLayout(\r\n el: HTMLElement,\r\n transform: string,\r\n ): Array<{\r\n char: string;\r\n x: number;\r\n y: number;\r\n width?: number;\r\n height?: number;\r\n scale?: number;\r\n }> {\r\n const layout: Array<{\r\n char: string;\r\n x: number;\r\n y: number;\r\n width?: number;\r\n height?: number;\r\n scale?: number;\r\n }> = [];\r\n if (typeof document === \"undefined\" || !document.createRange) return layout;\r\n\r\n const range = document.createRange();\r\n const elRect = el.getBoundingClientRect();\r\n const walker = document.createTreeWalker(el, NodeFilter.SHOW_TEXT);\r\n let node: Node | null;\r\n\r\n while ((node = walker.nextNode())) {\r\n const text = node.textContent || \"\";\r\n if (!text.trim() && text !== \" \") continue;\r\n\r\n for (let i = 0; i < text.length; i++) {\r\n const char = text[i];\r\n if (char === \"\\n\" || char === \"\\r\") continue;\r\n\r\n if (!char.trim()) continue;\r\n\r\n range.setStart(node, i);\r\n range.setEnd(node, i + 1);\r\n const rects = range.getClientRects();\r\n\r\n if (rects.length > 0) {\r\n const r = rects[0];\r\n const x = r.left - elRect.left;\r\n const y = r.top - elRect.top;\r\n\r\n const visibleChar = this.applyTextTransform(char, transform);\r\n\r\n layout.push({\r\n char: visibleChar,\r\n x,\r\n y,\r\n width: r.width,\r\n height: r.height,\r\n });\r\n }\r\n }\r\n }\r\n return layout;\r\n }\r\n\r\n private extractRawText(el: HTMLElement, transform: string): string {\r\n const text = Array.from(el.childNodes)\r\n .filter((node) => node.nodeType === Node.TEXT_NODE)\r\n .map((node) => node.textContent || \"\")\r\n .join(\"\");\r\n\r\n const normalized = text\r\n .split(/\\r?\\n/)\r\n .map((line) => line.trim())\r\n .filter((line) => line.length > 0)\r\n .join(\"\\n\")\r\n .trim();\r\n\r\n if (!normalized) return \"\";\r\n return this.applyTextTransform(normalized, transform);\r\n }\r\n\r\n private getTextMesh(object: String3DObject, ctx: SyncContext): any | null {\r\n return ctx.engine.getPrimaryMesh(object.object);\r\n }\r\n\r\n private updateCustomUniforms(el: HTMLElement, object: String3DObject, ctx: SyncContext): void {\r\n const factory = ctx.engine.getMaterialFactory?.();\r\n if (!factory) return;\r\n\r\n const style = getComputedStyle(el);\r\n\r\n const apply = (mat: any) => {\r\n const definition = factory.getMaterialDefinition?.(mat) ?? mat?.userData?.definition;\r\n if (!definition?.uniforms) return;\r\n\r\n const values = factory.parseUniformsFromCSS(definition, el, style);\r\n\r\n if (typeof factory.applyUniforms === \"function\") {\r\n factory.applyUniforms(mat, definition, values);\r\n return;\r\n }\r\n\r\n for (const [key, value] of Object.entries(values)) {\r\n const def = definition.uniforms?.[key];\r\n if (!def) continue;\r\n const converter = (factory as any).convertUniformValue?.bind(factory);\r\n const converted = converter ? converter(def.type, value) : value;\r\n if (mat.uniforms?.[key]) {\r\n mat.uniforms[key].value = converted;\r\n }\r\n }\r\n };\r\n ctx.engine.forEachMaterial(object.object, apply);\r\n }\r\n\r\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): StyleBundle {\r\n return TextSynchronizer.styleCache.get(el, ctx, (el) => {\r\n const styleMap = (el as any).computedStyleMap?.();\r\n const style = getComputedStyle(el);\r\n\r\n const readNumber = (prop: string, fallback: number): number => {\r\n const mapValue = styleMap?.get?.(prop);\r\n if (mapValue !== undefined && mapValue !== null) {\r\n const val =\r\n typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n const num = typeof val === \"number\" ? val : Number.parseFloat(String(val));\r\n if (!Number.isNaN(num)) return num;\r\n }\r\n const raw = style.getPropertyValue(prop);\r\n const num = Number.parseFloat(raw);\r\n return Number.isNaN(num) ? fallback : num;\r\n };\r\n\r\n const readString = (prop: string, fallback = \"\"): string => {\r\n const mapValue = styleMap?.get?.(prop);\r\n const val =\r\n mapValue && typeof mapValue === \"object\" && \"value\" in (mapValue as any)\r\n ? (mapValue as any).value\r\n : mapValue;\r\n if (typeof val === \"string\") {\r\n const normalized = val.trim();\r\n return normalized || fallback;\r\n }\r\n const normalized = style.getPropertyValue(prop).trim();\r\n return normalized || fallback;\r\n };\r\n\r\n const readBool = (prop: string, fallback = false): boolean => {\r\n const raw = readString(prop);\r\n if (!raw) return fallback;\r\n const norm = raw.toLowerCase();\r\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\r\n ? true\r\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\r\n ? false\r\n : fallback;\r\n };\r\n\r\n const colorVar = readString(\"--material-color\");\r\n const color = colorVar && colorVar !== \"none\" ? colorVar : style.color.trim();\r\n\r\n const fontSize = (() => {\r\n const raw = style.fontSize || \"\";\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isFinite(parsed) ? parsed : 16;\r\n })();\r\n\r\n const lineHeight = (() => {\r\n const raw = style.lineHeight || \"\";\r\n if (!raw || raw === \"normal\") return fontSize * 1.2;\r\n const parsed = Number.parseFloat(raw);\r\n if (!Number.isFinite(parsed)) return fontSize * 1.2;\r\n return raw.endsWith(\"px\") ? parsed : parsed * fontSize;\r\n })();\r\n\r\n const letterSpacing = (() => {\r\n const raw = style.letterSpacing || \"\";\r\n if (!raw || raw === \"normal\") return 0;\r\n const parsed = Number.parseFloat(raw);\r\n return Number.isFinite(parsed) ? parsed : 0;\r\n })();\r\n\r\n const fit = readString(\"--text-fit\") || \"none\";\r\n\r\n const depthRaw = readNumber(\"--text-depth\", NaN);\r\n const depth = Number.isFinite(depthRaw) ? depthRaw : Math.max(1, fontSize * 0.2);\r\n\r\n const bevelSize = readNumber(\"--text-bevel-size\", 0);\r\n const bevelThickness = readNumber(\"--text-bevel-thickness\", 0);\r\n const bevelOffset = readNumber(\"--text-bevel-offset\", 0);\r\n const bevelSegments = readNumber(\"--text-bevel-steps\", 0);\r\n\r\n const alignRaw = (style.textAlign || \"left\").toLowerCase();\r\n const align =\r\n alignRaw === \"center\"\r\n ? \"center\"\r\n : alignRaw === \"right\" || alignRaw === \"end\"\r\n ? \"right\"\r\n : \"left\";\r\n\r\n const fontCss = style.font?.trim();\r\n const computedFont =\r\n fontCss && fontCss.length > 0\r\n ? fontCss\r\n : [\r\n style.fontStyle || \"normal\",\r\n style.fontWeight || \"normal\",\r\n `${style.fontSize || \"16px\"}/${style.lineHeight || \"normal\"}`,\r\n style.fontFamily || \"sans-serif\",\r\n ].join(\" \");\r\n\r\n return {\r\n translateZ: readNumber(\"--translate-z\", 0),\r\n cssScale: readNumber(\"--scale\", 1),\r\n rotateX: readNumber(\"--rotate-x\", 0),\r\n rotateY: readNumber(\"--rotate-y\", 0),\r\n rotateZ: readNumber(\"--rotate-z\", 0),\r\n cssScaleZ: readNumber(\"--scale-z\", 1),\r\n opacity: readNumber(\"--opacity\", NaN),\r\n color,\r\n metalness: readNumber(\"--material-metalness\", NaN),\r\n roughness: readNumber(\"--material-roughness\", NaN),\r\n emissive: readString(\"--material-emissive\"),\r\n castShadow: readBool(\"--shadow-cast\", false),\r\n receiveShadow: readBool(\"--shadow-receive\", false),\r\n materialType: readString(\"--material-type\", \"basic\").split(\"[\")[0] || \"basic\",\r\n fontFamily: style.fontFamily || \"\",\r\n fontCss: computedFont,\r\n fontSize,\r\n lineHeight,\r\n letterSpacing,\r\n textAlign: align,\r\n textTransform: (style.textTransform || \"\").toLowerCase(),\r\n textDepth: depth,\r\n textCurveSegments: readNumber(\"--text-curve-segments\", 8),\r\n bevelEnabled: bevelSize > 0 || bevelThickness > 0,\r\n bevelSize,\r\n bevelThickness,\r\n bevelOffset,\r\n bevelSegments,\r\n textFit: fit === \"cover\" || fit === \"none\" ? fit : \"contain\",\r\n };\r\n });\r\n }\r\n\r\n private applyTextTransform(text: string, transform: string): string {\r\n if (!transform || transform === \"none\") return text;\r\n if (transform === \"uppercase\") return text.toUpperCase();\r\n if (transform === \"lowercase\") return text.toLowerCase();\r\n if (transform === \"capitalize\") {\r\n return text.replace(/\\b(\\p{L})/gu, (match) => match.toUpperCase());\r\n }\r\n return text;\r\n }\r\n\r\n private readLayout(el: HTMLElement, ctx: SyncContext): LayoutBundle {\r\n const cached = (el as any).__layoutCache;\r\n if (cached) {\r\n return cached;\r\n }\r\n\r\n return TextSynchronizer.layoutCache.get(el, ctx, (el) => {\r\n const rect = el.getBoundingClientRect();\r\n return { rect, width: rect.width, height: rect.height };\r\n });\r\n }\r\n}\r\n\r\ntype StyleBundle = {\r\n translateZ: number;\r\n cssScale: number;\r\n rotateX: number;\r\n rotateY: number;\r\n rotateZ: number;\r\n cssScaleZ: number;\r\n opacity: number;\r\n color: string;\r\n metalness: number;\r\n roughness: number;\r\n emissive: string;\r\n castShadow: boolean;\r\n receiveShadow: boolean;\r\n materialType: string;\r\n fontFamily: string;\r\n fontCss: string;\r\n fontSize: number;\r\n lineHeight: number;\r\n letterSpacing: number;\r\n textAlign: \"left\" | \"center\" | \"right\";\r\n textTransform: string;\r\n textDepth: number;\r\n textCurveSegments: number;\r\n bevelEnabled: boolean;\r\n bevelSize: number;\r\n bevelThickness: number;\r\n bevelOffset: number;\r\n bevelSegments: number;\r\n textFit: \"contain\" | \"cover\" | \"none\";\r\n};\r\n\r\ntype LayoutBundle = {\r\n rect: DOMRect;\r\n width: number;\r\n height: number;\r\n};\r\n","export interface SVGTransformMatrix {\n a: number;\n b: number;\n c: number;\n d: number;\n e: number;\n f: number;\n}\n\nexport interface ParsedSVGPath {\n d: string;\n transform: SVGTransformMatrix | null;\n}\n\nexport interface ParsedSVGData {\n paths: ParsedSVGPath[];\n viewBox: { x: number; y: number; width: number; height: number } | null;\n naturalWidth: number;\n naturalHeight: number;\n}\n\ninterface SVGRenderState {\n displayNone: boolean;\n visibilityHidden: boolean;\n opacity: number;\n fill: string;\n fillOpacity: number;\n}\n\nconst IDENTITY: SVGTransformMatrix = { a: 1, b: 0, c: 0, d: 1, e: 0, f: 0 };\nconst DEFAULT_RENDER_STATE: SVGRenderState = {\n displayNone: false,\n visibilityHidden: false,\n opacity: 1,\n fill: \"#000\",\n fillOpacity: 1,\n};\n\nfunction isIdentity(m: SVGTransformMatrix): boolean {\n return m.a === 1 && m.b === 0 && m.c === 0 && m.d === 1 && m.e === 0 && m.f === 0;\n}\n\nfunction multiplyMatrices(m1: SVGTransformMatrix, m2: SVGTransformMatrix): SVGTransformMatrix {\n return {\n a: m1.a * m2.a + m1.c * m2.b,\n b: m1.b * m2.a + m1.d * m2.b,\n c: m1.a * m2.c + m1.c * m2.d,\n d: m1.b * m2.c + m1.d * m2.d,\n e: m1.a * m2.e + m1.c * m2.f + m1.e,\n f: m1.b * m2.e + m1.d * m2.f + m1.f,\n };\n}\n\nfunction parseTransformAttribute(transform: string): SVGTransformMatrix {\n let result: SVGTransformMatrix = { ...IDENTITY };\n const parts = transform.match(/(\\w+)\\s*\\(([^)]*)\\)/g) || [];\n\n for (const part of parts) {\n const match = part.match(/(\\w+)\\s*\\(([^)]*)\\)/);\n if (!match) continue;\n const type = match[1];\n const args = match[2]\n .trim()\n .split(/[\\s,]+/)\n .map(Number);\n let mat: SVGTransformMatrix = { ...IDENTITY };\n\n switch (type) {\n case \"translate\":\n mat = { a: 1, b: 0, c: 0, d: 1, e: args[0] || 0, f: args[1] || 0 };\n break;\n case \"scale\": {\n const sx = args[0] ?? 1;\n const sy = args[1] ?? sx;\n mat = { a: sx, b: 0, c: 0, d: sy, e: 0, f: 0 };\n break;\n }\n case \"rotate\": {\n const angle = ((args[0] || 0) * Math.PI) / 180;\n const cos = Math.cos(angle);\n const sin = Math.sin(angle);\n const cx = args[1] || 0;\n const cy = args[2] || 0;\n mat = {\n a: cos,\n b: sin,\n c: -sin,\n d: cos,\n e: cx - cos * cx + sin * cy,\n f: cy - sin * cx - cos * cy,\n };\n break;\n }\n case \"matrix\":\n if (args.length >= 6) {\n mat = { a: args[0], b: args[1], c: args[2], d: args[3], e: args[4], f: args[5] };\n }\n break;\n case \"skewX\": {\n const angle = ((args[0] || 0) * Math.PI) / 180;\n mat = { a: 1, b: 0, c: Math.tan(angle), d: 1, e: 0, f: 0 };\n break;\n }\n case \"skewY\": {\n const angle = ((args[0] || 0) * Math.PI) / 180;\n mat = { a: 1, b: Math.tan(angle), c: 0, d: 1, e: 0, f: 0 };\n break;\n }\n }\n\n result = multiplyMatrices(result, mat);\n }\n\n return result;\n}\n\nfunction getElementTransformMatrix(el: Element): SVGTransformMatrix {\n const transform = el.getAttribute(\"transform\");\n if (!transform) return { ...IDENTITY };\n return parseTransformAttribute(transform);\n}\n\nfunction parseStyleAttribute(style: string | null): Map<string, string> {\n const entries = new Map<string, string>();\n if (!style) return entries;\n\n for (const chunk of style.split(\";\")) {\n const colonIndex = chunk.indexOf(\":\");\n if (colonIndex === -1) continue;\n const key = chunk.slice(0, colonIndex).trim().toLowerCase();\n const value = chunk.slice(colonIndex + 1).trim();\n if (key) entries.set(key, value);\n }\n\n return entries;\n}\n\nfunction getPresentationValue(el: Element, name: string): string | null {\n const styleValue = parseStyleAttribute(el.getAttribute(\"style\")).get(name);\n if (styleValue != null && styleValue !== \"\") return styleValue;\n const attrValue = el.getAttribute(name);\n return attrValue != null && attrValue !== \"\" ? attrValue : null;\n}\n\nfunction parseNumericValue(value: string | null, fallback: number): number {\n if (value == null) return fallback;\n const normalized = value.trim();\n if (!normalized) return fallback;\n const parsed = parseFloat(normalized);\n return Number.isFinite(parsed) ? parsed : fallback;\n}\n\nfunction computeRenderState(el: Element, parentState: SVGRenderState): SVGRenderState {\n const display = (getPresentationValue(el, \"display\") || \"\").trim().toLowerCase();\n const visibility = (getPresentationValue(el, \"visibility\") || \"\").trim().toLowerCase();\n const opacity = parseNumericValue(getPresentationValue(el, \"opacity\"), 1);\n const fill = getPresentationValue(el, \"fill\") ?? parentState.fill;\n const fillOpacity = parseNumericValue(\n getPresentationValue(el, \"fill-opacity\"),\n parentState.fillOpacity,\n );\n\n return {\n displayNone: parentState.displayNone || display === \"none\",\n visibilityHidden:\n parentState.visibilityHidden || visibility === \"hidden\" || visibility === \"collapse\",\n opacity: parentState.opacity * Math.max(0, opacity),\n fill,\n fillOpacity: Math.max(0, fillOpacity),\n };\n}\n\nfunction shouldCollectGeometry(\n tag: string,\n d: string | null,\n renderState: SVGRenderState,\n): d is string {\n if (!d || !d.trim()) return false;\n if (tag === \"g\" || tag === \"svg\" || tag === \"symbol\" || tag === \"a\") return false;\n if (renderState.displayNone || renderState.visibilityHidden) return false;\n if (renderState.opacity <= 0 || renderState.fillOpacity <= 0) return false;\n return renderState.fill.trim().toLowerCase() !== \"none\";\n}\n\nfunction rectToPath(el: Element): string {\n const x = parseFloat(el.getAttribute(\"x\") || \"0\");\n const y = parseFloat(el.getAttribute(\"y\") || \"0\");\n const w = parseFloat(el.getAttribute(\"width\") || \"0\");\n const h = parseFloat(el.getAttribute(\"height\") || \"0\");\n if (w <= 0 || h <= 0) return \"\";\n\n const rxRaw = parseFloat(el.getAttribute(\"rx\") || \"\");\n const ryRaw = parseFloat(el.getAttribute(\"ry\") || \"\");\n const rx = isNaN(rxRaw) ? (isNaN(ryRaw) ? 0 : ryRaw) : rxRaw;\n const ry = isNaN(ryRaw) ? rx : ryRaw;\n\n if (rx <= 0 && ry <= 0) {\n return `M ${x} ${y} H ${x + w} V ${y + h} H ${x} Z`;\n }\n\n const rx2 = Math.min(rx, w / 2);\n const ry2 = Math.min(ry, h / 2);\n return [\n `M ${x + rx2} ${y}`,\n `H ${x + w - rx2}`,\n `A ${rx2} ${ry2} 0 0 1 ${x + w} ${y + ry2}`,\n `V ${y + h - ry2}`,\n `A ${rx2} ${ry2} 0 0 1 ${x + w - rx2} ${y + h}`,\n `H ${x + rx2}`,\n `A ${rx2} ${ry2} 0 0 1 ${x} ${y + h - ry2}`,\n `V ${y + ry2}`,\n `A ${rx2} ${ry2} 0 0 1 ${x + rx2} ${y}`,\n \"Z\",\n ].join(\" \");\n}\n\nfunction circleToPath(el: Element): string {\n const cx = parseFloat(el.getAttribute(\"cx\") || \"0\");\n const cy = parseFloat(el.getAttribute(\"cy\") || \"0\");\n const r = parseFloat(el.getAttribute(\"r\") || \"0\");\n if (r <= 0) return \"\";\n return `M ${cx - r} ${cy} A ${r} ${r} 0 0 1 ${cx + r} ${cy} A ${r} ${r} 0 0 1 ${cx - r} ${cy} Z`;\n}\n\nfunction ellipseToPath(el: Element): string {\n const cx = parseFloat(el.getAttribute(\"cx\") || \"0\");\n const cy = parseFloat(el.getAttribute(\"cy\") || \"0\");\n const rx = parseFloat(el.getAttribute(\"rx\") || \"0\");\n const ry = parseFloat(el.getAttribute(\"ry\") || \"0\");\n if (rx <= 0 || ry <= 0) return \"\";\n return `M ${cx - rx} ${cy} A ${rx} ${ry} 0 0 1 ${cx + rx} ${cy} A ${rx} ${ry} 0 0 1 ${cx - rx} ${cy} Z`;\n}\n\nfunction polygonToPath(el: Element, close: boolean): string {\n const points = (el.getAttribute(\"points\") || \"\").trim();\n if (!points) return \"\";\n const coords = points.split(/[\\s,]+/).filter(Boolean);\n const pairs: string[] = [];\n for (let i = 0; i + 1 < coords.length; i += 2) {\n pairs.push(`${i === 0 ? \"M\" : \"L\"} ${coords[i]} ${coords[i + 1]}`);\n }\n return pairs.join(\" \") + (close ? \" Z\" : \"\");\n}\n\nfunction lineToPath(el: Element): string {\n const x1 = el.getAttribute(\"x1\") || \"0\";\n const y1 = el.getAttribute(\"y1\") || \"0\";\n const x2 = el.getAttribute(\"x2\") || \"0\";\n const y2 = el.getAttribute(\"y2\") || \"0\";\n return `M ${x1} ${y1} L ${x2} ${y2}`;\n}\n\nfunction elementToPathD(el: Element): string | null {\n const tag = el.tagName.toLowerCase().replace(/^svg:/, \"\");\n switch (tag) {\n case \"path\":\n return el.getAttribute(\"d\");\n case \"rect\":\n return rectToPath(el);\n case \"circle\":\n return circleToPath(el);\n case \"ellipse\":\n return ellipseToPath(el);\n case \"polygon\":\n return polygonToPath(el, true);\n case \"polyline\":\n return polygonToPath(el, false);\n case \"line\":\n return lineToPath(el);\n default:\n return null;\n }\n}\n\nfunction walkElement(\n el: Element,\n parentMatrix: SVGTransformMatrix,\n parentState: SVGRenderState,\n paths: ParsedSVGPath[],\n): void {\n const tag = el.tagName.toLowerCase().replace(/^svg:/, \"\");\n\n if (tag === \"defs\" || tag === \"title\" || tag === \"desc\" || tag === \"style\" || tag === \"script\") {\n return;\n }\n\n const localMatrix = getElementTransformMatrix(el);\n const accumulated = isIdentity(localMatrix)\n ? parentMatrix\n : multiplyMatrices(parentMatrix, localMatrix);\n const renderState = computeRenderState(el, parentState);\n\n const d = elementToPathD(el);\n if (shouldCollectGeometry(tag, d, renderState)) {\n const pathData = d.trim();\n paths.push({\n d: pathData,\n transform: isIdentity(accumulated) ? null : accumulated,\n });\n }\n\n if (tag === \"g\" || tag === \"svg\" || tag === \"symbol\" || tag === \"a\" || d === null) {\n for (const child of Array.from(el.children)) {\n walkElement(child, accumulated, renderState, paths);\n }\n }\n}\n\nfunction parseViewBox(\n svgEl: Element,\n): { x: number; y: number; width: number; height: number } | null {\n const vb = svgEl.getAttribute(\"viewBox\");\n if (vb) {\n const parts = vb\n .trim()\n .split(/[\\s,]+/)\n .map(Number);\n if (parts.length >= 4 && parts[2] > 0 && parts[3] > 0) {\n return { x: parts[0], y: parts[1], width: parts[2], height: parts[3] };\n }\n }\n const w = parseFloat(svgEl.getAttribute(\"width\") || \"0\");\n const h = parseFloat(svgEl.getAttribute(\"height\") || \"0\");\n if (w > 0 && h > 0) {\n return { x: 0, y: 0, width: w, height: h };\n }\n return null;\n}\n\nexport class SVGParser {\n static fromElement(svgEl: SVGSVGElement): ParsedSVGData {\n const viewBox = parseViewBox(svgEl);\n const naturalWidth = viewBox?.width || parseFloat(svgEl.getAttribute(\"width\") || \"0\") || 100;\n const naturalHeight = viewBox?.height || parseFloat(svgEl.getAttribute(\"height\") || \"0\") || 100;\n\n const paths: ParsedSVGPath[] = [];\n\n for (const child of Array.from(svgEl.children)) {\n walkElement(child, { ...IDENTITY }, computeRenderState(svgEl, DEFAULT_RENDER_STATE), paths);\n }\n\n return { paths, viewBox, naturalWidth, naturalHeight };\n }\n\n static fromString(svgString: string): ParsedSVGData | null {\n if (typeof DOMParser === \"undefined\") return null;\n const parser = new DOMParser();\n const doc = parser.parseFromString(svgString.trim(), \"image/svg+xml\");\n const parseError = doc.querySelector(\"parsererror\");\n if (parseError) return null;\n const svgEl = doc.querySelector(\"svg\");\n if (!svgEl) return null;\n return SVGParser.fromElement(svgEl as SVGSVGElement);\n }\n}\n","import { String3DObject } from \"../String3DObject\";\nimport type { SyncContext } from \"./SyncContext\";\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\nimport { StyleBundleCache } from \"./StyleBundleCache\";\nimport { MeshSynchronizer } from \"./MeshSynchronizer\";\nimport { SVGParser } from \"../svg/SVGParser\";\nimport type { ParsedSVGData } from \"../svg/SVGParser\";\nconst DEG_TO_RAD = Math.PI / 180;\nfunction easeInOut(t: number): number {\n return t < 0.5 ? 2 * t * t : -1 + (4 - 2 * t) * t;\n}\ntype MorphState = {\n startTime: number;\n duration: number;\n swapped: boolean;\n};\nexport class SVGSynchronizer implements String3DObjectSyncStrategy {\n private static styleCache = new StyleBundleCache<StyleBundle>();\n private static geometryKeys: WeakMap<String3DObject, string> = new WeakMap();\n private static lastMaterialType: WeakMap<String3DObject, string> = new WeakMap();\n private static svgCache: WeakMap<HTMLElement, ParsedSVGData> = new WeakMap();\n private static svgFetchCache: Map<string, ParsedSVGData | null> = new Map();\n private static svgFetchPromises: Map<string, Promise<ParsedSVGData | null>> = new Map();\n private static pendingSrcObjects: Map<string, Set<String3DObject>> = new Map();\n private static mutationObservers: WeakMap<HTMLElement, MutationObserver> = new WeakMap();\n private static morphStates: WeakMap<String3DObject, MorphState> = new WeakMap();\n private static svgSignatures: WeakMap<String3DObject, string> = new WeakMap();\n sync(el: HTMLElement, object: String3DObject, ctx: SyncContext, parentData: any): any {\n SVGSynchronizer.setupMutationObserver(el, object);\n const rect = el.getBoundingClientRect();\n const bundle = this.readStyleBundle(el, ctx);\n const {\n translateZ,\n cssScale,\n rotateX,\n rotateY,\n rotateZ,\n cssScaleZ,\n opacity,\n color,\n metalness,\n roughness,\n emissive,\n castShadow,\n receiveShadow,\n materialType,\n svgDepth,\n svgCurveSegments,\n bevelEnabled,\n bevelSize,\n bevelThickness,\n bevelOffset,\n bevelSegments,\n svgSrc,\n morphDuration,\n } = bundle;\n const screenCenterX = rect.left + rect.width * 0.5;\n const screenCenterY = rect.top + rect.height * 0.5;\n if (ctx.camera.getMode() === \"orthographic\") {\n object.object.position.set(\n screenCenterX - ctx.viewportWidth / 2,\n -(screenCenterY - ctx.viewportHeight / 2),\n translateZ,\n );\n } else {\n const frustum = ctx.camera.getFrustumSizeAt(translateZ);\n const normalizedX = screenCenterX / ctx.viewportWidth;\n const normalizedY = screenCenterY / ctx.viewportHeight;\n object.object.position.set(\n (normalizedX - 0.5) * frustum.width,\n -(normalizedY - 0.5) * frustum.height,\n translateZ,\n );\n }\n object.object.rotation.x = -rotateX * DEG_TO_RAD;\n object.object.rotation.z = -rotateZ * DEG_TO_RAD;\n object.object.rotation.order = \"XYZ\";\n if (opacity === 0) {\n object.object.visible = false;\n return { scale: cssScale * (parentData?.scale || 1) };\n }\n object.object.visible = true;\n if (!ctx.engine.createSVGGeometry) {\n object.object.rotation.y = rotateY * DEG_TO_RAD;\n return { scale: cssScale * (parentData?.scale || 1) };\n }\n const mesh = ctx.engine.getPrimaryMesh(object.object);\n if (!mesh) {\n object.object.rotation.y = rotateY * DEG_TO_RAD;\n return { scale: cssScale * (parentData?.scale || 1) };\n }\n const svgData = this.resolveSVGData(el, svgSrc, object);\n if (!svgData) {\n mesh.visible = false;\n object.object.rotation.y = rotateY * DEG_TO_RAD;\n return { scale: cssScale * (parentData?.scale || 1) };\n }\n mesh.visible = true;\n const currentSig = svgData.paths.map((p) => p.d).join(\"~\");\n const prevSig = SVGSynchronizer.svgSignatures.get(object);\n if (prevSig !== undefined && prevSig !== currentSig) {\n SVGSynchronizer.morphStates.set(object, {\n startTime: performance.now(),\n duration: morphDuration,\n swapped: false,\n });\n }\n SVGSynchronizer.svgSignatures.set(object, currentSig);\n let morphFactor = 1;\n let morphRotationBonus = 0;\n const morphState = SVGSynchronizer.morphStates.get(object);\n if (morphState) {\n const elapsed = performance.now() - morphState.startTime;\n const raw = Math.min(elapsed / morphState.duration, 1);\n const eased = easeInOut(raw);\n if (raw >= 1) {\n SVGSynchronizer.morphStates.delete(object);\n morphFactor = 1;\n } else if (eased < 0.5) {\n morphFactor = 1 - eased * 2;\n } else {\n if (!morphState.swapped) {\n morphState.swapped = true;\n SVGSynchronizer.geometryKeys.delete(object);\n }\n morphFactor = (eased - 0.5) * 2;\n }\n morphRotationBonus = Math.sin(eased * Math.PI) * 90 * DEG_TO_RAD;\n }\n object.object.rotation.y = rotateY * DEG_TO_RAD + morphRotationBonus;\n const vb = svgData.viewBox;\n const svgW = vb?.width || svgData.naturalWidth || rect.width;\n const svgH = vb?.height || svgData.naturalHeight || rect.height;\n const svgScale = svgW > 0 && svgH > 0 ? Math.min(rect.width / svgW, rect.height / svgH) : 1;\n const holdOldGeometry = morphState && !morphState.swapped;\n if (!holdOldGeometry) {\n const pathsSig = svgData.paths.map((p) => p.d.length).join(\",\");\n const key = [\n pathsSig,\n svgScale.toFixed(4),\n rect.width.toFixed(1),\n rect.height.toFixed(1),\n svgDepth.toFixed(3),\n svgCurveSegments,\n bevelEnabled ? \"1\" : \"0\",\n bevelSize.toFixed(3),\n bevelThickness.toFixed(3),\n bevelOffset.toFixed(3),\n bevelSegments,\n ].join(\"|\");\n const prevKey = SVGSynchronizer.geometryKeys.get(object);\n if (prevKey !== key) {\n const scaledPaths = svgData.paths.map((p) => {\n if (!p.transform) {\n return {\n d: p.d,\n transform: { a: svgScale, b: 0, c: 0, d: svgScale, e: 0, f: 0 },\n };\n }\n return {\n d: p.d,\n transform: {\n a: p.transform.a * svgScale,\n b: p.transform.b * svgScale,\n c: p.transform.c * svgScale,\n d: p.transform.d * svgScale,\n e: p.transform.e * svgScale,\n f: p.transform.f * svgScale,\n },\n };\n });\n const scaledViewBox = vb\n ? {\n x: vb.x * svgScale,\n y: vb.y * svgScale,\n width: vb.width * svgScale,\n height: vb.height * svgScale,\n }\n : null;\n const geometry = ctx.engine.createSVGGeometry(scaledPaths, scaledViewBox, {\n depth: svgDepth,\n curveSegments: Math.max(1, Math.round(svgCurveSegments)),\n bevelEnabled,\n bevelThickness,\n bevelSize,\n bevelOffset,\n bevelSegments: Math.max(0, Math.round(bevelSegments)),\n });\n if (geometry) {\n geometry.computeBoundingBox();\n const appliedToMesh = ctx.engine.applyTextGeometryToMesh(mesh, geometry);\n if (!appliedToMesh) {\n if (mesh.geometry) {\n mesh.geometry.dispose?.();\n }\n mesh.geometry = geometry;\n }\n object.geometry = geometry;\n SVGSynchronizer.geometryKeys.set(object, key);\n }\n }\n }\n const parentScale = parentData?.scale || 1;\n const perPixel =\n ctx.camera.getMode() === \"orthographic\"\n ? 1\n : ctx.camera.getScaleAtZ(translateZ, ctx.viewportHeight);\n const scaleFactor = cssScale * parentScale * perPixel;\n const mf = Math.max(0.0001, morphFactor);\n object.object.scale.set(scaleFactor * mf, scaleFactor * mf, scaleFactor * cssScaleZ * mf);\n mesh.position.set(0, 0, 0);\n const prevMaterialType = SVGSynchronizer.lastMaterialType.get(object);\n if (prevMaterialType !== undefined && prevMaterialType !== materialType) {\n const scene = ctx.scene;\n if (scene) {\n requestAnimationFrame(() => {\n scene.recreateMaterialForObject(object, el);\n });\n }\n }\n SVGSynchronizer.lastMaterialType.set(object, materialType);\n MeshSynchronizer.applyVisualProps(el, object, ctx.engine, {\n opacity,\n color: color && color !== \"none\" ? color : undefined,\n metalness: Number.isFinite(metalness) ? metalness : undefined,\n roughness: Number.isFinite(roughness) ? roughness : undefined,\n emissive: MeshSynchronizer.resolveEmissiveValue(el, emissive),\n castShadow,\n receiveShadow,\n });\n return { scale: scaleFactor };\n }\n cleanup(el: HTMLElement, object: String3DObject): void {\n SVGSynchronizer.geometryKeys.delete(object);\n SVGSynchronizer.svgCache.delete(el);\n SVGSynchronizer.morphStates.delete(object);\n SVGSynchronizer.svgSignatures.delete(object);\n const observer = SVGSynchronizer.mutationObservers.get(el);\n if (observer) {\n observer.disconnect();\n SVGSynchronizer.mutationObservers.delete(el);\n }\n }\n private resolveSVGData(\n el: HTMLElement,\n svgSrc: string,\n object: String3DObject,\n ): ParsedSVGData | null {\n const inlineSvg = el.querySelector(\"svg\");\n if (inlineSvg) {\n const cached = SVGSynchronizer.svgCache.get(el);\n if (cached) return cached;\n const data = SVGParser.fromElement(inlineSvg as SVGSVGElement);\n if (data && data.paths.length > 0) {\n SVGSynchronizer.svgCache.set(el, data);\n return data;\n }\n }\n const src = svgSrc || el.getAttribute(\"data-svg-src\") || \"\";\n if (!src) return null;\n const cached = SVGSynchronizer.svgFetchCache.get(src);\n if (cached !== undefined) return cached;\n if (!SVGSynchronizer.svgFetchPromises.has(src)) {\n const promise = fetch(src)\n .then((r) => r.text())\n .then((text) => {\n const data = SVGParser.fromString(text);\n SVGSynchronizer.svgFetchCache.set(src, data);\n SVGSynchronizer.invalidatePendingSrcObjects(src);\n return data;\n })\n .catch(() => {\n SVGSynchronizer.svgFetchCache.set(src, null);\n return null;\n });\n SVGSynchronizer.svgFetchPromises.set(src, promise);\n }\n SVGSynchronizer.markObjectPendingSrc(src, object);\n return null;\n }\n private static markObjectPendingSrc(src: string, object: String3DObject): void {\n let set = this.pendingSrcObjects.get(src);\n if (!set) {\n set = new Set();\n this.pendingSrcObjects.set(src, set);\n }\n set.add(object);\n }\n private static invalidatePendingSrcObjects(src: string): void {\n const set = this.pendingSrcObjects.get(src);\n if (set) {\n set.forEach((obj) => this.geometryKeys.delete(obj));\n set.clear();\n }\n }\n private static setupMutationObserver(el: HTMLElement, _object: String3DObject): void {\n if (SVGSynchronizer.mutationObservers.has(el)) return;\n const observer = new MutationObserver(() => {\n SVGSynchronizer.svgCache.delete(el);\n });\n observer.observe(el, { childList: true, subtree: true, attributes: true });\n SVGSynchronizer.mutationObservers.set(el, observer);\n }\n private readStyleBundle(el: HTMLElement, ctx: SyncContext): StyleBundle {\n return SVGSynchronizer.styleCache.get(el, ctx, (el) => {\n const styleMap = (el as any).computedStyleMap?.();\n const style = getComputedStyle(el);\n const readNumber = (prop: string, fallback: number): number => {\n const mapValue = styleMap?.get?.(prop);\n if (mapValue !== undefined && mapValue !== null) {\n const val =\n typeof mapValue === \"object\" && \"value\" in (mapValue as any)\n ? (mapValue as any).value\n : mapValue;\n const num = typeof val === \"number\" ? val : Number.parseFloat(String(val));\n if (!Number.isNaN(num)) return num;\n }\n const num = Number.parseFloat(style.getPropertyValue(prop));\n return Number.isNaN(num) ? fallback : num;\n };\n const readString = (prop: string, fallback = \"\"): string => {\n const mapValue = styleMap?.get?.(prop);\n const val =\n mapValue && typeof mapValue === \"object\" && \"value\" in (mapValue as any)\n ? (mapValue as any).value\n : mapValue;\n if (typeof val === \"string\") return val.trim() || fallback;\n return style.getPropertyValue(prop).trim() || fallback;\n };\n const readBool = (prop: string, fallback = false): boolean => {\n const raw = readString(prop);\n if (!raw) return fallback;\n const norm = raw.toLowerCase();\n return norm === \"true\" || norm === \"1\" || norm === \"yes\"\n ? true\n : norm === \"false\" || norm === \"0\" || norm === \"no\"\n ? false\n : fallback;\n };\n const colorVar = readString(\"--material-color\");\n const color = colorVar && colorVar !== \"none\" ? colorVar : style.color.trim();\n const bevelSize = readNumber(\"--svg-bevel-size\", 0);\n const bevelThickness = readNumber(\"--svg-bevel-thickness\", 0);\n const depthRaw = readNumber(\"--svg-depth\", NaN);\n const svgDepth = Number.isFinite(depthRaw) ? depthRaw : 10;\n return {\n translateZ: readNumber(\"--translate-z\", 0),\n cssScale: readNumber(\"--scale\", 1),\n rotateX: readNumber(\"--rotate-x\", 0),\n rotateY: readNumber(\"--rotate-y\", 0),\n rotateZ: readNumber(\"--rotate-z\", 0),\n cssScaleZ: readNumber(\"--scale-z\", 1),\n opacity: readNumber(\"--opacity\", NaN),\n color,\n metalness: readNumber(\"--material-metalness\", NaN),\n roughness: readNumber(\"--material-roughness\", NaN),\n emissive: readString(\"--material-emissive\"),\n castShadow: readBool(\"--shadow-cast\", false),\n receiveShadow: readBool(\"--shadow-receive\", false),\n materialType: readString(\"--material-type\", \"basic\").split(\"[\")[0] || \"basic\",\n svgDepth,\n svgCurveSegments: readNumber(\"--svg-curve-segments\", 12),\n bevelEnabled: bevelSize > 0 || bevelThickness > 0,\n bevelSize,\n bevelThickness,\n bevelOffset: readNumber(\"--svg-bevel-offset\", 0),\n bevelSegments: readNumber(\"--svg-bevel-steps\", 3),\n svgSrc: readString(\"--svg-src\"),\n morphDuration: readNumber(\"--svg-morph-duration\", 600),\n };\n });\n }\n}\ntype StyleBundle = {\n translateZ: number;\n cssScale: number;\n rotateX: number;\n rotateY: number;\n rotateZ: number;\n cssScaleZ: number;\n opacity: number;\n color: string;\n metalness: number;\n roughness: number;\n emissive: string;\n castShadow: boolean;\n receiveShadow: boolean;\n materialType: string;\n svgDepth: number;\n svgCurveSegments: number;\n bevelEnabled: boolean;\n bevelSize: number;\n bevelThickness: number;\n bevelOffset: number;\n bevelSegments: number;\n svgSrc: string;\n morphDuration: number;\n};\n","import { String3DCamera } from \"../String3DCamera\";\r\nimport { String3DObject } from \"../String3DObject\";\r\nimport { I3DEngine } from \"../abstractions/I3DEngine\";\r\nimport { GroupSynchronizer } from \"./GroupSynchronizer\";\r\nimport { LightSynchronizer } from \"./LightSynchronizer\";\r\nimport { MeshSynchronizer } from \"./MeshSynchronizer\";\r\nimport { ParticlesSynchronizer } from \"./ParticlesSynchronizer\";\r\nimport { TextSynchronizer } from \"./TextSynchronizer\";\r\nimport { SVGSynchronizer } from \"./SVGSynchronizer\";\r\nimport type { String3DScene } from \"../String3DScene\";\r\nimport type { String3DObjectSyncStrategy } from \"./String3DObjectSyncStrategy\";\r\n\r\nexport class String3DSynchronizer {\r\n private strategies: Map<string, String3DObjectSyncStrategy> = new Map();\r\n private styleReadIntervalMs = 0;\r\n private layoutReadIntervalMs = 0;\r\n private scene?: String3DScene;\r\n\r\n constructor(\r\n public camera: String3DCamera,\r\n public viewportWidth: number,\r\n public viewportHeight: number,\r\n public engine: I3DEngine,\r\n ) {\r\n this.strategies.set(\"box\", new MeshSynchronizer());\r\n this.strategies.set(\"sphere\", new MeshSynchronizer());\r\n this.strategies.set(\"plane\", new MeshSynchronizer());\r\n this.strategies.set(\"cylinder\", new MeshSynchronizer());\r\n this.strategies.set(\"model\", new MeshSynchronizer());\r\n this.strategies.set(\"group\", new GroupSynchronizer());\r\n this.strategies.set(\"pointLight\", new LightSynchronizer());\r\n this.strategies.set(\"ambientLight\", new LightSynchronizer());\r\n this.strategies.set(\"directionalLight\", new LightSynchronizer());\r\n this.strategies.set(\"spotLight\", new LightSynchronizer());\r\n this.strategies.set(\"hemisphereLight\", new LightSynchronizer());\r\n this.strategies.set(\"particles\", new ParticlesSynchronizer());\r\n this.strategies.set(\"text\", new TextSynchronizer());\r\n this.strategies.set(\"svg\", new SVGSynchronizer());\r\n }\r\n\r\n public syncElement(\r\n el: HTMLElement,\r\n object: String3DObject,\r\n parentData: any,\r\n hints?: { dirtySet?: Set<HTMLElement> | null; forceSync?: boolean },\r\n ): any {\r\n const strategy = this.strategies.get(object.type);\r\n if (!strategy) {\r\n return null;\r\n }\r\n\r\n return strategy.sync(\r\n el,\r\n object,\r\n {\r\n camera: this.camera,\r\n viewportWidth: this.viewportWidth,\r\n viewportHeight: this.viewportHeight,\r\n engine: this.engine,\r\n scene: this.scene,\r\n dirtySet: hints?.dirtySet,\r\n forceSync: hints?.forceSync,\r\n styleReadIntervalMs: this.styleReadIntervalMs,\r\n layoutReadIntervalMs: this.layoutReadIntervalMs,\r\n },\r\n parentData,\r\n );\r\n }\r\n\r\n public setSyncOptions(options: {\r\n styleReadIntervalMs?: number;\r\n layoutReadIntervalMs?: number;\r\n }): void {\r\n this.styleReadIntervalMs = Math.max(0, options.styleReadIntervalMs ?? 0);\r\n this.layoutReadIntervalMs = Math.max(0, options.layoutReadIntervalMs ?? 0);\r\n }\r\n\r\n public setScene(scene: String3DScene): void {\r\n this.scene = scene;\r\n }\r\n\r\n public updateViewportSize(width: number, height: number): void {\r\n this.viewportWidth = width;\r\n this.viewportHeight = height;\r\n }\r\n\r\n public cleanupElement(el: HTMLElement, object: String3DObject): void {\r\n const strategy = this.strategies.get(object.type);\r\n if (strategy?.cleanup) {\r\n strategy.cleanup(el, object);\r\n }\r\n }\r\n}\r\n","import { String3DObject } from \"../../core/String3DObject\";\r\n\r\nexport class DirtySyncManager {\r\n private readonly attributeFilter: string[];\r\n private readonly handleScrollBound = () => this.handleScroll();\r\n private dirtyElements: Set<HTMLElement> = new Set();\r\n private observedElements: Set<HTMLElement> = new Set();\r\n private resizeObserver: ResizeObserver | null = null;\r\n private mutationObserver: MutationObserver | null = null;\r\n private enabled = false;\r\n private domVersion = 0;\r\n\r\n constructor(attributeFilter: string[]) {\r\n this.attributeFilter = attributeFilter;\r\n }\r\n\r\n enable(): void {\r\n if (this.enabled) return;\r\n this.enabled = true;\r\n this.setupObservers();\r\n this.setupScrollListeners();\r\n }\r\n\r\n disable(): void {\r\n if (!this.enabled) return;\r\n this.enabled = false;\r\n this.removeScrollListeners();\r\n this.resizeObserver?.disconnect();\r\n this.mutationObserver?.disconnect();\r\n this.dirtyElements.clear();\r\n this.observedElements.clear();\r\n }\r\n\r\n observeElement(el: HTMLElement): void {\r\n if (!this.enabled || this.observedElements.has(el)) return;\r\n this.observedElements.add(el);\r\n this.resizeObserver?.observe(el);\r\n this.mutationObserver?.observe(el, {\r\n attributes: true,\r\n attributeFilter: this.attributeFilter,\r\n });\r\n }\r\n\r\n observeScene(rootObjects: String3DObject[]): void {\r\n if (!this.enabled) return;\r\n rootObjects.forEach((obj) => this.observeRecursive(obj));\r\n }\r\n\r\n markDirty(el: HTMLElement): void {\r\n if (!this.enabled) return;\r\n this.dirtyElements.add(el);\r\n this.bumpVersion();\r\n }\r\n\r\n markAllDirty(): void {\r\n if (!this.enabled) return;\r\n this.observedElements.forEach((el) => this.dirtyElements.add(el));\r\n this.bumpVersion();\r\n }\r\n\r\n getDirtySet(): Set<HTMLElement> | null {\r\n return this.enabled ? this.dirtyElements : null;\r\n }\r\n\r\n clearDirty(): void {\r\n this.dirtyElements.clear();\r\n }\r\n\r\n getVersion(): number {\r\n return this.domVersion;\r\n }\r\n\r\n isEnabled(): boolean {\r\n return this.enabled;\r\n }\r\n\r\n private observeRecursive(object: String3DObject): void {\r\n if (object.el instanceof HTMLElement) {\r\n this.observeElement(object.el);\r\n }\r\n object.children.forEach((child) => this.observeRecursive(child));\r\n }\r\n\r\n private handleScroll(): void {\r\n this.markAllDirty();\r\n }\r\n\r\n private setupObservers(): void {\r\n if (typeof ResizeObserver !== \"undefined\") {\r\n this.resizeObserver = new ResizeObserver((entries) => {\r\n entries.forEach((entry) => {\r\n if (entry.target instanceof HTMLElement) {\r\n this.markDirty(entry.target);\r\n }\r\n });\r\n });\r\n }\r\n\r\n if (typeof MutationObserver !== \"undefined\") {\r\n this.mutationObserver = new MutationObserver((mutations) => {\r\n mutations.forEach((mutation) => {\r\n if (mutation.target instanceof HTMLElement) {\r\n this.markDirty(mutation.target);\r\n }\r\n });\r\n });\r\n }\r\n }\r\n\r\n private setupScrollListeners(): void {\r\n window.addEventListener(\"scroll\", this.handleScrollBound, { passive: true });\r\n window.addEventListener(\"resize\", this.handleScrollBound, { passive: true });\r\n if (window.visualViewport) {\r\n window.visualViewport.addEventListener(\"scroll\", this.handleScrollBound, { passive: true });\r\n window.visualViewport.addEventListener(\"resize\", this.handleScrollBound, { passive: true });\r\n }\r\n }\r\n\r\n private removeScrollListeners(): void {\r\n window.removeEventListener(\"scroll\", this.handleScrollBound);\r\n window.removeEventListener(\"resize\", this.handleScrollBound);\r\n if (window.visualViewport) {\r\n window.visualViewport.removeEventListener(\"scroll\", this.handleScrollBound);\r\n window.visualViewport.removeEventListener(\"resize\", this.handleScrollBound);\r\n }\r\n }\r\n\r\n private bumpVersion(): void {\r\n this.domVersion += 1;\r\n }\r\n}\r\n","import { String3DObject } from \"../../core/String3DObject\";\r\nimport type { I3DCustomFilterRegistryRuntime } from \"../../core/abstractions/I3DEngine\";\r\nimport { String3DCustomFilterRegistry } from \"../../core/filters/String3DCustomFilter\";\r\nimport {\r\n String3DFilterChain,\r\n String3DFilterEffect,\r\n String3DFilterTarget,\r\n} from \"../../core/filters/String3DFilterTypes\";\r\nimport { readFilterRaw } from \"./styleUtils\";\r\n\r\ntype FilterTransitionState = {\r\n raw: string;\r\n effects: String3DFilterChain;\r\n animating: boolean;\r\n from: String3DFilterChain;\r\n to: String3DFilterChain;\r\n startTime: number;\r\n duration: number;\r\n easing: (t: number) => number;\r\n clearOnComplete: boolean;\r\n lastDuration: number;\r\n lastDelay: number;\r\n lastEasing: (t: number) => number;\r\n pendingRaw?: string;\r\n pendingEffects?: String3DFilterChain;\r\n effectsKey?: string;\r\n};\r\n\r\nexport class FilterController {\r\n private filterStates: WeakMap<HTMLElement, FilterTransitionState> = new WeakMap();\r\n private filterWarnings: WeakMap<HTMLElement, string> = new WeakMap();\r\n private customFilterRegistry: I3DCustomFilterRegistryRuntime = String3DCustomFilterRegistry;\r\n\r\n constructor(private easingParser?: (value: string) => (t: number) => number) {}\r\n\r\n setCustomFilterRegistry(registry: I3DCustomFilterRegistryRuntime | null | undefined): void {\r\n this.customFilterRegistry = registry || String3DCustomFilterRegistry;\r\n }\r\n\r\n collectTargets(\r\n rootObjects: String3DObject[],\r\n now: number,\r\n useDirtySync: boolean,\r\n dirtySet: Set<HTMLElement> | null,\r\n ): String3DFilterTarget[] {\r\n const targets: String3DFilterTarget[] = [];\r\n const walk = (obj: String3DObject): void => {\r\n const el = obj.el as HTMLElement | undefined;\r\n if (el) {\r\n const animating = this.filterStates.get(el)?.animating === true;\r\n const shouldReadStyle = !useDirtySync || !dirtySet || dirtySet.has(el) || animating;\r\n const chain = this.readFilterChain(el, now, shouldReadStyle);\r\n if (chain && chain.length > 0) {\r\n const dirty = !useDirtySync || !dirtySet || dirtySet.has(el) || animating;\r\n const effectsKey =\r\n this.filterStates.get(el)?.effectsKey || this.stringifyFilterChain(chain);\r\n targets.push({\r\n object: obj,\r\n effects: chain,\r\n effectsKey,\r\n dirty,\r\n });\r\n return;\r\n }\r\n }\r\n obj.children.forEach((child) => walk(child));\r\n };\r\n rootObjects.forEach((obj) => walk(obj));\r\n return targets;\r\n }\r\n\r\n clear(): void {\r\n this.filterStates = new WeakMap();\r\n this.filterWarnings = new WeakMap();\r\n }\r\n\r\n private readFilterChain(\r\n el: HTMLElement,\r\n now: number,\r\n shouldReadStyle: boolean,\r\n ): String3DFilterChain | null {\r\n const existing = this.filterStates.get(el);\r\n if (!shouldReadStyle && existing) {\r\n if (existing.animating) {\r\n return this.sampleTransition(existing, now);\r\n }\r\n return existing.effects;\r\n }\r\n\r\n const raw = readFilterRaw(el);\r\n if (!raw || raw === \"none\") {\r\n if (existing) {\r\n if (existing.animating && existing.clearOnComplete) {\r\n const current = this.sampleTransition(existing, now);\r\n if (!existing.animating) {\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n return current;\r\n }\r\n let { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration <= 0 && existing.lastDuration > 0) {\r\n duration = existing.lastDuration;\r\n delay = existing.lastDelay;\r\n easing = existing.lastEasing;\r\n }\r\n if (duration > 0) {\r\n const zero = this.makeZeroChain(existing.effects);\r\n existing.from = existing.effects;\r\n existing.to = zero;\r\n existing.startTime = now + delay;\r\n existing.duration = duration;\r\n existing.easing = easing;\r\n existing.animating = true;\r\n existing.clearOnComplete = true;\r\n existing.lastDuration = duration;\r\n existing.lastDelay = delay;\r\n existing.lastEasing = easing;\r\n return this.sampleTransition(existing, now);\r\n }\r\n }\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n\r\n const { effects, warnings } = this.parseFilterChain(raw);\r\n this.warnFilterIssues(el, raw, warnings);\r\n if (effects.length === 0) return null;\r\n\r\n const state = this.filterStates.get(el);\r\n if (!state) {\r\n const { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration > 0) {\r\n const zero = this.makeZeroChain(effects);\r\n const newState: FilterTransitionState = {\r\n raw,\r\n effects,\r\n animating: true,\r\n from: zero,\r\n to: effects,\r\n startTime: now + delay,\r\n duration,\r\n easing,\r\n clearOnComplete: false,\r\n lastDuration: duration,\r\n lastDelay: delay,\r\n lastEasing: easing,\r\n };\r\n newState.effectsKey = this.stringifyFilterChain(effects);\r\n this.filterStates.set(el, newState);\r\n return this.sampleTransition(newState, now);\r\n }\r\n this.filterStates.set(el, {\r\n raw,\r\n effects,\r\n animating: false,\r\n from: effects,\r\n to: effects,\r\n startTime: 0,\r\n duration: 0,\r\n easing: (t) => t,\r\n clearOnComplete: false,\r\n lastDuration: 0,\r\n lastDelay: 0,\r\n lastEasing: (t) => t,\r\n effectsKey: this.stringifyFilterChain(effects),\r\n });\r\n return effects;\r\n }\r\n\r\n if (state.raw === raw) {\r\n if (state.animating) {\r\n const current = this.sampleTransition(state, now);\r\n if (!state.animating && state.clearOnComplete) {\r\n this.filterStates.delete(el);\r\n return null;\r\n }\r\n return current;\r\n }\r\n return state.effects;\r\n }\r\n\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n\r\n let { duration, delay, easing } = this.getFilterTransition(el);\r\n if (duration <= 0 && state.lastDuration > 0) {\r\n duration = state.lastDuration;\r\n delay = state.lastDelay;\r\n easing = state.lastEasing;\r\n }\r\n if (duration > 0) {\r\n const canTween = this.canInterpolate(state.effects, effects);\r\n const current = state.animating ? this.getCurrentChain(state, now) : state.effects;\r\n if (!canTween && this.isZeroChain(effects)) {\r\n state.pendingRaw = raw;\r\n state.pendingEffects = effects;\r\n state.raw = raw;\r\n state.effects = current;\r\n state.from = current;\r\n state.to = this.makeZeroChain(current);\r\n state.startTime = now + delay;\r\n state.duration = duration;\r\n state.easing = easing;\r\n state.animating = true;\r\n state.clearOnComplete = false;\r\n state.lastDuration = duration;\r\n state.lastDelay = delay;\r\n state.lastEasing = easing;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return this.sampleTransition(state, now);\r\n }\r\n\r\n const fromChain = canTween ? current : this.makeZeroChain(effects);\r\n state.raw = raw;\r\n state.effects = effects;\r\n state.from = fromChain;\r\n state.to = effects;\r\n state.startTime = now + delay;\r\n state.duration = duration;\r\n state.easing = easing;\r\n state.animating = true;\r\n state.clearOnComplete = false;\r\n state.lastDuration = duration;\r\n state.lastDelay = delay;\r\n state.lastEasing = easing;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return this.sampleTransition(state, now);\r\n }\r\n\r\n state.raw = raw;\r\n state.effects = effects;\r\n state.animating = false;\r\n state.clearOnComplete = false;\r\n state.effectsKey = this.stringifyFilterChain(effects);\r\n return effects;\r\n }\r\n\r\n private warnFilterIssues(el: HTMLElement, raw: string, warnings: string[]): void {\r\n if (warnings.length === 0) return;\r\n const lastRaw = this.filterWarnings.get(el);\r\n if (lastRaw === raw) return;\r\n this.filterWarnings.set(el, raw);\r\n }\r\n\r\n private parseFilterChain(raw: string): { effects: String3DFilterChain; warnings: string[] } {\r\n const warnings: string[] = [];\r\n const effects: String3DFilterChain = [];\r\n\r\n const parseNumber = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n const match = cleaned.match(/^(-?\\d*\\.?\\d+)(px)?$/);\r\n if (!match) return null;\r\n const num = Number.parseFloat(match[1]);\r\n return Number.isFinite(num) ? num : null;\r\n };\r\n\r\n const parseRatio = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n if (!cleaned) return null;\r\n if (cleaned.endsWith(\"%\")) {\r\n const num = Number.parseFloat(cleaned.slice(0, -1));\r\n return Number.isFinite(num) ? num / 100 : null;\r\n }\r\n const num = Number.parseFloat(cleaned);\r\n return Number.isFinite(num) ? num : null;\r\n };\r\n\r\n const parseAngle = (value: string): number | null => {\r\n const cleaned = value.trim().toLowerCase();\r\n if (!cleaned) return null;\r\n if (cleaned.endsWith(\"rad\")) {\r\n const num = Number.parseFloat(cleaned.slice(0, -3));\r\n return Number.isFinite(num) ? num : null;\r\n }\r\n const stripped = cleaned.endsWith(\"deg\") ? cleaned.slice(0, -3) : cleaned;\r\n const num = Number.parseFloat(stripped);\r\n return Number.isFinite(num) ? (num * Math.PI) / 180 : null;\r\n };\r\n\r\n const parseBloom = (value: string): { intensity: number; threshold: number } | null => {\r\n const parts = value.split(\",\").map((part) => part.trim());\r\n const intensity = parseNumber(parts[0] || \"\");\r\n if (intensity === null) return null;\r\n const threshold = parts[1] ? parseRatio(parts[1]) : null;\r\n return {\r\n intensity: Math.max(0, intensity),\r\n threshold: threshold === null ? 0.8 : Math.max(0, Math.min(1, threshold)),\r\n };\r\n };\r\n\r\n const parseAmount = (value: string, name: string, allowZero = false): number | null => {\r\n const amount = parseNumber(value);\r\n if (amount === null) {\r\n warnings.push(`[String3D] Invalid ${name} value \"${value}\".`);\r\n return null;\r\n }\r\n if (!allowZero && amount <= 0) {\r\n warnings.push(`[String3D] ${name} must be > 0.`);\r\n return null;\r\n }\r\n return amount;\r\n };\r\n\r\n const parseRatioAmount = (value: string, name: string): number | null => {\r\n const amount = parseRatio(value);\r\n if (amount === null) {\r\n warnings.push(`[String3D] Invalid ${name} value \"${value}\".`);\r\n return null;\r\n }\r\n return amount;\r\n };\r\n\r\n const re = /([a-zA-Z-]+)\\(([^)]*)\\)/g;\r\n let match: RegExpExecArray | null;\r\n while ((match = re.exec(raw))) {\r\n const name = match[1].toLowerCase();\r\n const args = (match[2] || \"\").trim();\r\n\r\n if (name === \"blur\") {\r\n const amount = parseAmount(args, \"blur\", true);\r\n if (amount !== null) effects.push({ type: \"blur\", amount });\r\n } else if (name === \"pixel\" || name === \"pixelate\") {\r\n const size = parseAmount(args, \"pixel\", true);\r\n if (size !== null) effects.push({ type: \"pixel\", size });\r\n } else if (name === \"bloom\") {\r\n const bloom = parseBloom(args);\r\n if (bloom) effects.push({ type: \"bloom\", ...bloom });\r\n else warnings.push(`[String3D] Invalid bloom value \"${args}\".`);\r\n } else if (name === \"brightness\") {\r\n const amount = parseRatioAmount(args, \"brightness\");\r\n if (amount !== null) effects.push({ type: \"brightness\", amount: Math.max(0, amount) });\r\n } else if (name === \"contrast\") {\r\n const amount = parseRatioAmount(args, \"contrast\");\r\n if (amount !== null) effects.push({ type: \"contrast\", amount: Math.max(0, amount) });\r\n } else if (name === \"saturate\") {\r\n const amount = parseRatioAmount(args, \"saturate\");\r\n if (amount !== null) effects.push({ type: \"saturate\", amount: Math.max(0, amount) });\r\n } else if (name === \"grayscale\") {\r\n const amount = parseRatioAmount(args, \"grayscale\");\r\n if (amount !== null)\r\n effects.push({ type: \"grayscale\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"sepia\") {\r\n const amount = parseRatioAmount(args, \"sepia\");\r\n if (amount !== null)\r\n effects.push({ type: \"sepia\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"invert\") {\r\n const amount = parseRatioAmount(args, \"invert\");\r\n if (amount !== null)\r\n effects.push({ type: \"invert\", amount: Math.max(0, Math.min(1, amount)) });\r\n } else if (name === \"hue-rotate\") {\r\n const angle = parseAngle(args);\r\n if (angle !== null) effects.push({ type: \"hue-rotate\", angle });\r\n else warnings.push(`[String3D] Invalid hue-rotate value \"${args}\".`);\r\n } else if (name) {\r\n const custom = this.customFilterRegistry.get(name);\r\n if (custom) {\r\n const parsed = custom.parse ? custom.parse(args) : {};\r\n if (parsed === null) {\r\n warnings.push(`[String3D] Invalid custom filter \"${name}\" args \"${args}\".`);\r\n } else {\r\n effects.push({ type: \"custom\", name, uniforms: parsed });\r\n }\r\n } else {\r\n warnings.push(`[String3D] Unknown filter \"${name}\".`);\r\n }\r\n }\r\n }\r\n\r\n if (effects.length === 0) {\r\n warnings.push(\"[String3D] No valid filters parsed from --filter.\");\r\n }\r\n\r\n return { effects, warnings };\r\n }\r\n\r\n private getFilterTransition(el: HTMLElement): {\r\n duration: number;\r\n delay: number;\r\n easing: (t: number) => number;\r\n } {\r\n const style = getComputedStyle(el);\r\n const properties = this.splitTransitionList(style.transitionProperty);\r\n const durations = this.splitTransitionList(style.transitionDuration);\r\n const delays = this.splitTransitionList(style.transitionDelay);\r\n const timings = this.splitTransitionList(style.transitionTimingFunction);\r\n\r\n const index = this.findTransitionIndex(properties, \"--filter\");\r\n if (index === -1) {\r\n const shorthand = this.parseTransitionShorthand(style.transition);\r\n const fallback = shorthand.get(\"--filter\") || shorthand.get(\"all\");\r\n if (fallback) {\r\n return fallback;\r\n }\r\n return { duration: 0, delay: 0, easing: (t) => t };\r\n }\r\n\r\n const duration = this.parseTime(durations[index] || durations[durations.length - 1] || \"0s\");\r\n const delay = this.parseTime(delays[index] || delays[delays.length - 1] || \"0s\");\r\n const easingRaw = timings[index] || timings[timings.length - 1] || \"linear\";\r\n return { duration, delay, easing: this.parseEasing(easingRaw) };\r\n }\r\n\r\n private splitTransitionList(value: string): string[] {\r\n const result: string[] = [];\r\n let current = \"\";\r\n let depth = 0;\r\n for (let i = 0; i < value.length; i += 1) {\r\n const ch = value[i];\r\n if (ch === \"(\") depth += 1;\r\n if (ch === \")\") depth = Math.max(0, depth - 1);\r\n if (ch === \",\" && depth === 0) {\r\n result.push(current.trim());\r\n current = \"\";\r\n } else {\r\n current += ch;\r\n }\r\n }\r\n if (current.trim()) result.push(current.trim());\r\n return result.length > 0 ? result : [\"all\"];\r\n }\r\n\r\n private findTransitionIndex(properties: string[], name: string): number {\r\n const normalized = properties.map((prop) => prop.trim().toLowerCase());\r\n let index = normalized.indexOf(name);\r\n if (index === -1) {\r\n index = normalized.indexOf(\"all\");\r\n }\r\n return index;\r\n }\r\n\r\n private parseTime(value: string): number {\r\n const raw = value.trim().toLowerCase();\r\n if (raw.endsWith(\"ms\")) {\r\n const num = Number.parseFloat(raw.slice(0, -2));\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n if (raw.endsWith(\"s\")) {\r\n const num = Number.parseFloat(raw.slice(0, -1));\r\n return Number.isFinite(num) ? num * 1000 : 0;\r\n }\r\n const num = Number.parseFloat(raw);\r\n return Number.isFinite(num) ? num : 0;\r\n }\r\n\r\n private parseTransitionShorthand(\r\n value: string,\r\n ): Map<string, { duration: number; delay: number; easing: (t: number) => number }> {\r\n const map = new Map<\r\n string,\r\n { duration: number; delay: number; easing: (t: number) => number }\r\n >();\r\n const parts = this.splitTransitionList(value);\r\n parts.forEach((part) => {\r\n if (!part) return;\r\n const tokens = part.trim().split(/\\s+(?![^()]*\\))/g);\r\n let prop = \"\";\r\n let duration = \"\";\r\n let delay = \"\";\r\n let easing = \"\";\r\n tokens.forEach((token) => {\r\n const lower = token.toLowerCase();\r\n if (lower.endsWith(\"ms\") || lower.endsWith(\"s\") || /^[0-9.]+$/.test(lower)) {\r\n if (!duration) duration = lower;\r\n else if (!delay) delay = lower;\r\n } else if (\r\n lower.startsWith(\"cubic-bezier\") ||\r\n lower.startsWith(\"steps\") ||\r\n lower === \"linear\" ||\r\n lower === \"ease\" ||\r\n lower === \"ease-in\" ||\r\n lower === \"ease-out\" ||\r\n lower === \"ease-in-out\"\r\n ) {\r\n easing = token;\r\n } else if (!prop) {\r\n prop = token;\r\n }\r\n });\r\n if (!prop) return;\r\n map.set(prop.trim().toLowerCase(), {\r\n duration: this.parseTime(duration || \"0s\"),\r\n delay: this.parseTime(delay || \"0s\"),\r\n easing: this.parseEasing(easing || \"linear\"),\r\n });\r\n });\r\n return map;\r\n }\r\n\r\n private parseEasing(value: string): (t: number) => number {\r\n const raw = value.trim();\r\n if (!raw) return (t) => t;\r\n if (!this.easingParser) return (t) => t;\r\n try {\r\n const fn = this.easingParser(raw);\r\n return typeof fn === \"function\" ? fn : (t) => t;\r\n } catch {\r\n return (t) => t;\r\n }\r\n }\r\n\r\n private canInterpolate(from: String3DFilterChain, to: String3DFilterChain): boolean {\r\n if (from.length !== to.length) return false;\r\n return from.every((effect, index) => {\r\n const other = to[index];\r\n if (effect.type !== other.type) return false;\r\n if (effect.type === \"custom\" && other.type === \"custom\") {\r\n if (effect.name !== other.name) return false;\r\n const keys = Object.keys(effect.uniforms || {});\r\n const otherKeys = Object.keys(other.uniforms || {});\r\n if (keys.length !== otherKeys.length) return false;\r\n return keys.every(\r\n (key) => key in (other.uniforms || {}) && this.isNumeric(effect.uniforms?.[key]),\r\n );\r\n }\r\n return true;\r\n });\r\n }\r\n\r\n private makeZeroChain(chain: String3DFilterChain): String3DFilterChain {\r\n return chain.map((effect) => {\r\n switch (effect.type) {\r\n case \"blur\":\r\n return { type: \"blur\", amount: 0 };\r\n case \"pixel\":\r\n return { type: \"pixel\", size: 0 };\r\n case \"bloom\":\r\n return { type: \"bloom\", intensity: 0, threshold: effect.threshold };\r\n case \"brightness\":\r\n return { type: \"brightness\", amount: 1 };\r\n case \"contrast\":\r\n return { type: \"contrast\", amount: 1 };\r\n case \"saturate\":\r\n return { type: \"saturate\", amount: 1 };\r\n case \"grayscale\":\r\n return { type: \"grayscale\", amount: 0 };\r\n case \"sepia\":\r\n return { type: \"sepia\", amount: 0 };\r\n case \"invert\":\r\n return { type: \"invert\", amount: 0 };\r\n case \"hue-rotate\":\r\n return { type: \"hue-rotate\", angle: 0 };\r\n case \"custom\": {\r\n const uniforms: Record<string, any> = {};\r\n Object.entries(effect.uniforms || {}).forEach(([key, value]) => {\r\n uniforms[key] = this.isNumeric(value) ? 0 : value;\r\n });\r\n return { type: \"custom\", name: effect.name, uniforms };\r\n }\r\n default:\r\n return effect;\r\n }\r\n });\r\n }\r\n\r\n private sampleTransition(state: FilterTransitionState, now: number): String3DFilterChain {\r\n if (!state.animating) return state.effects;\r\n if (now < state.startTime) {\r\n return state.from;\r\n }\r\n const elapsed = now - state.startTime;\r\n const duration = Math.max(1, state.duration);\r\n const t = Math.min(1, Math.max(0, elapsed / duration));\r\n const eased = state.easing(t);\r\n const interpolated = this.interpolateChain(state.from, state.to, eased);\r\n if (t >= 1) {\r\n state.animating = false;\r\n state.from = state.to;\r\n if (state.pendingEffects && state.pendingRaw === state.raw) {\r\n state.effects = state.pendingEffects;\r\n state.raw = state.pendingRaw || state.raw;\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n } else if (state.pendingEffects) {\r\n state.pendingEffects = undefined;\r\n state.pendingRaw = undefined;\r\n }\r\n }\r\n return interpolated;\r\n }\r\n\r\n private getCurrentChain(state: FilterTransitionState, now: number): String3DFilterChain {\r\n if (!state.animating) return state.effects;\r\n if (now < state.startTime) return state.from;\r\n const elapsed = now - state.startTime;\r\n const duration = Math.max(1, state.duration);\r\n const t = Math.min(1, Math.max(0, elapsed / duration));\r\n const eased = state.easing(t);\r\n return this.interpolateChain(state.from, state.to, eased);\r\n }\r\n\r\n private interpolateChain(\r\n from: String3DFilterChain,\r\n to: String3DFilterChain,\r\n t: number,\r\n ): String3DFilterChain {\r\n if (!this.canInterpolate(from, to)) return to;\r\n return from.map((effect, index) => this.interpolateEffect(effect, to[index], t));\r\n }\r\n\r\n private interpolateEffect(\r\n from: String3DFilterEffect,\r\n to: String3DFilterEffect,\r\n t: number,\r\n ): String3DFilterEffect {\r\n const lerp = (a: number, b: number) => a + (b - a) * t;\r\n if (from.type === \"blur\" && to.type === \"blur\") {\r\n return { type: \"blur\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"pixel\" && to.type === \"pixel\") {\r\n return { type: \"pixel\", size: lerp(from.size, to.size) };\r\n }\r\n if (from.type === \"bloom\" && to.type === \"bloom\") {\r\n return {\r\n type: \"bloom\",\r\n intensity: lerp(from.intensity, to.intensity),\r\n threshold: lerp(from.threshold, to.threshold),\r\n };\r\n }\r\n if (from.type === \"brightness\" && to.type === \"brightness\") {\r\n return { type: \"brightness\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"contrast\" && to.type === \"contrast\") {\r\n return { type: \"contrast\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"saturate\" && to.type === \"saturate\") {\r\n return { type: \"saturate\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"grayscale\" && to.type === \"grayscale\") {\r\n return { type: \"grayscale\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"sepia\" && to.type === \"sepia\") {\r\n return { type: \"sepia\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"invert\" && to.type === \"invert\") {\r\n return { type: \"invert\", amount: lerp(from.amount, to.amount) };\r\n }\r\n if (from.type === \"hue-rotate\" && to.type === \"hue-rotate\") {\r\n return { type: \"hue-rotate\", angle: lerp(from.angle, to.angle) };\r\n }\r\n if (from.type === \"custom\" && to.type === \"custom\" && from.name === to.name) {\r\n const uniforms: Record<string, any> = {};\r\n Object.entries(to.uniforms || {}).forEach(([key, value]) => {\r\n const fromValue = from.uniforms?.[key];\r\n if (this.isNumeric(fromValue) && this.isNumeric(value)) {\r\n uniforms[key] = lerp(fromValue, value);\r\n } else {\r\n uniforms[key] = value;\r\n }\r\n });\r\n return { type: \"custom\", name: to.name, uniforms };\r\n }\r\n return to;\r\n }\r\n\r\n private stringifyFilterChain(chain: String3DFilterChain): string {\r\n const parts = chain.map((effect) => {\r\n if (effect.type === \"blur\") return `blur:${effect.amount}`;\r\n if (effect.type === \"pixel\") return `pixel:${effect.size}`;\r\n if (effect.type === \"bloom\") return `bloom:${effect.intensity},${effect.threshold}`;\r\n if (effect.type === \"brightness\") return `brightness:${effect.amount}`;\r\n if (effect.type === \"contrast\") return `contrast:${effect.amount}`;\r\n if (effect.type === \"saturate\") return `saturate:${effect.amount}`;\r\n if (effect.type === \"grayscale\") return `grayscale:${effect.amount}`;\r\n if (effect.type === \"sepia\") return `sepia:${effect.amount}`;\r\n if (effect.type === \"invert\") return `invert:${effect.amount}`;\r\n if (effect.type === \"hue-rotate\") return `hue-rotate:${effect.angle}`;\r\n if (effect.type === \"custom\") {\r\n const uniforms = Object.keys(effect.uniforms || {})\r\n .sort()\r\n .map((key) => `${key}=${(effect.uniforms as any)[key]}`)\r\n .join(\",\");\r\n return `custom:${effect.name}:${uniforms}`;\r\n }\r\n return \"unknown\";\r\n });\r\n return parts.join(\"|\");\r\n }\r\n\r\n private isNumeric(value: unknown): value is number {\r\n return typeof value === \"number\" && Number.isFinite(value);\r\n }\r\n\r\n private isZeroChain(chain: String3DFilterChain): boolean {\r\n return chain.every((effect) => {\r\n switch (effect.type) {\r\n case \"blur\":\r\n return effect.amount <= 0;\r\n case \"pixel\":\r\n return effect.size <= 0;\r\n case \"bloom\":\r\n return effect.intensity <= 0;\r\n case \"brightness\":\r\n return effect.amount === 1;\r\n case \"contrast\":\r\n return effect.amount === 1;\r\n case \"saturate\":\r\n return effect.amount === 1;\r\n case \"grayscale\":\r\n return effect.amount === 0;\r\n case \"sepia\":\r\n return effect.amount === 0;\r\n case \"invert\":\r\n return effect.amount === 0;\r\n case \"hue-rotate\":\r\n return effect.angle === 0;\r\n case \"custom\":\r\n return false;\r\n default:\r\n return false;\r\n }\r\n });\r\n }\r\n}\r\n","import type {\r\n String3DCustomMaterialDefinition,\r\n IMaterialInstance,\r\n IMaterialFactory,\r\n} from \"../core/materials\";\r\nimport { collectUniformsFromCSS, mergeInjections } from \"../core/materials\";\r\n\r\nexport class ThreeJSMaterialFactory implements IMaterialFactory {\r\n private THREE: any;\r\n private textureLoader: any;\r\n private textureCache: Map<string, any> = new Map();\r\n private meshTransmissionMaterialClass: any = null;\r\n\r\n constructor(THREE: any) {\r\n this.THREE = THREE;\r\n this.textureLoader = new THREE.TextureLoader();\r\n }\r\n\r\n supports(definition: String3DCustomMaterialDefinition): boolean {\r\n return true;\r\n }\r\n\r\n create(\r\n definition: String3DCustomMaterialDefinition,\r\n initialUniforms?: Record<string, any>,\r\n ): IMaterialInstance {\r\n const uniforms = this.buildUniforms(definition, initialUniforms);\r\n\r\n let material: any;\r\n\r\n if (definition.extends === \"shader\" || (!definition.extends && definition.vertexShader)) {\r\n material = this.createShaderMaterial(definition, uniforms);\r\n } else {\r\n material = this.createExtendedMaterial(definition, uniforms);\r\n }\r\n\r\n this.applyMaterialProperties(material, definition);\r\n\r\n const update = (newUniforms: Record<string, any>) => {\r\n this.updateUniforms(material, definition, newUniforms);\r\n };\r\n\r\n const dispose = () => {\r\n material.dispose();\r\n };\r\n\r\n return { material, definition, update, dispose };\r\n }\r\n\r\n parseUniformsFromCSS(\r\n definition: String3DCustomMaterialDefinition,\r\n element: HTMLElement,\r\n style: CSSStyleDeclaration,\r\n ): Record<string, any> {\r\n return collectUniformsFromCSS(definition, element, style);\r\n }\r\n\r\n getMaterialDefinition(material: any): String3DCustomMaterialDefinition | null {\r\n const definition = material?.userData?.definition;\r\n return definition || null;\r\n }\r\n\r\n isShaderMaterial(material: any): boolean {\r\n return !!material?.isShaderMaterial;\r\n }\r\n\r\n applyUniforms(\r\n material: any,\r\n definition: String3DCustomMaterialDefinition,\r\n values: Record<string, any>,\r\n ): void {\r\n const shader = material?.userData?.shader;\r\n const customUniforms = material?.userData?.customUniforms;\r\n\r\n if (shader?.uniforms) {\r\n for (const [key, value] of Object.entries(values)) {\r\n const uniformDef = definition.uniforms?.[key];\r\n if (uniformDef && shader.uniforms[key]) {\r\n shader.uniforms[key].value = this.convertUniformValue(uniformDef.type, value);\r\n }\r\n }\r\n }\r\n\r\n if (customUniforms) {\r\n for (const [key, value] of Object.entries(values)) {\r\n const uniformDef = definition.uniforms?.[key];\r\n if (uniformDef && customUniforms[key]) {\r\n customUniforms[key].value = this.convertUniformValue(uniformDef.type, value);\r\n }\r\n }\r\n }\r\n\r\n if (material?.uniforms) {\r\n for (const [key, value] of Object.entries(values)) {\r\n const uniformDef = definition.uniforms?.[key];\r\n if (uniformDef && material.uniforms[key]) {\r\n material.uniforms[key].value = this.convertUniformValue(uniformDef.type, value);\r\n }\r\n }\r\n }\r\n }\r\n\r\n private buildUniforms(\r\n definition: String3DCustomMaterialDefinition,\r\n initialValues?: Record<string, any>,\r\n ): Record<string, { value: any }> {\r\n const result: Record<string, { value: any }> = {};\r\n\r\n if (definition.uniforms) {\r\n for (const [key, def] of Object.entries(definition.uniforms)) {\r\n let value = initialValues?.[key] ?? def.value;\r\n value = this.convertUniformValue(def.type, value);\r\n result[key] = { value };\r\n }\r\n }\r\n\r\n return result;\r\n }\r\n\r\n private convertUniformValue(type: string, value: any): any {\r\n switch (type) {\r\n case \"vec2\":\r\n if (Array.isArray(value)) {\r\n return new this.THREE.Vector2(value[0], value[1]);\r\n }\r\n return value;\r\n case \"vec3\":\r\n if (Array.isArray(value)) {\r\n return new this.THREE.Vector3(value[0], value[1], value[2]);\r\n }\r\n return value;\r\n case \"vec4\":\r\n if (Array.isArray(value)) {\r\n return new this.THREE.Vector4(value[0], value[1], value[2], value[3]);\r\n }\r\n return value;\r\n case \"color\":\r\n if (Array.isArray(value)) {\r\n return new this.THREE.Color(value[0], value[1], value[2]);\r\n }\r\n if (typeof value === \"string\") {\r\n return new this.THREE.Color(value);\r\n }\r\n return value;\r\n case \"texture\":\r\n if (typeof value === \"string\" && value) {\r\n return this.loadTexture(value);\r\n }\r\n return value;\r\n default:\r\n return value;\r\n }\r\n }\r\n\r\n private loadTexture(url: string): any {\r\n if (this.textureCache.has(url)) {\r\n return this.textureCache.get(url);\r\n }\r\n const texture = this.textureLoader.load(url);\r\n this.textureCache.set(url, texture);\r\n return texture;\r\n }\r\n\r\n private createShaderMaterial(\r\n definition: String3DCustomMaterialDefinition,\r\n uniforms: Record<string, { value: any }>,\r\n ): any {\r\n const material = new this.THREE.ShaderMaterial({\r\n uniforms,\r\n vertexShader: definition.vertexShader || this.getDefaultVertexShader(),\r\n fragmentShader: definition.fragmentShader || this.getDefaultFragmentShader(),\r\n lights: definition.lights ?? false,\r\n transparent: definition.properties?.transparent ?? false,\r\n });\r\n material.userData.customUniforms = uniforms;\r\n material.userData.definition = definition;\r\n return material;\r\n }\r\n\r\n private createExtendedMaterial(\r\n definition: String3DCustomMaterialDefinition,\r\n uniforms: Record<string, { value: any }>,\r\n ): any {\r\n const baseType = definition.extends || \"standard\";\r\n let BaseMaterial: any;\r\n\r\n switch (baseType) {\r\n case \"basic\":\r\n BaseMaterial = this.THREE.MeshBasicMaterial;\r\n break;\r\n case \"physical\":\r\n BaseMaterial = this.THREE.MeshPhysicalMaterial;\r\n break;\r\n case \"standard\":\r\n default:\r\n BaseMaterial = this.THREE.MeshStandardMaterial;\r\n break;\r\n }\r\n\r\n const material = new BaseMaterial({\r\n transparent: definition.properties?.transparent ?? false,\r\n });\r\n\r\n if (definition.injections && definition.injections.length > 0) {\r\n const injectionMap = mergeInjections(definition.injections);\r\n\r\n material.onBeforeCompile = (shader: any) => {\r\n Object.assign(shader.uniforms, uniforms);\r\n\r\n shader.vertexShader = this.injectVertexShader(shader.vertexShader, injectionMap, uniforms);\r\n shader.fragmentShader = this.injectFragmentShader(\r\n shader.fragmentShader,\r\n injectionMap,\r\n uniforms,\r\n );\r\n\r\n material.userData.shader = shader;\r\n };\r\n }\r\n\r\n material.userData.customUniforms = uniforms;\r\n material.userData.definition = definition;\r\n\r\n return material;\r\n }\r\n\r\n\r\n private injectVertexShader(\r\n shader: string,\r\n injections: Map<string, string>,\r\n uniforms: Record<string, { value: any }>,\r\n ): string {\r\n let result = shader;\r\n\r\n const pars = injections.get(\"vertex_pars\");\r\n if (pars) {\r\n result = result.replace(\"#include <common>\", `#include <common>\\n${pars}`);\r\n }\r\n\r\n const header = injections.get(\"vertex_header\");\r\n if (header) {\r\n const uniformDeclarations = this.generateUniformDeclarations(uniforms);\r\n result = result.replace(\"void main() {\", `${uniformDeclarations}\\n${header}\\nvoid main() {`);\r\n }\r\n\r\n const transform = injections.get(\"vertex_transform\");\r\n if (transform) {\r\n result = result.replace(\"#include <begin_vertex>\", `#include <begin_vertex>\\n${transform}`);\r\n }\r\n\r\n const output = injections.get(\"vertex_output\");\r\n if (output) {\r\n result = result.replace(\"#include <project_vertex>\", `${output}\\n#include <project_vertex>`);\r\n }\r\n\r\n return result;\r\n }\r\n\r\n private injectFragmentShader(\r\n shader: string,\r\n injections: Map<string, string>,\r\n uniforms: Record<string, { value: any }>,\r\n ): string {\r\n let result = shader;\r\n\r\n const pars = injections.get(\"fragment_pars\");\r\n if (pars) {\r\n result = result.replace(\"#include <common>\", `#include <common>\\n${pars}`);\r\n }\r\n\r\n const header = injections.get(\"fragment_header\");\r\n if (header) {\r\n const uniformDeclarations = this.generateUniformDeclarations(uniforms);\r\n result = result.replace(\"void main() {\", `${uniformDeclarations}\\n${header}\\nvoid main() {`);\r\n }\r\n\r\n const color = injections.get(\"fragment_color\");\r\n if (color) {\r\n result = result.replace(\"#include <color_fragment>\", `#include <color_fragment>\\n${color}`);\r\n }\r\n\r\n const normal = injections.get(\"fragment_normal\");\r\n if (normal) {\r\n result = result.replace(\r\n \"#include <normal_fragment_maps>\",\r\n `#include <normal_fragment_maps>\\n${normal}`,\r\n );\r\n }\r\n\r\n const roughness = injections.get(\"fragment_roughness\");\r\n if (roughness) {\r\n result = result.replace(\r\n \"#include <roughnessmap_fragment>\",\r\n `#include <roughnessmap_fragment>\\n${roughness}`,\r\n );\r\n }\r\n\r\n const metalness = injections.get(\"fragment_metalness\");\r\n if (metalness) {\r\n result = result.replace(\r\n \"#include <metalnessmap_fragment>\",\r\n `#include <metalnessmap_fragment>\\n${metalness}`,\r\n );\r\n }\r\n\r\n const ao = injections.get(\"fragment_ao\");\r\n if (ao) {\r\n result = result.replace(\"#include <aomap_fragment>\", `#include <aomap_fragment>\\n${ao}`);\r\n }\r\n\r\n const transmission = injections.get(\"fragment_transmission\");\r\n if (transmission) {\r\n result = result.replace(\r\n \"#include <transmission_fragment>\",\r\n `#include <transmission_fragment>\\n${transmission}`,\r\n );\r\n }\r\n\r\n const lights = injections.get(\"fragment_lights\");\r\n if (lights) {\r\n result = result.replace(\r\n \"#include <lights_physical_fragment>\",\r\n `#include <lights_physical_fragment>\\n${lights}`,\r\n );\r\n }\r\n\r\n const emissive = injections.get(\"fragment_emissive\");\r\n if (emissive) {\r\n result = result.replace(\r\n \"#include <emissivemap_fragment>\",\r\n `#include <emissivemap_fragment>\\n${emissive}`,\r\n );\r\n }\r\n\r\n const output = injections.get(\"fragment_output\");\r\n if (output) {\r\n result = result.replace(\r\n \"#include <dithering_fragment>\",\r\n `${output}\\n#include <dithering_fragment>`,\r\n );\r\n }\r\n\r\n return result;\r\n }\r\n\r\n private generateUniformDeclarations(uniforms: Record<string, { value: any }>): string {\r\n const lines: string[] = [];\r\n\r\n for (const [name, uniform] of Object.entries(uniforms)) {\r\n const type = this.inferGLSLType(uniform.value);\r\n lines.push(`uniform ${type} ${name};`);\r\n }\r\n\r\n return lines.join(\"\\n\");\r\n }\r\n\r\n private inferGLSLType(value: any): string {\r\n if (typeof value === \"number\") return \"float\";\r\n if (typeof value === \"boolean\") return \"bool\";\r\n if (value instanceof this.THREE.Vector2) return \"vec2\";\r\n if (value instanceof this.THREE.Vector3) return \"vec3\";\r\n if (value instanceof this.THREE.Vector4) return \"vec4\";\r\n if (value instanceof this.THREE.Color) return \"vec3\";\r\n if (value instanceof this.THREE.Matrix3) return \"mat3\";\r\n if (value instanceof this.THREE.Matrix4) return \"mat4\";\r\n if (value?.isTexture) return \"sampler2D\";\r\n return \"float\";\r\n }\r\n\r\n private applyMaterialProperties(\r\n material: any,\r\n definition: String3DCustomMaterialDefinition,\r\n ): void {\r\n const props = definition.properties;\r\n if (!props) return;\r\n\r\n if (props.transparent !== undefined) {\r\n material.transparent = props.transparent;\r\n }\r\n if (props.opacity !== undefined && \"opacity\" in material) {\r\n material.opacity = props.opacity;\r\n }\r\n\r\n if (props.side !== undefined) {\r\n switch (props.side) {\r\n case \"front\":\r\n material.side = this.THREE.FrontSide;\r\n break;\r\n case \"back\":\r\n material.side = this.THREE.BackSide;\r\n break;\r\n case \"double\":\r\n material.side = this.THREE.DoubleSide;\r\n break;\r\n }\r\n }\r\n\r\n if (props.depthWrite !== undefined) {\r\n material.depthWrite = props.depthWrite;\r\n }\r\n\r\n if (props.depthTest !== undefined) {\r\n material.depthTest = props.depthTest;\r\n }\r\n\r\n if (props.blending !== undefined) {\r\n switch (props.blending) {\r\n case \"additive\":\r\n material.blending = this.THREE.AdditiveBlending;\r\n break;\r\n case \"subtractive\":\r\n material.blending = this.THREE.SubtractiveBlending;\r\n break;\r\n case \"multiply\":\r\n material.blending = this.THREE.MultiplyBlending;\r\n break;\r\n default:\r\n material.blending = this.THREE.NormalBlending;\r\n }\r\n }\r\n\r\n if (props.wireframe !== undefined) {\r\n material.wireframe = props.wireframe;\r\n }\r\n\r\n if (props.color !== undefined && material.color) {\r\n material.color.set(props.color);\r\n }\r\n if (props.emissive !== undefined && material.emissive) {\r\n material.emissive.set(props.emissive);\r\n }\r\n if (props.metalness !== undefined && \"metalness\" in material) {\r\n material.metalness = props.metalness;\r\n }\r\n if (props.roughness !== undefined && \"roughness\" in material) {\r\n material.roughness = props.roughness;\r\n }\r\n if (props.transmission !== undefined && \"transmission\" in material) {\r\n material.transmission = props.transmission;\r\n }\r\n if (props.thickness !== undefined && \"thickness\" in material) {\r\n material.thickness = props.thickness;\r\n }\r\n if (props.ior !== undefined && \"ior\" in material) {\r\n material.ior = props.ior;\r\n }\r\n if (props.reflectivity !== undefined && \"reflectivity\" in material) {\r\n material.reflectivity = props.reflectivity;\r\n }\r\n if (props.clearcoat !== undefined && \"clearcoat\" in material) {\r\n material.clearcoat = props.clearcoat;\r\n }\r\n if (props.clearcoatRoughness !== undefined && \"clearcoatRoughness\" in material) {\r\n material.clearcoatRoughness = props.clearcoatRoughness;\r\n }\r\n if (props.attenuationDistance !== undefined && \"attenuationDistance\" in material) {\r\n material.attenuationDistance = props.attenuationDistance;\r\n }\r\n if (props.attenuationColor !== undefined && material.attenuationColor) {\r\n material.attenuationColor.set(props.attenuationColor);\r\n }\r\n }\r\n\r\n private updateUniforms(\r\n material: any,\r\n definition: String3DCustomMaterialDefinition,\r\n newValues: Record<string, any>,\r\n ): void {\r\n this.applyUniforms(material, definition, newValues);\r\n }\r\n\r\n private getDefaultVertexShader(): string {\r\n return `\r\n varying vec2 vUv;\r\n varying vec3 vNormal;\r\n varying vec3 vPosition;\r\n\r\n void main() {\r\n vUv = uv;\r\n vNormal = normalize(normalMatrix * normal);\r\n vPosition = (modelMatrix * vec4(position, 1.0)).xyz;\r\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\r\n }\r\n `;\r\n }\r\n\r\n private getDefaultFragmentShader(): string {\r\n return `\r\n varying vec2 vUv;\r\n varying vec3 vNormal;\r\n varying vec3 vPosition;\r\n\r\n void main() {\r\n gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0);\r\n }\r\n `;\r\n }\r\n\r\n dispose(): void {\r\n this.textureCache.forEach((texture) => texture.dispose());\r\n this.textureCache.clear();\r\n }\r\n}\r\n","import {\n I3DCustomFilterRegistryRuntime,\n I3DBackend,\n I3DEngine,\n I3DPostProcessPipelineRuntime,\n I3DPostProcessRuntime,\n I3DRenderer,\n I3DRenderTarget,\n I3DScene,\r\n I3DCamera,\r\n I3DMaterial,\n I3DObject,\n} from \"../core/abstractions/I3DEngine\";\nimport type {\n String3DCustomFilterDefinition,\n String3DCustomFilterImplementation,\n} from \"../core/filters/String3DCustomFilter\";\nimport type { String3DFilterChain } from \"../core/filters/String3DFilterTypes\";\n\r\ntype RenderTargetFactory = (width: number, height: number) => I3DRenderTarget;\r\n\r\nclass RenderTargetPool {\r\n private pool: I3DRenderTarget[] = [];\r\n private create: RenderTargetFactory;\r\n\r\n constructor(create: RenderTargetFactory) {\r\n this.create = create;\r\n }\r\n\r\n acquire(width: number, height: number): I3DRenderTarget {\r\n const target = this.pool.pop() || this.create(width, height);\r\n if (target.width !== width || target.height !== height) {\r\n target.setSize(width, height);\r\n }\r\n return target;\r\n }\r\n\r\n release(target: I3DRenderTarget): void {\r\n this.pool.push(target);\r\n }\r\n\r\n dispose(): void {\r\n this.pool.forEach((target) => target.dispose());\r\n this.pool = [];\r\n }\r\n}\r\n\r\nexport class ThreePostProcessPipeline implements I3DPostProcessPipelineRuntime {\n private readonly backend: I3DBackend;\n private engine: I3DEngine;\n private renderer: I3DRenderer;\r\n private runtime: I3DPostProcessRuntime;\r\n private customFilterRegistry: I3DCustomFilterRegistryRuntime;\r\n private width: number;\r\n private height: number;\r\n private scale = 1;\r\n private scene: I3DScene;\r\n private camera: I3DCamera;\r\n private quad: I3DObject;\r\n private copyMaterial: I3DMaterial;\r\n private blurMaterial: I3DMaterial;\r\n private pixelMaterial: I3DMaterial;\r\n private bloomExtractMaterial: I3DMaterial;\r\n private bloomAddMaterial: I3DMaterial;\r\n private colorMaterial: I3DMaterial;\r\n private customMaterials: Map<string, I3DMaterial> = new Map();\r\n private pool: RenderTargetPool;\r\n\r\n constructor(context: {\n engine: I3DEngine;\n renderer: I3DRenderer;\n runtime: I3DPostProcessRuntime;\n width: number;\n height: number;\n customFilterRegistry: I3DCustomFilterRegistryRuntime;\n }) {\n const { engine, renderer, runtime, width, height, customFilterRegistry } = context;\n this.backend = engine.getBackend?.() || \"webgl\";\n this.engine = engine;\n this.renderer = renderer;\n this.runtime = runtime;\n this.customFilterRegistry = customFilterRegistry;\n this.width = width;\r\n this.height = height;\r\n\r\n this.scene = engine.createScene();\r\n this.camera = engine.createOrthographicCamera(-1, 1, 1, -1, 0, 1);\r\n\r\n const geometry = engine.createPlaneGeometry(2, 2);\r\n this.copyMaterial = this.createCopyMaterial();\r\n this.blurMaterial = this.createBlurMaterial();\r\n this.pixelMaterial = this.createPixelMaterial();\r\n this.bloomExtractMaterial = this.createBloomExtractMaterial();\r\n this.bloomAddMaterial = this.createBloomAddMaterial();\r\n this.colorMaterial = this.createColorMaterial();\r\n\r\n this.quad = engine.createMesh(geometry, this.copyMaterial);\r\n this.scene.add(this.quad);\r\n\r\n const create = (w: number, h: number) => this.runtime.createRenderTarget(w, h);\r\n this.pool = new RenderTargetPool(create);\r\n }\r\n\r\n public isSupported(): boolean {\r\n return this.runtime.isSupported(this.renderer);\r\n }\r\n\r\n public resize(width: number, height: number): void {\r\n this.width = width;\r\n this.height = height;\r\n }\r\n\r\n public setScale(scale: number): void {\r\n const next = Math.max(0.75, Math.min(1, scale));\r\n this.scale = next;\r\n }\r\n\r\n public applyFilters(\r\n input: I3DRenderTarget,\r\n effects: String3DFilterChain,\r\n quality = 1,\r\n ): I3DRenderTarget {\r\n let current = input;\r\n const locals: I3DRenderTarget[] = [];\r\n\r\n const releaseLocal = (target: I3DRenderTarget): void => {\r\n const idx = locals.indexOf(target);\r\n if (idx >= 0) {\r\n locals.splice(idx, 1);\r\n this.pool.release(target);\r\n }\r\n };\r\n\r\n const acquire = (): I3DRenderTarget => {\r\n const { width, height } = this.getScaledSize();\r\n const target = this.pool.acquire(width, height);\r\n locals.push(target);\r\n return target;\r\n };\r\n\r\n effects.forEach((effect) => {\r\n if (effect.type === \"blur\") {\r\n const radius = effect.amount * quality;\r\n if (radius <= 0.0001) return;\r\n const first = acquire();\r\n this.renderPass(this.blurMaterial, current, first, {\r\n uDirection: [1, 0],\r\n uRadius: radius,\r\n });\r\n const second = acquire();\r\n this.renderPass(this.blurMaterial, first, second, {\r\n uDirection: [0, 1],\r\n uRadius: radius,\r\n });\r\n releaseLocal(first);\r\n if (current !== input) {\r\n releaseLocal(current);\r\n }\r\n current = second;\r\n } else if (effect.type === \"pixel\") {\r\n if (effect.size <= 0.5) return;\r\n const output = acquire();\r\n this.renderPass(this.pixelMaterial, current, output, {\r\n uPixelSize: effect.size,\r\n });\r\n if (current !== input) {\r\n releaseLocal(current);\r\n }\r\n current = output;\r\n } else if (effect.type === \"bloom\") {\r\n const intensity = effect.intensity;\r\n if (intensity <= 0.0001) return;\r\n if (effect.threshold >= 0.99) return;\r\n const blurRadius = Math.max(1, 4 * quality);\r\n const extracted = acquire();\r\n this.renderPass(this.bloomExtractMaterial, current, extracted, {\r\n uThreshold: effect.threshold,\r\n });\r\n\r\n const blur1 = acquire();\r\n this.renderPass(this.blurMaterial, extracted, blur1, {\r\n uDirection: [1, 0],\r\n uRadius: blurRadius,\r\n });\r\n const blur2 = acquire();\r\n this.renderPass(this.blurMaterial, blur1, blur2, {\r\n uDirection: [0, 1],\r\n uRadius: blurRadius,\r\n });\r\n\r\n releaseLocal(extracted);\r\n releaseLocal(blur1);\r\n\r\n const combined = acquire();\r\n this.renderAddPass(current, blur2, combined, intensity);\r\n releaseLocal(blur2);\r\n\r\n if (current !== input) {\r\n releaseLocal(current);\r\n }\r\n current = combined;\r\n } else if (\r\n effect.type === \"brightness\" ||\r\n effect.type === \"contrast\" ||\r\n effect.type === \"saturate\" ||\r\n effect.type === \"grayscale\" ||\r\n effect.type === \"sepia\" ||\r\n effect.type === \"invert\" ||\r\n effect.type === \"hue-rotate\"\r\n ) {\r\n const output = acquire();\r\n const mode = this.getColorMode(effect.type);\r\n const amount = effect.type === \"hue-rotate\" ? effect.angle : effect.amount;\r\n this.renderPass(this.colorMaterial, current, output, {\r\n uMode: mode,\r\n uAmount: amount,\r\n });\r\n if (current !== input) {\r\n releaseLocal(current);\r\n }\r\n current = output;\r\n } else if (effect.type === \"custom\") {\r\n const output = acquire();\r\n const material = this.getCustomMaterial(effect.name);\r\n if (material) {\r\n this.renderPass(material, current, output, effect.uniforms);\r\n if (current !== input) {\r\n releaseLocal(current);\r\n }\r\n current = output;\r\n } else {\r\n releaseLocal(output);\r\n }\r\n }\r\n });\r\n\r\n locals.forEach((target) => {\r\n if (target !== current) {\r\n this.pool.release(target);\r\n }\r\n });\r\n\r\n return current;\r\n }\r\n\r\n public acquireTarget(): I3DRenderTarget {\r\n const { width, height } = this.getScaledSize();\r\n return this.pool.acquire(width, height);\r\n }\r\n\r\n public releaseTarget(target: I3DRenderTarget): void {\r\n this.pool.release(target);\r\n }\r\n\r\n public renderToScreen(input: I3DRenderTarget): void {\r\n this.renderPass(this.copyMaterial, input, null, {}, false);\r\n }\r\n\r\n public dispose(): void {\r\n this.pool.dispose();\r\n this.customMaterials.forEach((material) => material.dispose());\r\n this.customMaterials.clear();\r\n }\r\n\r\n private renderPass(\r\n material: I3DMaterial,\r\n input: I3DRenderTarget,\r\n output: I3DRenderTarget | null,\r\n uniforms: Record<string, any> = {},\r\n clear = true,\r\n ): void {\r\n this.runtime.setRenderTarget(this.renderer, output);\r\n\r\n this.setMaterial(this.quad, material);\r\n this.setUniform(material, \"tDiffuse\", input.texture);\r\n const { width, height } = this.getScaledSize();\r\n this.setUniform(material, \"uResolution\", [width, height]);\r\n this.setUniform(material, \"uTexel\", [1 / width, 1 / height]);\r\n Object.entries(uniforms).forEach(([key, value]) => this.setUniform(material, key, value));\r\n\r\n if (clear) {\r\n this.runtime.clear(this.renderer, true, true, true);\r\n }\r\n this.renderer.render(this.scene, this.camera);\r\n }\r\n\r\n private renderAddPass(\r\n base: I3DRenderTarget,\r\n bloom: I3DRenderTarget,\r\n output: I3DRenderTarget,\r\n intensity: number,\r\n ): void {\r\n this.runtime.setRenderTarget(this.renderer, output);\r\n\r\n this.setMaterial(this.quad, this.bloomAddMaterial);\r\n this.setUniform(this.bloomAddMaterial, \"tBase\", base.texture);\r\n this.setUniform(this.bloomAddMaterial, \"tBloom\", bloom.texture);\r\n this.setUniform(this.bloomAddMaterial, \"uIntensity\", intensity);\r\n const { width, height } = this.getScaledSize();\r\n this.setUniform(this.bloomAddMaterial, \"uResolution\", [width, height]);\r\n\r\n this.runtime.clear(this.renderer, true, true, true);\r\n this.renderer.render(this.scene, this.camera);\r\n }\r\n\r\n private setMaterial(object: I3DObject, material: I3DMaterial): void {\r\n const anyObj = object as any;\r\n if (anyObj.material !== material) {\r\n anyObj.material = material as any;\r\n }\r\n }\r\n\r\n private setUniform(material: I3DMaterial, name: string, value: any): void {\r\n const uniforms = (material as any).uniforms;\r\n if (!uniforms) return;\r\n if (!uniforms[name]) {\r\n uniforms[name] = { value };\r\n } else {\r\n uniforms[name].value = value;\r\n }\r\n }\r\n\r\n private createCopyMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: { tDiffuse: { value: null } },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tDiffuse;\r\n void main() {\r\n gl_FragColor = texture2D(tDiffuse, vUv);\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private createPixelMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: {\r\n tDiffuse: { value: null },\r\n uResolution: { value: [this.width, this.height] },\r\n uPixelSize: { value: 1 },\r\n },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tDiffuse;\r\n uniform vec2 uResolution;\r\n uniform float uPixelSize;\r\n void main() {\r\n vec2 pixel = uPixelSize / uResolution;\r\n vec2 coord = floor(vUv / pixel) * pixel + pixel * 0.5;\r\n gl_FragColor = texture2D(tDiffuse, coord);\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private createBlurMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: {\r\n tDiffuse: { value: null },\r\n uTexel: { value: [1 / this.width, 1 / this.height] },\r\n uDirection: { value: [1, 0] },\r\n uRadius: { value: 2 },\r\n },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tDiffuse;\r\n uniform vec2 uTexel;\r\n uniform vec2 uDirection;\r\n uniform float uRadius;\r\n void main() {\r\n vec2 off1 = uDirection * uTexel * uRadius;\r\n vec2 off2 = uDirection * uTexel * uRadius * 2.0;\r\n vec2 off3 = uDirection * uTexel * uRadius * 3.0;\r\n vec2 off4 = uDirection * uTexel * uRadius * 4.0;\r\n vec4 color = texture2D(tDiffuse, vUv) * 0.227027;\r\n color += texture2D(tDiffuse, vUv + off1) * 0.1945946;\r\n color += texture2D(tDiffuse, vUv - off1) * 0.1945946;\r\n color += texture2D(tDiffuse, vUv + off2) * 0.1216216;\r\n color += texture2D(tDiffuse, vUv - off2) * 0.1216216;\r\n color += texture2D(tDiffuse, vUv + off3) * 0.054054;\r\n color += texture2D(tDiffuse, vUv - off3) * 0.054054;\r\n color += texture2D(tDiffuse, vUv + off4) * 0.016216;\r\n color += texture2D(tDiffuse, vUv - off4) * 0.016216;\r\n gl_FragColor = color;\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private createBloomExtractMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: {\r\n tDiffuse: { value: null },\r\n uThreshold: { value: 0.8 },\r\n },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tDiffuse;\r\n uniform float uThreshold;\r\n void main() {\r\n vec4 color = texture2D(tDiffuse, vUv);\r\n float brightness = max(max(color.r, color.g), color.b);\r\n gl_FragColor = brightness > uThreshold ? color : vec4(0.0);\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private createBloomAddMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: {\r\n tBase: { value: null },\r\n tBloom: { value: null },\r\n uIntensity: { value: 1 },\r\n uResolution: { value: [this.width, this.height] },\r\n },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tBase;\r\n uniform sampler2D tBloom;\r\n uniform float uIntensity;\r\n void main() {\r\n vec4 base = texture2D(tBase, vUv);\r\n vec4 bloom = texture2D(tBloom, vUv);\r\n gl_FragColor = vec4(base.rgb + bloom.rgb * uIntensity, base.a);\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private createColorMaterial(): I3DMaterial {\r\n return this.createShaderMaterial({\r\n uniforms: {\r\n tDiffuse: { value: null },\r\n uMode: { value: 0 },\r\n uAmount: { value: 1 },\r\n },\r\n vertexShader: this.getVertexShader(),\r\n fragmentShader: `\r\n varying vec2 vUv;\r\n uniform sampler2D tDiffuse;\r\n uniform int uMode;\r\n uniform float uAmount;\r\n\r\n vec3 applyHueRotate(vec3 color, float angle) {\r\n float cosA = cos(angle);\r\n float sinA = sin(angle);\r\n mat3 m = mat3(\r\n 0.213 + cosA * 0.787 - sinA * 0.213,\r\n 0.715 - cosA * 0.715 - sinA * 0.715,\r\n 0.072 - cosA * 0.072 + sinA * 0.928,\r\n 0.213 - cosA * 0.213 + sinA * 0.143,\r\n 0.715 + cosA * 0.285 + sinA * 0.140,\r\n 0.072 - cosA * 0.072 - sinA * 0.283,\r\n 0.213 - cosA * 0.213 - sinA * 0.787,\r\n 0.715 - cosA * 0.715 + sinA * 0.715,\r\n 0.072 + cosA * 0.928 + sinA * 0.072\r\n );\r\n return clamp(m * color, 0.0, 1.0);\r\n }\r\n\r\n void main() {\r\n vec4 color = texture2D(tDiffuse, vUv);\r\n float luma = dot(color.rgb, vec3(0.299, 0.587, 0.114));\r\n\r\n if (uMode == 1) {\r\n color.rgb *= uAmount;\r\n } else if (uMode == 2) {\r\n color.rgb = (color.rgb - 0.5) * uAmount + 0.5;\r\n } else if (uMode == 3) {\r\n color.rgb = mix(vec3(luma), color.rgb, uAmount);\r\n } else if (uMode == 4) {\r\n color.rgb = mix(color.rgb, vec3(luma), uAmount);\r\n } else if (uMode == 5) {\r\n vec3 sepia = vec3(\r\n dot(color.rgb, vec3(0.393, 0.769, 0.189)),\r\n dot(color.rgb, vec3(0.349, 0.686, 0.168)),\r\n dot(color.rgb, vec3(0.272, 0.534, 0.131))\r\n );\r\n color.rgb = mix(color.rgb, sepia, uAmount);\r\n } else if (uMode == 6) {\r\n color.rgb = mix(color.rgb, vec3(1.0) - color.rgb, uAmount);\r\n } else if (uMode == 7) {\r\n color.rgb = applyHueRotate(color.rgb, uAmount);\r\n }\r\n\r\n gl_FragColor = color;\r\n }\r\n `,\r\n transparent: true,\r\n depthTest: false,\r\n depthWrite: false,\r\n });\r\n }\r\n\r\n private getColorMode(type: string): number {\r\n switch (type) {\r\n case \"brightness\":\r\n return 1;\r\n case \"contrast\":\r\n return 2;\r\n case \"saturate\":\r\n return 3;\r\n case \"grayscale\":\r\n return 4;\r\n case \"sepia\":\r\n return 5;\r\n case \"invert\":\r\n return 6;\r\n case \"hue-rotate\":\r\n return 7;\r\n default:\r\n return 0;\r\n }\r\n }\r\n\r\n private createShaderMaterial(params: any): I3DMaterial {\r\n return this.runtime.createShaderMaterial(params);\r\n }\r\n\r\n private getCustomMaterial(name: string): I3DMaterial | null {\n const normalized = name.trim().toLowerCase();\r\n if (!normalized) return null;\r\n if (this.customMaterials.has(normalized)) {\r\n return this.customMaterials.get(normalized)!;\r\n }\r\n const def = this.customFilterRegistry.get(normalized) as\n | String3DCustomFilterDefinition\n | undefined;\n if (!def) return null;\n const impl = this.resolveCustomFilterImplementation(def);\n if (!impl) return null;\n const shaders = this.resolveCustomFilterShaders(impl);\n if (!shaders) return null;\n\r\n const uniforms: Record<string, any> = { tDiffuse: { value: null } };\r\n const { width, height } = this.getScaledSize();\r\n uniforms.uResolution = { value: [width, height] };\r\n uniforms.uTexel = { value: [1 / width, 1 / height] };\r\n Object.entries(def.uniforms || {}).forEach(([key, value]) => {\r\n uniforms[key] = { value };\r\n });\r\n\r\n const material = this.createShaderMaterial({\n uniforms,\n vertexShader: shaders.vertexShader,\n fragmentShader: shaders.fragmentShader,\n transparent: true,\n depthTest: false,\n depthWrite: false,\n });\r\n\r\n this.customMaterials.set(normalized, material);\n return material;\n }\n\n private resolveCustomFilterImplementation(\n definition: String3DCustomFilterDefinition,\n ): String3DCustomFilterImplementation | undefined {\n const byBackend =\n definition.implementations?.[this.backend] || definition.implementations?.custom;\n if (byBackend) return byBackend;\n if (definition.fragmentShader && this.backend === \"webgl\") {\n return {\n kind: \"shader\",\n language: \"glsl\",\n stage: \"fragment\",\n code: definition.fragmentShader,\n };\n }\n return undefined;\n }\n\n private resolveCustomFilterShaders(\n implementation: String3DCustomFilterImplementation,\n ): { vertexShader: string; fragmentShader: string } | null {\n if (implementation.kind !== \"shader\") return null;\n if (implementation.language !== \"glsl\" && implementation.language !== \"custom\") return null;\n if (implementation.stage && implementation.stage !== \"fragment\") return null;\n return {\n vertexShader: implementation.vertexCode || this.getVertexShader(),\n fragmentShader: implementation.code,\n };\n }\n\r\n private getScaledSize(): { width: number; height: number } {\r\n const width = Math.max(1, Math.round(this.width * this.scale));\r\n const height = Math.max(1, Math.round(this.height * this.scale));\r\n return { width, height };\r\n }\r\n\r\n private getVertexShader(): string {\r\n return `\r\n varying vec2 vUv;\r\n void main() {\r\n vUv = uv;\r\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\r\n }\r\n `;\r\n }\r\n}\r\n","import {\r\n I3DBackend,\r\n I3DCustomFilterRegistryRuntime,\r\n I3DCustomMaterialRegistryRuntime,\r\n I3DEngineCapabilities,\r\n I3DPostProcessRuntime,\r\n I3DEngine,\r\n I3DVector3,\r\n I3DVector2,\r\n I3DQuaternion,\r\n I3DEuler,\r\n I3DMatrix4,\r\n I3DBox3,\r\n I3DScene,\r\n I3DRenderer,\r\n I3DRendererConfigContext,\r\n I3DPerspectiveCamera,\r\n I3DOrthographicCamera,\r\n I3DObject,\r\n I3DMesh,\r\n I3DGeometry,\r\n I3DMaterial,\r\n I3DRenderTarget,\r\n I3DLight,\r\n I3DTextureLoader,\r\n I3DModelLoader,\r\n I3DLayerIsolationState,\r\n I3DCamera,\r\n I3DModelLoaderOptions,\r\n I3DMaterialVisualProps,\r\n ParticleSystemConfig,\r\n I3DParticleSystem,\r\n} from \"../core/abstractions/I3DEngine\";\r\nimport { I3DEngineProvider } from \"../core/abstractions/I3DEngineProvider\";\r\nimport { IMaterialFactory } from \"../core/materials\";\r\nimport { ThreeJSMaterialFactory } from \"./ThreeJSMaterialFactory\";\r\nimport { ThreePostProcessPipeline } from \"./ThreePostProcessPipeline\";\r\nimport { String3DCustomFilterRegistry } from \"../core/filters/String3DCustomFilter\";\r\nimport { FontConverter } from \"../core/text\";\r\nimport { String3DCustomMaterialRegistry } from \"../core/materials\";\r\n\r\nexport class ThreeJSEngine implements I3DEngine {\r\n private THREE: any;\r\n private loaders: Record<string, any>;\r\n private materialFactory: ThreeJSMaterialFactory | null = null;\r\n private particleModelCache: Map<string, any> = new Map();\r\n private particleModelPromiseCache: Map<string, Promise<any>> = new Map();\r\n private fontCache: Map<string, any> = new Map();\r\n private fontPromiseCache: Map<string, Promise<any>> = new Map();\r\n private fontMetricsCache: Map<string, { ascent: number; descent: number }> = new Map();\r\n\r\n constructor(THREE: any, loaders: Record<string, any> = {}) {\r\n this.THREE = THREE;\r\n this.loaders = loaders;\r\n this.materialFactory = new ThreeJSMaterialFactory(THREE);\r\n }\r\n\r\n getMaterialFactory(): IMaterialFactory | null {\r\n return this.materialFactory;\r\n }\r\n\r\n createVector3(x = 0, y = 0, z = 0): I3DVector3 {\r\n return new this.THREE.Vector3(x, y, z);\r\n }\r\n\r\n createVector2(x = 0, y = 0): I3DVector2 {\r\n return new this.THREE.Vector2(x, y);\r\n }\r\n\r\n createQuaternion(x = 0, y = 0, z = 0, w = 1): I3DQuaternion {\r\n return new this.THREE.Quaternion(x, y, z, w);\r\n }\r\n\r\n createEuler(x = 0, y = 0, z = 0, order = \"XYZ\"): I3DEuler {\r\n return new this.THREE.Euler(x, y, z, order);\r\n }\r\n\r\n createMatrix4(): I3DMatrix4 {\r\n return new this.THREE.Matrix4();\r\n }\r\n\r\n createBox3(min?: I3DVector3, max?: I3DVector3): I3DBox3 {\r\n return new this.THREE.Box3(min, max);\r\n }\r\n\r\n createScene(): I3DScene {\r\n return new this.THREE.Scene();\r\n }\r\n\r\n createRenderer(options?: {\n antialias?: boolean;\n alpha?: boolean;\n logarithmicDepthBuffer?: boolean;\n }): I3DRenderer {\n const renderer = new this.THREE.WebGLRenderer(options);\n if (\"outputColorSpace\" in renderer && this.THREE.SRGBColorSpace) {\n (renderer as any).outputColorSpace = this.THREE.SRGBColorSpace;\n } else if (\"outputEncoding\" in renderer && this.THREE.sRGBEncoding) {\n (renderer as any).outputEncoding = this.THREE.sRGBEncoding;\n }\n return renderer;\n }\n\r\n getRecommendedPixelRatio(): number {\r\n if (typeof window !== \"undefined\" && Number.isFinite(window.devicePixelRatio)) {\r\n return Math.max(0.1, window.devicePixelRatio);\r\n }\r\n return 1;\r\n }\r\n\r\n configureRenderer(renderer: I3DRenderer, _context: I3DRendererConfigContext): void {\r\n const anyRenderer = renderer as any;\r\n if (typeof anyRenderer.setClearColor === \"function\") {\r\n anyRenderer.setClearColor(0x000000, 0);\r\n }\r\n\r\n if (renderer.shadowMap) {\r\n renderer.shadowMap.enabled = true;\r\n }\r\n }\r\n\r\n createPerspectiveCamera(fov = 45, aspect = 1, near = 0.1, far = 2000): I3DPerspectiveCamera {\r\n return new this.THREE.PerspectiveCamera(fov, aspect, near, far);\r\n }\r\n\r\n createOrthographicCamera(\r\n left: number,\r\n right: number,\r\n top: number,\r\n bottom: number,\r\n near = 0.1,\r\n far = 10000,\r\n ): I3DOrthographicCamera {\r\n return new this.THREE.OrthographicCamera(left, right, top, bottom, near, far);\r\n }\r\n\r\n createGroup(): I3DObject {\r\n return new this.THREE.Group();\r\n }\r\n\r\n createMesh(geometry: I3DGeometry, material: I3DMaterial): I3DMesh {\r\n return new this.THREE.Mesh(geometry, material);\r\n }\r\n\r\n createBoxGeometry(width: number, height: number, depth: number): I3DGeometry {\r\n return new this.THREE.BoxGeometry(width, height, depth);\r\n }\r\n\r\n createSphereGeometry(radius: number, widthSegments = 32, heightSegments = 32): I3DGeometry {\r\n return new this.THREE.SphereGeometry(radius, widthSegments, heightSegments);\r\n }\r\n\r\n createPlaneGeometry(width: number, height: number): I3DGeometry {\r\n return new this.THREE.PlaneGeometry(width, height);\r\n }\r\n\r\n createCylinderGeometry(\r\n radiusTop: number,\r\n radiusBottom: number,\r\n height: number,\r\n segments = 32,\r\n ): I3DGeometry {\r\n return new this.THREE.CylinderGeometry(radiusTop, radiusBottom, height, segments);\r\n }\r\n\r\n createMeshBasicMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.MeshBasicMaterial(params);\r\n }\r\n\r\n createMeshStandardMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.MeshStandardMaterial(params);\r\n }\r\n\r\n createShaderMaterial(params?: any): I3DMaterial {\r\n return new this.THREE.ShaderMaterial(params);\r\n }\r\n createPointLight(color?: string | number, intensity = 1, distance = 0, decay = 2): I3DLight {\r\n return new this.THREE.PointLight(color, intensity, distance, decay);\r\n }\r\n\r\n createSpotLight(\r\n color?: string | number,\r\n intensity = 1,\r\n distance = 0,\r\n angle = Math.PI / 3,\r\n penumbra = 0,\r\n decay = 1,\r\n ): I3DLight {\r\n return new this.THREE.SpotLight(color, intensity, distance, angle, penumbra, decay);\r\n }\r\n\r\n createHemisphereLight(\r\n skyColor?: string | number,\r\n groundColor?: string | number,\r\n intensity = 1,\r\n ): I3DLight {\r\n return new this.THREE.HemisphereLight(skyColor, groundColor, intensity);\r\n }\r\n\r\n createAmbientLight(color?: string | number, intensity = 1): I3DLight {\r\n return new this.THREE.AmbientLight(color, intensity);\r\n }\r\n\r\n createDirectionalLight(color?: string | number, intensity = 1): I3DLight {\r\n return new this.THREE.DirectionalLight(color, intensity);\r\n }\r\n\r\n createTextureLoader(): I3DTextureLoader {\r\n return new this.THREE.TextureLoader();\r\n }\r\n\r\n createModelLoader(type: string): I3DModelLoader {\r\n const LoaderClass = this.loaders[type];\r\n if (!LoaderClass) {\r\n throw new Error(`[ThreeJSEngine] Model loader \"${type}\" not registered`);\r\n }\r\n return new LoaderClass();\r\n }\r\n\r\n configureModelLoader(loader: I3DModelLoader, options: I3DModelLoaderOptions): void {\r\n const manager = (loader as any)?.manager;\r\n if (!manager || typeof manager.setURLModifier !== \"function\") {\r\n return;\r\n }\r\n\r\n const baseRaw = (options.textureBaseUrl || \"\").trim();\r\n const base = baseRaw ? baseRaw.replace(/\\/?$/, \"/\") : \"\";\r\n const textureMap = options.textureMap || null;\r\n\r\n manager.setURLModifier((url: string) => {\r\n const mapped =\r\n textureMap && Object.prototype.hasOwnProperty.call(textureMap, url)\r\n ? textureMap[url]\r\n : url;\r\n const resolved = typeof mapped === \"string\" && mapped ? mapped : url;\r\n if (!base) return resolved;\r\n if (/^(blob:|data:|https?:|file:|\\/)/i.test(resolved)) return resolved;\r\n return base + resolved.replace(/^\\.?\\//, \"\");\r\n });\r\n }\r\n\r\n resolveLoadedModelRoot(loadedModel: any): I3DObject | null {\r\n if (!loadedModel || typeof loadedModel !== \"object\") return null;\r\n return (loadedModel?.scene || loadedModel?.object || loadedModel) as I3DObject;\r\n }\r\n\r\n createRenderTarget(width: number, height: number, options: any = {}): I3DRenderTarget {\r\n const defaults = {\r\n minFilter: this.THREE.LinearFilter,\r\n magFilter: this.THREE.LinearFilter,\r\n format: this.THREE.RGBAFormat,\r\n depthBuffer: true,\r\n stencilBuffer: false,\r\n };\r\n return new this.THREE.WebGLRenderTarget(width, height, { ...defaults, ...options });\r\n }\r\n\r\n loadFont(url: string): Promise<any> {\r\n const normalized = url.trim();\r\n if (!normalized || normalized === \"none\") {\r\n return Promise.resolve(null);\r\n }\r\n if (this.fontCache.has(normalized)) {\r\n return Promise.resolve(this.fontCache.get(normalized));\r\n }\r\n const cachedPromise = this.fontPromiseCache.get(normalized);\r\n if (cachedPromise) return cachedPromise;\r\n\r\n const isFontFile = FontConverter.isFontFile(normalized);\r\n\r\n let promise: Promise<any>;\r\n\r\n if (isFontFile) {\r\n promise = this.loadFontWithConverter(normalized);\r\n } else {\r\n promise = this.loadFontWithLoader(normalized);\r\n }\r\n\r\n this.fontPromiseCache.set(normalized, promise);\r\n return promise;\r\n }\r\n\r\n private async loadFontWithConverter(url: string): Promise<any> {\r\n try {\r\n const fontData = await FontConverter.load(url);\r\n const font = this.createFontFromData(fontData);\r\n this.fontCache.set(url, font);\r\n return font;\r\n } catch (error) {\r\n return null;\r\n }\r\n }\r\n\r\n private loadFontWithLoader(url: string): Promise<any> {\r\n const LoaderClass = this.loaders.font || this.loaders.FontLoader;\r\n if (!LoaderClass) {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const loader = new LoaderClass();\r\n return new Promise<any>((resolve) => {\r\n loader.load(\r\n url,\r\n (font: any) => {\r\n this.fontCache.set(url, font);\r\n resolve(font);\r\n },\r\n undefined,\r\n () => {\r\n resolve(null);\r\n },\r\n );\r\n });\r\n }\r\n\r\n private createFontFromData(fontData: any): any {\r\n const LoaderClass = this.loaders.font || this.loaders.FontLoader;\r\n if (LoaderClass && LoaderClass.utils && LoaderClass.utils.convert) {\r\n const loader = new LoaderClass();\r\n if (loader.parse) {\r\n return loader.parse(fontData);\r\n }\r\n }\r\n\r\n const font = {\r\n data: fontData,\r\n isFont: true,\r\n generateShapes: (text: string, size: number) => {\r\n return this.generateShapesFromFontData(fontData, text, size, false);\r\n },\r\n generateNormalizedShapes: (text: string, size: number) => {\r\n return this.generateShapesFromFontData(fontData, text, size, true);\r\n },\r\n };\r\n return font;\r\n }\r\n\r\n private generateShapesFromFontData(\r\n fontData: any,\r\n text: string,\r\n size: number,\r\n normalizePosition: boolean = false,\r\n ): any[] {\r\n const shapes: any[] = [];\r\n const scale = size / fontData.resolution;\r\n\r\n const char = text[0];\r\n if (!char) return shapes;\r\n\r\n const glyph = fontData.glyphs[char];\r\n if (!glyph || !glyph.o) return shapes;\r\n\r\n let xOffset = 0;\r\n if (normalizePosition) {\r\n const xMin = this.getOutlineXMin(glyph.o);\r\n xOffset = -xMin * scale;\r\n }\r\n\r\n const charShapes = this.parseOutlineToShapes(glyph.o, scale, xOffset, fontData?.outlineFormat);\r\n shapes.push(...charShapes);\r\n\r\n return shapes;\r\n }\r\n\r\n private getOutlineXMin(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let minX = Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 3]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n minX = Math.min(minX, parseFloat(commands[i + 1]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 3]) || 0);\r\n minX = Math.min(minX, parseFloat(commands[i + 5]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return minX === Infinity ? 0 : minX;\r\n }\r\n\r\n private getOutlineXMax(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let maxX = -Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 3]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n maxX = Math.max(maxX, parseFloat(commands[i + 1]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 3]) || 0);\r\n maxX = Math.max(maxX, parseFloat(commands[i + 5]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return maxX === -Infinity ? 0 : maxX;\r\n }\r\n\r\n private getOutlineYMin(outline: string): number {\r\n const commands = outline.split(\" \");\r\n let minY = Infinity;\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n case \"l\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n i += 3;\r\n break;\r\n case \"q\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 4]) || 0);\r\n i += 5;\r\n break;\r\n case \"b\":\r\n minY = Math.min(minY, parseFloat(commands[i + 2]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 4]) || 0);\r\n minY = Math.min(minY, parseFloat(commands[i + 6]) || 0);\r\n i += 7;\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n return minY === Infinity ? 0 : minY;\r\n }\r\n\r\n private pointInPolygon(\r\n px: number,\r\n py: number,\r\n polygon: Array<{ x: number; y: number }>,\r\n ): boolean {\r\n let inside = false;\r\n for (let i = 0, j = polygon.length - 1; i < polygon.length; j = i++) {\r\n const xi = polygon[i].x;\r\n const yi = polygon[i].y;\r\n const xj = polygon[j].x;\r\n const yj = polygon[j].y;\r\n\r\n if (yi > py !== yj > py && px < ((xj - xi) * (py - yi)) / (yj - yi) + xi) {\r\n inside = !inside;\r\n }\r\n }\r\n return inside;\r\n }\r\n\r\n private samplePathPoints(path: any, numSamples: number = 80): Array<{ x: number; y: number }> {\r\n if (!path?.getPoints) return [];\r\n return path.getPoints(numSamples).map((p: any) => ({ x: p.x, y: p.y }));\r\n }\r\n\r\n private getBoundingBox(points: Array<{ x: number; y: number }>): {\r\n minX: number;\r\n maxX: number;\r\n minY: number;\r\n maxY: number;\r\n area: number;\r\n } {\r\n if (points.length === 0) {\r\n return { minX: 0, maxX: 0, minY: 0, maxY: 0, area: 0 };\r\n }\r\n let minX = Infinity;\r\n let maxX = -Infinity;\r\n let minY = Infinity;\r\n let maxY = -Infinity;\r\n for (const p of points) {\r\n if (p.x < minX) minX = p.x;\r\n if (p.x > maxX) maxX = p.x;\r\n if (p.y < minY) minY = p.y;\r\n if (p.y > maxY) maxY = p.y;\r\n }\r\n return { minX, maxX, minY, maxY, area: (maxX - minX) * (maxY - minY) };\r\n }\r\n\r\n private getInteriorPoint(points: Array<{ x: number; y: number }>): { x: number; y: number } {\r\n if (points.length < 3) return points[0] || { x: 0, y: 0 };\r\n const contour = points.map((p) => new this.THREE.Vector2(p.x, p.y));\r\n const triangles = this.THREE.ShapeUtils.triangulateShape(contour, []);\r\n for (const tri of triangles) {\r\n const a = contour[tri[0]];\r\n const b = contour[tri[1]];\r\n const c = contour[tri[2]];\r\n const cx = (a.x + b.x + c.x) / 3;\r\n const cy = (a.y + b.y + c.y) / 3;\r\n if (this.pointInPolygon(cx, cy, points)) {\r\n return { x: cx, y: cy };\r\n }\r\n }\r\n return points[0];\r\n }\r\n\r\n private parseOutlineToShapes(\r\n outline: string,\r\n scale: number,\r\n offsetX: number = 0,\r\n outlineFormat?: string,\r\n ): any[] {\r\n if (!outline) return [];\r\n\r\n const shapePath = new this.THREE.ShapePath();\r\n const commands = outline.split(\" \");\r\n let i = 0;\r\n\r\n while (i < commands.length) {\r\n const cmd = commands[i];\r\n switch (cmd) {\r\n case \"m\":\r\n {\r\n const mx = parseFloat(commands[i + 1]) * scale + offsetX;\r\n const my = -parseFloat(commands[i + 2]) * scale;\r\n shapePath.moveTo(mx, my);\r\n i += 3;\r\n }\r\n break;\r\n case \"l\":\r\n {\r\n const lx = parseFloat(commands[i + 1]) * scale + offsetX;\r\n const ly = -parseFloat(commands[i + 2]) * scale;\r\n shapePath.lineTo(lx, ly);\r\n i += 3;\r\n }\r\n break;\r\n case \"q\":\r\n {\r\n const qx = parseFloat(commands[i + 3]) * scale + offsetX;\r\n const qy = -parseFloat(commands[i + 4]) * scale;\r\n shapePath.quadraticCurveTo(\r\n parseFloat(commands[i + 1]) * scale + offsetX,\r\n -parseFloat(commands[i + 2]) * scale,\r\n qx,\r\n qy,\r\n );\r\n i += 5;\r\n }\r\n break;\r\n case \"b\":\r\n {\r\n const bx = parseFloat(commands[i + 5]) * scale + offsetX;\r\n const by = -parseFloat(commands[i + 6]) * scale;\r\n shapePath.bezierCurveTo(\r\n parseFloat(commands[i + 1]) * scale + offsetX,\r\n -parseFloat(commands[i + 2]) * scale,\r\n parseFloat(commands[i + 3]) * scale + offsetX,\r\n -parseFloat(commands[i + 4]) * scale,\r\n bx,\r\n by,\r\n );\r\n i += 7;\r\n }\r\n break;\r\n case \"z\":\r\n {\r\n if (typeof shapePath.closePath === \"function\") {\r\n shapePath.closePath();\r\n } else if (\r\n shapePath.currentPath &&\r\n typeof shapePath.currentPath.closePath === \"function\"\r\n ) {\r\n shapePath.currentPath.closePath();\r\n }\r\n i += 1;\r\n }\r\n break;\r\n default:\r\n i++;\r\n break;\r\n }\r\n }\r\n\r\n const subPaths = shapePath.subPaths;\r\n if (!subPaths || subPaths.length === 0) return [];\r\n\r\n const paths = subPaths.map((sp: any) => {\r\n const points = sp.getPoints();\r\n const area = this.THREE.ShapeUtils.area(points);\r\n const bbox = this.getBoundingBox(points.map((p: any) => ({ x: p.x, y: p.y })));\r\n return {\r\n path: sp,\r\n points,\r\n area: Math.abs(area),\r\n signedArea: area,\r\n bbox,\r\n };\r\n });\r\n\r\n paths.sort((a: any, b: any) => b.area - a.area);\r\n\r\n const finalShapes: any[] = [];\r\n const used = new Set<number>();\r\n\r\n for (let i = 0; i < paths.length; i++) {\r\n if (used.has(i)) continue;\r\n\r\n const outerPath = paths[i];\r\n const shape = new this.THREE.Shape(outerPath.points);\r\n used.add(i);\r\n\r\n for (let j = 0; j < paths.length; j++) {\r\n if (used.has(j) || i === j) continue;\r\n\r\n const innerPath = paths[j];\r\n\r\n if (\r\n innerPath.bbox.minX < outerPath.bbox.minX ||\r\n innerPath.bbox.maxX > outerPath.bbox.maxX ||\r\n innerPath.bbox.minY < outerPath.bbox.minY ||\r\n innerPath.bbox.maxY > outerPath.bbox.maxY\r\n ) {\r\n continue;\r\n }\r\n\r\n let allPointsInside = true;\r\n const testPoints = [\r\n innerPath.points[0],\r\n innerPath.points[Math.floor(innerPath.points.length / 2)],\r\n ];\r\n\r\n for (const testPoint of testPoints) {\r\n if (\r\n !testPoint ||\r\n !this.pointInPolygon(\r\n testPoint.x,\r\n testPoint.y,\r\n outerPath.points.map((p: any) => ({ x: p.x, y: p.y })),\r\n )\r\n ) {\r\n allPointsInside = false;\r\n break;\r\n }\r\n }\r\n\r\n if (allPointsInside) {\r\n shape.holes.push(new this.THREE.Path(innerPath.points));\r\n used.add(j);\r\n }\r\n }\r\n\r\n finalShapes.push(shape);\r\n }\r\n\r\n return finalShapes.length > 0 ? finalShapes : shapePath.toShapes(true);\r\n }\r\n\r\n private reversePath(path: any): any {\n const newPath = new this.THREE.Path();\n if (!path.curves || path.curves.length === 0) return newPath;\n\n const lastCurve = path.curves[path.curves.length - 1];\n const endPoint = this.getCurveEndPoint(lastCurve);\n if (endPoint) {\n newPath.moveTo(endPoint.x, endPoint.y);\n }\n\r\n for (let i = path.curves.length - 1; i >= 0; i--) {\r\n const curve = path.curves[i];\r\n if (curve.isLineCurve || curve.type === \"LineCurve\" || curve.type === \"LineCurve3\") {\r\n newPath.lineTo(curve.v1.x, curve.v1.y);\r\n } else if (\r\n curve.isQuadraticBezierCurve ||\r\n curve.type === \"QuadraticBezierCurve\" ||\r\n curve.type === \"QuadraticBezierCurve3\"\r\n ) {\r\n newPath.quadraticCurveTo(curve.v1.x, curve.v1.y, curve.v0.x, curve.v0.y);\r\n } else if (\r\n curve.isCubicBezierCurve ||\r\n curve.type === \"CubicBezierCurve\" ||\r\n curve.type === \"CubicBezierCurve3\"\r\n ) {\r\n newPath.bezierCurveTo(\r\n curve.v2.x,\r\n curve.v2.y,\r\n curve.v1.x,\r\n curve.v1.y,\r\n curve.v0.x,\r\n curve.v0.y,\r\n );\r\n }\r\n }\r\n\n return newPath;\n }\n\n private getCurveEndPoint(curve: any): any {\n if (!curve) return null;\n return curve.v3 || curve.v2 || curve.v1 || (curve.getPoint ? curve.getPoint(1) : null);\n }\n\r\n createTextGeometry(text: string, font: any, options: any): I3DGeometry | null {\r\n if (!text || !font) return null;\r\n\r\n const size = Math.max(0.001, options.size || 16);\r\n const height = Math.max(0, options.height || 0);\r\n const lineHeight = Math.max(0.001, options.lineHeight || size * 1.2);\r\n const letterSpacing = Number.isFinite(options.letterSpacing) ? options.letterSpacing : 0;\r\n const align = options.align || \"left\";\r\n const bevelEnabled = !!options.bevelEnabled;\r\n const bevelThickness = Math.max(0, options.bevelThickness || 0);\r\n const bevelSize = Math.max(0, options.bevelSize || 0);\r\n const bevelOffset = options.bevelOffset || 0;\r\n const bevelSegments = Math.max(0, options.bevelSegments || 0);\r\n const curveSegments = Math.max(1, Math.round(options.curveSegments || 8));\r\n\r\n const lines = String(text).split(/\\r?\\n/);\r\n const shapes: any[] = [];\r\n\r\n const fontData = font?.data;\r\n const resolution = fontData?.resolution || 1000;\r\n if (options.layout && options.layout.length > 0) {\r\n const fontAscender = fontData?.ascender || resolution * 0.8;\r\n const fontDescender = fontData?.descender || -resolution * 0.2;\r\n const fontEmHeight = fontAscender - fontDescender;\r\n const baselineRatio = fontAscender / fontEmHeight;\r\n\r\n const elementWidth = options.elementWidth || 0;\r\n const elementHeight = options.elementHeight || 0;\r\n const centerOffsetX = 0;\r\n const centerOffsetY = 0;\r\n\r\n options.layout.forEach((item: any) => {\r\n const charShapes = font.generateShapes(item.char, size);\r\n\r\n const offsetX = item.x + centerOffsetX;\r\n\r\n const charHeight = item.height || size;\r\n const baselineFromTop = charHeight * baselineRatio;\r\n const offsetY = -(item.y + centerOffsetY) - baselineFromTop;\r\n\r\n charShapes.forEach((shape: any) => {\r\n let finalShape = this.translateShape(shape, offsetX, offsetY);\r\n if (item.scale && item.scale !== 1) {\r\n finalShape = this.scaleShape(finalShape, item.scale);\r\n }\r\n shapes.push(finalShape);\r\n });\r\n });\r\n } else {\r\n lines.forEach((line, index) => {\r\n const { shapes: lineShapes, width } = this.buildLineShapes(line, font, size, letterSpacing);\r\n let offsetX = 0;\r\n if (align === \"center\") {\r\n offsetX = -width * 0.5;\r\n } else if (align === \"right\") {\r\n offsetX = -width;\r\n }\r\n const offsetY = -index * lineHeight;\r\n lineShapes.forEach((shape) => {\r\n shapes.push(this.translateShape(shape, offsetX, offsetY));\r\n });\r\n });\r\n }\r\n\r\n if (!shapes.length) {\r\n return null;\r\n }\r\n\r\n const geometry = new this.THREE.ExtrudeGeometry(shapes, {\r\n depth: height,\r\n curveSegments,\r\n bevelEnabled,\r\n bevelThickness,\r\n bevelSize,\r\n bevelOffset,\r\n bevelSegments,\r\n });\r\n geometry.computeBoundingBox();\r\n return geometry;\r\n }\r\n\r\n createSVGGeometry(\r\n paths: import(\"../core/abstractions/I3DEngine\").SVGPathData[],\r\n viewBox: import(\"../core/abstractions/I3DEngine\").SVGViewBox | null,\r\n options: import(\"../core/abstractions/I3DEngine\").SVGGeometryOptions,\r\n ): import(\"../core/abstractions/I3DEngine\").I3DGeometry | null {\r\n if (!paths || paths.length === 0) return null;\r\n\r\n const depth = Math.max(0, options.depth || 0);\r\n const curveSegments = Math.max(1, Math.round(options.curveSegments || 12));\r\n const bevelEnabled = !!options.bevelEnabled;\r\n const bevelThickness = Math.max(0, options.bevelThickness || 0);\r\n const bevelSize = Math.max(0, options.bevelSize || 0);\r\n const bevelOffset = options.bevelOffset || 0;\r\n const bevelSegments = Math.max(0, options.bevelSegments || 0);\r\n\r\n // Collect ALL raw subpaths from every path element\r\n const allSubpaths: Array<{ path: any; points: any[]; area: number; signedArea: number; bbox: any }> = [];\n\r\n for (const pathData of paths) {\r\n const subpaths = this.parseSVGPathToSubpaths(pathData.d, pathData.transform);\r\n allSubpaths.push(...subpaths);\r\n }\r\n\r\n if (allSubpaths.length === 0) return null;\r\n\r\n // Center points by viewBox BEFORE building shapes\r\n // (Y was already negated in applyTransform, so offset is -cx, +cy)\r\n if (viewBox) {\r\n const cx = viewBox.x + viewBox.width * 0.5;\r\n const cy = viewBox.y + viewBox.height * 0.5;\r\n for (const sp of allSubpaths) {\r\n for (const pt of sp.points) {\r\n pt.x -= cx;\r\n pt.y += cy;\r\n }\r\n sp.bbox = this.getBoundingBox(sp.points.map((p: any) => ({ x: p.x, y: p.y })));\r\n }\r\n }\r\n\r\n // Global hole detection across all subpaths\r\n const allShapes = this.buildShapesWithHoles(allSubpaths);\r\n\r\n if (allShapes.length === 0) return null;\r\n\r\n const geometry = new this.THREE.ExtrudeGeometry(allShapes, {\r\n depth,\r\n curveSegments,\r\n bevelEnabled,\r\n bevelThickness,\r\n bevelSize,\r\n bevelOffset,\r\n bevelSegments,\r\n });\r\n // Center geometry so rotation pivots around geometric center, not a face.\r\n // ExtrudeGeometry places front face at z=0 and back face at z=depth,\r\n // so without centering the object rotates around its front face.\r\n geometry.center();\r\n geometry.computeBoundingBox();\r\n return geometry;\r\n }\r\n\r\n private buildShapesWithHoles(\n subpaths: Array<{ path: any; points: any[]; area: number; signedArea: number; bbox: any }>,\n ): any[] {\n if (subpaths.length === 0) return [];\r\n\r\n // Sort largest → smallest\r\n subpaths.sort((a, b) => b.area - a.area);\r\n\r\n const n = subpaths.length;\r\n\r\n // For each path find its direct parent:\r\n // the smallest-area path (highest index, since sorted descending) that contains it.\r\n // Iterate j from i-1 down to 0 — first match is the direct parent.\r\n const parent = new Array<number>(n).fill(-1);\r\n\r\n for (let i = 1; i < n; i++) {\r\n for (let j = i - 1; j >= 0; j--) {\r\n if (this.svgPathContains(subpaths[j], subpaths[i])) {\r\n parent[i] = j;\r\n break;\r\n }\r\n }\r\n }\r\n\r\n // Compute nesting depth by walking up the parent chain\r\n const depth = new Array<number>(n).fill(0);\r\n for (let i = 0; i < n; i++) {\r\n let p = parent[i];\r\n let d = 0;\r\n while (p !== -1) {\r\n d++;\r\n p = parent[p];\r\n }\r\n depth[i] = d;\r\n }\r\n\r\n // Even depth → outer shape; odd depth → hole in its parent shape\r\n const shapeByIndex = new Map<number, any>();\r\n const finalShapes: any[] = [];\r\n\r\n for (let i = 0; i < n; i++) {\n if (depth[i] % 2 === 0) {\n const srcPath = this.ensurePathWinding(subpaths[i].path, subpaths[i].points, true);\n const shape = this.clonePathAsShape(srcPath);\n shapeByIndex.set(i, shape);\n finalShapes.push(shape);\n }\n }\r\n\r\n for (let i = 0; i < n; i++) {\r\n if (depth[i] % 2 === 1) {\r\n // Walk up to find the nearest even-depth ancestor (the shape to punch the hole into)\r\n let p = parent[i];\r\n while (p !== -1 && depth[p] % 2 !== 0) {\n p = parent[p];\n }\n const parentShape = p !== -1 ? shapeByIndex.get(p) : undefined;\n if (parentShape) {\n const holePath = this.ensurePathWinding(subpaths[i].path, subpaths[i].points, false);\n parentShape.holes.push(holePath);\n }\n }\n }\n\r\n return finalShapes;\r\n }\r\n\r\n private svgPathContains(\r\n outer: { points: any[]; bbox: any },\r\n inner: { points: any[]; bbox: any },\r\n ): boolean {\r\n // Quick bbox rejection\r\n if (\r\n inner.bbox.minX < outer.bbox.minX ||\r\n inner.bbox.maxX > outer.bbox.maxX ||\r\n inner.bbox.minY < outer.bbox.minY ||\r\n inner.bbox.maxY > outer.bbox.maxY\r\n ) {\r\n return false;\r\n }\r\n\r\n // Test a few distributed points of inner against outer polygon\r\n const outerPoly = outer.points.map((p: any) => ({ x: p.x, y: p.y }));\r\n const stride = Math.max(1, Math.floor(inner.points.length / 4));\r\n for (let k = 0; k < inner.points.length; k += stride) {\r\n const pt = inner.points[k];\r\n if (pt && !this.pointInPolygon(pt.x, pt.y, outerPoly)) {\r\n return false;\r\n }\r\n }\r\n\r\n return true;\r\n }\r\n\r\n private parseSVGPathToSubpaths(\n d: string,\n transform: { a: number; b: number; c: number; d: number; e: number; f: number } | null,\n ): Array<{ path: any; points: any[]; area: number; signedArea: number; bbox: any }> {\n if (!d) return [];\r\n\r\n const shapePath = new this.THREE.ShapePath();\r\n\r\n // Tokenize SVG path data\r\n const tokens = this.tokenizeSVGPath(d);\r\n let i = 0;\r\n\r\n let cx = 0; // current x\r\n let cy = 0; // current y\r\n let startX = 0; // subpath start x\r\n let startY = 0; // subpath start y\r\n let lastCmd = \"\";\r\n let lastCtrlX = 0; // for smooth curves\r\n let lastCtrlY = 0;\r\n\r\n const applyTransform = (x: number, y: number): [number, number] => {\r\n if (!transform) return [x, -y];\r\n return [\r\n transform.a * x + transform.c * y + transform.e,\r\n -(transform.b * x + transform.d * y + transform.f),\r\n ];\r\n };\r\n\r\n while (i < tokens.length) {\r\n const cmd = tokens[i];\r\n if (typeof cmd !== \"string\" || cmd.length !== 1 || !/[MLHVQCSATZmlhvqcsatz]/.test(cmd)) {\r\n i++;\r\n continue;\r\n }\r\n i++;\r\n\r\n const isRelative = cmd === cmd.toLowerCase() && cmd !== \"z\" && cmd !== \"Z\";\r\n const upper = cmd.toUpperCase();\r\n\r\n // Each command can repeat with implicit repetition\r\n do {\r\n switch (upper) {\r\n case \"M\": {\r\n const nx = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ny = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n [cx, cy] = [nx, ny];\r\n startX = cx;\r\n startY = cy;\r\n const [tx, ty] = applyTransform(cx, cy);\r\n shapePath.moveTo(tx, ty);\r\n // Subsequent coords after M are implicit L\r\n lastCmd = isRelative ? \"l\" : \"L\";\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n continue;\r\n }\r\n case \"L\": {\r\n const nx = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ny = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n [cx, cy] = [nx, ny];\r\n const [tx, ty] = applyTransform(cx, cy);\r\n shapePath.lineTo(tx, ty);\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n break;\r\n }\r\n case \"H\": {\r\n const nx = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n cx = nx;\r\n const [tx, ty] = applyTransform(cx, cy);\r\n shapePath.lineTo(tx, ty);\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n break;\r\n }\r\n case \"V\": {\r\n const ny = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n cy = ny;\r\n const [tx, ty] = applyTransform(cx, cy);\r\n shapePath.lineTo(tx, ty);\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n break;\r\n }\r\n case \"Q\": {\r\n const qx1 = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const qy1 = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const qx = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const qy = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n lastCtrlX = qx1;\r\n lastCtrlY = qy1;\r\n [cx, cy] = [qx, qy];\r\n const [tc1x, tc1y] = applyTransform(qx1, qy1);\r\n const [tex, tey] = applyTransform(cx, cy);\r\n shapePath.quadraticCurveTo(tc1x, tc1y, tex, tey);\r\n break;\r\n }\r\n case \"T\": {\r\n // Smooth quadratic: control point is reflection of last Q control\r\n const qx1 = 2 * cx - lastCtrlX;\r\n const qy1 = 2 * cy - lastCtrlY;\r\n const qx = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const qy = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n lastCtrlX = qx1;\r\n lastCtrlY = qy1;\r\n [cx, cy] = [qx, qy];\r\n const [tc1x, tc1y] = applyTransform(qx1, qy1);\r\n const [tex, tey] = applyTransform(cx, cy);\r\n shapePath.quadraticCurveTo(tc1x, tc1y, tex, tey);\r\n break;\r\n }\r\n case \"C\": {\r\n const cx1 = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const cy1 = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const cx2 = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const cy2 = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ex = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ey = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n lastCtrlX = cx2;\r\n lastCtrlY = cy2;\r\n [cx, cy] = [ex, ey];\r\n const [tb1x, tb1y] = applyTransform(cx1, cy1);\r\n const [tb2x, tb2y] = applyTransform(cx2, cy2);\r\n const [tbex, tbey] = applyTransform(cx, cy);\r\n shapePath.bezierCurveTo(tb1x, tb1y, tb2x, tb2y, tbex, tbey);\r\n break;\r\n }\r\n case \"S\": {\r\n // Smooth cubic: first control is reflection of last C's second control\r\n const cx1 = 2 * cx - lastCtrlX;\r\n const cy1 = 2 * cy - lastCtrlY;\r\n const cx2 = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const cy2 = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ex = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ey = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n lastCtrlX = cx2;\r\n lastCtrlY = cy2;\r\n [cx, cy] = [ex, ey];\r\n const [tb1x, tb1y] = applyTransform(cx1, cy1);\r\n const [tb2x, tb2y] = applyTransform(cx2, cy2);\r\n const [tbex, tbey] = applyTransform(cx, cy);\r\n shapePath.bezierCurveTo(tb1x, tb1y, tb2x, tb2y, tbex, tbey);\r\n break;\r\n }\r\n case \"A\": {\r\n let rx = Math.abs(this.nextNum(tokens, i));\r\n i++;\r\n let ry = Math.abs(this.nextNum(tokens, i));\r\n i++;\r\n const xAxisRotation = this.nextNum(tokens, i);\r\n i++;\r\n const largeArcFlag = this.nextNum(tokens, i) !== 0;\r\n i++;\r\n const sweepFlag = this.nextNum(tokens, i) !== 0;\r\n i++;\r\n const ex = (isRelative ? cx : 0) + this.nextNum(tokens, i);\r\n i++;\r\n const ey = (isRelative ? cy : 0) + this.nextNum(tokens, i);\r\n i++;\r\n\r\n if (rx === 0 || ry === 0) {\r\n // Degenerate arc → line\r\n [cx, cy] = [ex, ey];\r\n const [tx, ty] = applyTransform(cx, cy);\r\n shapePath.lineTo(tx, ty);\r\n } else {\r\n const curves = this.arcToBezier(\r\n cx, cy, rx, ry, xAxisRotation, largeArcFlag, sweepFlag, ex, ey,\r\n );\r\n for (const [x1, y1, x2, y2, xe, ye] of curves) {\r\n const [tb1x, tb1y] = applyTransform(x1, y1);\r\n const [tb2x, tb2y] = applyTransform(x2, y2);\r\n const [tbex, tbey] = applyTransform(xe, ye);\r\n shapePath.bezierCurveTo(tb1x, tb1y, tb2x, tb2y, tbex, tbey);\r\n }\r\n [cx, cy] = [ex, ey];\r\n }\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n break;\r\n }\r\n case \"Z\": {\r\n if (typeof shapePath.closePath === \"function\") {\r\n shapePath.closePath();\r\n } else if (shapePath.currentPath?.closePath) {\r\n shapePath.currentPath.closePath();\r\n }\r\n cx = startX;\r\n cy = startY;\r\n lastCtrlX = cx;\r\n lastCtrlY = cy;\r\n break;\r\n }\r\n }\r\n\r\n lastCmd = cmd;\r\n } while (\r\n i < tokens.length &&\r\n typeof tokens[i] === \"number\" &&\r\n upper !== \"Z\"\r\n );\r\n }\r\n\r\n const subPaths = shapePath.subPaths;\r\n if (!subPaths || subPaths.length === 0) return [];\r\n\r\n return subPaths\r\n .map((sp: any) => {\n // 64 divisions for area/containment accuracy; actual geometry uses sp directly (curves preserved)\n const points = sp.getPoints(64);\n if (!points || points.length < 3) return null;\n const signedArea = this.THREE.ShapeUtils.area(points);\n const bbox = this.getBoundingBox(points.map((p: any) => ({ x: p.x, y: p.y })));\n return { path: sp, points, area: Math.abs(signedArea), signedArea, bbox };\n })\n .filter((sp: any) => sp !== null && sp.area > 0);\n }\n\n private ensurePathWinding(path: any, points: any[], clockwise: boolean): any {\n const isClockwise = this.THREE.ShapeUtils.isClockWise(points);\n return isClockwise === clockwise ? path : this.reversePath(path);\n }\n\n private clonePathAsShape(path: any): any {\n const shape = new this.THREE.Shape();\n shape.curves = path.curves.slice();\n if (path.currentPoint) {\n shape.currentPoint.copy(path.currentPoint);\n }\n return shape;\n }\n\r\n private tokenizeSVGPath(d: string): Array<string | number> {\r\n const tokens: Array<string | number> = [];\r\n // Split on commands and numbers (including negative and scientific notation)\r\n const re = /([MLHVQCSATZmlhvqcsatz])|([+-]?(?:\\d+\\.?\\d*|\\.\\d+)(?:[eE][+-]?\\d+)?)/g;\r\n let match: RegExpExecArray | null;\r\n while ((match = re.exec(d)) !== null) {\r\n if (match[1]) {\r\n tokens.push(match[1]);\r\n } else if (match[2]) {\r\n tokens.push(parseFloat(match[2]));\r\n }\r\n }\r\n return tokens;\r\n }\r\n\r\n private nextNum(tokens: Array<string | number>, i: number): number {\r\n const v = tokens[i];\r\n return typeof v === \"number\" ? v : 0;\r\n }\r\n\r\n // Convert SVG arc to bezier curves\r\n // Returns array of [x1,y1, x2,y2, ex,ey] control points for each bezier segment\r\n private arcToBezier(\r\n x1: number,\r\n y1: number,\r\n rx: number,\r\n ry: number,\r\n xAxisRotationDeg: number,\r\n largeArcFlag: boolean,\r\n sweepFlag: boolean,\r\n x2: number,\r\n y2: number,\r\n ): Array<[number, number, number, number, number, number]> {\r\n const phi = (xAxisRotationDeg * Math.PI) / 180;\r\n const cosPhi = Math.cos(phi);\r\n const sinPhi = Math.sin(phi);\r\n\r\n const dx = (x1 - x2) / 2;\r\n const dy = (y1 - y2) / 2;\r\n const x1p = cosPhi * dx + sinPhi * dy;\r\n const y1p = -sinPhi * dx + cosPhi * dy;\r\n\r\n const x1pSq = x1p * x1p;\r\n const y1pSq = y1p * y1p;\r\n let rxSq = rx * rx;\r\n let rySq = ry * ry;\r\n\r\n // Ensure radii are large enough\r\n const lambda = x1pSq / rxSq + y1pSq / rySq;\r\n if (lambda > 1) {\r\n const sqrtLambda = Math.sqrt(lambda);\r\n rx *= sqrtLambda;\r\n ry *= sqrtLambda;\r\n rxSq = rx * rx;\r\n rySq = ry * ry;\r\n }\r\n\r\n const sign = largeArcFlag !== sweepFlag ? 1 : -1;\r\n const num = Math.max(0, rxSq * rySq - rxSq * y1pSq - rySq * x1pSq);\r\n const den = rxSq * y1pSq + rySq * x1pSq;\r\n const sq = sign * Math.sqrt(num / den);\r\n\r\n const cxp = sq * (rx * y1p) / ry;\r\n const cyp = sq * -(ry * x1p) / rx;\r\n\r\n const cx = cosPhi * cxp - sinPhi * cyp + (x1 + x2) / 2;\r\n const cy = sinPhi * cxp + cosPhi * cyp + (y1 + y2) / 2;\r\n\r\n const ux = (x1p - cxp) / rx;\r\n const uy = (y1p - cyp) / ry;\r\n const vx = (-x1p - cxp) / rx;\r\n const vy = (-y1p - cyp) / ry;\r\n\r\n const angle1 = Math.atan2(uy, ux);\r\n let dAngle = Math.atan2(vy, vx) - angle1;\r\n\r\n if (!sweepFlag && dAngle > 0) dAngle -= 2 * Math.PI;\r\n if (sweepFlag && dAngle < 0) dAngle += 2 * Math.PI;\r\n\r\n const segments = Math.ceil(Math.abs(dAngle) / (Math.PI / 2));\r\n const delta = dAngle / segments;\r\n const t = (8 / 3) * Math.sin(delta / 4) * Math.sin(delta / 4) / Math.sin(delta / 2);\r\n\r\n const result: Array<[number, number, number, number, number, number]> = [];\r\n let startAngle = angle1;\r\n\r\n for (let s = 0; s < segments; s++) {\r\n const endAngle = startAngle + delta;\r\n\r\n const cosStart = Math.cos(startAngle);\r\n const sinStart = Math.sin(startAngle);\r\n const cosEnd = Math.cos(endAngle);\r\n const sinEnd = Math.sin(endAngle);\r\n\r\n const px1 = cosPhi * rx * cosStart - sinPhi * ry * sinStart + cx;\r\n const py1 = sinPhi * rx * cosStart + cosPhi * ry * sinStart + cy;\r\n const px2 = cosPhi * rx * cosEnd - sinPhi * ry * sinEnd + cx;\r\n const py2 = sinPhi * rx * cosEnd + cosPhi * ry * sinEnd + cy;\r\n\r\n const dx1 = cosPhi * rx * (-sinStart) - sinPhi * ry * cosStart;\r\n const dy1 = sinPhi * rx * (-sinStart) + cosPhi * ry * cosStart;\r\n const dx2 = cosPhi * rx * (-sinEnd) - sinPhi * ry * cosEnd;\r\n const dy2 = sinPhi * rx * (-sinEnd) + cosPhi * ry * cosEnd;\r\n\r\n result.push([\r\n px1 + t * dx1,\r\n py1 + t * dy1,\r\n px2 - t * dx2,\r\n py2 - t * dy2,\r\n px2,\r\n py2,\r\n ]);\r\n\r\n startAngle = endAngle;\r\n }\r\n\r\n return result;\r\n }\r\n\r\n private buildLineShapes(\r\n line: string,\r\n font: any,\r\n size: number,\r\n letterSpacing: number,\r\n ): { shapes: any[]; width: number } {\r\n const shapes: any[] = [];\r\n let x = 0;\r\n const chars = Array.from(line);\r\n\r\n chars.forEach((char, index) => {\r\n const charShapes = font.generateShapes(char, size);\r\n charShapes.forEach((shape: any) => {\r\n const translated = this.translateShape(shape, x, 0);\r\n shapes.push(translated);\r\n });\r\n const advance = this.getGlyphAdvance(font, char, size);\r\n\r\n x += advance;\r\n if (letterSpacing !== 0 && index < chars.length - 1) {\r\n x += letterSpacing;\r\n }\r\n });\r\n\r\n return { shapes, width: x };\r\n }\r\n\r\n private getGlyphAdvance(font: any, char: string, size: number): number {\r\n const data = font?.data;\r\n const glyphs = data?.glyphs || {};\r\n const glyph = glyphs[char] || glyphs[char.charCodeAt(0)] || glyphs[\"?\"];\r\n const ha = glyph?.ha ?? data?.ha;\r\n const resolution = data?.resolution || 1000;\r\n if (typeof ha === \"number\") {\r\n return (ha / resolution) * size;\r\n }\r\n return size * 0.5;\r\n }\r\n\r\n private translateShape(shape: any, x: number, y: number): any {\r\n if (!shape || (!x && !y)) return shape;\r\n if (typeof shape.translate === \"function\") {\r\n shape.translate(x, y);\r\n return shape;\r\n }\r\n if (typeof shape.applyMatrix4 === \"function\") {\r\n const matrix = new this.THREE.Matrix4().makeTranslation(x, y, 0);\r\n shape.applyMatrix4(matrix);\r\n return shape;\r\n }\r\n if (typeof shape.extractPoints === \"function\") {\r\n const { shape: points, holes } = shape.extractPoints(12);\r\n const toVec2 = (pt: any) => new this.THREE.Vector2((pt.x || 0) + x, (pt.y || 0) + y);\r\n const newShape = new this.THREE.Shape(points.map(toVec2));\r\n if (Array.isArray(holes)) {\r\n holes.forEach((hole: any[]) => {\r\n const holePath = new this.THREE.Path();\r\n holePath.setFromPoints(hole.map(toVec2));\r\n newShape.holes.push(holePath);\r\n });\r\n }\r\n return newShape;\r\n }\r\n return shape;\r\n }\r\n\r\n private scaleShape(shape: any, s: number): any {\r\n if (s === 1) return shape;\r\n if (typeof shape.scale === \"function\") {\r\n shape.scale(s, s);\r\n return shape;\r\n }\r\n if (typeof shape.applyMatrix4 === \"function\") {\r\n const matrix = new this.THREE.Matrix4().makeScale(s, s, 1);\r\n shape.applyMatrix4(matrix);\r\n return shape;\r\n }\r\n\r\n if (typeof shape.extractPoints === \"function\") {\r\n const { shape: points, holes } = shape.extractPoints(12);\r\n const toVec2 = (pt: any) => new this.THREE.Vector2((pt.x || 0) * s, (pt.y || 0) * s);\r\n const newShape = new this.THREE.Shape(points.map(toVec2));\r\n if (Array.isArray(holes)) {\r\n holes.forEach((hole: any[]) => {\r\n const holePath = new this.THREE.Path();\r\n holePath.setFromPoints(hole.map(toVec2));\r\n newShape.holes.push(holePath);\r\n });\r\n }\r\n return newShape;\r\n }\r\n return shape;\r\n }\r\n\r\n private resolveParticleModelGeometry(\r\n modelUrl: string,\r\n loaderType?: string,\r\n nodeName?: string,\r\n ): Promise<any | null> {\r\n const url = modelUrl.trim();\r\n if (!url || url === \"none\") {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const normalizedLoader =\r\n loaderType && loaderType !== \"none\"\r\n ? loaderType\r\n : this.loaders.gltf\r\n ? \"gltf\"\r\n : Object.keys(this.loaders)[0];\r\n if (!normalizedLoader) {\r\n return Promise.resolve(null);\r\n }\r\n\r\n const nodeKey = (nodeName || \"\").trim();\r\n const cacheKey = `${normalizedLoader}|${url}|${nodeKey}`;\r\n if (this.particleModelCache.has(cacheKey)) {\r\n return Promise.resolve(this.particleModelCache.get(cacheKey));\r\n }\r\n const cachedPromise = this.particleModelPromiseCache.get(cacheKey);\r\n if (cachedPromise) {\r\n return cachedPromise;\r\n }\r\n\r\n const promise = new Promise<any | null>((resolve) => {\r\n let loader: I3DModelLoader | null = null;\r\n try {\r\n loader = this.createModelLoader(normalizedLoader);\r\n } catch (error) {\r\n resolve(null);\r\n return;\r\n }\r\n\r\n loader.load(\r\n url,\r\n (gltf: any) => {\r\n const root = gltf?.scene || gltf?.object || gltf;\r\n if (!root) {\r\n resolve(null);\r\n return;\r\n }\r\n let mesh: any = null;\r\n if (nodeKey) {\r\n if (root.getObjectByName) {\r\n const found = root.getObjectByName(nodeKey);\r\n if (found?.isMesh) mesh = found;\r\n }\r\n if (!mesh && root.traverse) {\r\n root.traverse((child: any) => {\r\n if (mesh) return;\r\n if (child?.isMesh && child?.name === nodeKey) {\r\n mesh = child;\r\n }\r\n });\r\n }\r\n }\r\n if (!mesh) {\r\n if (root.isMesh) {\r\n mesh = root;\r\n } else if (root.traverse) {\r\n root.traverse((child: any) => {\r\n if (!mesh && child?.isMesh) {\r\n mesh = child;\r\n }\r\n });\r\n }\r\n }\r\n\r\n const geometry = mesh?.geometry || null;\r\n if (!geometry) {\r\n resolve(null);\r\n return;\r\n }\r\n this.particleModelCache.set(cacheKey, geometry);\r\n resolve(geometry);\r\n },\r\n undefined,\r\n () => {\r\n resolve(null);\r\n },\r\n );\r\n });\r\n\r\n this.particleModelPromiseCache.set(cacheKey, promise);\r\n return promise;\r\n }\r\n\r\n createParticleSystem(config: ParticleSystemConfig): I3DParticleSystem {\r\n const THREE = this.THREE;\r\n const engine = this;\r\n\r\n const makeRng = (seed: number) => {\r\n let s = Math.max(1, seed | 0);\r\n return () => {\r\n s ^= s << 13;\r\n s ^= s >> 17;\r\n s ^= s << 5;\r\n return ((s >>> 0) % 100000) / 100000;\r\n };\r\n };\r\n\r\n class ParticleSystem extends THREE.Object3D {\r\n private cfg: ParticleSystemConfig;\r\n private rng = makeRng(config.seed);\r\n private points: any = null;\r\n private instanced: any = null;\r\n private positions: Float32Array = new Float32Array(0);\r\n private velocities: Float32Array = new Float32Array(0);\r\n private life: Float32Array = new Float32Array(0);\r\n private colors: Float32Array = new Float32Array(0);\r\n private sizeFactors: Float32Array = new Float32Array(0);\r\n private alive = 0;\r\n private emitRemainder = 0;\r\n private pendingBurst = 0;\r\n private basePositions: Float32Array = new Float32Array(0);\r\n private baseScales: Float32Array = new Float32Array(0);\r\n private baseJitter: Float32Array = new Float32Array(0);\r\n private basePhase: Float32Array = new Float32Array(0);\r\n private elapsed = 0;\r\n private modelGeometry: any = null;\r\n private modelKey = \"\";\r\n private instancedUsesSharedGeometry = false;\r\n private distributionGeometry: any = null;\r\n private distributionKey = \"\";\r\n private materialOverride: any = null;\r\n private materialOverrideForPoints: any = null;\r\n private defaultEmitterMaterial: any = null;\r\n private defaultInstancedMaterial: any = null;\r\n private transitionStartTime = 0;\r\n private transitionDuration = 0;\r\n private isTransitioning = false;\r\n private transitionFromPositions: Float32Array = new Float32Array(0);\r\n private transitionToPositions: Float32Array = new Float32Array(0);\r\n private pendingTransition = false;\r\n private pendingTransitionKey = \"\";\r\n private pendingDistributionLoad = false;\r\n\r\n constructor(cfg: ParticleSystemConfig) {\r\n super();\r\n this.cfg = { ...cfg };\r\n this.refreshModelGeometry();\r\n this.rebuild();\r\n }\r\n\r\n setConfig(config: ParticleSystemConfig): void {\r\n const prev = this.cfg;\r\n this.cfg = { ...config };\r\n const emitterReset =\r\n this.cfg.mode === \"emitter\" &&\r\n (prev.emitRate !== this.cfg.emitRate ||\r\n prev.emitBurst !== this.cfg.emitBurst ||\r\n prev.particleLife !== this.cfg.particleLife ||\r\n prev.particleSpeed !== this.cfg.particleSpeed ||\r\n !this.isVec3Equal(prev.particleDirection, this.cfg.particleDirection) ||\r\n !this.isVec3Equal(prev.particleGravity, this.cfg.particleGravity) ||\r\n prev.particleDrag !== this.cfg.particleDrag ||\r\n prev.particleSizeVariation !== this.cfg.particleSizeVariation ||\r\n prev.particleColorVariation !== this.cfg.particleColorVariation ||\r\n prev.color !== this.cfg.color);\r\n const needsRebuild =\n prev.mode !== this.cfg.mode ||\n prev.count !== this.cfg.count ||\n prev.seed !== this.cfg.seed ||\n prev.spread !== this.cfg.spread ||\n prev.spreadX !== this.cfg.spreadX ||\n prev.spreadY !== this.cfg.spreadY ||\n prev.particleShape !== this.cfg.particleShape ||\n prev.particleModelUrl !== this.cfg.particleModelUrl ||\n prev.particleModelLoader !== this.cfg.particleModelLoader ||\n prev.particleModelNode !== this.cfg.particleModelNode ||\n prev.instanceShape !== this.cfg.instanceShape ||\n prev.instanceModelUrl !== this.cfg.instanceModelUrl ||\r\n prev.instanceModelLoader !== this.cfg.instanceModelLoader ||\r\n prev.instanceModelNode !== this.cfg.instanceModelNode ||\n prev.instanceScale !== this.cfg.instanceScale ||\n prev.instanceScaleVariation !== this.cfg.instanceScaleVariation;\n if (needsRebuild) {\n const isInstanceModelChange =\n this.cfg.mode === \"instanced\" &&\n this.instanced &&\n this.cfg.modelTransitionDuration > 0 &&\n (prev.instanceModelUrl !== this.cfg.instanceModelUrl ||\n prev.instanceModelLoader !== this.cfg.instanceModelLoader ||\n prev.instanceModelNode !== this.cfg.instanceModelNode ||\n prev.instanceShape !== this.cfg.instanceShape);\n\n if (isInstanceModelChange) {\n this.startModelTransition();\n } else {\n this.refreshModelGeometry();\n this.refreshDistributionGeometry();\n this.rebuild();\r\n }\r\n return;\r\n }\r\n if (emitterReset) {\r\n this.resetEmitter();\r\n }\r\n if (this.points) {\r\n const uniforms = this.points.material.uniforms;\r\n if (uniforms) {\r\n if (uniforms.uOpacity) {\r\n uniforms.uOpacity.value = this.cfg.opacity;\r\n }\r\n if (uniforms.uSize) {\r\n uniforms.uSize.value = this.cfg.size;\r\n }\r\n if (uniforms.uSizeVar) {\r\n uniforms.uSizeVar.value = this.cfg.particleSizeVariation;\r\n }\r\n if (uniforms.uPointSize) {\r\n uniforms.uPointSize.value = this.cfg.size;\r\n }\r\n }\r\n }\r\n if (this.instanced) {\r\n this.instanced.material.opacity = this.cfg.opacity;\r\n this.instanced.material.color = new THREE.Color(this.cfg.color);\r\n }\r\n this.pendingBurst = this.cfg.emitBurst;\r\n }\r\n\r\n private startModelTransition(): void {\r\n this.transitionFromPositions = new Float32Array(this.basePositions);\r\n this.transitionDuration = this.cfg.modelTransitionDuration;\r\n\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n this.pendingTransition = true;\r\n this.pendingTransitionKey = key;\r\n\r\n this.refreshModelGeometry();\r\n this.refreshDistributionGeometryForTransition();\r\n }\r\n\r\n private refreshDistributionGeometryForTransition(): void {\r\n if (this.cfg.instanceShape !== \"model\") {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n\r\n if (this.distributionKey === key && this.distributionGeometry) {\r\n this.startMorphTransition();\r\n return;\r\n }\r\n\r\n this.distributionKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.instanceModelLoader,\r\n this.cfg.instanceModelNode,\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.distributionKey !== key) return;\r\n if (!this.pendingTransition || this.pendingTransitionKey !== key) return;\r\n\r\n this.distributionGeometry = geometry;\r\n this.startMorphTransition();\r\n });\r\n }\r\n\r\n private startMorphTransition(): void {\r\n this.pendingTransition = false;\r\n this.pendingTransitionKey = \"\";\r\n\r\n const count = Math.max(1, this.cfg.count);\r\n this.transitionToPositions = new Float32Array(count * 3);\r\n\r\n const useModel = this.cfg.instanceShape === \"model\" && this.distributionGeometry;\r\n if (useModel) {\r\n this.fillFromModelToArray(count, this.distributionGeometry, this.transitionToPositions);\r\n } else {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos =\r\n this.cfg.instanceShape === \"box\"\r\n ? this.randomInBox(this.cfg.spread)\r\n : this.randomInSphere(this.cfg.spread);\r\n this.transitionToPositions.set(pos, i * 3);\r\n }\r\n }\r\n\r\n this.transitionStartTime = this.elapsed;\r\n this.isTransitioning = true;\r\n }\r\n\r\n private cleanupOutgoing(): void {\r\n this.isTransitioning = false;\r\n this.pendingTransition = false;\r\n this.pendingTransitionKey = \"\";\r\n this.transitionFromPositions = new Float32Array(0);\r\n this.transitionToPositions = new Float32Array(0);\r\n }\r\n\r\n private updateTransition(): void {\r\n if (!this.isTransitioning) return;\r\n\r\n const elapsed = this.elapsed - this.transitionStartTime;\r\n const progress = Math.min(1, elapsed / this.transitionDuration);\r\n\r\n const eased =\r\n progress < 0.5 ? 2 * progress * progress : 1 - Math.pow(-2 * progress + 2, 2) / 2;\r\n\r\n const count = Math.min(\r\n this.transitionFromPositions.length / 3,\r\n this.transitionToPositions.length / 3,\r\n this.basePositions.length / 3,\r\n );\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.basePositions[i3] =\r\n this.transitionFromPositions[i3] +\r\n (this.transitionToPositions[i3] - this.transitionFromPositions[i3]) * eased;\r\n this.basePositions[i3 + 1] =\r\n this.transitionFromPositions[i3 + 1] +\r\n (this.transitionToPositions[i3 + 1] - this.transitionFromPositions[i3 + 1]) * eased;\r\n this.basePositions[i3 + 2] =\r\n this.transitionFromPositions[i3 + 2] +\r\n (this.transitionToPositions[i3 + 2] - this.transitionFromPositions[i3 + 2]) * eased;\r\n }\r\n\r\n if (progress >= 1) {\r\n for (let i = 0; i < count * 3; i += 1) {\r\n this.basePositions[i] = this.transitionToPositions[i];\r\n }\r\n this.cleanupOutgoing();\r\n }\r\n }\r\n\r\n private fillFromModelToArray(count: number, geometry: any, targetArray: Float32Array): void {\r\n const attr = geometry?.attributes?.position;\r\n if (!attr?.array || attr.itemSize < 3) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n targetArray.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n const array = attr.array as ArrayLike<number>;\r\n const itemSize = attr.itemSize;\r\n const vertexCount = Math.floor(array.length / itemSize);\r\n if (vertexCount <= 0) {\r\n return;\r\n }\r\n\r\n const indexArray = geometry?.index?.array as ArrayLike<number> | undefined;\r\n const triangleCount = indexArray\r\n ? Math.floor(indexArray.length / 3)\r\n : Math.floor(vertexCount / 3);\r\n if (triangleCount <= 0) {\r\n return;\r\n }\r\n\r\n let minX = Infinity;\r\n let minY = Infinity;\r\n let minZ = Infinity;\r\n let maxX = -Infinity;\r\n let maxY = -Infinity;\r\n let maxZ = -Infinity;\r\n for (let i = 0; i < vertexCount; i += 1) {\r\n const idx = i * itemSize;\r\n const x = array[idx];\r\n const y = array[idx + 1];\r\n const z = array[idx + 2];\r\n minX = Math.min(minX, x);\r\n minY = Math.min(minY, y);\r\n minZ = Math.min(minZ, z);\r\n maxX = Math.max(maxX, x);\r\n maxY = Math.max(maxY, y);\r\n maxZ = Math.max(maxZ, z);\r\n }\r\n const sizeX = Math.max(1e-6, maxX - minX);\r\n const sizeY = Math.max(1e-6, maxY - minY);\r\n const sizeZ = Math.max(1e-6, maxZ - minZ);\r\n const targetX = (this.cfg.spreadX > 0 ? this.cfg.spreadX : this.cfg.spread) * 2;\r\n const targetY = (this.cfg.spreadY > 0 ? this.cfg.spreadY : this.cfg.spread) * 2;\r\n const scaleX = targetX > 0 ? targetX / sizeX : 1;\r\n const scaleY = targetY > 0 ? targetY / sizeY : 1;\r\n const scale = Math.min(scaleX, scaleY);\r\n const centerX = (minX + maxX) * 0.5;\r\n const centerY = (minY + maxY) * 0.5;\r\n const centerZ = (minZ + maxZ) * 0.5;\r\n\r\n const cumulativeAreas = new Float32Array(triangleCount);\r\n let totalArea = 0;\r\n for (let i = 0; i < triangleCount; i += 1) {\r\n const base = i * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const abx = bx - ax;\r\n const aby = by - ay;\r\n const abz = bz - az;\r\n const acx = cx - ax;\r\n const acy = cy - ay;\r\n const acz = cz - az;\r\n const crossX = aby * acz - abz * acy;\r\n const crossY = abz * acx - abx * acz;\r\n const crossZ = abx * acy - aby * acx;\r\n const area = Math.sqrt(crossX * crossX + crossY * crossY + crossZ * crossZ) * 0.5;\r\n totalArea += area;\r\n cumulativeAreas[i] = totalArea;\r\n }\r\n if (totalArea <= 0) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n targetArray.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const r = this.rng() * totalArea;\r\n let lo = 0;\r\n let hi = triangleCount - 1;\r\n while (lo < hi) {\r\n const mid = Math.floor((lo + hi) / 2);\r\n if (r <= cumulativeAreas[mid]) {\r\n hi = mid;\r\n } else {\r\n lo = mid + 1;\r\n }\r\n }\r\n const base = lo * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const u = this.rng();\r\n const v = this.rng();\r\n const su = Math.sqrt(u);\r\n const w1 = 1 - su;\r\n const w2 = su * (1 - v);\r\n const w3 = su * v;\r\n const x = (ax * w1 + bx * w2 + cx * w3 - centerX) * scale;\r\n const y = (ay * w1 + by * w2 + cy * w3 - centerY) * scale;\r\n const z = (az * w1 + bz * w2 + cz * w3 - centerZ) * scale;\r\n targetArray[i * 3] = x;\r\n targetArray[i * 3 + 1] = y;\r\n targetArray[i * 3 + 2] = z;\r\n }\r\n }\r\n\r\n update(dt: number): void {\r\n if (dt <= 0) return;\r\n this.elapsed += dt;\r\n\r\n this.updateTransition();\r\n\r\n if (this.cfg.mode === \"emitter\") {\r\n this.updateEmitter(dt);\r\n } else {\r\n this.updateInstanced(this.elapsed);\r\n }\r\n }\r\n\r\n dispose(): void {\r\n this.cleanupOutgoing();\r\n if (this.points) {\r\n this.points.geometry.dispose();\r\n this.points.material.dispose();\r\n }\r\n if (this.instanced) {\r\n if (!this.instancedUsesSharedGeometry) {\r\n this.instanced.geometry.dispose();\r\n }\r\n this.instanced.material.dispose();\r\n }\r\n }\r\n\r\n private rebuild(): void {\r\n if (this.points) {\r\n this.remove(this.points);\r\n this.points.geometry.dispose();\r\n this.points.material.dispose();\r\n this.points = null;\r\n }\r\n if (this.instanced) {\r\n this.remove(this.instanced);\r\n if (!this.instancedUsesSharedGeometry) {\r\n this.instanced.geometry.dispose();\r\n }\r\n this.instanced.material.dispose();\r\n this.instanced = null;\r\n }\r\n this.elapsed = 0;\r\n\r\n if (this.cfg.mode === \"emitter\") {\r\n this.buildEmitter();\r\n } else {\r\n const needsModel = this.cfg.instanceShape === \"model\";\r\n const hasModel = this.distributionGeometry !== null;\r\n if (needsModel && !hasModel) {\r\n this.pendingDistributionLoad = true;\r\n this.refreshDistributionGeometry();\r\n return;\r\n }\r\n this.pendingDistributionLoad = false;\r\n this.refreshDistributionGeometry();\r\n this.buildInstanced();\r\n }\r\n this.applyMaterialOverrides();\r\n }\r\n\r\n private buildEmitter(): void {\r\n const count = Math.max(1, this.cfg.count);\r\n this.positions = new Float32Array(count * 3);\r\n this.velocities = new Float32Array(count * 3);\r\n this.life = new Float32Array(count);\r\n this.colors = new Float32Array(count * 3);\r\n this.sizeFactors = new Float32Array(count);\r\n const hide = 1e6;\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.positions[i3] = hide;\r\n this.positions[i3 + 1] = hide;\r\n this.positions[i3 + 2] = hide;\r\n }\r\n this.alive = 0;\r\n this.emitRemainder = 0;\r\n this.pendingBurst = this.cfg.emitBurst;\r\n\r\n const geometry = new THREE.BufferGeometry();\r\n geometry.setAttribute(\"position\", new THREE.BufferAttribute(this.positions, 3));\r\n geometry.setAttribute(\"color\", new THREE.BufferAttribute(this.colors, 3));\r\n geometry.setAttribute(\"sizeFactor\", new THREE.BufferAttribute(this.sizeFactors, 1));\r\n const material = new THREE.ShaderMaterial({\r\n transparent: this.cfg.opacity < 1,\r\n depthWrite: false,\r\n uniforms: {\r\n uOpacity: { value: this.cfg.opacity },\r\n uSize: { value: this.cfg.size },\r\n uSizeVar: { value: this.cfg.particleSizeVariation },\r\n },\r\n vertexShader: `\r\n attribute vec3 color;\r\n attribute float sizeFactor;\r\n varying vec3 vColor;\r\n uniform float uSize;\r\n uniform float uSizeVar;\r\n void main() {\r\n vColor = color;\r\n float size = uSize * mix(1.0 - uSizeVar, 1.0, sizeFactor);\r\n gl_PointSize = size;\r\n gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);\r\n }\r\n `,\r\n fragmentShader: `\r\n varying vec3 vColor;\r\n uniform float uOpacity;\r\n void main() {\r\n float dist = length(gl_PointCoord - vec2(0.5));\r\n if (dist > 0.5) discard;\r\n gl_FragColor = vec4(vColor, uOpacity);\r\n }\r\n `,\r\n });\r\n this.points = new THREE.Points(geometry, material);\r\n this.defaultEmitterMaterial = material;\r\n this.add(this.points);\r\n }\r\n\r\n private buildInstanced(): void {\r\n const count = Math.max(1, this.cfg.count);\r\n const useSharedGeometry = this.cfg.particleShape === \"model\" && this.modelGeometry;\r\n const geometry =\r\n this.cfg.particleShape === \"model\" && this.modelGeometry\r\n ? this.modelGeometry\r\n : this.cfg.particleShape === \"box\"\r\n ? new THREE.BoxGeometry(1, 1, 1)\r\n : new THREE.SphereGeometry(0.5, 8, 8);\r\n this.instancedUsesSharedGeometry = useSharedGeometry;\r\n const material = new THREE.MeshStandardMaterial({\r\n color: new THREE.Color(this.cfg.color),\r\n transparent: this.cfg.opacity < 1,\r\n opacity: this.cfg.opacity,\r\n });\r\n this.defaultInstancedMaterial = material;\r\n this.instanced = new THREE.InstancedMesh(geometry, material, count);\r\n this.basePositions = new Float32Array(count * 3);\r\n this.baseScales = new Float32Array(count);\r\n this.baseJitter = new Float32Array(count * 3);\r\n this.basePhase = new Float32Array(count);\r\n this.fillBasePositions(count);\r\n this.applyInstancedTransforms(0);\r\n this.add(this.instanced);\r\n }\r\n\r\n setMaterial(\r\n material: any | null,\r\n options: { points?: boolean; meshes?: boolean } = {},\r\n ): void {\r\n const setPoints = options.points ?? true;\r\n const setMeshes = options.meshes ?? true;\r\n if (setMeshes) {\r\n this.materialOverride = material;\r\n }\r\n if (setPoints) {\r\n this.materialOverrideForPoints = material;\r\n }\r\n this.applyMaterialOverrides();\r\n }\r\n\r\n private updateEmitter(dt: number): void {\r\n const count = this.cfg.count;\r\n const dir = this.normalize(this.cfg.particleDirection);\r\n const gravity = this.cfg.particleGravity;\r\n const drag = Math.max(0, Math.min(1, this.cfg.particleDrag));\r\n const emitRate = this.cfg.emitRate;\r\n const totalToEmit = emitRate * dt + this.emitRemainder;\r\n const emitCount = Math.floor(totalToEmit);\r\n this.emitRemainder = totalToEmit - emitCount;\r\n let colorDirty = false;\r\n const hide = 1e6;\r\n\r\n for (let i = 0; i < emitCount; i += 1) {\r\n this.spawnParticle(dir);\r\n }\r\n while (this.pendingBurst > 0) {\r\n this.spawnParticle(dir);\r\n this.pendingBurst -= 1;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n if (this.life[i] <= 0) continue;\r\n this.life[i] -= dt;\r\n if (this.life[i] <= 0) {\r\n this.life[i] = 0;\r\n const i3 = i * 3;\r\n this.positions[i3] = hide;\r\n this.positions[i3 + 1] = hide;\r\n this.positions[i3 + 2] = hide;\r\n this.colors[i3] = 0;\r\n this.colors[i3 + 1] = 0;\r\n this.colors[i3 + 2] = 0;\r\n colorDirty = true;\r\n continue;\r\n }\r\n const idx = i * 3;\r\n this.velocities[idx] += gravity[0] * dt;\r\n this.velocities[idx + 1] += gravity[1] * dt;\r\n this.velocities[idx + 2] += gravity[2] * dt;\r\n this.velocities[idx] *= 1 - drag * dt;\r\n this.velocities[idx + 1] *= 1 - drag * dt;\r\n this.velocities[idx + 2] *= 1 - drag * dt;\r\n this.positions[idx] += this.velocities[idx] * dt;\r\n this.positions[idx + 1] += this.velocities[idx + 1] * dt;\r\n this.positions[idx + 2] += this.velocities[idx + 2] * dt;\r\n }\r\n\r\n if (this.points) {\r\n this.points.geometry.attributes.position.needsUpdate = true;\r\n if (colorDirty) {\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n }\r\n }\r\n }\r\n\r\n private spawnParticle(dir: [number, number, number]): void {\r\n const count = this.cfg.count;\r\n let idx = -1;\r\n for (let i = 0; i < count; i += 1) {\r\n if (this.life[i] <= 0) {\r\n idx = i;\r\n break;\r\n }\r\n }\r\n if (idx === -1) return;\r\n\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n const speed =\r\n this.cfg.particleSpeed *\r\n (1 - this.cfg.particleSizeVariation + this.rng() * this.cfg.particleSizeVariation);\r\n const vel = [\r\n dir[0] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n dir[1] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n dir[2] * speed + (this.rng() - 0.5) * speed * 0.2,\r\n ];\r\n\r\n const i3 = idx * 3;\r\n this.positions.set(pos, i3);\r\n this.velocities.set(vel, i3);\r\n this.life[idx] = this.cfg.particleLife;\r\n this.sizeFactors[idx] = this.rng();\r\n\r\n const color = new THREE.Color(this.cfg.color);\r\n if (this.cfg.particleColorVariation > 0) {\r\n color.offsetHSL((this.rng() - 0.5) * this.cfg.particleColorVariation, 0, 0);\r\n }\r\n this.colors[i3] = color.r;\r\n this.colors[i3 + 1] = color.g;\r\n this.colors[i3 + 2] = color.b;\r\n if (this.points) {\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n this.points.geometry.attributes.sizeFactor.needsUpdate = true;\r\n }\r\n }\r\n\r\n private updateInstanced(time: number): void {\r\n this.applyInstancedTransforms(time);\r\n if (this.instanced) {\r\n this.instanced.instanceMatrix.needsUpdate = true;\r\n }\r\n }\r\n\r\n private applyInstancedTransforms(time: number): void {\r\n if (!this.instanced) return;\r\n const count = this.cfg.count;\r\n const jitter = this.cfg.instanceJitter;\r\n const flow = this.cfg.instanceFlow;\r\n const disperse = Math.max(0, this.cfg.instanceDisperse);\r\n const scatter = Math.max(0, this.cfg.instanceDisperseScatter);\r\n const scatterX =\r\n this.cfg.instanceDisperseScatterX > 0 ? this.cfg.instanceDisperseScatterX : scatter;\r\n const scatterY =\r\n this.cfg.instanceDisperseScatterY > 0 ? this.cfg.instanceDisperseScatterY : scatter;\r\n const scatterZ =\r\n this.cfg.instanceDisperseScatterZ > 0 ? this.cfg.instanceDisperseScatterZ : scatter;\r\n const rotSpeed = this.cfg.instanceRotationSpeed;\r\n const temp = new THREE.Object3D();\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n const baseX = this.basePositions[i3];\r\n const baseY = this.basePositions[i3 + 1];\r\n const baseZ = this.basePositions[i3 + 2];\r\n const phase = this.basePhase[i];\r\n const driftX = Math.sin((baseY + time * 1.4) * 0.7 + phase) * flow * this.cfg.spread;\r\n const driftY = Math.cos((baseX - time * 1.1) * 0.6 + phase) * flow * this.cfg.spread;\r\n const driftZ = Math.sin((baseZ + time * 1.2) * 0.8 + phase) * flow * this.cfg.spread;\r\n const jitterX = Math.sin(time * 2.1 + phase + this.baseJitter[i3] * 2.5) * jitter;\r\n const jitterY = Math.cos(time * 1.7 + phase + this.baseJitter[i3 + 1] * 2.5) * jitter;\r\n const jitterZ = Math.sin(time * 1.9 + phase + this.baseJitter[i3 + 2] * 2.5) * jitter;\r\n const dispersal = 1 + disperse;\r\n const dirX = this.baseJitter[i3];\r\n const dirY = this.baseJitter[i3 + 1];\r\n const dirZ = this.baseJitter[i3 + 2];\r\n const dirLen = Math.sqrt(dirX * dirX + dirY * dirY + dirZ * dirZ) || 1;\r\n const scatterScale = disperse * this.cfg.spread;\r\n const scatterOffsetX = (dirX / dirLen) * scatterX * scatterScale;\r\n const scatterOffsetY = (dirY / dirLen) * scatterY * scatterScale;\r\n const scatterOffsetZ = (dirZ / dirLen) * scatterZ * scatterScale;\r\n temp.position.set(\r\n baseX * dispersal + scatterOffsetX + driftX + jitterX,\r\n baseY * dispersal + scatterOffsetY + driftY + jitterY,\r\n baseZ * dispersal + scatterOffsetZ + driftZ + jitterZ,\r\n );\r\n temp.rotation.set(\r\n this.baseJitter[i3] * 0.5,\r\n time * rotSpeed + i * 0.1,\r\n this.baseJitter[i3 + 2] * 0.5,\r\n );\r\n const scale = this.baseScales[i] * this.cfg.size;\r\n temp.scale.set(scale, scale, scale);\r\n temp.updateMatrix();\r\n this.instanced.setMatrixAt(i, temp.matrix);\r\n }\r\n }\r\n\r\n private applyMaterialOverrides(): void {\r\n if (this.points) {\r\n const next = this.materialOverrideForPoints || this.defaultEmitterMaterial;\r\n if (next && this.points.material !== next) {\r\n this.points.material = next;\r\n this.ensurePointMaterial(next);\r\n }\r\n }\r\n if (this.instanced) {\r\n const next = this.materialOverride || this.defaultInstancedMaterial;\r\n if (next && this.instanced.material !== next) {\r\n this.instanced.material = next;\r\n }\r\n }\r\n }\r\n\r\n private ensurePointMaterial(material: any): void {\r\n if (!material?.isShaderMaterial) return;\r\n if (!material.uniforms) {\r\n material.uniforms = {};\r\n }\r\n if (!material.uniforms.uPointSize) {\r\n material.uniforms.uPointSize = { value: this.cfg.size };\r\n }\r\n if (!material.uniforms.uOpacity) {\r\n material.uniforms.uOpacity = { value: this.cfg.opacity };\r\n }\r\n if (!material.vertexShader.includes(\"gl_PointSize\")) {\r\n if (!material.vertexShader.includes(\"uPointSize\")) {\r\n material.vertexShader = `uniform float uPointSize;\\n${material.vertexShader}`;\r\n }\r\n material.vertexShader = material.vertexShader.replace(\r\n /void\\\\s+main\\\\s*\\\\(\\\\)\\\\s*\\\\{/,\r\n \"void main() {\\\\n gl_PointSize = uPointSize;\",\r\n );\r\n material.needsUpdate = true;\r\n }\r\n }\r\n\r\n private refreshModelGeometry(): void {\r\n if (this.cfg.particleShape !== \"model\") {\r\n this.modelGeometry = null;\r\n this.modelKey = \"\";\r\n return;\r\n }\r\n const url = this.cfg.particleModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.modelGeometry = null;\r\n this.modelKey = \"\";\r\n return;\r\n }\r\n const key = `${this.cfg.particleModelLoader}|${url}|${this.cfg.particleModelNode}`;\r\n if (this.modelKey === key && this.modelGeometry) {\r\n return;\r\n }\r\n this.modelKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.particleModelLoader,\r\n this.cfg.particleModelNode,\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.modelKey !== key) return;\r\n this.modelGeometry = geometry;\r\n if (this.cfg.mode === \"instanced\" && this.cfg.particleShape === \"model\") {\r\n this.rebuild();\r\n }\r\n });\r\n }\r\n\r\n private refreshDistributionGeometry(): void {\r\n if (this.cfg.instanceShape !== \"model\") {\r\n this.distributionGeometry = null;\r\n this.distributionKey = \"\";\r\n return;\r\n }\r\n const url = this.cfg.instanceModelUrl?.trim();\r\n if (!url || url === \"none\") {\r\n this.distributionGeometry = null;\r\n this.distributionKey = \"\";\r\n return;\r\n }\r\n const key = `${this.cfg.instanceModelLoader}|${url}|${this.cfg.instanceModelNode}`;\r\n if (this.distributionKey === key && this.distributionGeometry) {\r\n return;\r\n }\r\n this.distributionKey = key;\r\n engine\r\n .resolveParticleModelGeometry(\r\n url,\r\n this.cfg.instanceModelLoader,\r\n this.cfg.instanceModelNode,\r\n )\r\n .then((geometry) => {\r\n if (!geometry) return;\r\n if (this.distributionKey !== key) return;\r\n this.distributionGeometry = geometry;\r\n if (this.cfg.mode === \"instanced\" && this.cfg.instanceShape === \"model\") {\r\n if (this.pendingDistributionLoad) {\r\n this.pendingDistributionLoad = false;\r\n this.buildInstanced();\r\n this.applyMaterialOverrides();\r\n } else {\r\n this.rebuild();\r\n }\r\n }\r\n });\r\n }\r\n\r\n private fillBasePositions(count: number): void {\r\n const useModel = this.cfg.instanceShape === \"model\" && this.distributionGeometry;\r\n if (useModel) {\r\n this.fillFromModel(count, this.distributionGeometry);\r\n } else {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos =\r\n this.cfg.instanceShape === \"box\"\r\n ? this.randomInBox(this.cfg.spread)\r\n : this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const i3 = i * 3;\r\n this.baseJitter[i3] = this.rng() * 2 - 1;\r\n this.baseJitter[i3 + 1] = this.rng() * 2 - 1;\r\n this.baseJitter[i3 + 2] = this.rng() * 2 - 1;\r\n this.basePhase[i] = this.rng() * Math.PI * 2;\r\n const scale =\r\n this.cfg.instanceScale *\r\n (1 - this.cfg.instanceScaleVariation + this.rng() * this.cfg.instanceScaleVariation);\r\n this.baseScales[i] = scale;\r\n }\r\n }\r\n\r\n private fillFromModel(count: number, geometry: any): void {\r\n const attr = geometry?.attributes?.position;\r\n if (!attr?.array || attr.itemSize < 3) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n const array = attr.array as ArrayLike<number>;\r\n const itemSize = attr.itemSize;\r\n const vertexCount = Math.floor(array.length / itemSize);\r\n if (vertexCount <= 0) {\r\n return;\r\n }\r\n\r\n const indexArray = geometry?.index?.array as ArrayLike<number> | undefined;\r\n const triangleCount = indexArray\r\n ? Math.floor(indexArray.length / 3)\r\n : Math.floor(vertexCount / 3);\r\n if (triangleCount <= 0) {\r\n return;\r\n }\r\n\r\n let minX = Infinity;\r\n let minY = Infinity;\r\n let minZ = Infinity;\r\n let maxX = -Infinity;\r\n let maxY = -Infinity;\r\n let maxZ = -Infinity;\r\n for (let i = 0; i < vertexCount; i += 1) {\r\n const idx = i * itemSize;\r\n const x = array[idx];\r\n const y = array[idx + 1];\r\n const z = array[idx + 2];\r\n minX = Math.min(minX, x);\r\n minY = Math.min(minY, y);\r\n minZ = Math.min(minZ, z);\r\n maxX = Math.max(maxX, x);\r\n maxY = Math.max(maxY, y);\r\n maxZ = Math.max(maxZ, z);\r\n }\r\n const sizeX = Math.max(1e-6, maxX - minX);\r\n const sizeY = Math.max(1e-6, maxY - minY);\r\n const sizeZ = Math.max(1e-6, maxZ - minZ);\r\n const targetX = (this.cfg.spreadX > 0 ? this.cfg.spreadX : this.cfg.spread) * 2;\r\n const targetY = (this.cfg.spreadY > 0 ? this.cfg.spreadY : this.cfg.spread) * 2;\r\n const scaleX = targetX > 0 ? targetX / sizeX : 1;\r\n const scaleY = targetY > 0 ? targetY / sizeY : 1;\r\n const scale = Math.min(scaleX, scaleY);\r\n const centerX = (minX + maxX) * 0.5;\r\n const centerY = (minY + maxY) * 0.5;\r\n const centerZ = (minZ + maxZ) * 0.5;\r\n\r\n const cumulativeAreas = new Float32Array(triangleCount);\r\n let totalArea = 0;\r\n for (let i = 0; i < triangleCount; i += 1) {\r\n const base = i * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const abx = bx - ax;\r\n const aby = by - ay;\r\n const abz = bz - az;\r\n const acx = cx - ax;\r\n const acy = cy - ay;\r\n const acz = cz - az;\r\n const crossX = aby * acz - abz * acy;\r\n const crossY = abz * acx - abx * acz;\r\n const crossZ = abx * acy - aby * acx;\r\n const area = Math.sqrt(crossX * crossX + crossY * crossY + crossZ * crossZ) * 0.5;\r\n totalArea += area;\r\n cumulativeAreas[i] = totalArea;\r\n }\r\n if (totalArea <= 0) {\r\n for (let i = 0; i < count; i += 1) {\r\n const pos = this.randomInSphere(this.cfg.spread);\r\n this.basePositions.set(pos, i * 3);\r\n }\r\n return;\r\n }\r\n\r\n for (let i = 0; i < count; i += 1) {\r\n const r = this.rng() * totalArea;\r\n let lo = 0;\r\n let hi = triangleCount - 1;\r\n while (lo < hi) {\r\n const mid = Math.floor((lo + hi) / 2);\r\n if (r <= cumulativeAreas[mid]) {\r\n hi = mid;\r\n } else {\r\n lo = mid + 1;\r\n }\r\n }\r\n const base = lo * 3;\r\n const ia = indexArray ? indexArray[base] : base;\r\n const ib = indexArray ? indexArray[base + 1] : base + 1;\r\n const ic = indexArray ? indexArray[base + 2] : base + 2;\r\n const a = ia * itemSize;\r\n const b = ib * itemSize;\r\n const c = ic * itemSize;\r\n const ax = array[a];\r\n const ay = array[a + 1];\r\n const az = array[a + 2];\r\n const bx = array[b];\r\n const by = array[b + 1];\r\n const bz = array[b + 2];\r\n const cx = array[c];\r\n const cy = array[c + 1];\r\n const cz = array[c + 2];\r\n const u = this.rng();\r\n const v = this.rng();\r\n const su = Math.sqrt(u);\r\n const w1 = 1 - su;\r\n const w2 = su * (1 - v);\r\n const w3 = su * v;\r\n const x = (ax * w1 + bx * w2 + cx * w3 - centerX) * scale;\r\n const y = (ay * w1 + by * w2 + cy * w3 - centerY) * scale;\r\n const z = (az * w1 + bz * w2 + cz * w3 - centerZ) * scale;\r\n this.basePositions[i * 3] = x;\r\n this.basePositions[i * 3 + 1] = y;\r\n this.basePositions[i * 3 + 2] = z;\r\n }\r\n }\r\n\r\n private resetEmitter(): void {\r\n if (!this.points) return;\r\n const hide = 1e6;\r\n for (let i = 0; i < this.positions.length; i += 3) {\r\n this.positions[i] = hide;\r\n this.positions[i + 1] = hide;\r\n this.positions[i + 2] = hide;\r\n }\r\n this.velocities.fill(0);\r\n this.life.fill(0);\r\n this.colors.fill(0);\r\n this.sizeFactors.fill(0);\r\n this.alive = 0;\r\n this.emitRemainder = 0;\r\n this.pendingBurst = this.cfg.emitBurst;\r\n this.points.geometry.attributes.position.needsUpdate = true;\r\n this.points.geometry.attributes.color.needsUpdate = true;\r\n this.points.geometry.attributes.sizeFactor.needsUpdate = true;\r\n }\r\n\r\n private normalize(vec: [number, number, number]): [number, number, number] {\r\n const len = Math.sqrt(vec[0] * vec[0] + vec[1] * vec[1] + vec[2] * vec[2]) || 1;\r\n return [vec[0] / len, vec[1] / len, vec[2] / len];\r\n }\r\n\r\n private isVec3Equal(a: [number, number, number], b: [number, number, number]): boolean {\r\n return a[0] === b[0] && a[1] === b[1] && a[2] === b[2];\r\n }\r\n\r\n private randomInSphere(radius: number): [number, number, number] {\r\n const u = this.rng();\r\n const v = this.rng();\r\n const theta = u * Math.PI * 2;\r\n const phi = Math.acos(2 * v - 1);\r\n const r = Math.cbrt(this.rng()) * radius;\r\n return [\r\n r * Math.sin(phi) * Math.cos(theta),\r\n r * Math.sin(phi) * Math.sin(theta),\r\n r * Math.cos(phi),\r\n ];\r\n }\r\n\r\n private randomInBox(size: number): [number, number, number] {\r\n const half = size * 0.5;\r\n return [\r\n (this.rng() * 2 - 1) * half,\r\n (this.rng() * 2 - 1) * half,\r\n (this.rng() * 2 - 1) * half,\r\n ];\r\n }\r\n }\r\n\r\n return new ParticleSystem(config) as unknown as I3DParticleSystem;\r\n }\r\n\r\n forEachMesh(object: I3DObject, callback: (mesh: I3DMesh) => void): void {\r\n const visit = (node: any) => {\r\n if (node?.isMesh) {\r\n callback(node as I3DMesh);\r\n }\r\n };\r\n\r\n const anyObject = object as any;\r\n if (typeof anyObject?.traverse === \"function\") {\r\n anyObject.traverse((child: any) => visit(child));\r\n return;\r\n }\r\n\r\n visit(anyObject);\r\n }\r\n\r\n forEachMaterial(object: I3DObject, callback: (material: I3DMaterial) => void): void {\r\n const visit = (node: any) => {\r\n if (!node || (!node.isMesh && !node.isPoints)) return;\r\n const materials = Array.isArray(node.material) ? node.material : [node.material];\r\n materials.forEach((mat: any) => {\r\n if (mat) callback(mat as I3DMaterial);\r\n });\r\n };\r\n\r\n const anyObject = object as any;\r\n if (typeof anyObject?.traverse === \"function\") {\r\n anyObject.traverse((child: any) => visit(child));\r\n return;\r\n }\r\n\r\n visit(anyObject);\r\n }\r\n\r\n getPrimaryMesh(object: I3DObject): I3DMesh | null {\r\n let first: I3DMesh | null = null;\r\n this.forEachMesh(object, (mesh) => {\r\n if (!first) first = mesh;\r\n });\r\n return first;\r\n }\r\n\r\n applyTextGeometryToMesh(mesh: I3DMesh, geometry: I3DGeometry): boolean {\r\n const anyGeometry = geometry as any;\r\n if (typeof anyGeometry?.applyToMesh !== \"function\") {\r\n return false;\r\n }\r\n\r\n anyGeometry.applyToMesh(mesh);\r\n return true;\r\n }\r\n\r\n setObjectPosition(target: any, x: number, y: number, z: number): boolean {\r\n if (target?.position?.set && typeof target.position.set === \"function\") {\r\n target.position.set(x, y, z);\r\n return true;\r\n }\r\n\r\n if (typeof target?.setPosition === \"function\") {\r\n target.setPosition(x, y, z);\r\n return true;\r\n }\r\n\r\n if (target?.position) {\r\n target.position.x = x;\r\n target.position.y = y;\r\n target.position.z = z;\r\n return true;\r\n }\r\n\r\n return false;\r\n }\r\n\r\n supportsObjectLayerIsolation(camera: I3DCamera, objects: I3DObject[]): boolean {\r\n const anyCamera = camera as any;\r\n if (!anyCamera?.layers || typeof anyCamera.layers.set !== \"function\") {\r\n return false;\r\n }\r\n return objects.some((obj) => this.hasLayers(obj));\r\n }\r\n\r\n beginObjectLayerIsolation(\r\n camera: I3DCamera,\r\n objects: I3DObject[],\r\n lights: I3DObject[],\r\n layer: number,\r\n ): I3DLayerIsolationState | null {\r\n const anyCamera = camera as any;\r\n if (!anyCamera?.layers || typeof anyCamera.layers.set !== \"function\") {\r\n return null;\r\n }\r\n\r\n const restored = new Map<any, number>();\r\n const apply = (target: any, mode: \"set\" | \"enable\") => {\r\n if (!this.hasLayers(target)) return;\r\n if (!restored.has(target)) {\r\n restored.set(target, target.layers.mask);\r\n }\r\n if (mode === \"set\") {\r\n target.layers.set(layer);\r\n } else {\r\n target.layers.enable(layer);\r\n }\r\n };\r\n\r\n objects.forEach((obj) => apply(obj as any, \"set\"));\r\n lights.forEach((light) => apply(light as any, \"enable\"));\r\n\r\n const prevCameraMask = anyCamera.layers.mask;\r\n anyCamera.layers.set(layer);\r\n\r\n return {\r\n cameraMask: prevCameraMask,\r\n objectMasks: Array.from(restored.entries()).map(([object, mask]) => ({ object, mask })),\r\n };\r\n }\r\n\r\n endObjectLayerIsolation(camera: I3DCamera, state: I3DLayerIsolationState): void {\r\n const anyCamera = camera as any;\r\n const anyState = state as any;\r\n\r\n if (Array.isArray(anyState?.objectMasks)) {\r\n anyState.objectMasks.forEach((entry: any) => {\r\n const object = entry?.object;\r\n const mask = entry?.mask;\r\n if (this.hasLayers(object) && typeof mask === \"number\") {\r\n object.layers.mask = mask;\r\n }\r\n });\r\n }\r\n\r\n if (anyCamera?.layers && typeof anyState?.cameraMask === \"number\") {\r\n anyCamera.layers.mask = anyState.cameraMask;\r\n }\r\n }\r\n\r\n applyMaterialProps(material: I3DMaterial, props: I3DMaterialVisualProps): boolean {\r\n const mat = material as any;\r\n if (!mat) return false;\r\n\r\n let applied = false;\r\n\r\n if (typeof props.opacity === \"number\" && Number.isFinite(props.opacity)) {\r\n mat.opacity = props.opacity;\r\n if (\"transparent\" in mat) {\r\n mat.transparent = props.opacity < 1;\r\n }\r\n applied = true;\r\n }\r\n\r\n if (props.color && mat.color && typeof mat.color.set === \"function\") {\r\n try {\r\n mat.color.set(props.color);\r\n applied = true;\r\n } catch { }\r\n }\r\n\r\n if (typeof props.metalness === \"number\" && Number.isFinite(props.metalness) && \"metalness\" in mat) {\r\n mat.metalness = props.metalness;\r\n applied = true;\r\n }\r\n\r\n if (typeof props.roughness === \"number\" && Number.isFinite(props.roughness) && \"roughness\" in mat) {\r\n mat.roughness = props.roughness;\r\n applied = true;\r\n }\r\n\r\n if (props.emissive && mat.emissive && typeof mat.emissive.set === \"function\") {\r\n try {\r\n mat.emissive.set(props.emissive);\r\n applied = true;\r\n } catch { }\r\n }\r\n\r\n return applied;\r\n }\r\n\r\n private hasLayers(target: any): boolean {\r\n return !!target?.layers && typeof target.layers.set === \"function\";\r\n }\r\n\r\n simplifyGeometry(geometry: I3DGeometry, quality: number): I3DGeometry | null {\r\n const Modifier = (this.THREE as any)?.SimplifyModifier;\r\n if (!Modifier) return null;\r\n const anyGeom: any = geometry as any;\r\n const count = anyGeom?.attributes?.position?.count;\r\n if (!Number.isFinite(count)) return null;\r\n const clamped = Math.max(0.05, Math.min(1, quality));\r\n const target = Math.max(3, Math.floor(count * clamped));\r\n if (target >= count) return geometry;\r\n try {\r\n const modifier = new Modifier();\r\n return modifier.modify(anyGeom, target);\r\n } catch {\r\n return null;\r\n }\r\n }\r\n\r\n degToRad(degrees: number): number {\r\n return this.THREE.MathUtils.degToRad(degrees);\r\n }\r\n\r\n radToDeg(radians: number): number {\r\n return this.THREE.MathUtils.radToDeg(radians);\r\n }\r\n\r\n computeBoundingBoxRecursively(object: I3DObject): I3DBox3 {\r\n const boundingBox = new this.THREE.Box3();\r\n let hasBox = false;\r\n\r\n if (object.traverse) {\r\n object.traverse((child: any) => {\r\n if (!child.visible) return;\r\n if (child.geometry) {\r\n if (typeof child.geometry.computeBoundingBox === \"function\") {\r\n child.geometry.computeBoundingBox();\r\n }\r\n const box = child.geometry.boundingBox;\r\n if (box) {\r\n const childBox = box.clone().applyMatrix4(child.matrixWorld);\r\n boundingBox.union(childBox);\r\n hasBox = true;\r\n }\r\n }\r\n });\r\n }\r\n\r\n return hasBox ? boundingBox : new this.THREE.Box3();\r\n }\r\n\r\n getBackend(): I3DBackend {\r\n return \"webgl\";\r\n }\r\n\r\n getCapabilities(): I3DEngineCapabilities {\r\n return {\r\n renderTargets: true,\r\n shaderMaterials: true,\r\n postProcess: true,\r\n customMaterialFactory: true,\r\n particles: true,\r\n text: true,\r\n geometrySimplify: !!(this.THREE as any)?.SimplifyModifier,\r\n };\r\n }\r\n\r\n getPostProcessRuntime(): I3DPostProcessRuntime {\r\n return {\r\n isSupported: (renderer: I3DRenderer) => typeof renderer.setRenderTarget === \"function\",\r\n createRenderTarget: (width: number, height: number, options?: any) =>\r\n this.createRenderTarget(width, height, options),\r\n createShaderMaterial: (params?: any) => this.createShaderMaterial(params),\r\n setRenderTarget: (renderer: I3DRenderer, target: I3DRenderTarget | null) => {\r\n renderer.setRenderTarget?.(target);\r\n },\r\n clear: (renderer: I3DRenderer, color = true, depth = true, stencil = true) => {\r\n renderer.clear?.(color, depth, stencil);\r\n },\r\n createPipeline: ({ engine, renderer, width, height, customFilterRegistry }) =>\r\n new ThreePostProcessPipeline({\r\n engine,\r\n renderer,\r\n runtime: this.getPostProcessRuntime(),\r\n width,\r\n height,\r\n customFilterRegistry,\r\n }),\r\n };\r\n }\r\n\r\n getCustomFilterRegistry(): I3DCustomFilterRegistryRuntime {\r\n return {\r\n get: (name: string) => String3DCustomFilterRegistry.get(name),\r\n };\r\n }\r\n\r\n getCustomMaterialRegistry(): I3DCustomMaterialRegistryRuntime {\r\n return {\r\n get: (name: string) => String3DCustomMaterialRegistry.get(name),\r\n };\r\n }\r\n}\r\n\r\nexport class ThreeJSProvider implements I3DEngineProvider {\r\n private engine: ThreeJSEngine;\r\n\r\n constructor(THREE: any, loaders: Record<string, any> = {}) {\r\n this.engine = new ThreeJSEngine(THREE, loaders);\r\n }\r\n\r\n initialize(): void { }\r\n\r\n getEngine(): I3DEngine {\r\n return this.engine;\r\n }\r\n\r\n getName(): string {\r\n return \"Three.js\";\r\n }\r\n\r\n getBackend(): I3DBackend {\r\n return this.engine.getBackend?.() ?? \"webgl\";\r\n }\r\n\r\n getCapabilities(): I3DEngineCapabilities {\r\n return (\r\n this.engine.getCapabilities?.() || {\r\n renderTargets: false,\r\n shaderMaterials: false,\r\n postProcess: false,\r\n customMaterialFactory: false,\r\n particles: false,\r\n text: false,\r\n geometrySimplify: false,\r\n }\r\n );\r\n }\r\n}\r\n"],"mappings":"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","names":["StringModule","String3DCamera","engine","mode","fov","near","far","width","height","ortho","x","y","z","screenX","screenY","normalizedX","normalizedY","distance","viewportHeight","roundedZ","scale","DEFAULT_CAPABILITIES","resolveEngineCapabilities","engine","reported","resolvePostProcessRuntime","engine","renderer","explicit","capabilities","resolveEngineCapabilities","width","height","options","params","activeRenderer","target","color","depth","stencil","String3DCustomFilterRegistry","definition","name","backend","def","impl","String3DFilterPipeline","engine","renderer","runtime","width","height","customFilterRegistry","String3DCustomFilterRegistry","scale","input","effects","quality","target","String3DRenderer","container","engine","width","height","configuredPixelRatio","pixelRatio","resolvePostProcessRuntime","scene","camera","filterTargets","pipeline","allObjects","visibility","obj","anyObj","filteredSet","target","rendererAny","prevAutoClear","originalVisible","lights","supportsLayerIsolation","entry","usedVisibilityFallback","cache","effects","allowed","isolationState","subtree","input","output","existing","runtime","String3DFilterPipeline","object","set","child","visible","el","cached","rect","cx","cy","clamp","value","effect","center","changed","next","uniforms","filterCount","now","dt","fps","countScale","targetScale","maxAge","key","String3DObject","id","type","object","engine","options","child","originalScale","matrix","pos","quat","scale","position","quaternion","euler","value","mat","texture","material","geometry","result","walk","obj","anyObj","childMat","StyleReader","el","prop","fallback","mapValue","val","num","raw","value","norm","readNumberStyle","parsed","stripQuotes","readStringStyle","style","readBooleanStyle","normalized","readFilterRaw","styleMap","String3DCustomMaterialRegistry","definition","name","css","uniforms","def","cssVar","syntax","type","parseUniformValue","def","cssValue","trimmed","num","parts","s","n","parseColorValue","match","value","hex","r","g","b","rgbMatch","collectUniformsFromCSS","definition","element","style","result","parsed","key","mergeInjections","injections","grouped","injection","list","point","sorted","i","String3DScene","engine","options","String3DCustomMaterialRegistry","synchronizer","id","element","el","result","walk","obj","child","root","object","type","onAdd","added3DObject","parentId","group","String3DObject","kind","colorRaw","readStringStyle","color","intensity","readNumberStyle","light","distance","decay","angle","penumbra","groundRaw","groundColor","readBooleanStyle","bias","mapSize","mesh","castShadow","receiveShadow","geometry","material","quality","widthSegments","heightSegments","segments","modelPath","loaderType","loader","loaderOptions","shouldCenter","loadedModel","overrideMaterial","config","system","bbox","center","box","style","getCSS","prop","resolve","cssProp","parser","defaultValue","cssVal","parseNumber","v","parseColor","parseUrl","match","customMaterial","opacity","metalness","roughness","emissive","params","mapSrc","normalMapSrc","roughnessMapSrc","metalnessMapSrc","aoMapSrc","flipY","colorSpace","hasMaps","finalType","definition","factory","initialUniforms","instance","objectId","uniforms","oldInstance","stringObject","newMaterial","current","mat","src","texture","value","normalized","hasStyle","val","baseRaw","mappingRaw","parsed","StyleBundleCache","el","ctx","reader","isDirty","cached","now","interval","metaData","bundle","DEG_TO_RAD","_GroupSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","styles","StyleReader","StyleBundleCache","GroupSynchronizer","_LightSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenAnchor","translateX","translateY","frustum","normalizedX","normalizedY","light","targetEl","tCached","tRect","tStyles","StyleReader","tTranslateX","tTranslateY","tTranslateZ","tScreenAnchor","tOffsetX","tOffsetY","x","y","z","styles","groundColor","targetId","offsetRaw","offset","value","parts","part","num","target","StyleBundleCache","LightSynchronizer","DEG_TO_RAD","parseCssColorToRgb","value","raw","normalized","g","b","rgb","parts","part","num","isBlackCssColor","parsed","applyColorToTarget","target","_MeshSynchronizer","el","emissive","object","engine","props","prev","castShadow","receiveShadow","opacity","materialProps","applyMaterialProps","mat","mesh","ctx","parentData","rect","originalWidth","originalHeight","bundle","translateZ","cssScale","rotateX","rotateY","rotateZ","cssScaleZ","color","metalness","roughness","geometryQuality","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","targetWidth","targetHeight","parentScale","baseScaleZ","minTargetSize","scaleX","scaleY","scaleZ","uniformSize","bbox","size","fitMode","modelScale","finalModelScale","scaleW","scaleH","uniformScale","fallbackSize","quality","simplify","applyToMesh","original","lodCache","key","simplified","factory","style","apply","definition","values","def","converter","converted","styleMap","readNumber","prop","fallback","mapValue","val","readString","readBool","norm","cached","width","height","StyleBundleCache","MeshSynchronizer","DEG_TO_RAD","DEFAULT_CONFIG","_ParticlesSynchronizer","el","object","ctx","parentData","cached","rect","bundle","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","parentScale","scale","config","prev","particleSystem","now","last","dt","styles","StyleReader","mode","property","style","properties","durations","index","shorthand","match","value","result","current","depth","i","ch","name","normalized","prop","raw","num","map","part","tokens","duration","token","lower","fallback","parts","fitMultiplier","spread","spreadX","spreadY","z","perPixel","a","b","type","definition","String3DCustomMaterialRegistry","factory","existing","initialUniforms","instance","material","isShader","apply","mat","values","key","def","converter","converted","StyleBundleCache","ParticlesSynchronizer","String3DFontRegistry","name","url","normalized","fontFamily","families","value","family","entry","opentypePromise","opentypeModule","woff2Promise","woff2Module","loadOpentype","resolve","reject","script","loadWoff2Decoder","attempts","maxAttempts","checkReady","win","decompressWoff2","buffer","woff2","inputArray","outputArray","newBuffer","isWoff2","FontConverter","source","cacheKey","cached","loading","promise","result","opentype","loadOpentype","buffer","isWoff2","decompressWoff2","font","scale","glyphs","cmap","codeStr","glyphIndex","code","glyph","path","outline","advanceWidth","char","i","unicodeValues","spaceGlyph","commands","cmd","value","url","lower","DEG_TO_RAD","PSEUDO_ELEMENT_CSS","_TextSynchronizer","fontUrl","object","set","obj","style","el","textContent","computed","rx","ry","rz","tx","ty","tz","s","transform","resolveObject","lastContent","observer","mutations","currentContent","currentObject","ctx","parentData","rect","originalWidth","originalHeight","bundle","translateZ","cssScale","rotateX","rotateY","rotateZ","cssScaleZ","opacity","color","metalness","roughness","emissive","castShadow","receiveShadow","materialType","fontFamily","fontSize","textTransform","textDepth","textCurveSegments","bevelEnabled","bevelSize","bevelThickness","bevelOffset","bevelSegments","fontCss","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","layout","l","mesh","fontEntry","String3DFontRegistry","font","promise","loaded","layoutSig","effectiveLayoutSig","key","geometry","parentScale","perPixel","scaleFactor","scaleZ","localOffsetX","localOffsetY","prevMaterialType","scene","MeshSynchronizer","range","elRect","walker","node","text","i","char","rects","r","x","y","visibleChar","normalized","line","factory","apply","mat","definition","values","value","def","converter","converted","styleMap","readNumber","prop","fallback","mapValue","val","num","raw","readString","readBool","norm","colorVar","parsed","lineHeight","letterSpacing","fit","depthRaw","depth","alignRaw","align","computedFont","match","cached","StyleBundleCache","TextSynchronizer","IDENTITY","DEFAULT_RENDER_STATE","isIdentity","m","multiplyMatrices","m1","m2","parseTransformAttribute","transform","result","parts","part","match","type","args","mat","sx","sy","angle","cos","sin","cx","cy","getElementTransformMatrix","el","parseStyleAttribute","style","entries","chunk","colonIndex","key","value","getPresentationValue","name","styleValue","attrValue","parseNumericValue","fallback","normalized","parsed","computeRenderState","parentState","display","visibility","opacity","fill","fillOpacity","shouldCollectGeometry","tag","d","renderState","rectToPath","x","y","w","h","rxRaw","ryRaw","rx","ry","rx2","ry2","circleToPath","r","ellipseToPath","polygonToPath","close","points","coords","pairs","i","lineToPath","x1","y1","x2","y2","elementToPathD","walkElement","parentMatrix","paths","localMatrix","accumulated","pathData","child","parseViewBox","svgEl","vb","SVGParser","_SVGParser","viewBox","naturalWidth","naturalHeight","svgString","doc","DEG_TO_RAD","easeInOut","t","_SVGSynchronizer","el","object","ctx","parentData","rect","bundle","translateZ","cssScale","rotateX","rotateY","rotateZ","cssScaleZ","opacity","color","metalness","roughness","emissive","castShadow","receiveShadow","materialType","svgDepth","svgCurveSegments","bevelEnabled","bevelSize","bevelThickness","bevelOffset","bevelSegments","svgSrc","morphDuration","screenCenterX","screenCenterY","frustum","normalizedX","normalizedY","mesh","svgData","currentSig","p","prevSig","morphFactor","morphRotationBonus","morphState","elapsed","raw","eased","vb","svgW","svgH","svgScale","key","scaledPaths","scaledViewBox","geometry","parentScale","perPixel","scaleFactor","mf","prevMaterialType","scene","MeshSynchronizer","observer","inlineSvg","cached","data","SVGParser","src","promise","r","text","set","obj","_object","styleMap","style","readNumber","prop","fallback","mapValue","val","num","readString","readBool","norm","colorVar","depthRaw","StyleBundleCache","SVGSynchronizer","String3DSynchronizer","camera","viewportWidth","viewportHeight","engine","MeshSynchronizer","GroupSynchronizer","LightSynchronizer","ParticlesSynchronizer","TextSynchronizer","SVGSynchronizer","el","object","parentData","hints","strategy","options","scene","width","height","DirtySyncManager","attributeFilter","el","rootObjects","obj","object","child","entries","entry","mutations","mutation","FilterController","easingParser","String3DCustomFilterRegistry","registry","rootObjects","now","useDirtySync","dirtySet","targets","walk","obj","el","animating","shouldReadStyle","chain","dirty","effectsKey","child","existing","raw","readFilterRaw","current","duration","delay","easing","zero","effects","warnings","state","newState","t","canTween","fromChain","parseNumber","value","match","num","parseRatio","cleaned","parseAngle","stripped","parseBloom","parts","part","intensity","threshold","parseAmount","name","allowZero","amount","parseRatioAmount","re","args","size","bloom","angle","custom","parsed","style","properties","durations","delays","timings","index","shorthand","fallback","easingRaw","result","depth","i","ch","normalized","prop","map","tokens","token","lower","fn","from","to","effect","other","keys","otherKeys","key","uniforms","elapsed","eased","interpolated","lerp","a","b","fromValue","_String3D","StringModule","context","DirtySyncManager","FilterController","value","provider","name","url","options","String3DFontRegistry","object","globalId","element","attributes","parentElement","parentId","initResult","String3DRenderer","String3DCamera","modelLoader","modelLoaderFactory","String3DScene","String3DSynchronizer","pending","shouldUseDirtySync","key","fallback","engine","type","loaderType","existing","container","el","nodeType","data","dirtySet","forceSync","obj","filterTargets","rootObjects","walk","rect","width","height","parentData","shouldSync","nextParentData","cached","forceChildren","child","style","css","initialValue","String3D","ThreeJSMaterialFactory","THREE","definition","initialUniforms","uniforms","material","newUniforms","element","style","collectUniformsFromCSS","values","shader","customUniforms","key","value","uniformDef","initialValues","result","def","type","url","texture","baseType","BaseMaterial","injectionMap","mergeInjections","injections","pars","header","uniformDeclarations","transform","output","color","normal","roughness","metalness","ao","transmission","lights","emissive","lines","name","uniform","props","newValues","RenderTargetPool","create","width","height","target","ThreePostProcessPipeline","context","engine","renderer","runtime","customFilterRegistry","geometry","w","h","scale","next","input","effects","quality","current","locals","releaseLocal","idx","acquire","effect","radius","first","second","output","intensity","blurRadius","extracted","blur1","blur2","combined","mode","amount","material","uniforms","clear","key","value","base","bloom","object","anyObj","name","type","params","normalized","def","impl","shaders","definition","byBackend","implementation","ThreeJSEngine","THREE","loaders","ThreeJSMaterialFactory","x","y","z","w","order","min","max","options","renderer","_context","anyRenderer","fov","aspect","near","far","left","right","top","bottom","geometry","material","width","height","depth","radius","widthSegments","heightSegments","radiusTop","radiusBottom","segments","params","color","intensity","distance","decay","angle","penumbra","skyColor","groundColor","type","LoaderClass","loader","manager","baseRaw","base","textureMap","url","mapped","resolved","loadedModel","defaults","normalized","cachedPromise","isFontFile","FontConverter","promise","fontData","font","resolve","text","size","normalizePosition","shapes","scale","char","glyph","xOffset","charShapes","outline","commands","minX","i","maxX","minY","px","py","polygon","inside","j","xi","yi","xj","yj","path","numSamples","p","points","maxY","contour","triangles","tri","a","b","c","cx","cy","offsetX","outlineFormat","shapePath","mx","my","lx","ly","qx","qy","bx","by","subPaths","paths","sp","area","bbox","finalShapes","used","outerPath","shape","innerPath","allPointsInside","testPoints","testPoint","newPath","lastCurve","endPoint","curve","lineHeight","letterSpacing","align","bevelEnabled","bevelThickness","bevelSize","bevelOffset","bevelSegments","curveSegments","lines","resolution","fontAscender","fontDescender","fontEmHeight","baselineRatio","elementWidth","elementHeight","centerOffsetX","centerOffsetY","item","baselineFromTop","offsetY","finalShape","line","index","lineShapes","viewBox","allSubpaths","pathData","subpaths","pt","allShapes","n","parent","d","shapeByIndex","srcPath","parentShape","holePath","outer","inner","outerPoly","stride","k","transform","tokens","startX","startY","lastCmd","lastCtrlX","lastCtrlY","applyTransform","cmd","isRelative","upper","nx","ny","tx","ty","qx1","qy1","tc1x","tc1y","tex","tey","cx1","cy1","cx2","cy2","ex","ey","tb1x","tb1y","tb2x","tb2y","tbex","tbey","rx","ry","xAxisRotation","largeArcFlag","sweepFlag","curves","x1","y1","x2","y2","xe","ye","signedArea","clockwise","re","match","v","xAxisRotationDeg","phi","cosPhi","sinPhi","dx","dy","x1p","y1p","x1pSq","y1pSq","rxSq","rySq","lambda","sqrtLambda","sign","num","den","sq","cxp","cyp","ux","uy","vx","vy","angle1","dAngle","delta","t","result","startAngle","s","endAngle","cosStart","sinStart","cosEnd","sinEnd","px1","py1","px2","py2","dx1","dy1","dx2","dy2","chars","translated","advance","data","glyphs","ha","matrix","holes","toVec2","newShape","hole","modelUrl","loaderType","nodeName","normalizedLoader","nodeKey","cacheKey","gltf","root","mesh","found","child","config","engine","makeRng","seed","ParticleSystem","cfg","prev","emitterReset","uniforms","key","count","pos","elapsed","progress","eased","i3","targetArray","attr","array","itemSize","vertexCount","indexArray","triangleCount","minZ","maxZ","idx","sizeX","sizeY","sizeZ","targetX","targetY","scaleX","scaleY","centerX","centerY","centerZ","cumulativeAreas","totalArea","ia","ib","ic","ax","ay","az","bz","cz","abx","aby","abz","acx","acy","acz","crossX","crossY","crossZ","r","lo","hi","mid","u","su","w1","w2","w3","dt","needsModel","hasModel","hide","useSharedGeometry","setPoints","dir","gravity","drag","totalToEmit","emitCount","colorDirty","speed","vel","time","jitter","flow","disperse","scatter","scatterX","scatterY","scatterZ","rotSpeed","temp","baseX","baseY","baseZ","phase","driftX","driftY","driftZ","jitterX","jitterY","jitterZ","dispersal","dirX","dirY","dirZ","dirLen","scatterScale","scatterOffsetX","scatterOffsetY","scatterOffsetZ","next","vec","len","theta","half","object","callback","visit","node","anyObject","mat","first","anyGeometry","target","camera","objects","anyCamera","obj","lights","layer","restored","apply","mode","light","prevCameraMask","mask","state","anyState","entry","props","applied","quality","Modifier","anyGeom","clamped","degrees","radians","boundingBox","hasBox","box","childBox","stencil","customFilterRegistry","ThreePostProcessPipeline","name","String3DCustomFilterRegistry","String3DCustomMaterialRegistry","ThreeJSProvider"]}