diff --git a/src/core/CoreTextNode.ts b/src/core/CoreTextNode.ts index 0e9a1d2..15bc9da 100644 --- a/src/core/CoreTextNode.ts +++ b/src/core/CoreTextNode.ts @@ -239,27 +239,23 @@ export class CoreTextNode extends CoreNode implements CoreTextNodeProps { // Handle Canvas renderer (uses ImageData) if (textRendererType === 'canvas') { if (result.imageData === undefined) { - this.emit('failed', { - type: 'text', - error: new Error( - 'Canvas text rendering failed, no image data returned', - ), - } satisfies NodeTextFailedPayload); - return; - } - - this.texture = this.stage.txManager.createTexture('ImageTexture', { - premultiplyAlpha: true, - src: result.imageData as ImageData, - }); - // It isn't renderable until the texture is loaded we have to set it to false here to avoid it - // being detected as a renderable default color node in the next frame - // it will be corrected once the texture is loaded - this.setRenderable(false); - - if (this.renderState > CoreNodeRenderState.OutOfBounds) { - // We do want the texture to load immediately - this.texture.setRenderableOwner(this._id, true); + // Empty text returns no imageData — mark not renderable and continue + // to update dimensions (w=0, h=0) rather than emitting a failure. + this.setRenderable(false); + } else { + this.texture = this.stage.txManager.createTexture('ImageTexture', { + premultiplyAlpha: true, + src: result.imageData as ImageData, + }); + // It isn't renderable until the texture is loaded we have to set it to false here to avoid it + // being detected as a renderable default color node in the next frame + // it will be corrected once the texture is loaded + this.setRenderable(false); + + if (this.renderState > CoreNodeRenderState.OutOfBounds) { + // We do want the texture to load immediately + this.texture.setRenderableOwner(this._id, true); + } } } diff --git a/src/core/CoreTextureManager.ts b/src/core/CoreTextureManager.ts index 16e9c5f..5fd673d 100644 --- a/src/core/CoreTextureManager.ts +++ b/src/core/CoreTextureManager.ts @@ -340,8 +340,6 @@ export class CoreTextureManager extends EventEmitter { * @param immediate - Whether to prioritize the texture for immediate loading */ async loadTexture(texture: Texture, priority?: boolean): Promise { - this.stage.txMemManager.removeFromOrphanedTextures(texture); - if (texture.type === TextureType.subTexture) { // ignore subtextures - they get loaded through their parent return; diff --git a/src/core/TextureMemoryManager.ts b/src/core/TextureMemoryManager.ts index 80548b4..361db79 100644 --- a/src/core/TextureMemoryManager.ts +++ b/src/core/TextureMemoryManager.ts @@ -98,7 +98,6 @@ export interface MemoryInfo { export class TextureMemoryManager { private memUsed = 0; private loadedTextures: Set = new Set(); - private orphanedTextures: Set = new Set(); private criticalThreshold: number = 124e6; private targetThreshold: number = 0.5; private cleanupInterval: number = 5000; @@ -127,32 +126,6 @@ export class TextureMemoryManager { this.updateSettings(settings); } - /** - * Add a texture to the orphaned textures list - * - * @param texture - The texture to add to the orphaned textures list - */ - addToOrphanedTextures(texture: Texture) { - // if the texture is already in the orphaned textures list add it at the end - if (this.orphanedTextures.has(texture)) { - this.orphanedTextures.delete(texture); - } - - // If the texture can be cleaned up, add it to the orphaned textures list - if (texture.preventCleanup === false) { - this.orphanedTextures.add(texture); - } - } - - /** - * Remove a texture from the orphaned textures list - * - * @param texture - The texture to remove from the orphaned textures list - */ - removeFromOrphanedTextures(texture: Texture) { - this.orphanedTextures.delete(texture); - } - /** * Set the memory usage of a texture * diff --git a/src/core/text-rendering/CanvasTextRenderer.ts b/src/core/text-rendering/CanvasTextRenderer.ts index 42df42f..297e58d 100644 --- a/src/core/text-rendering/CanvasTextRenderer.ts +++ b/src/core/text-rendering/CanvasTextRenderer.ts @@ -77,6 +77,14 @@ const renderText = (props: CoreTextNodeProps): TextRenderInfo => { assertTruthy(canvas, 'Canvas is not initialized'); assertTruthy(context, 'Canvas context is not available'); assertTruthy(measureContext, 'Canvas measureContext is not available'); + + if (props.text.length === 0) { + return { + width: 0, + height: 0, + }; + } + // Extract already normalized properties const { text,