UNPKG

lume

Version:

Build next-level interactive web applications.

61 lines (48 loc) 1.61 kB
import {untrack, onCleanup} from 'solid-js' import {MeshBehavior, type MeshComponentType} from './MeshBehavior.js' import type {Material} from 'three/src/materials/Material.js' import type {BufferGeometry} from 'three/src/core/BufferGeometry.js' /** * @class GeometryOrMaterialBehavior * Abstract base class for Geometry and Material behaviors, not intended for direct use. * * Subclasses should implement: * _createComponent() - return a BufferGeometry or Material instance. * * @extends MeshBehavior */ export abstract class GeometryOrMaterialBehavior extends MeshBehavior { abstract type: MeshComponentType override connectedCallback() { super.connectedCallback() this.createEffect(() => this.resetMeshComponent()) } resetMeshComponent(): void { this.#setMeshComponent() this.element.needsUpdate() onCleanup(this.#disposeMeshComponent) } override _createComponent(): BufferGeometry | Material { throw new Error('`_createComponent()` is not implemented by subclass.') } // records the initial size of the geometry, so that we have a // reference for how much scale to apply when accepting new sizes from // the user. // TODO // #initialSize: null, #disposeMeshComponent = () => { // TODO handle material arrays this.meshComponent?.dispose() this.meshComponent = null } #setMeshComponent() { const newComponent = this._createComponent() // untrack in case we make .three reactive later untrack(() => { // @ts-expect-error FIXME this.element.three[this.type] = newComponent }) // @ts-expect-error this.meshComponent = newComponent } }