From 0bae8c9c9da0c27b9bffd5affcd09e2af8d84215 Mon Sep 17 00:00:00 2001 From: Dariusz L Date: Mon, 28 Jul 2025 16:38:45 +0200 Subject: [PATCH] fixed the persistent shape preview bug fixed the persistent shape preview bug where blue dashed lines would remain visible even when the user was no longer interacting with the slider. The issue was caused by race conditions and timing problems in the preview system. --- js/CustomShapeMenu.js | 4 ++++ js/MaskTool.js | 9 ++++++++- src/CustomShapeMenu.ts | 5 +++++ src/MaskTool.ts | 11 ++++++++++- 4 files changed, 27 insertions(+), 2 deletions(-) diff --git a/js/CustomShapeMenu.js b/js/CustomShapeMenu.js index a1a0be0..2bde6a1 100644 --- a/js/CustomShapeMenu.js +++ b/js/CustomShapeMenu.js @@ -88,6 +88,8 @@ export class CustomShapeMenu { `; // Add main auto-apply checkbox to the new container const checkboxContainer = this._createCheckbox(() => `${this.canvas.autoApplyShapeMask ? "☑" : "☐"} Auto-apply shape mask`, () => { + // Always hide any active shape preview lines first to prevent them from getting stuck + this.canvas.maskTool.hideShapePreview(); this.canvas.autoApplyShapeMask = !this.canvas.autoApplyShapeMask; if (this.canvas.autoApplyShapeMask) { this.canvas.maskTool.applyShapeMask(); @@ -108,6 +110,7 @@ export class CustomShapeMenu { this.canvas.shapeMaskExpansion = !this.canvas.shapeMaskExpansion; this._updateUI(); if (this.canvas.autoApplyShapeMask) { + this.canvas.maskTool.hideShapePreview(); this.canvas.maskTool.applyShapeMask(); this.canvas.render(); } @@ -201,6 +204,7 @@ export class CustomShapeMenu { this.canvas.shapeMaskFeather = !this.canvas.shapeMaskFeather; this._updateUI(); if (this.canvas.autoApplyShapeMask) { + this.canvas.maskTool.hideShapePreview(); this.canvas.maskTool.applyShapeMask(); this.canvas.render(); } diff --git a/js/MaskTool.js b/js/MaskTool.js index ca53eee..b4e67e2 100644 --- a/js/MaskTool.js +++ b/js/MaskTool.js @@ -1005,11 +1005,18 @@ export class MaskTool { * Hide shape preview and switch back to normal mode */ hideShapePreview() { + // Cancel any pending throttled preview updates to prevent race conditions + if (this.shapePreviewThrottleTimeout !== null) { + clearTimeout(this.shapePreviewThrottleTimeout); + this.shapePreviewThrottleTimeout = null; + } + // Clear any pending preview parameters + this.pendingPreviewParams = null; this.isPreviewMode = false; this.shapePreviewVisible = false; this.clearShapePreview(); this.shapePreviewCanvas.style.display = 'none'; - log.debug("Shape preview hidden"); + log.debug("Shape preview hidden and all pending operations cancelled"); } /** * Clear shape preview canvas diff --git a/src/CustomShapeMenu.ts b/src/CustomShapeMenu.ts index 5b44fab..4a65893 100644 --- a/src/CustomShapeMenu.ts +++ b/src/CustomShapeMenu.ts @@ -113,6 +113,9 @@ export class CustomShapeMenu { const checkboxContainer = this._createCheckbox( () => `${this.canvas.autoApplyShapeMask ? "☑" : "☐"} Auto-apply shape mask`, () => { + // Always hide any active shape preview lines first to prevent them from getting stuck + this.canvas.maskTool.hideShapePreview(); + this.canvas.autoApplyShapeMask = !this.canvas.autoApplyShapeMask; if (this.canvas.autoApplyShapeMask) { @@ -140,6 +143,7 @@ export class CustomShapeMenu { this._updateUI(); if (this.canvas.autoApplyShapeMask) { + this.canvas.maskTool.hideShapePreview(); this.canvas.maskTool.applyShapeMask(); this.canvas.render(); } @@ -252,6 +256,7 @@ export class CustomShapeMenu { this._updateUI(); if (this.canvas.autoApplyShapeMask) { + this.canvas.maskTool.hideShapePreview(); this.canvas.maskTool.applyShapeMask(); this.canvas.render(); } diff --git a/src/MaskTool.ts b/src/MaskTool.ts index 0dd8ac4..015d6d7 100644 --- a/src/MaskTool.ts +++ b/src/MaskTool.ts @@ -1265,11 +1265,20 @@ export class MaskTool { * Hide shape preview and switch back to normal mode */ hideShapePreview(): void { + // Cancel any pending throttled preview updates to prevent race conditions + if (this.shapePreviewThrottleTimeout !== null) { + clearTimeout(this.shapePreviewThrottleTimeout); + this.shapePreviewThrottleTimeout = null; + } + + // Clear any pending preview parameters + this.pendingPreviewParams = null; + this.isPreviewMode = false; this.shapePreviewVisible = false; this.clearShapePreview(); this.shapePreviewCanvas.style.display = 'none'; - log.debug("Shape preview hidden"); + log.debug("Shape preview hidden and all pending operations cancelled"); } /**