Pārlūkot izejas kodu

Optimize picking when detectPointerOnOpaqueOnly is true (#8661)

Popov72 5 gadi atpakaļ
vecāks
revīzija
acfda85448
1 mainītis faili ar 20 papildinājumiem un 4 dzēšanām
  1. 20 4
      gui/src/2D/controls/image.ts

+ 20 - 4
gui/src/2D/controls/image.ts

@@ -39,6 +39,11 @@ export class Image extends Control {
 
     private _detectPointerOnOpaqueOnly: boolean;
 
+    private _imageDataCache: {
+                data: Uint8ClampedArray | null;
+                key: string;
+            } = { data: null, key: "" };
+
     /**
      * Observable notified when the content is loaded
      */
@@ -301,6 +306,8 @@ export class Image extends Control {
 
         this._handleRotationForSVGImage(this, rotatedImage, n);
 
+        this._imageDataCache.data = null;
+
         return rotatedImage;
     }
 
@@ -361,6 +368,7 @@ export class Image extends Control {
     public set domImage(value: HTMLImageElement) {
         this._domImage = value;
         this._loaded = false;
+        this._imageDataCache.data = null;
 
         if (this._domImage.width) {
             this._onImageLoaded();
@@ -453,6 +461,7 @@ export class Image extends Control {
 
         this._loaded = false;
         this._source = value;
+        this._imageDataCache.data = null;
 
         if (value) {
             value = this._svgCheck(value);
@@ -632,16 +641,23 @@ export class Image extends Control {
             return true;
         }
 
-        const canvas = this._workingCanvas;
-        const context = canvas.getContext("2d")!;
         const width = this._currentMeasure.width | 0;
         const height = this._currentMeasure.height | 0;
-        const imageData = context.getImageData(0, 0, width, height).data;
+        const key = width + "_" + height;
+
+        let imageData = this._imageDataCache.data;
+
+        if (!imageData || this._imageDataCache.key !== key) {
+            const canvas = this._workingCanvas;
+            const context = canvas.getContext("2d")!;
+
+            this._imageDataCache.data = imageData = context.getImageData(0, 0, width, height).data;
+        }
 
         x = (x - this._currentMeasure.left) | 0;
         y = (y - this._currentMeasure.top) | 0;
 
-        const pickedPixel = imageData[(x + y * this._currentMeasure.width) * 4 + 3];
+        const pickedPixel = imageData[(x + y * width) * 4 + 3];
 
         return pickedPixel > 0;
     }