@bensitu/image-editor 1.2.0 → 1.2.2
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.
- package/LICENSE +20 -20
- package/README.md +220 -208
- package/dist/image-editor.esm.js +2566 -0
- package/dist/image-editor.esm.js.map +7 -0
- package/dist/image-editor.esm.min.js +3 -8
- package/dist/image-editor.esm.min.js.map +4 -4
- package/dist/image-editor.esm.min.mjs +9 -0
- package/dist/image-editor.esm.min.mjs.map +7 -0
- package/dist/image-editor.esm.mjs +2566 -0
- package/dist/image-editor.esm.mjs.map +7 -0
- package/dist/image-editor.js +2563 -0
- package/dist/image-editor.js.map +7 -0
- package/dist/image-editor.min.js +3 -8
- package/dist/image-editor.min.js.map +4 -4
- package/image-editor.d.ts +203 -0
- package/package.json +84 -71
- package/src/browser.js +11 -0
- package/src/esm.js +9 -0
- package/src/image-editor.js +1518 -804
|
@@ -1,14 +1,9 @@
|
|
|
1
|
-
|
|
1
|
+
import M from"fabric";/**
|
|
2
2
|
* @file image-editor.js
|
|
3
3
|
* @module image-editor
|
|
4
|
-
* @version 1.2.
|
|
4
|
+
* @version 1.2.2
|
|
5
5
|
* @author Ben Situ
|
|
6
6
|
* @license MIT
|
|
7
7
|
* @description Lightweight canvas-based image editor with masking/transform/export support.
|
|
8
|
-
*
|
|
9
|
-
* This source file is free software, available under the MIT license.
|
|
10
|
-
* It is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
|
|
11
|
-
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
12
|
-
* See the license files for details.
|
|
13
|
-
*/(function(u,l){typeof define=="function"&&define.amd?define([],l):(typeof N>"u"?"undefined":F(N))==="object"&&N.exports?N.exports=l():u.ImageEditor=l()})(typeof self<"u"?self:K,function(){"use strict";var u=function(){function S(){var o=arguments.length>0&&arguments[0]!==void 0?arguments[0]:{};z(this,S),this._fabricLoaded=typeof fabric<"u",this._fabricLoaded||console.error("fabric.js is not loaded. Please include fabric.js first. Initialization will be aborted."),this.options=H({canvasWidth:800,canvasHeight:600,backgroundColor:"transparent",animationDuration:300,minScale:.1,maxScale:5,scaleStep:.05,rotationStep:90,expandCanvasToImage:!0,fitImageToCanvas:!1,coverImageToCanvas:!1,downsampleOnLoad:!0,downsampleMaxWidth:4e3,downsampleMaxHeight:3e3,downsampleQuality:.92,exportMultiplier:1,exportImageAreaByDefault:!0,defaultMaskWidth:50,defaultMaskHeight:80,maskRotatable:!1,maskLabelOnSelect:!0,maskLabelOffset:3,maskName:"mask",groupSelection:!1,showPlaceholder:!0,initialImageBase64:null,defaultDownloadFileName:"edited_image.jpg"},o),this.options.label={getText:function(a,n){return a.maskName},textOptions:{fontSize:12,fill:"#fff",backgroundColor:"rgba(0,0,0,0.7)",padding:2,fontFamily:"monospace",fontWeight:"bold",selectable:!1,evented:!1,originX:"left",originY:"top"}},this.options.crop={minWidth:100,minHeight:100,padding:10,hideMasksDuringCrop:!0,preserveMasksAfterCrop:!0,allowRotationOfCropRect:!1},this.canvas=null,this.canvasEl=null,this.containerEl=null,this.placeholderEl=null,this.originalImage=null,this.baseImageScale=1,this.currentScale=1,this.currentRotation=0,this.maskCounter=0,this.isAnimating=!1,this.elements={},this.isImageLoadedToCanvas=!1,this.maxHistorySize=50,this._boundHandlers={},this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null,this._cropMode=!1,this._cropRect=null,this._cropHandlers=[],this.onImageLoaded=typeof o.onImageLoaded=="function"?o.onImageLoaded:null,this.animQueue=new l,this.historyManager=new y(this.maxHistorySize)}return Q(S,[{key:"init",value:function(){var t=arguments.length>0&&arguments[0]!==void 0?arguments[0]:{};if(this._fabricLoaded){var a={canvas:"fabricCanvas",canvasContainer:null,imgPlaceholder:"imgPlaceholder",scaleRate:"scaleRate",rotationLeftInput:"rotationLeftInput",rotationRightInput:"rotationRightInput",rotateLeftBtn:"rotateLeftBtn",rotateRightBtn:"rotateRightBtn",addMaskBtn:"addMaskBtn",removeMaskBtn:"removeMaskBtn",removeAllMasksBtn:"removeAllMasksBtn",mergeBtn:"mergeBtn",downloadBtn:"downloadBtn",maskList:"maskList",zoomInBtn:"zoomInBtn",zoomOutBtn:"zoomOutBtn",resetBtn:"resetBtn",undoBtn:"undoBtn",redoBtn:"redoBtn",imageInput:"imageInput",cropBtn:"cropBtn",applyCropBtn:"applyCropBtn",cancelCropBtn:"cancelCropBtn"};this.elements=H(H({},a),t),this._initCanvas(),this._bindEvents(),this._updateInputs(),this._updateMaskList(),this._updateUI(),this.options.initialImageBase64?this.loadImage(this.options.initialImageBase64):this._updatePlaceholderStatus()}}},{key:"_initCanvas",value:function(){var t=this,a=document.getElementById(this.elements.canvas);if(!a)throw new Error("Canvas is not found: "+this.elements.canvas);if(this.canvasEl=a,this.elements.canvasContainer){var n=document.getElementById(this.elements.canvasContainer);this.containerEl=n||a.parentElement}else this.containerEl=a.parentElement;this.placeholderEl=document.getElementById(this.elements.imgPlaceholder)||null;var e=this.options.canvasWidth,i=this.options.canvasHeight;if(this.containerEl){var r=Math.floor(this.containerEl.clientWidth),c=Math.floor(this.containerEl.clientHeight);r>0&&c>0&&(e=r,i=c)}this.canvas=new fabric.Canvas(a,{width:e,height:i,backgroundColor:this.options.backgroundColor,selection:this.options.groupSelection,preserveObjectStacking:!0}),this.canvas.on("selection:created",function(s){return t._onSelectionChanged(s.selected)}),this.canvas.on("selection:updated",function(s){return t._onSelectionChanged(s.selected)}),this.canvas.on("selection:cleared",function(){return t._onSelectionChanged([])}),this.canvas.on("object:moving",function(s){s.target&&s.target.maskId&&t._syncMaskLabel(s.target)}),this.canvas.on("object:scaling",function(s){s.target&&s.target.maskId&&t._syncMaskLabel(s.target)}),this.canvas.on("object:rotating",function(s){s.target&&s.target.maskId&&t._syncMaskLabel(s.target)}),this.canvas.on("object:modified",function(s){s.target&&s.target.maskId&&t._syncMaskLabel(s.target)}),this.canvasEl.style.display="block"}},{key:"_bindEvents",value:function(){var t=this;this._bindIfExists("uploadArea","click",function(){var i;return(i=document.getElementById(t.elements.imageInput))===null||i===void 0?void 0:i.click()});var a=document.getElementById(this.elements.imageInput);a&&a.addEventListener("change",function(i){var r=i.target.files&&i.target.files[0];r&&t._loadImageFile(r)}),this._bindIfExists("zoomInBtn","click",function(){return t.scaleImage(t.currentScale+t.options.scaleStep)}),this._bindIfExists("zoomOutBtn","click",function(){return t.scaleImage(t.currentScale-t.options.scaleStep)}),this._bindIfExists("resetBtn","click",function(){t.reset()}),this._bindIfExists("addMaskBtn","click",function(){return t.addMask()}),this._bindIfExists("removeMaskBtn","click",function(){return t.removeSelectedMask()}),this._bindIfExists("removeAllMasksBtn","click",function(){return t.removeAllMasks()}),this._bindIfExists("mergeBtn","click",function(){return t.merge()}),this._bindIfExists("downloadBtn","click",function(){return t.downloadImage()}),this._bindIfExists("undoBtn","click",function(){return t.undo()}),this._bindIfExists("redoBtn","click",function(){return t.redo()});var n=document.getElementById(this.elements.rotateLeftBtn),e=document.getElementById(this.elements.rotateRightBtn);n&&n.addEventListener("click",function(){var i=document.getElementById(t.elements.rotationLeftInput),r=t.options.rotationStep;if(i){var c=parseFloat(i.value);isNaN(c)||(r=c)}t.rotateImage(t.currentRotation-r)}),e&&e.addEventListener("click",function(){var i=document.getElementById(t.elements.rotationRightInput),r=t.options.rotationStep;if(i){var c=parseFloat(i.value);isNaN(c)||(r=c)}t.rotateImage(t.currentRotation+r)}),this._bindIfExists("cropBtn","click",function(){return t.enterCropMode()}),this._bindIfExists("applyCropBtn","click",function(){t.applyCrop().catch(function(i){return console.error("applyCrop failed",i)})}),this._bindIfExists("cancelCropBtn","click",function(){return t.cancelCrop()})}},{key:"_bindIfExists",value:function(t,a,n){var e=document.getElementById(this.elements[t]);e&&(e.addEventListener(a,n),this._boundHandlers=this._boundHandlers||{},this._boundHandlers[t]||(this._boundHandlers[t]=[]),this._boundHandlers[t].push({event:a,handler:n}))}},{key:"_loadImageFile",value:function(t){var a=this;if(!(!t||!t.type.startsWith("image/"))){var n=new FileReader;n.onload=function(e){return a.loadImage(e.target.result)},n.onerror=function(e){console.error("[ImageEditor: fileReadError]",e)},n.readAsDataURL(t)}}},{key:"loadImage",value:function(){var o=D(P().m(function a(n){var e=this,i,r,c,s,d,m;return P().w(function(k){for(;;)switch(k.n){case 0:if(this._fabricLoaded){k.n=1;break}return k.a(2);case 1:if(!(!n||typeof n!="string"||!n.startsWith("data:image/"))){k.n=2;break}return k.a(2);case 2:return this._setPlaceholderVisible(!1),k.n=3,this._createImageElement(n);case 3:i=k.v,r=n,this.options.downsampleOnLoad&&(c=i.naturalWidth>this.options.downsampleMaxWidth||i.naturalHeight>this.options.downsampleMaxHeight,c&&(s=Math.min(this.options.downsampleMaxWidth/i.naturalWidth,this.options.downsampleMaxHeight/i.naturalHeight),d=Math.round(i.naturalWidth*s),m=Math.round(i.naturalHeight*s),r=this._resampleImageToDataURL(i,d,m,this.options.downsampleQuality))),fabric.Image.fromURL(r,function(v){e.canvas.discardActiveObject(),e._hideAllMaskLabels(),e.canvas.clear(),e.canvas.setBackgroundColor(e.options.backgroundColor,e.canvas.renderAll.bind(e.canvas)),v.set({originX:"left",originY:"top",selectable:!1,evented:!1});var A=v.width,w=v.height,L=e.containerEl?Math.floor(e.containerEl.clientWidth||e.options.canvasWidth):e.options.canvasWidth,j=e.containerEl?Math.floor(e.containerEl.clientHeight||e.options.canvasHeight):e.options.canvasHeight;if(e.options.fitImageToCanvas){var O=Math.max(1,Math.min(e.options.canvasWidth,L)-1),b=Math.max(1,Math.min(e.options.canvasHeight,j)-1);e._setCanvasSizeInt(O,b);var h=Math.min(O/A,b/w,1);v.set({left:0,top:0}),v.scale(h),e.baseImageScale=v.scaleX||1}else if(e.options.coverImageToCanvas){var g=Math.max(e.options.canvasWidth,L),p=Math.max(e.options.canvasHeight,j);e._setCanvasSizeInt(g,p);var f=Math.min(1,Math.max(g/A,p/w));v.set({left:0,top:0}),v.scale(f),e.baseImageScale=v.scaleX||1}else if(e.options.expandCanvasToImage){var _=Math.max(L,Math.floor(A)),E=Math.max(j,Math.floor(w));e._setCanvasSizeInt(_,E),v.set({left:0,top:0}),v.scale(1),e.baseImageScale=1}else{var B=Math.max(e.options.canvasWidth,L),C=Math.max(e.options.canvasHeight,j);e._setCanvasSizeInt(B,C);var M=Math.min(B/A,C/w,1);v.set({left:0,top:0}),v.scale(M),e.baseImageScale=v.scaleX||1}e.originalImage=v,e.canvas.add(v),e.canvas.sendToBack(v),e._lastMaskInitialLeft=null,e._lastMaskInitialTop=null,e._lastMaskInitialWidth=null,e.maskCounter=0,e.currentScale=1,e.currentRotation=0,e._updateInputs(),e._updateMaskList(),e._updateUI(),e.canvas.renderAll(),e.isImageLoadedToCanvas=!0,typeof e.onImageLoaded=="function"&&e.onImageLoaded()},{crossOrigin:"anonymous"});case 4:return k.a(2)}},a,this)}));function t(a){return o.apply(this,arguments)}return t}()},{key:"isImageLoaded",value:function(){return!!(this.originalImage&&this.originalImage instanceof fabric.Image&&this.originalImage.width>0&&this.originalImage.height>0)}},{key:"_createImageElement",value:function(t){return new Promise(function(a,n){var e=new Image;e.onload=function(){e.onload=null,e.onerror=null,a(e)},e.onerror=function(i){e.onload=null,e.onerror=null,n(i)},e.src=t})}},{key:"_resampleImageToDataURL",value:function(t,a,n){var e=arguments.length>3&&arguments[3]!==void 0?arguments[3]:.92,i=document.createElement("canvas");i.width=a,i.height=n;var r=i.getContext("2d");return r.drawImage(t,0,0,t.naturalWidth,t.naturalHeight,0,0,a,n),i.toDataURL("image/jpeg",e)}},{key:"_setCanvasSizeInt",value:function(t,a){var n=Math.max(1,Math.round(Number(t)||1)),e=Math.max(1,Math.round(Number(a)||1));this.canvas.setWidth(n),this.canvas.setHeight(e),typeof this.canvas.calcOffset=="function"&&this.canvas.calcOffset(),this.canvasEl&&(this.canvasEl.style.width=n+"px",this.canvasEl.style.height=e+"px",this.canvasEl.style.maxWidth="none")}},{key:"_getObjectTopLeftPoint",value:function(t){if(!t)return{x:0,y:0};t.setCoords();var a=typeof t.getCoords=="function"?t.getCoords():null;if(a&&a.length)return a[0];var n=t.getBoundingRect(!0,!0);return{x:n.left,y:n.top}}},{key:"_setObjectOriginKeepingPosition",value:function(t,a,n,e){!t||!e||!t.setPositionByOrigin||(t.set({originX:a,originY:n}),t.setPositionByOrigin(e,a,n),t.setCoords())}},{key:"_alignObjectBoundingBoxToCanvasTopLeft",value:function(t){if(t){t.setCoords();var a=t.getBoundingRect(!0,!0),n=a.left,e=a.top;t.set({left:(t.left||0)-n,top:(t.top||0)-e}),t.setCoords(),this.canvas.renderAll()}}},{key:"_updateCanvasSizeToImageBounds",value:function(){if(this.originalImage){this.originalImage.setCoords();var t=this.originalImage.getBoundingRect(!0,!0),a=this.containerEl?Math.ceil(this.containerEl.clientWidth||0):0,n=this.containerEl?Math.ceil(this.containerEl.clientHeight||0):0;if(a>0&&n>0&&t.width<=a&&t.height<=n){this._setCanvasSizeInt(a,n);return}var e=Math.max(a||0,Math.floor(t.width)),i=Math.max(n||0,Math.floor(t.height));this._setCanvasSizeInt(e,i)}}},{key:"scaleImage",value:function(t){var a=this;return this.animQueue.add(function(){return a._scaleImageImpl(t)})}},{key:"_scaleImageImpl",value:function(t){var a=this;if(!this.originalImage||this.isAnimating)return Promise.resolve();t=Math.max(this.options.minScale,Math.min(this.options.maxScale,t)),this.currentScale=t,this.isAnimating=!0,this._updateUI();var n=this.baseImageScale*t,e=this._getObjectTopLeftPoint(this.originalImage);this._setObjectOriginKeepingPosition(this.originalImage,"left","top",e);var i=new Promise(function(c){a.originalImage.animate("scaleX",n,{duration:a.options.animationDuration,onChange:a.canvas.renderAll.bind(a.canvas),onComplete:c})}),r=new Promise(function(c){a.originalImage.animate("scaleY",n,{duration:a.options.animationDuration,onChange:a.canvas.renderAll.bind(a.canvas),onComplete:c})});return Promise.all([i,r]).then(function(){a.originalImage.set({scaleX:n,scaleY:n}),a.originalImage.setCoords(),a.options.expandCanvasToImage&&a._updateCanvasSizeToImageBounds(),a._alignObjectBoundingBoxToCanvasTopLeft(a.originalImage),a.canvas.getObjects().forEach(function(c){c.maskId&&a._syncMaskLabel(c)}),a.isAnimating=!1,a._updateInputs(),a._updateUI(),a.saveState()}).catch(function(){a.isAnimating=!1,a._updateUI()})}},{key:"rotateImage",value:function(t){var a=this;return this.animQueue.add(function(){return a._rotateImageImpl(t)})}},{key:"_rotateImageImpl",value:function(t){var a=this;if(!this.originalImage||this.isAnimating||isNaN(t))return Promise.resolve();this.currentRotation=t,this.isAnimating=!0,this._updateUI();var n=this.originalImage.getCenterPoint();this._setObjectOriginKeepingPosition(this.originalImage,"center","center",n);var e=new Promise(function(i){a.originalImage.animate("angle",t,{duration:a.options.animationDuration,onChange:a.canvas.renderAll.bind(a.canvas),onComplete:i})});return e.then(function(){a.originalImage.set("angle",t),a.originalImage.setCoords(),a.options.expandCanvasToImage&&a._updateCanvasSizeToImageBounds(),a._alignObjectBoundingBoxToCanvasTopLeft(a.originalImage);var i=a._getObjectTopLeftPoint(a.originalImage);a._setObjectOriginKeepingPosition(a.originalImage,"left","top",i),a.canvas.getObjects().forEach(function(r){r.maskId&&a._syncMaskLabel(r)}),a.isAnimating=!1,a._updateInputs(),a._updateUI(),a.saveState()}).catch(function(){a.isAnimating=!1,a._updateUI()})}},{key:"reset",value:function(){var t=this;return this.originalImage?this.scaleImage(1).then(function(){return t.rotateImage(0)}).then(function(){t.saveState()}).catch(function(a){console.error("reset() failed",a)}):Promise.resolve()}},{key:"loadFromState",value:function(t){var a=this;if(!(!t||!this.canvas))try{var n=typeof t=="string"?JSON.parse(t):t;this.canvas.loadFromJSON(n,function(){a._hideAllMaskLabels();var e=a.canvas.getObjects();a.originalImage=e.find(function(r){return r.type==="image"&&!r.maskId})||null,a.originalImage.set({originX:"left",originY:"top",selectable:!1,evented:!1,hasControls:!1,hoverCursor:"default"}),a.canvas.sendToBack(a.originalImage);var i=e.filter(function(r){return r.maskId});a.maskCounter=i.reduce(function(r,c){return Math.max(r,c.maskId)},0),a.canvas.renderAll(),a._updateMaskList(),a._updateUI()})}catch(e){console.error("loadFromState() failed",e)}}},{key:"saveState",value:function(){var t=this;if(this.canvas){var a=this.canvas.getActiveObject();this._hideAllMaskLabels();try{var n=this.canvas.toJSON(["maskId","maskName","isCropRect"]);Array.isArray(n.objects)&&(n.objects=n.objects.filter(function(s){return!s.isCropRect}));var e=JSON.stringify(n),i=this._lastSnapshot||e,r=!1,c=new I(function(){r&&t.loadFromState(e),r=!0},function(){t.loadFromState(i)});this.historyManager.execute(c),this._lastSnapshot=e,a&&a.maskId&&this._showLabelForMask(a),this._updateUI()}catch(s){console.warn("saveState: failed to save canvas snapshot",s)}}}},{key:"undo",value:function(){this.historyManager.undo()}},{key:"redo",value:function(){this.historyManager.redo()}},{key:"addMask",value:function(){var t=this,a=arguments.length>0&&arguments[0]!==void 0?arguments[0]:{};if(!this.canvas)return null;var n=a.shape||"rect",e=H({shape:n,width:this.options.defaultMaskWidth,height:this.options.defaultMaskHeight,color:"rgba(0,0,0,0.5)",alpha:.5,gap:5,left:void 0,top:void 0,angle:0,selectable:!0},a),i=10,r=i,c=i,s=function(E,B){if(typeof E=="function")return E(t.canvas,t.options);if(typeof E=="string"&&E.endsWith("%")){var C=parseFloat(E)/100;return Math.floor((t.canvas?t.canvas.getWidth():0)*C)}return E??B};if(e.left===void 0&&this._lastMask){var d,m=this._lastMask,k=m.left;if(m.getScaledWidth)k+=m.getScaledWidth();else if(m.width){var v;k+=m.width*((v=m.scaleX)!==null&&v!==void 0?v:1)}r=Math.round(k+e.gap),c=(d=m.top)!==null&&d!==void 0?d:i}else r=s(e.left,i),c=s(e.top,i);if(e.width=s(e.width,this.options.defaultMaskWidth),e.height=s(e.height,this.options.defaultMaskHeight),this.options.expandCanvasToImage&&n==="rect"){var A=Math.ceil(r+e.width+10),w=Math.ceil(c+e.height+10),L=this.containerEl?Math.floor(this.containerEl.clientWidth||0):0,j=this.containerEl?Math.floor(this.containerEl.clientHeight||0):0,O=Math.max(this.canvas.getWidth(),L,A),b=Math.max(this.canvas.getHeight(),j,w);this._setCanvasSizeInt(O,b)}var h;if(typeof e.fabricGenerator=="function")h=e.fabricGenerator(e,this.canvas,this.options);else switch(n){case"circle":h=new fabric.Circle(H({left:r,top:c,radius:s(e.radius,Math.min(e.width,e.height)/2),fill:e.color,opacity:e.alpha,angle:e.angle},e.styles));break;case"ellipse":h=new fabric.Ellipse(H({left:r,top:c,rx:s(e.rx,e.width/2),ry:s(e.ry,e.height/2),fill:e.color,opacity:e.alpha,angle:e.angle},e.styles));break;case"polygon":var g=e.points||[];Array.isArray(g)&&g.length&&F(g[0])==="object"&&(g=g.map(function(_){return{x:Number(_.x),y:Number(_.y)}})),h=new fabric.Polygon(g,H({left:r,top:c,fill:e.color,opacity:e.alpha,angle:e.angle},e.styles));break;case"rect":default:h=new fabric.Rect(H({left:r,top:c,width:s(e.width,this.options.defaultMaskWidth),height:s(e.height,this.options.defaultMaskHeight),fill:e.color,opacity:e.alpha,angle:e.angle,rx:e.rx,ry:e.ry},e.styles))}h.selectable=e.selectable!==!1,h.hasControls="hasControls"in e?e.hasControls:!0,h.lockRotation=!this.options.maskRotatable,h.borderColor=e.borderColor||"red",h.cornerColor=e.cornerColor||"black",h.cornerSize=e.cornerSize||8,h.transparentCorners="transparentCorners"in e?e.transparentCorners:!1,h.stroke=e.styles&&e.styles.stroke||"#ccc",h.strokeWidth=e.styles&&e.styles.strokeWidth||1,h.strokeUniform="strokeUniform"in e?e.strokeUniform:!0,e.styles&&e.styles.strokeDashArray&&(h.strokeDashArray=e.styles.strokeDashArray),h.originalAlpha=e.alpha;var p={stroke:h.stroke,strokeWidth:h.strokeWidth,opacity:h.originalAlpha},f={stroke:"#ff5500",strokeWidth:2,opacity:Math.min(h.originalAlpha+.2,1)};return h.on("mouseover",function(){h.set(f),h.canvas.requestRenderAll()}),h.on("mouseout",function(){h.set(p),h.canvas.requestRenderAll()}),this._lastMaskInitialLeft=r,this._lastMaskInitialTop=c,this._lastMaskInitialWidth=s(e.width,this.options.defaultMaskWidth),h.maskId=++this.maskCounter,h.maskName="".concat(this.options.maskName).concat(h.maskId),this._lastMask=h,this.canvas.add(h),this.canvas.bringToFront(h),e.selectable&&this.canvas.setActiveObject(h),this._onSelectionChanged([h]),this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),this.saveState(),typeof e.onCreate=="function"&&e.onCreate(h,this.canvas),h}},{key:"removeSelectedMask",value:function(){var t=this.canvas.getActiveObject();!t||!t.maskId||(this._removeLabelForMask(t),this.canvas.remove(t),this.canvas.discardActiveObject(),this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),this.saveState())}},{key:"removeAllMasks",value:function(){var t=this,a=this.canvas.getObjects().filter(function(n){return n.maskId});a.forEach(function(n){return t._removeLabelForMask(n)}),a.forEach(function(n){return t.canvas.remove(n)}),this.canvas.discardActiveObject(),this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null,this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),this.saveState()}},{key:"_removeLabelForMask",value:function(t){if(!(!t||!this.canvas)&&t.__label){try{var a=this.canvas.getObjects();a.includes(t.__label)&&this.canvas.remove(t.__label)}catch{}try{delete t.__label}catch{}}}},{key:"_createLabelForMask",value:function(t){if(!(!t||!this.options.maskLabelOnSelect)){this._removeLabelForMask(t);var a=null;if(this.options.label&&typeof this.options.label.create=="function"&&(a=this.options.label.create(t,fabric)),!a){var n=t.maskName,e={left:0,top:0,fontSize:12,fill:"#fff",backgroundColor:"rgba(0,0,0,0.7)",selectable:!1,evented:!1,padding:2,originX:"left",originY:"top"};this.options.label&&(typeof this.options.label.getText=="function"&&(n=this.options.label.getText(t,this.maskCounter)),this.options.label.textOptions&&Object.assign(e,this.options.label.textOptions)),a=new fabric.Text(n,e)}a.maskLabel=!0,t.__label=a,this.canvas.add(a),this.canvas.bringToFront(a),this._syncMaskLabel(t)}}},{key:"_hideAllMaskLabels",value:function(){var t=this;if(this.canvas){var a=this.canvas.getObjects(),n=a.filter(function(e){return e.maskLabel});n.forEach(function(e){try{a.includes(e)&&t.canvas.remove(e)}catch{}}),a.forEach(function(e){if(e.maskId&&e.__label)try{delete e.__label}catch{}})}}},{key:"_syncMaskLabel",value:function(t){var a;if(t&&this.options.maskLabelOnSelect&&t.__label){var n=t.getCoords?t.getCoords():null;if(!(!n||n.length<4)){var e=n[0],i=t.getCenterPoint(),r=i.x-e.x,c=i.y-e.y,s=Math.sqrt(r*r+c*c)||1,d=r/s,m=c/s,k=Math.max(0,(a=this.options.maskLabelOffset)!==null&&a!==void 0?a:3),v=e.x+d*k,A=e.y+m*k;t.__label.set({left:Math.round(v),top:Math.round(A),angle:t.angle||0,originX:"left",originY:"top",visible:!0}),t.__label.setCoords(),this.canvas.renderAll()}}}},{key:"_showLabelForMask",value:function(t){t&&this.options.maskLabelOnSelect&&(t.__label||this._createLabelForMask(t),t.__label.visible=!0,this._syncMaskLabel(t))}},{key:"_onSelectionChanged",value:function(t){var a=this,n=(t||[]).find(function(i){return i.maskId}),e=this.canvas.getObjects().filter(function(i){return i.maskId});e.forEach(function(i){if(i!==n){if(i.__label){try{a.canvas.remove(i.__label)}catch{}delete i.__label}i.set({stroke:"#ccc",strokeWidth:1})}else i.set({stroke:"#ff0000",strokeWidth:1})}),n&&this._showLabelForMask(n),this._updateMaskListSelection(n),this.canvas.renderAll(),this._updateUI()}},{key:"_updateMaskList",value:function(){var t=this,a=document.getElementById(this.elements.maskList);if(a){a.innerHTML="";var n=this.canvas.getObjects().filter(function(e){return e.maskId});n.forEach(function(e){var i=document.createElement("li");i.className="list-group-item mask-item",i.textContent=e.maskName,i.onclick=function(){t.canvas.setActiveObject(e),t._onSelectionChanged([e])},a.appendChild(i)})}}},{key:"_updateMaskListSelection",value:function(t){var a=document.getElementById(this.elements.maskList);if(a){var n=a.querySelectorAll(".mask-item");n.forEach(function(e){var i=!!t&&e.textContent===t.maskName;e.classList.toggle("active",i)})}}},{key:"merge",value:function(){var o=D(P().m(function a(){var n,e,i;return P().w(function(r){for(;;)switch(r.p=r.n){case 0:if(this.originalImage){r.n=1;break}return r.a(2);case 1:if(n=this.canvas.getObjects().filter(function(c){return c.maskId}),n.length){r.n=2;break}return r.a(2);case 2:return this.canvas.discardActiveObject(),this.canvas.renderAll(),r.p=3,r.n=4,this.getImageBase64({exportImageArea:!0,multiplier:this.options.exportMultiplier});case 4:return e=r.v,this.removeAllMasks(),r.n=5,this.loadImage(e);case 5:this.saveState(),r.n=7;break;case 6:r.p=6,i=r.v,console.error("merge error",i),this.canvasEl&&(this.canvasEl.style.visibility="");case 7:return r.a(2)}},a,this,[[3,6]])}));function t(){return o.apply(this,arguments)}return t}()},{key:"downloadImage",value:function(){var t=arguments.length>0&&arguments[0]!==void 0?arguments[0]:this.options.defaultDownloadFileName;if(this.originalImage){var a=this.options.exportImageAreaByDefault;this.getImageBase64({exportImageArea:a,multiplier:this.options.exportMultiplier}).then(function(n){var e=document.createElement("a");e.download=t,e.href=n,document.body.appendChild(e),e.click(),document.body.removeChild(e)}).catch(function(n){return console.error("download error",n)})}}},{key:"getImageBase64",value:function(){var o=D(P().m(function a(){var n=this,e,i,r,c,s,d,m,k,v,A,w,L,j,O,b,h,g=arguments;return P().w(function(p){for(;;)switch(p.n){case 0:if(e=g.length>0&&g[0]!==void 0?g[0]:{},this.originalImage){p.n=1;break}throw new Error("No image loaded");case 1:if(i=typeof e.exportImageArea=="boolean"?e.exportImageArea:this.options.exportImageAreaByDefault,r=e.multiplier||this.options.exportMultiplier||1,i){p.n=3;break}if(c=this.originalImage.getElement?this.originalImage.getElement():this.originalImage._element||null,c){p.n=2;break}return p.a(2,this.canvas.toDataURL({format:"jpeg",quality:this.options.downsampleQuality,multiplier:r}));case 2:return s=this.originalImage.width,d=this.originalImage.height,m=document.createElement("canvas"),m.width=s,m.height=d,k=m.getContext("2d"),k.drawImage(c,0,0,s,d),p.a(2,m.toDataURL("image/jpeg",this.options.downsampleQuality));case 3:return v=this.canvas.getObjects().filter(function(f){return f.maskId}),A=v.map(function(f){return{obj:f,opacity:f.opacity,fill:f.fill,strokeWidth:f.strokeWidth,stroke:f.stroke,selectable:f.selectable,lockRotation:f.lockRotation}}),v.forEach(function(f){return n._removeLabelForMask(f)}),this.canvas.discardActiveObject(),this.canvas.renderAll(),v.forEach(function(f){f.set({opacity:1,fill:"#000000",strokeWidth:0,stroke:null,selectable:!1}),f.setCoords()}),this.canvas.renderAll(),this.originalImage.setCoords(),w=this.originalImage.getBoundingRect(!0,!0),L=Math.max(0,Math.round(w.left)),j=Math.max(0,Math.round(w.top)),O=Math.max(1,Math.round(w.width)),b=Math.max(1,Math.round(w.height)),p.n=4,new Promise(function(f,_){try{var E=n.canvas.toDataURL({format:"jpeg",quality:n.options.downsampleQuality,multiplier:r}),B=new Image;B.onload=function(){try{var C=Math.round(L*r),M=Math.round(j*r),x=Math.round(O*r),W=Math.round(b*r),R=document.createElement("canvas");R.width=x,R.height=W;var U=R.getContext("2d");U.drawImage(B,C,M,x,W,0,0,x,W);var q=R.toDataURL("image/jpeg",n.options.downsampleQuality);f(q)}catch(G){_(G)}},B.onerror=_,B.src=E}catch(C){_(C)}});case 4:return h=p.v,A.forEach(function(f){try{f.obj.set({opacity:f.opacity,fill:f.fill,strokeWidth:f.strokeWidth,stroke:f.stroke,selectable:f.selectable,lockRotation:f.lockRotation}),f.obj.setCoords()}catch{}}),this.canvas.renderAll(),p.a(2,h)}},a,this)}));function t(){return o.apply(this,arguments)}return t}()},{key:"exportImageFile",value:function(){var o=D(P().m(function a(){var n,e,i,r,c,s,d,m,k,v,A,w,L,j,O,b,h,g,p,f,_,E,B,C=arguments;return P().w(function(M){for(;;)switch(M.n){case 0:if(r=C.length>0&&C[0]!==void 0?C[0]:{},this.originalImage){M.n=1;break}throw new Error("No image loaded");case 1:if(c=r.mergeMask,s=c===void 0?!0:c,d=r.fileType,m=d===void 0?"jpeg":d,k=r.quality,v=k===void 0?(n=this.options.downsampleQuality)!==null&&n!==void 0?n:.92:k,A=r.multiplier,w=A===void 0?(e=this.options.exportMultiplier)!==null&&e!==void 0?e:1:A,L=r.fileName,j=L===void 0?(i=this.options.defaultDownloadFileName)!==null&&i!==void 0?i:"exported_image.jpg":L,O={jpeg:"jpeg",jpg:"jpeg","image/jpeg":"jpeg",png:"png","image/png":"png",webp:"webp","image/webp":"webp"},b=O[String(m).toLowerCase()]||"jpeg",!s){M.n=3;break}return M.n=2,this.getImageBase64({exportImageArea:!0,multiplier:w});case 2:h=M.v,M.n=5;break;case 3:return M.n=4,this.getImageBase64({exportImageArea:!1,multiplier:w});case 4:h=M.v;case 5:if(g=h,g.startsWith("data:image/".concat(b))){M.n=7;break}return M.n=6,new Promise(function(x,W){var R=new window.Image;R.crossOrigin="Anonymous",R.onload=function(){try{var U=document.createElement("canvas");U.width=R.width,U.height=R.height;var q=U.getContext("2d");q.drawImage(R,0,0);var G=U.toDataURL("image/".concat(b),v);x(G)}catch(V){W(V)}},R.onerror=W,R.src=h});case 6:g=M.v;case 7:for(p=atob(g.split(",")[1]),f="image/".concat(b),_=p.length,E=new Uint8Array(_);_--;)E[_]=p.charCodeAt(_);return B=new File([E],j,{type:f}),M.a(2,B)}},a,this)}));function t(){return o.apply(this,arguments)}return t}()},{key:"enterCropMode",value:function(){var t=this;if(!(!this.canvas||!this.originalImage||this._cropMode)&&this.isImageLoaded()){this._cropMode=!0,this._prevSelectionSetting=this.canvas.selection,this.canvas.selection=!1,this.canvas.discardActiveObject(),this.originalImage.setCoords();var a=this.originalImage.getBoundingRect(!0,!0),n=this.options.crop&&this.options.crop.padding?this.options.crop.padding:10,e=Math.max(0,Math.floor(a.left+n)),i=Math.max(0,Math.floor(a.top+n)),r=Math.min(this.options.crop.minWidth||50,Math.floor(a.width-n*2)),c=Math.min(this.options.crop.minHeight||50,Math.floor(a.height-n*2)),s=new fabric.Rect({left:e,top:i,width:r,height:c,fill:"rgba(0,0,0,0.12)",stroke:"#00aaff",strokeDashArray:[6,4],strokeWidth:1,strokeUniform:!0,selectable:!0,hasRotatingPoint:!!(this.options.crop&&this.options.crop.allowRotationOfCropRect),lockRotation:!(this.options.crop&&this.options.crop.allowRotationOfCropRect),cornerSize:8,objectCaching:!1,originX:"left",originY:"top"});this.canvas.add(s),s.isCropRect=!0,this.canvas.bringToFront(s),this.canvas.setActiveObject(s),this._cropRect=s,this._cropPrevEvented=[],this.canvas.getObjects().forEach(function(m){if(m!==s){t._cropPrevEvented.push({obj:m,evented:m.evented,selectable:m.selectable});try{m.evented=!1,m.selectable=!1}catch{}}});var d=function(){try{s.setCoords(),t.canvas.requestRenderAll()}catch{}};s.on("modified",d),s.on("moving",d),s.on("scaling",d),this._cropHandlers.push({target:s,handlers:[{evt:"modified",fn:d},{evt:"moving",fn:d},{evt:"scaling",fn:d}]}),this._updateUI(),this.canvas.renderAll()}}},{key:"cancelCrop",value:function(){if(!(!this.canvas||!this._cropMode)){if(this._cropRect){try{this._cropHandlers&&this._cropHandlers.length&&this._cropHandlers.forEach(function(t){t.handlers.forEach(function(a){return t.target.off(a.evt,a.fn)})})}catch{}try{this.canvas.remove(this._cropRect)}catch{}this._cropRect=null}Array.isArray(this._cropPrevEvented)&&this._cropPrevEvented.forEach(function(t){try{t.obj.evented=t.evented,t.obj.selectable=t.selectable}catch{}}),this._cropPrevEvented=null,this._cropHandlers=[],this._cropMode=!1,this.canvas.selection=!!this._prevSelectionSetting,this._prevSelectionSetting=void 0,this.canvas.discardActiveObject(),this._updateUI(),this.canvas.renderAll()}}},{key:"applyCrop",value:function(){var o=D(P().m(function a(){var n=this,e,i,r,c,s,d,m,k,v,A,w,L,j,O,b,h;return P().w(function(g){for(;;)switch(g.p=g.n){case 0:if(!(!this.canvas||!this._cropMode||!this._cropRect)){g.n=1;break}return g.a(2);case 1:this._cropRect.setCoords(),e=this._cropRect.getBoundingRect(!0,!0),i=Math.max(0,Math.round(e.left)),r=Math.max(0,Math.round(e.top)),c=Math.max(1,Math.round(Math.min(e.width,this.canvas.getWidth()-i))),s=Math.max(1,Math.round(Math.min(e.height,this.canvas.getHeight()-r))),d=null;try{m=this.canvas.toJSON(["maskId","maskName","isCropRect"]),Array.isArray(m.objects)&&(m.objects=m.objects.filter(function(p){return!p.isCropRect})),d=JSON.stringify(m)}catch(p){console.warn("applyCrop: could not serialize before state",p),d=null}try{k=this.canvas.getObjects().filter(function(p){return p.maskId}),k&&k.length&&(k.forEach(function(p){try{n._removeLabelForMask(p),n.canvas.remove(p)}catch(f){console.warn("applyCrop: failed to remove mask",f)}}),this.canvas.discardActiveObject(),this.canvas.renderAll())}catch(p){console.warn("applyCrop: error while removing masks",p)}try{if(this._cropRect){try{this._cropHandlers&&this._cropHandlers.length&&this._cropHandlers.forEach(function(p){p.handlers.forEach(function(f){return p.target.off(f.evt,f.fn)})})}catch{}try{this.canvas.remove(this._cropRect)}catch{}this._cropRect=null}}catch{}return this._cropMode=!1,this.canvas.selection=!!this._prevSelectionSetting,this._prevSelectionSetting=void 0,g.p=2,A=this.canvas.toDataURL({format:"jpeg",quality:this.options.downsampleQuality||.92,multiplier:1}),g.n=3,new Promise(function(p,f){var _=new Image;_.onload=function(){try{var E=document.createElement("canvas");E.width=c,E.height=s;var B=E.getContext("2d");B.drawImage(_,i,r,c,s,0,0,c,s);var C=E.toDataURL("image/jpeg",n.options.downsampleQuality||.92);p(C)}catch(M){f(M)}},_.onerror=function(E){return f(E)},_.src=A});case 3:v=g.v,g.n=5;break;case 4:return g.p=4,b=g.v,console.error("applyCrop: failed to create cropped image",b),this._updateUI(),g.a(2);case 5:return g.p=5,g.n=6,this.loadImage(v);case 6:g.n=8;break;case 7:return g.p=7,h=g.v,console.error("applyCrop: loadImage(croppedBase64) failed",h),this._updateUI(),g.a(2);case 8:w=null;try{L=this.canvas.toJSON(["maskId","maskName","isCropRect"]),Array.isArray(L.objects)&&(L.objects=L.objects.filter(function(p){return!p.isCropRect})),w=JSON.stringify(L)}catch(p){console.warn("applyCrop: failed to serialize after state",p),w=null}try{j=this,O=new I(function(){w&&j.loadFromState(w)},function(){d&&j.loadFromState(d)}),this.historyManager||(this.historyManager=new y(this.maxHistorySize||50)),this.historyManager.currentIndex<this.historyManager.history.length-1&&(this.historyManager.history=this.historyManager.history.slice(0,this.historyManager.currentIndex+1)),this.historyManager.history.push(O),this.historyManager.history.length>this.historyManager.maxSize?this.historyManager.history.shift():this.historyManager.currentIndex++}catch(p){console.warn("applyCrop: failed to push history command",p)}this._updateUI(),this.canvas.renderAll();case 9:return g.a(2)}},a,this,[[5,7],[2,4]])}));function t(){return o.apply(this,arguments)}return t}()},{key:"_updateInputs",value:function(){var t=document.getElementById(this.elements.scaleRate);t&&(t.value=Math.round(this.currentScale*100))}},{key:"_updateUI",value:function(){var t,a,n=!!this.originalImage,e=n?this.canvas.getObjects().filter(function(j){return j.maskId}):[],i=e.length>0,r=this.canvas.getActiveObject(),c=r&&r.maskId,s=this.currentScale===1&&this.currentRotation===0,d=(t=this.historyManager)===null||t===void 0?void 0:t.canUndo(),m=(a=this.historyManager)===null||a===void 0?void 0:a.canRedo(),k=!!this._cropMode;if(k){for(var v=0,A=Object.keys(this.elements||{});v<A.length;v++){var w=A[v],L=document.getElementById(this.elements[w]);L&&(w==="applyCropBtn"||w==="cancelCropBtn"?L.disabled=!1:L.disabled=!0)}return}this._setDisabled("zoomInBtn",!n||this.isAnimating||this.currentScale>=this.options.maxScale),this._setDisabled("zoomOutBtn",!n||this.isAnimating||this.currentScale<=this.options.minScale),this._setDisabled("rotateLeftBtn",!n||this.isAnimating),this._setDisabled("rotateRightBtn",!n||this.isAnimating),this._setDisabled("addMaskBtn",!n||this.isAnimating),this._setDisabled("removeMaskBtn",!c||this.isAnimating),this._setDisabled("removeAllMasksBtn",!i||this.isAnimating),this._setDisabled("mergeBtn",!n||!i||this.isAnimating),this._setDisabled("downloadBtn",!n||this.isAnimating),this._setDisabled("resetBtn",!n||s||this.isAnimating),this._setDisabled("undoBtn",!n||this.isAnimating||!d),this._setDisabled("redoBtn",!n||this.isAnimating||!m),this._setDisabled("cropBtn",!n||this.isAnimating),this._setDisabled("applyCropBtn",!0),this._setDisabled("cancelCropBtn",!0)}},{key:"_setDisabled",value:function(t,a){var n=document.getElementById(this.elements[t]);n&&(n.disabled=!!a)}},{key:"_updatePlaceholderStatus",value:function(){this.options.showPlaceholder&&this._setPlaceholderVisible(!this.originalImage)}},{key:"_setPlaceholderVisible",value:function(t){this.placeholderEl&&(t?(this.placeholderEl.classList.remove("d-none"),this.placeholderEl.classList.add("d-flex"),this.containerEl.classList.add("d-none")):(this.placeholderEl.classList.remove("d-flex"),this.placeholderEl.classList.add("d-none"),this.containerEl.classList.remove("d-none")))}},{key:"dispose",value:function(){var t=this;try{var a=function(){var i=t._boundHandlers[n]||[],r=document.getElementById(t.elements[n]);if(!r)return 1;i.forEach(function(c){try{r.removeEventListener(c.event,c.handler)}catch{}})};for(var n in this._boundHandlers||{})a()}catch{}if(this._cropRect){try{this.canvas.remove(this._cropRect)}catch{}this._cropRect=null}if(this.canvas){try{this.canvas.dispose()}catch{}this.canvas=null,this.canvasEl=null,this.isImageLoadedToCanvas=!1}this._boundHandlers={}}}])}(),l=function(){function S(){z(this,S),this.queue=[],this.running=!1}return Q(S,[{key:"add",value:function(){var o=D(P().m(function a(n){var e=this;return P().w(function(i){for(;;)switch(i.n){case 0:return i.a(2,new Promise(function(r,c){e.queue.push({fn:n,resolve:r,reject:c}),e.running||e.processQueue()}))}},a)}));function t(a){return o.apply(this,arguments)}return t}()},{key:"processQueue",value:function(){var o=D(P().m(function a(){var n,e,i,r,c,s;return P().w(function(d){for(;;)switch(d.p=d.n){case 0:if(this.queue.length!==0){d.n=1;break}return this.running=!1,d.a(2);case 1:return this.running=!0,n=this.queue.shift(),e=n.fn,i=n.resolve,r=n.reject,d.p=2,d.n=3,e();case 3:c=d.v,i(c),d.n=5;break;case 4:d.p=4,s=d.v,r(s);case 5:this.processQueue();case 6:return d.a(2)}},a,this,[[2,4]])}));function t(){return o.apply(this,arguments)}return t}()}])}(),I=Q(function S(o,t){z(this,S),this.execute=o,this.undo=t}),y=function(){function S(){var o=arguments.length>0&&arguments[0]!==void 0?arguments[0]:50;z(this,S),this.history=[],this.currentIndex=-1,this.maxSize=o}return Q(S,[{key:"execute",value:function(t){t.execute(),this.currentIndex<this.history.length-1&&(this.history=this.history.slice(0,this.currentIndex+1)),this.history.push(t),this.history.length>this.maxSize?this.history.shift():this.currentIndex++}},{key:"canUndo",value:function(){return this.currentIndex>=0}},{key:"canRedo",value:function(){return this.currentIndex<this.history.length-1}},{key:"undo",value:function(){this.currentIndex>=0&&(this.history[this.currentIndex].undo(),this.currentIndex--)}},{key:"redo",value:function(){this.currentIndex<this.history.length-1&&(this.currentIndex++,this.history[this.currentIndex].execute())}}])}();return u})});export default ae();
|
|
8
|
+
*/var v=null;function A(){return typeof globalThis<"u"?globalThis:typeof self<"u"?self:typeof window<"u"?window:null}function B(){let _=A();return _&&_.fabric?_.fabric:null}function x(_){return v=_||B(),v}function w(){return v||x(),v}var k=class{constructor(t={}){let s={getText:a=>a.maskName,textOptions:{fontSize:12,fill:"#fff",backgroundColor:"rgba(0,0,0,0.7)",padding:2,fontFamily:"monospace",fontWeight:"bold",selectable:!1,evented:!1,originX:"left",originY:"top"}},e={minWidth:100,minHeight:100,padding:10,hideMasksDuringCrop:!0,preserveMasksAfterCrop:!1,allowRotationOfCropRect:!1},i=t.label||{},n=t.crop||{};this.options={canvasWidth:800,canvasHeight:600,backgroundColor:"transparent",animationDuration:300,minScale:.1,maxScale:5,scaleStep:.05,rotationStep:90,expandCanvasToImage:!0,fitImageToCanvas:!1,coverImageToCanvas:!1,downsampleOnLoad:!0,downsampleMaxWidth:4e3,downsampleMaxHeight:3e3,downsampleQuality:.92,exportMultiplier:1,exportImageAreaByDefault:!0,defaultMaskWidth:50,defaultMaskHeight:80,maskRotatable:!1,maskLabelOnSelect:!0,maskLabelOffset:3,maskName:"mask",groupSelection:!1,showPlaceholder:!0,initialImageBase64:null,defaultDownloadFileName:"edited_image.jpg",onError:null,onWarning:null,...t,label:{...s,...i,textOptions:{...s.textOptions,...i.textOptions||{}}},crop:{...e,...n}},this._fabricLoaded=!!w(),this._fabricLoaded||this._reportError("fabric.js is not loaded. Please include fabric.js first. Initialization will be aborted."),this.canvas=null,this.canvasElement=null,this.containerElement=null,this.placeholderElement=null,this.originalImage=null,this.baseImageScale=1,this.currentScale=1,this.currentRotation=0,this.maskCounter=0,this.isAnimating=!1,this.elements={},this.isImageLoadedToCanvas=!1,this.maxHistorySize=50,this._handlersByElementKey={},this._lastMask=null,this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null,this._lastSnapshot=null,this._cropMode=!1,this._cropRect=null,this._cropHandlers=[],this._cropPrevEvented=null,this._prevSelectionSetting=void 0,this._containerOriginalOverflow=void 0,this.onImageLoaded=typeof t.onImageLoaded=="function"?t.onImageLoaded:null,this.animQueue=new S,this.historyManager=new I(this.maxHistorySize)}get canvasEl(){return this.canvasElement}set canvasEl(t){this.canvasElement=t}get containerEl(){return this.containerElement}set containerEl(t){this.containerElement=t}get placeholderEl(){return this.placeholderElement}set placeholderEl(t){this.placeholderElement=t}init(t={}){if(!this._fabricLoaded)return;let s={canvas:"fabricCanvas",canvasContainer:null,imgPlaceholder:"imgPlaceholder",scaleRate:"scaleRate",rotationLeftInput:"rotationLeftInput",rotationRightInput:"rotationRightInput",rotateLeftBtn:"rotateLeftBtn",rotateRightBtn:"rotateRightBtn",addMaskBtn:"addMaskBtn",removeMaskBtn:"removeMaskBtn",removeAllMasksBtn:"removeAllMasksBtn",mergeBtn:"mergeBtn",downloadBtn:"downloadBtn",maskList:"maskList",zoomInBtn:"zoomInBtn",zoomOutBtn:"zoomOutBtn",resetBtn:"resetBtn",undoBtn:"undoBtn",redoBtn:"redoBtn",imageInput:"imageInput",cropBtn:"cropBtn",applyCropBtn:"applyCropBtn",cancelCropBtn:"cancelCropBtn"};this.elements={...s,...t},this._initCanvas(),this._bindEvents(),this._updateInputs(),this._updateMaskList(),this._updateUI(),this.options.initialImageBase64?this.loadImage(this.options.initialImageBase64):this._updatePlaceholderStatus()}_reportError(t,s=null){let e=this.options&&this.options.onError;if(typeof e=="function")try{e(s,t)}catch{}}_reportWarning(t,s=null){let e=this.options&&this.options.onWarning;if(typeof e=="function")try{e(s,t)}catch{}}_initCanvas(){let t=document.getElementById(this.elements.canvas);if(!t)throw new Error("Canvas is not found: "+this.elements.canvas);if(this.canvasElement=t,this.elements.canvasContainer){let i=document.getElementById(this.elements.canvasContainer);this.containerElement=i||t.parentElement}else this.containerElement=t.parentElement;this.placeholderElement=document.getElementById(this.elements.imgPlaceholder)||null;let s=this.options.canvasWidth,e=this.options.canvasHeight;if(this.containerElement){let i=Math.floor(this.containerElement.clientWidth),n=Math.floor(this.containerElement.clientHeight);i>0&&n>0&&(s=i,e=n)}this.canvas=new v.Canvas(t,{width:s,height:e,backgroundColor:this.options.backgroundColor,selection:this.options.groupSelection,preserveObjectStacking:!0}),this.canvas.on("selection:created",i=>this._handleSelectionChanged(i.selected)),this.canvas.on("selection:updated",i=>this._handleSelectionChanged(i.selected)),this.canvas.on("selection:cleared",()=>this._handleSelectionChanged([])),this.canvas.on("object:moving",i=>{i.target&&i.target.maskId&&this._syncMaskLabel(i.target)}),this.canvas.on("object:scaling",i=>{i.target&&i.target.maskId&&this._syncMaskLabel(i.target)}),this.canvas.on("object:rotating",i=>{i.target&&i.target.maskId&&this._syncMaskLabel(i.target)}),this.canvas.on("object:modified",i=>this._handleObjectModified(i.target)),this.canvasElement.style.display="block"}_handleObjectModified(t){let s=this._getModifiedMasks(t);s.length&&(s.forEach(e=>{typeof e.setCoords=="function"&&e.setCoords(),this._syncMaskLabel(e),this._expandCanvasToFitObject(e)}),this.saveState())}_getModifiedMasks(t){if(!t)return[];if(t.maskId)return[t];let s=typeof t.getObjects=="function"?t.getObjects():[];return Array.isArray(s)?s.filter(e=>e&&e.maskId):[]}_syncContainerOverflow(){if(!(!this.containerElement||!this.containerElement.style))if(this._containerOriginalOverflow===void 0&&(this._containerOriginalOverflow=this.containerElement.style.overflow||""),this.options.coverImageToCanvas){let t=!this.isImageLoadedToCanvas;this.containerElement.style.overflow="scroll",t&&(this.containerElement.scrollLeft=0,this.containerElement.scrollTop=0)}else this.options.fitImageToCanvas?(this.containerElement.style.overflow="auto",this.containerElement.scrollLeft=0,this.containerElement.scrollTop=0):this.containerElement.style.overflow=this._containerOriginalOverflow}_bindEvents(){this._bindIfExists("uploadArea","click",()=>{let t=document.getElementById(this.elements.uploadArea);this._isElementDisabled(t)||document.getElementById(this.elements.imageInput)?.click()}),this._bindIfExists("imageInput","change",t=>{let s=t.target.files&&t.target.files[0];s&&this._loadImageFile(s)}),this._bindIfExists("zoomInBtn","click",()=>this.scaleImage(this.currentScale+this.options.scaleStep)),this._bindIfExists("zoomOutBtn","click",()=>this.scaleImage(this.currentScale-this.options.scaleStep)),this._bindIfExists("resetBtn","click",()=>{this.resetImageTransform()}),this._bindIfExists("addMaskBtn","click",()=>this.createMask()),this._bindIfExists("removeMaskBtn","click",()=>this.removeSelectedMask()),this._bindIfExists("removeAllMasksBtn","click",()=>this.removeAllMasks()),this._bindIfExists("mergeBtn","click",()=>this.mergeMasks()),this._bindIfExists("downloadBtn","click",()=>this.downloadImage()),this._bindIfExists("undoBtn","click",()=>this.undo()),this._bindIfExists("redoBtn","click",()=>this.redo()),this._bindIfExists("rotateLeftBtn","click",()=>{let t=document.getElementById(this.elements.rotationLeftInput),s=this.options.rotationStep;if(t){let e=parseFloat(t.value);isNaN(e)||(s=e)}this.rotateImage(this.currentRotation-s)}),this._bindIfExists("rotateRightBtn","click",()=>{let t=document.getElementById(this.elements.rotationRightInput),s=this.options.rotationStep;if(t){let e=parseFloat(t.value);isNaN(e)||(s=e)}this.rotateImage(this.currentRotation+s)}),this._bindIfExists("cropBtn","click",()=>this.enterCropMode()),this._bindIfExists("applyCropBtn","click",()=>{this.applyCrop().catch(t=>this._reportError("applyCrop failed",t))}),this._bindIfExists("cancelCropBtn","click",()=>this.cancelCrop())}_bindIfExists(t,s,e){let i=document.getElementById(this.elements[t]);i&&(i.addEventListener(s,e),this._handlersByElementKey=this._handlersByElementKey||{},this._handlersByElementKey[t]||(this._handlersByElementKey[t]=[]),this._handlersByElementKey[t].push({eventName:s,handler:e}))}_loadImageFile(t){if(!t||!t.type.startsWith("image/"))return;let s=new FileReader;s.onload=e=>this.loadImage(e.target.result),s.onerror=e=>{this._reportError("Image file could not be read",e)},s.readAsDataURL(t)}async loadImage(t){if(!this._fabricLoaded||!this.canvas||!t||typeof t!="string"||!t.startsWith("data:image/"))return;this._setPlaceholderVisible(!1),this._syncContainerOverflow();let s=await this._createImageElement(t),e=t;if(this.options.downsampleOnLoad&&(s.naturalWidth>this.options.downsampleMaxWidth||s.naturalHeight>this.options.downsampleMaxHeight)){let n=Math.min(this.options.downsampleMaxWidth/s.naturalWidth,this.options.downsampleMaxHeight/s.naturalHeight),a=Math.round(s.naturalWidth*n),o=Math.round(s.naturalHeight*n);e=this._resampleImageToDataURL(s,a,o,this.options.downsampleQuality)}return new Promise((i,n)=>{v.Image.fromURL(e,a=>{try{if(!a)throw new Error("Image could not be loaded");this.canvas.discardActiveObject(),this._hideAllMaskLabels(),this.canvas.clear(),this.canvas.setBackgroundColor(this.options.backgroundColor,this.canvas.renderAll.bind(this.canvas)),a.set({originX:"left",originY:"top",selectable:!1,evented:!1});let o=a.width,r=a.height,h=this._getContainerViewportSize(),c=h.width,l=h.height;if(this.options.fitImageToCanvas){let u=Math.max(1,Math.min(this.options.canvasWidth,c)-1),d=Math.max(1,Math.min(this.options.canvasHeight,l)-1);this._setCanvasSizeInt(u,d);let p=Math.min(u/o,d/r,1);a.set({left:0,top:0}),a.scale(p),this.baseImageScale=a.scaleX||1}else if(this.options.coverImageToCanvas){let u=this._calculateCoverCanvasLayout(o,r);this._setCanvasSizeInt(u.canvasWidth,u.canvasHeight),a.set({left:0,top:0}),a.scale(u.scale),this.baseImageScale=a.scaleX||1}else if(this.options.expandCanvasToImage){let u=Math.max(c,Math.floor(o)),d=Math.max(l,Math.floor(r));this._setCanvasSizeInt(u,d),a.set({left:0,top:0}),a.scale(1),this.baseImageScale=1}else{let u=Math.max(this.options.canvasWidth,c),d=Math.max(this.options.canvasHeight,l);this._setCanvasSizeInt(u,d);let p=Math.min(u/o,d/r,1);a.set({left:0,top:0}),a.scale(p),this.baseImageScale=a.scaleX||1}this.originalImage=a,this.canvas.add(a),this.canvas.sendToBack(a),this._lastMask=null,this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null,this.maskCounter=0,this.currentScale=1,this.currentRotation=0,this._updateInputs(),this._updateMaskList(),this.isImageLoadedToCanvas=!0,this._updateUI(),this.canvas.renderAll();try{this._lastSnapshot=this._serializeCanvasState()}catch(u){this._reportWarning("loadImage: failed to capture initial canvas snapshot",u)}typeof this.onImageLoaded=="function"&&this.onImageLoaded(),i()}catch(o){n(o)}},{crossOrigin:"anonymous"})})}isImageLoaded(){let t=w();return!!(this.originalImage&&t&&this.originalImage instanceof t.Image&&this.originalImage.width>0&&this.originalImage.height>0)}_createImageElement(t){return new Promise((s,e)=>{let i=new Image;i.onload=()=>{i.onload=null,i.onerror=null,s(i)},i.onerror=n=>{i.onload=null,i.onerror=null,e(n)},i.src=t})}_resampleImageToDataURL(t,s,e,i=.92){let n=document.createElement("canvas");return n.width=s,n.height=e,n.getContext("2d").drawImage(t,0,0,t.naturalWidth,t.naturalHeight,0,0,s,e),n.toDataURL("image/jpeg",i)}_setCanvasSizeInt(t,s){let e=Math.max(1,Math.round(Number(t)||1)),i=Math.max(1,Math.round(Number(s)||1));this.canvas.setWidth(e),this.canvas.setHeight(i),typeof this.canvas.calcOffset=="function"&&this.canvas.calcOffset(),this.canvasElement&&(this.canvasElement.style.width=e+"px",this.canvasElement.style.height=i+"px",this.canvasElement.style.maxWidth="none")}_ceilCanvasDimension(t){let s=Number(t)||0,e=Math.round(s);return Math.abs(s-e)<.01?e:Math.ceil(s)}_getContainerViewportSize(){if(!this.containerElement)return{width:Math.max(1,Math.floor(this.options.canvasWidth||1)),height:Math.max(1,Math.floor(this.options.canvasHeight||1))};if(this._hasFixedContainerScrollbars())return{width:Math.max(1,Math.floor(this.containerElement.clientWidth||this.options.canvasWidth||1)),height:Math.max(1,Math.floor(this.containerElement.clientHeight||this.options.canvasHeight||1))};let t=this.containerElement.style.overflow;this.containerElement.style.overflow="hidden";let s=Math.max(1,Math.floor(this.containerElement.clientWidth||this.options.canvasWidth||1)),e=Math.max(1,Math.floor(this.containerElement.clientHeight||this.options.canvasHeight||1));return this.containerElement.style.overflow=t,{width:s,height:e}}_hasFixedContainerScrollbars(){if(!this.containerElement)return!1;let t=this.containerElement.style.overflow,s=this.containerElement.style.overflowX,e=this.containerElement.style.overflowY,i="",n="",a="";if(typeof window<"u"&&typeof window.getComputedStyle=="function"){let o=window.getComputedStyle(this.containerElement);i=o.overflow,n=o.overflowX,a=o.overflowY}return[t,s,e,i,n,a].some(o=>o==="scroll")}_getScrollbarSize(){if(typeof document>"u"||!document.createElement||!document.body)return{width:0,height:0};let t=document.createElement("div");t.style.position="absolute",t.style.visibility="hidden",t.style.overflow="scroll",t.style.width="100px",t.style.height="100px",t.style.top="-9999px",document.body.appendChild(t);let s=Math.max(0,t.offsetWidth-t.clientWidth),e=Math.max(0,t.offsetHeight-t.clientHeight);return document.body.removeChild(t),{width:s,height:e}}_getScrollSafetyMargin(){return 2}_getScrollableCanvasSize(t,s,e=this._getContainerViewportSize()){if(this._hasFixedContainerScrollbars()){let h=this._getScrollSafetyMargin(),c=Math.max(1,e.width-h),l=Math.max(1,e.height-h);return{width:t>e.width+.5?this._ceilCanvasDimension(t):c,height:s>e.height+.5?this._ceilCanvasDimension(s):l,viewportWidth:e.width,viewportHeight:e.height,hasHorizontal:!0,hasVertical:!0}}let i=this._getScrollbarSize(),n=!1,a=!1,o=e.width,r=e.height;for(let h=0;h<4;h+=1){o=Math.max(1,e.width-(n?i.width:0)),r=Math.max(1,e.height-(a?i.height:0));let c=s>r+.5,l=t>o+.5;if(c===n&&l===a)break;n=c,a=l}return o=Math.max(1,e.width-(n?i.width:0)),r=Math.max(1,e.height-(a?i.height:0)),{width:a?this._ceilCanvasDimension(t):o,height:n?this._ceilCanvasDimension(s):r,viewportWidth:o,viewportHeight:r,hasHorizontal:a,hasVertical:n}}_calculateCoverCanvasLayout(t,s){let e=this._getContainerViewportSize();if(this._hasFixedContainerScrollbars()){let d=this._getScrollSafetyMargin(),p=Math.max(1,e.width-d),g=Math.max(1,e.height-d),m=Math.min(1,Math.max(p/t,g/s)),f=t*m,C=s*m,y=this._getScrollableCanvasSize(f,C,e);return{scale:m,canvasWidth:y.width,canvasHeight:y.height}}let i=this._getScrollbarSize(),n=!1,a=!1,o=1,r=t,h=s,c=e.width,l=e.height;for(let d=0;d<4;d+=1){c=Math.max(1,e.width-(n?i.width:0)),l=Math.max(1,e.height-(a?i.height:0)),o=Math.min(1,Math.max(c/t,l/s)),r=t*o,h=s*o;let p=h>l+.5,g=r>c+.5;if(p===n&&g===a)break;n=p,a=g}let u=this._getScrollableCanvasSize(r,h,e);return{scale:o,canvasWidth:u.width,canvasHeight:u.height}}_getStateProperties(){return["maskId","maskName","maskLabel","isCropRect","originalAlpha","originalStroke","originalStrokeWidth","selectable","evented","hasControls","lockRotation","borderColor","cornerColor","cornerSize","transparentCorners","strokeUniform","strokeDashArray"]}_getMaskNormalStyle(t){let s=Number(t&&t.originalStrokeWidth),e=Number(t&&t.originalAlpha),i={stroke:t&&t.originalStroke||"#ccc",strokeWidth:Number.isFinite(s)?s:1};return Number.isFinite(e)&&(i.opacity=e),i}_withNormalizedMaskStyles(t){if(!this.canvas)return t();let s=this.canvas.getObjects().filter(i=>i.maskId),e=s.map(i=>({object:i,stroke:i.stroke,strokeWidth:i.strokeWidth,opacity:i.opacity}));try{return s.forEach(i=>{i.set(this._getMaskNormalStyle(i))}),t()}finally{e.forEach(i=>{try{i.object.set({stroke:i.stroke,strokeWidth:i.strokeWidth,opacity:i.opacity})}catch(n){}})}}_restoreMaskControls(t){if(!t)return;let s=Number(t.cornerSize);t.set({selectable:t.selectable!==!1,evented:t.evented!==!1,hasControls:t.hasControls!==!1,lockRotation:typeof t.lockRotation=="boolean"?t.lockRotation:!this.options.maskRotatable,borderColor:t.borderColor||"red",cornerColor:t.cornerColor||"black",cornerSize:Number.isFinite(s)?s:8,transparentCorners:t.transparentCorners===!0,strokeUniform:t.strokeUniform!==!1}),typeof t.setCoords=="function"&&t.setCoords()}_serializeCanvasState(){return this.canvas?this._withNormalizedMaskStyles(()=>{let t=this.canvas.toJSON(this._getStateProperties());return Array.isArray(t.objects)&&(t.objects=t.objects.filter(s=>!s.isCropRect&&!s.maskLabel)),JSON.stringify(t)}):null}_normalizeQuality(t){let s=Number(t);return Number.isFinite(s)?Math.max(0,Math.min(1,s)):this.options.downsampleQuality??.92}_normalizeImageFormat(t){return{jpeg:"jpeg",jpg:"jpeg","image/jpeg":"jpeg",png:"png","image/png":"png",webp:"webp","image/webp":"webp"}[String(t||"jpeg").toLowerCase()]||"jpeg"}_getClampedCanvasRegion(t,s={}){let e=Math.max(1,Math.round(this.canvas.getWidth())),i=Math.max(1,Math.round(this.canvas.getHeight())),n=Number(t.left)||0,a=Number(t.top)||0,o=Math.max(0,Number(t.width)||0),r=Math.max(0,Number(t.height)||0),c=s.includePartialPixels!==!1?Math.ceil:Math.floor,l=Math.min(e-1,Math.max(0,Math.floor(n))),u=Math.min(i-1,Math.max(0,Math.floor(a))),d=Math.min(e,Math.max(l+1,c(n+o))),p=Math.min(i,Math.max(u+1,c(a+r)));return{sx:l,sy:u,sw:Math.max(1,d-l),sh:Math.max(1,p-u)}}async _cropDataUrl(t,s,e,i,n,a,o="jpeg",r=.92){return new Promise((h,c)=>{let l=new Image;l.onload=()=>{try{let u=Math.max(1,Number(a)||1),d=Math.round(s*u),p=Math.round(e*u),g=Math.max(1,Math.round(i*u)),m=Math.max(1,Math.round(n*u)),f=document.createElement("canvas");f.width=g,f.height=m,f.getContext("2d").drawImage(l,d,p,g,m,0,0,g,m),h(f.toDataURL(`image/${o}`,r))}catch(u){c(u)}},l.onerror=c,l.src=t})}async _exportCanvasRegionToDataURL({sx:t,sy:s,sw:e,sh:i,multiplier:n=1,quality:a=.92,format:o="jpeg"}){let r=Math.max(1,Number(n)||1),h=this.canvas.toDataURL({format:o,quality:a,multiplier:r});return this._cropDataUrl(h,t,s,e,i,r,o,a)}_getObjectTopLeftPoint(t){if(!t)return{x:0,y:0};t.setCoords();let s=typeof t.getCoords=="function"?t.getCoords():null;if(s&&s.length)return s[0];let e=t.getBoundingRect(!0,!0);return{x:e.left,y:e.top}}_setObjectOriginKeepingPosition(t,s,e,i){!t||!i||!t.setPositionByOrigin||(t.set({originX:s,originY:e}),t.setPositionByOrigin(i,s,e),t.setCoords())}_alignObjectBoundingBoxToCanvasTopLeft(t){if(!t)return;t.setCoords();let s=t.getBoundingRect(!0,!0),e=s.left,i=s.top;t.set({left:(t.left||0)-e,top:(t.top||0)-i}),t.setCoords(),this.canvas.renderAll()}_updateCanvasSizeToImageBounds(){if(!this.originalImage)return;this.originalImage.setCoords();let t=this.originalImage.getBoundingRect(!0,!0),s=this._getScrollableCanvasSize(t.width,t.height);this._setCanvasSizeInt(s.width,s.height)}_expandCanvasToFitObject(t,s=10){if(!(!this.canvas||!t||!this.options.expandCanvasToImage))try{t.setCoords();let e=t.getBoundingRect(!0,!0),i=Math.ceil(e.left+e.width+s),n=Math.ceil(e.top+e.height+s),a=this.containerElement?Math.floor(this.containerElement.clientWidth||0):0,o=this.containerElement?Math.floor(this.containerElement.clientHeight||0):0,r=Math.max(this.canvas.getWidth(),a,i),h=Math.max(this.canvas.getHeight(),o,n);this._setCanvasSizeInt(r,h)}catch(e){this._reportWarning("expandCanvasToFitObject: failed to expand canvas",e)}}scaleImage(t,s={}){return this.animQueue.add(()=>this._scaleImageImpl(t,s))}_scaleImageImpl(t,s={}){if(!this.originalImage||this.isAnimating)return Promise.resolve();let e=s.saveHistory!==!1;t=Math.max(this.options.minScale,Math.min(this.options.maxScale,t)),this.currentScale=t,this.isAnimating=!0,this._updateUI();let i=this.baseImageScale*t,n=this._getObjectTopLeftPoint(this.originalImage);this._setObjectOriginKeepingPosition(this.originalImage,"left","top",n);let a=new Promise(r=>{this.originalImage.animate("scaleX",i,{duration:this.options.animationDuration,onChange:this.canvas.renderAll.bind(this.canvas),onComplete:r})}),o=new Promise(r=>{this.originalImage.animate("scaleY",i,{duration:this.options.animationDuration,onChange:this.canvas.renderAll.bind(this.canvas),onComplete:r})});return Promise.all([a,o]).then(()=>{this.originalImage.set({scaleX:i,scaleY:i}),this.originalImage.setCoords(),(this.options.expandCanvasToImage||this.options.coverImageToCanvas)&&this._updateCanvasSizeToImageBounds(),this._alignObjectBoundingBoxToCanvasTopLeft(this.originalImage),this.canvas.getObjects().forEach(r=>{r.maskId&&this._syncMaskLabel(r)}),this.isAnimating=!1,this._updateInputs(),this._updateUI(),e&&this.saveState()}).catch(()=>{this.isAnimating=!1,this._updateUI()})}rotateImage(t,s={}){return this.animQueue.add(()=>this._rotateImageImpl(t,s))}_rotateImageImpl(t,s={}){if(!this.originalImage||this.isAnimating||isNaN(t))return Promise.resolve();let e=s.saveHistory!==!1;this.currentRotation=t,this.isAnimating=!0,this._updateUI();let i=this.originalImage.getCenterPoint();return this._setObjectOriginKeepingPosition(this.originalImage,"center","center",i),new Promise(a=>{this.originalImage.animate("angle",t,{duration:this.options.animationDuration,onChange:this.canvas.renderAll.bind(this.canvas),onComplete:a})}).then(()=>{this.originalImage.set("angle",t),this.originalImage.setCoords(),(this.options.expandCanvasToImage||this.options.coverImageToCanvas)&&this._updateCanvasSizeToImageBounds(),this._alignObjectBoundingBoxToCanvasTopLeft(this.originalImage);let a=this._getObjectTopLeftPoint(this.originalImage);this._setObjectOriginKeepingPosition(this.originalImage,"left","top",a),this.canvas.getObjects().forEach(o=>{o.maskId&&this._syncMaskLabel(o)}),this.isAnimating=!1,this._updateInputs(),this._updateUI(),e&&this.saveState()}).catch(()=>{this.isAnimating=!1,this._updateUI()})}resetImageTransform(){return this.originalImage?this.animQueue.add(async()=>{let t=this._serializeCanvasState();await this._scaleImageImpl(1,{saveHistory:!1}),await this._rotateImageImpl(0,{saveHistory:!1});let s=this._serializeCanvasState();this._pushStateTransition(t,s)}).catch(t=>{this._reportError("resetImageTransform() failed",t)}):Promise.resolve()}reset(){return this.resetImageTransform()}loadFromState(t){return!t||!this.canvas?Promise.resolve():new Promise(s=>{try{let e=typeof t=="string"?JSON.parse(t):t;this.canvas.loadFromJSON(e,()=>{try{this._hideAllMaskLabels();let i=this.canvas.getObjects();if(this.originalImage=i.find(a=>a.type==="image"&&!a.maskId)||null,this.originalImage){this.originalImage.set({originX:"left",originY:"top",selectable:!1,evented:!1,hasControls:!1,hoverCursor:"default"}),this.canvas.sendToBack(this.originalImage),this.currentRotation=Number(this.originalImage.angle)||0;let a=Number(this.baseImageScale)||1,o=Number(this.originalImage.scaleX)||a;this.currentScale=o/a}else this.currentScale=1,this.currentRotation=0;let n=i.filter(a=>a.maskId);n.forEach(a=>{this._restoreMaskControls(a),this._rebindMaskEvents(a),a.set(this._getMaskNormalStyle(a))}),this.maskCounter=n.reduce((a,o)=>Math.max(a,o.maskId),0),this._lastMask=n.length?n[n.length-1]:null,this._lastMask||(this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null),this.isImageLoadedToCanvas=!!this.originalImage,this.canvas.renderAll(),this._updateInputs(),this._updateMaskList(),this._updatePlaceholderStatus(),this._lastSnapshot=this._serializeCanvasState(),this._updateUI()}catch(i){this._reportError("loadFromState() failed",i)}finally{s()}})}catch(e){this._reportError("loadFromState() failed",e),s()}})}saveState(){if(!this.canvas)return;let t=this.canvas.getActiveObject();this._hideAllMaskLabels();try{let s=this._serializeCanvasState(),e=this._lastSnapshot||s;if(s===e)return;let i=!1,n=new b(()=>{if(i)return this.loadFromState(s);i=!0},()=>this.loadFromState(e));this.historyManager.execute(n),this._lastSnapshot=s}catch(s){this._reportWarning("saveState: failed to save canvas snapshot",s)}finally{t&&t.maskId&&this.canvas.getObjects().includes(t)&&this._handleSelectionChanged([t]),this._updateUI()}}_pushStateTransition(t,s){if(!t||!s||t===s)return;this.historyManager||(this.historyManager=new I(this.maxHistorySize||50));let e=new b(()=>this.loadFromState(s),()=>this.loadFromState(t));this.historyManager.push(e),this._lastSnapshot=s,this._updateUI()}undo(){return this.historyManager.undo().then(()=>{this._updateUI()}).catch(t=>{this._reportError("undo failed",t)})}redo(){return this.historyManager.redo().then(()=>{this._updateUI()}).catch(t=>{this._reportError("redo failed",t)})}_rebindMaskEvents(t){if(!t)return;if(t.__imageEditorMaskHandlers)try{t.off("mouseover",t.__imageEditorMaskHandlers.mouseover),t.off("mouseout",t.__imageEditorMaskHandlers.mouseout)}catch(o){}let s={};Number.isFinite(Number(t.originalAlpha))||(s.originalAlpha=Number.isFinite(Number(t.opacity))?Number(t.opacity):.5),t.originalStroke||(s.originalStroke=t.stroke||"#ccc"),Number.isFinite(Number(t.originalStrokeWidth))||(s.originalStrokeWidth=Number.isFinite(Number(t.strokeWidth))?Number(t.strokeWidth):1),Object.keys(s).length&&t.set(s);let e={stroke:t.originalStroke||"#ccc",strokeWidth:t.originalStrokeWidth,opacity:t.originalAlpha},i={stroke:"#ff5500",strokeWidth:2,opacity:Math.min(t.originalAlpha+.2,1)},n=()=>{t.set(i),t.canvas&&t.canvas.requestRenderAll()},a=()=>{t.set(e),t.canvas&&t.canvas.requestRenderAll()};t.on("mouseover",n),t.on("mouseout",a),t.__imageEditorMaskHandlers={mouseover:n,mouseout:a}}createMask(t={}){if(!this.canvas)return null;let s=t.shape||"rect",e={shape:s,width:this.options.defaultMaskWidth,height:this.options.defaultMaskHeight,color:"rgba(0,0,0,0.5)",alpha:.5,gap:5,left:void 0,top:void 0,angle:0,selectable:!0,...t},i=10,n=i,a=i,o=(d,p)=>{if(typeof d=="function")return d(this.canvas,this.options);if(typeof d=="string"&&d.endsWith("%")){let g=parseFloat(d)/100;return Math.floor((this.canvas?this.canvas.getWidth():0)*g)}return d??p};if(e.left===void 0&&this._lastMask){let d=this._lastMask,p=d.left;d.getScaledWidth?p+=d.getScaledWidth():d.width&&(p+=d.width*(d.scaleX??1)),n=Math.round(p+e.gap),a=d.top??i}else n=o(e.left,i),a=o(e.top,i);e.width=o(e.width,this.options.defaultMaskWidth),e.height=o(e.height,this.options.defaultMaskHeight);let r;if(typeof e.fabricGenerator=="function")r=e.fabricGenerator(e,this.canvas,this.options);else switch(s){case"circle":r=new v.Circle({left:n,top:a,radius:o(e.radius,Math.min(e.width,e.height)/2),fill:e.color,opacity:e.alpha,angle:e.angle,...e.styles});break;case"ellipse":r=new v.Ellipse({left:n,top:a,rx:o(e.rx,e.width/2),ry:o(e.ry,e.height/2),fill:e.color,opacity:e.alpha,angle:e.angle,...e.styles});break;case"polygon":{let d=e.points||[];Array.isArray(d)&&d.length&&typeof d[0]=="object"&&(d=d.map(p=>({x:Number(p.x),y:Number(p.y)}))),r=new v.Polygon(d,{left:n,top:a,fill:e.color,opacity:e.alpha,angle:e.angle,...e.styles});break}case"rect":default:r=new v.Rect({left:n,top:a,width:o(e.width,this.options.defaultMaskWidth),height:o(e.height,this.options.defaultMaskHeight),fill:e.color,opacity:e.alpha,angle:e.angle,rx:e.rx,ry:e.ry,...e.styles})}let h=e.styles||{},c=d=>Object.prototype.hasOwnProperty.call(h,d),l={selectable:e.selectable!==!1,hasControls:"hasControls"in e?e.hasControls:!0,lockRotation:!this.options.maskRotatable,borderColor:"borderColor"in e?e.borderColor:"red",cornerColor:"cornerColor"in e?e.cornerColor:"black",cornerSize:"cornerSize"in e?e.cornerSize:8,transparentCorners:"transparentCorners"in e?e.transparentCorners:!1,stroke:c("stroke")?h.stroke:"#ccc",strokeWidth:c("strokeWidth")?h.strokeWidth:1,strokeUniform:"strokeUniform"in e?e.strokeUniform:c("strokeUniform")?h.strokeUniform:!0};c("strokeDashArray")&&(l.strokeDashArray=h.strokeDashArray),r.set(l),r.setCoords(),r.set({originalAlpha:e.alpha,originalStroke:r.stroke||"#ccc",originalStrokeWidth:Number.isFinite(Number(r.strokeWidth))?Number(r.strokeWidth):1}),this._rebindMaskEvents(r),this._expandCanvasToFitObject(r),this._lastMaskInitialLeft=n,this._lastMaskInitialTop=a,this._lastMaskInitialWidth=o(e.width,this.options.defaultMaskWidth);let u=++this.maskCounter;return r.set({maskId:u,maskName:`${this.options.maskName}${u}`}),this._lastMask=r,this.canvas.add(r),this.canvas.bringToFront(r),e.selectable&&this.canvas.setActiveObject(r),this._handleSelectionChanged([r]),this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),this.saveState(),typeof e.onCreate=="function"&&e.onCreate(r,this.canvas),r}addMask(t={}){return this.createMask(t)}removeSelectedMask(){let t=this.canvas.getActiveObject(),s=this._getModifiedMasks(t);if(!s.length)return;this.canvas.discardActiveObject(),s.forEach(i=>{this._removeLabelForMask(i),this.canvas.remove(i)});let e=this.canvas.getObjects().filter(i=>i.maskId);this._lastMask=e.length?e[e.length-1]:null,this._lastMask||(this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null),this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),this.saveState()}removeAllMasks(t={}){let s=t.saveHistory!==!1,e=this.canvas.getObjects().filter(i=>i.maskId);e.forEach(i=>this._removeLabelForMask(i)),e.forEach(i=>this.canvas.remove(i)),this.canvas.discardActiveObject(),this._lastMask=null,this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null,this._updateMaskList(),this._updateUI(),this.canvas.renderAll(),s&&this.saveState()}_removeLabelForMask(t){if(!(!t||!this.canvas)&&t.__label){try{this.canvas.getObjects().includes(t.__label)&&this.canvas.remove(t.__label)}catch(s){}try{delete t.__label}catch(s){}}}_createLabelForMask(t){if(!t||!this.options.maskLabelOnSelect)return;this._removeLabelForMask(t);let s=null;if(this.options.label&&typeof this.options.label.create=="function"&&(s=this.options.label.create(t,v)),!s){let e=t.maskName,i={left:0,top:0,fontSize:12,fill:"#fff",backgroundColor:"rgba(0,0,0,0.7)",selectable:!1,evented:!1,padding:2,originX:"left",originY:"top"};if(this.options.label){if(typeof this.options.label.getText=="function"){let n=this.canvas?this.canvas.getObjects().filter(o=>o.maskId):[],a=Math.max(0,n.indexOf(t));e=this.options.label.getText(t,a)}this.options.label.textOptions&&Object.assign(i,this.options.label.textOptions)}s=new v.Text(e,i)}s.maskLabel=!0,t.__label=s,this.canvas.add(s),this.canvas.bringToFront(s),this._syncMaskLabel(t)}_hideAllMaskLabels(){if(!this.canvas)return;let t=this.canvas.getObjects();t.filter(e=>e.maskLabel).forEach(e=>{try{t.includes(e)&&this.canvas.remove(e)}catch(i){}}),t.forEach(e=>{if(e.maskId&&e.__label)try{delete e.__label}catch(i){}})}_syncMaskLabel(t){if(!t||!this.options.maskLabelOnSelect||!t.__label)return;let s=t.getCoords?t.getCoords():null;if(!s||s.length<4)return;let e=s[0],i=t.getCenterPoint(),n=i.x-e.x,a=i.y-e.y,o=Math.sqrt(n*n+a*a)||1,r=n/o,h=a/o,c=Math.max(0,this.options.maskLabelOffset??3),l=e.x+r*c,u=e.y+h*c;t.__label.set({left:Math.round(l),top:Math.round(u),angle:t.angle||0,originX:"left",originY:"top",visible:!0}),t.__label.setCoords(),typeof this.canvas.requestRenderAll=="function"?this.canvas.requestRenderAll():this.canvas.renderAll()}_showLabelForMask(t){t&&this.options.maskLabelOnSelect&&(t.__label||this._createLabelForMask(t),t.__label.set({visible:!0}),this._syncMaskLabel(t))}_handleSelectionChanged(t){let s=(t||[]).find(i=>i.maskId);this.canvas.getObjects().filter(i=>i.maskId).forEach(i=>{if(i!==s){if(i.__label){try{this.canvas.remove(i.__label)}catch(a){}delete i.__label}let n=Number(i.originalStrokeWidth);i.set({stroke:i.originalStroke||"#ccc",strokeWidth:Number.isFinite(n)?n:1})}else i.set({stroke:"#ff0000",strokeWidth:1})}),s&&this._showLabelForMask(s),this._updateMaskListSelection(s),this.canvas.renderAll(),this._updateUI()}_updateMaskList(){let t=document.getElementById(this.elements.maskList);if(!t)return;t.innerHTML="",this.canvas.getObjects().filter(e=>e.maskId).forEach(e=>{let i=document.createElement("li");i.className="list-group-item mask-item",i.textContent=e.maskName,i.onclick=()=>{this.canvas.setActiveObject(e),this._handleSelectionChanged([e])},t.appendChild(i)})}_updateMaskListSelection(t){let s=document.getElementById(this.elements.maskList);if(!s)return;s.querySelectorAll(".mask-item").forEach(i=>{let n=!!t&&i.textContent===t.maskName;i.classList.toggle("active",n)})}async mergeMasks(){if(!(!this.originalImage||!this.canvas.getObjects().filter(s=>s.maskId).length)){this.canvas.discardActiveObject(),this.canvas.renderAll();try{let s=this._serializeCanvasState(),e=await this.exportImageBase64({exportImageArea:!0,multiplier:this.options.exportMultiplier});this.removeAllMasks({saveHistory:!1}),await this.loadImage(e);let i=this._serializeCanvasState();this._pushStateTransition(s,i)}catch(s){this._reportError("merge error",s)}}}async merge(){return this.mergeMasks()}downloadImage(t=this.options.defaultDownloadFileName){if(!this.originalImage)return;let s=this.options.exportImageAreaByDefault;this.exportImageBase64({exportImageArea:s,multiplier:this.options.exportMultiplier}).then(e=>{let i=document.createElement("a");i.download=t,i.href=e,document.body.appendChild(i),i.click(),document.body.removeChild(i)}).catch(e=>this._reportError("download error",e))}async exportImageBase64(t={}){if(!this.originalImage)throw new Error("No image loaded");let s=typeof t.exportImageArea=="boolean"?t.exportImageArea:this.options.exportImageAreaByDefault,e=t.multiplier||this.options.exportMultiplier||1,i=this._normalizeQuality(t.quality??this.options.downsampleQuality),n=this._normalizeImageFormat(t.fileType||t.format);if(!s){let h=this.canvas.getObjects().filter(l=>l.maskId||l.maskLabel),c=h.map(l=>({object:l,visible:l.visible}));try{h.forEach(m=>{m.set({visible:!1})}),this.canvas.discardActiveObject(),this.canvas.renderAll(),this.originalImage.setCoords();let l=this.originalImage.getBoundingRect(!0,!0),{sx:u,sy:d,sw:p,sh:g}=this._getClampedCanvasRegion(l,{includePartialPixels:!1});return await this._exportCanvasRegionToDataURL({sx:u,sy:d,sw:p,sh:g,multiplier:e,quality:i,format:n})}finally{c.forEach(l=>{try{l.object.set({visible:l.visible})}catch(u){}}),this.canvas.renderAll()}}let a=this.canvas.getObjects().filter(h=>h.maskId),o=a.map(h=>({object:h,opacity:h.opacity,fill:h.fill,strokeWidth:h.strokeWidth,stroke:h.stroke,selectable:h.selectable,lockRotation:h.lockRotation})),r;try{a.forEach(p=>this._removeLabelForMask(p)),this.canvas.discardActiveObject(),this.canvas.renderAll(),a.forEach(p=>{p.set({opacity:1,fill:"#000000",strokeWidth:0,stroke:null,selectable:!1}),p.setCoords()}),this.canvas.renderAll(),this.originalImage.setCoords();let h=this.originalImage.getBoundingRect(!0,!0),{sx:c,sy:l,sw:u,sh:d}=this._getClampedCanvasRegion(h,{includePartialPixels:!1});r=await this._exportCanvasRegionToDataURL({sx:c,sy:l,sw:u,sh:d,multiplier:e,quality:i,format:n})}finally{o.forEach(h=>{try{h.object.set({opacity:h.opacity,fill:h.fill,strokeWidth:h.strokeWidth,stroke:h.stroke,selectable:h.selectable,lockRotation:h.lockRotation}),h.object.setCoords()}catch(c){}}),this.canvas.renderAll()}return r}async getImageBase64(t={}){return this.exportImageBase64(t)}async exportImageFile(t={}){if(!this.originalImage)throw new Error("No image loaded");let{mergeMask:s=!0,fileType:e="jpeg",quality:i=this.options.downsampleQuality??.92,multiplier:n=this.options.exportMultiplier??1,fileName:a=this.options.defaultDownloadFileName??"exported_image.jpg"}=t,o=this._normalizeImageFormat(e),r;s?r=await this.exportImageBase64({exportImageArea:!0,multiplier:n,quality:i,fileType:o}):r=await this.exportImageBase64({exportImageArea:!1,multiplier:n,quality:i,fileType:o});let h=r;h.startsWith(`data:image/${o}`)||(h=await new Promise((p,g)=>{let m=new window.Image;m.crossOrigin="Anonymous",m.onload=()=>{try{let f=document.createElement("canvas");f.width=m.width,f.height=m.height,f.getContext("2d").drawImage(m,0,0);let y=f.toDataURL(`image/${o}`,i);p(y)}catch(f){g(f)}},m.onerror=g,m.src=r}));let c=atob(h.split(",")[1]),l=`image/${o}`,u=c.length,d=new Uint8Array(u);for(;u--;)d[u]=c.charCodeAt(u);return new File([d],a,{type:l})}_clearMaskPlacementMemory(){this._lastMask=null,this._lastMaskInitialLeft=null,this._lastMaskInitialTop=null,this._lastMaskInitialWidth=null}async _restoreStateAfterCropFailure(t,s,e){if(this._reportError(s,e),this._cropRect&&this.canvas&&this._removeCropRect(),this._cropRect=null,this._cropMode=!1,this.canvas&&this._prevSelectionSetting!==void 0&&(this.canvas.selection=!!this._prevSelectionSetting),this._prevSelectionSetting=void 0,t)try{await this.loadFromState(t)}catch(i){this._reportError("applyCrop: rollback failed",i)}this._updateUI(),this.canvas&&this.canvas.renderAll()}_restoreCropObjectState(){Array.isArray(this._cropPrevEvented)&&this._cropPrevEvented.forEach(t=>{try{t.object.set({evented:t.evented,selectable:t.selectable,visible:t.visible})}catch(s){}}),this._cropPrevEvented=null}_removeCropRect(){if(this._cropRect){try{this._cropHandlers&&this._cropHandlers.length&&this._cropHandlers.forEach(t=>{t.handlers.forEach(s=>{t.target.off(s.eventName,s.handler)})})}catch(t){}try{this.canvas.remove(this._cropRect)}catch(t){}this._cropRect=null,this._cropHandlers=[]}}enterCropMode(){if(!this.canvas||!this.originalImage||this._cropMode||!this.isImageLoaded())return;this._cropMode=!0,this._prevSelectionSetting=this.canvas.selection,this.canvas.selection=!1,this.canvas.discardActiveObject(),this.originalImage.setCoords();let t=this.originalImage.getBoundingRect(!0,!0),s=this.options.crop&&this.options.crop.padding?this.options.crop.padding:10,e=Math.max(0,Math.floor(t.left+s)),i=Math.max(0,Math.floor(t.top+s)),n=Math.min(this.options.crop.minWidth||50,Math.floor(t.width-s*2)),a=Math.min(this.options.crop.minHeight||50,Math.floor(t.height-s*2)),o=new v.Rect({left:e,top:i,width:n,height:a,fill:"rgba(0,0,0,0.12)",stroke:"#00aaff",strokeDashArray:[6,4],strokeWidth:1,strokeUniform:!0,selectable:!0,hasRotatingPoint:!!(this.options.crop&&this.options.crop.allowRotationOfCropRect),lockRotation:!(this.options.crop&&this.options.crop.allowRotationOfCropRect),cornerSize:8,objectCaching:!1,originX:"left",originY:"top"});this.canvas.add(o),o.isCropRect=!0,this.canvas.bringToFront(o),this.canvas.setActiveObject(o),this._cropRect=o,this._cropPrevEvented=[];let r=!!(this.options.crop&&this.options.crop.hideMasksDuringCrop);this.canvas.getObjects().forEach(c=>{if(c!==o){this._cropPrevEvented.push({object:c,evented:c.evented,selectable:c.selectable,visible:c.visible});try{let l={evented:!1,selectable:!1};r&&(c.maskId||c.maskLabel)&&(l.visible=!1),c.set(l)}catch(l){}}});let h=()=>{try{o.setCoords(),this.canvas.requestRenderAll()}catch(c){}};o.on("modified",h),o.on("moving",h),o.on("scaling",h),this._cropHandlers.push({target:o,handlers:[{eventName:"modified",handler:h},{eventName:"moving",handler:h},{eventName:"scaling",handler:h}]}),this._updateUI(),this.canvas.renderAll()}cancelCrop(){!this.canvas||!this._cropMode||(this._removeCropRect(),this._restoreCropObjectState(),this._cropMode=!1,this.canvas.selection=!!this._prevSelectionSetting,this._prevSelectionSetting=void 0,this.canvas.discardActiveObject(),this._updateUI(),this.canvas.renderAll())}async applyCrop(){if(!this.canvas||!this._cropMode||!this._cropRect)return;this._cropRect.setCoords();let t=this._cropRect.getBoundingRect(!0,!0),{sx:s,sy:e,sw:i,sh:n}=this._getClampedCanvasRegion(t),a=!!(this.options.crop&&this.options.crop.preserveMasksAfterCrop);this._restoreCropObjectState();let o=null;try{o=this._serializeCanvasState()}catch(l){this._reportWarning("applyCrop: could not serialize before state",l),o=null}let r=[];try{let l=this.canvas.getObjects().filter(u=>u.maskId);l&&l.length&&(l.forEach(u=>{try{u.setCoords();let d=u.getBoundingRect(!0,!0),p=d.left<s+i&&d.left+d.width>s&&d.top<e+n&&d.top+d.height>e;this._removeLabelForMask(u),this.canvas.remove(u),a&&p&&(u.set({left:(u.left||0)-s,top:(u.top||0)-e,visible:!0}),u.setCoords(),r.push(u))}catch(d){this._reportWarning("applyCrop: failed to remove mask",d)}}),this._clearMaskPlacementMemory(),this.canvas.discardActiveObject(),this.canvas.renderAll())}catch(l){this._reportWarning("applyCrop: error while removing masks",l)}this._removeCropRect(),this._cropMode=!1,this.canvas.selection=!!this._prevSelectionSetting,this._prevSelectionSetting=void 0;let h;try{h=await this._exportCanvasRegionToDataURL({sx:s,sy:e,sw:i,sh:n,multiplier:1,quality:this._normalizeQuality(this.options.downsampleQuality),format:"jpeg"})}catch(l){await this._restoreStateAfterCropFailure(o,"applyCrop: failed to create cropped image",l);return}try{await this.loadImage(h),r.length&&(r.forEach(l=>{this._rebindMaskEvents(l),this.canvas.add(l),this.canvas.bringToFront(l)}),this._lastMask=r[r.length-1],this.maskCounter=r.reduce((l,u)=>Math.max(l,u.maskId||0),this.maskCounter),this._updateMaskList(),this.canvas.renderAll())}catch(l){await this._restoreStateAfterCropFailure(o,"applyCrop: loadImage(croppedBase64) failed",l);return}let c=null;try{c=this._serializeCanvasState()}catch(l){this._reportWarning("applyCrop: failed to serialize after state",l),c=null}try{this._pushStateTransition(o,c)}catch(l){this._reportWarning("applyCrop: failed to push history command",l)}this._updateUI(),this.canvas.renderAll()}_updateInputs(){let t=document.getElementById(this.elements.scaleRate);t&&(t.value=Math.round(this.currentScale*100))}_updateUI(){let t=!!this.originalImage,e=(t?this.canvas.getObjects().filter(c=>c.maskId):[]).length>0,i=this.canvas.getActiveObject(),n=i&&i.maskId,a=this.currentScale===1&&this.currentRotation===0,o=this.historyManager?.canUndo(),r=this.historyManager?.canRedo();if(!!this._cropMode){for(let c of Object.keys(this.elements||{}))document.getElementById(this.elements[c])&&(c==="applyCropBtn"||c==="cancelCropBtn"?this._setDisabled(c,!1):this._setDisabled(c,!0));return}this._setDisabled("zoomInBtn",!t||this.isAnimating||this.currentScale>=this.options.maxScale),this._setDisabled("zoomOutBtn",!t||this.isAnimating||this.currentScale<=this.options.minScale),this._setDisabled("rotateLeftBtn",!t||this.isAnimating),this._setDisabled("rotateRightBtn",!t||this.isAnimating),this._setDisabled("addMaskBtn",!t||this.isAnimating),this._setDisabled("removeMaskBtn",!n||this.isAnimating),this._setDisabled("removeAllMasksBtn",!e||this.isAnimating),this._setDisabled("mergeBtn",!t||!e||this.isAnimating),this._setDisabled("downloadBtn",!t||this.isAnimating),this._setDisabled("resetBtn",!t||a||this.isAnimating),this._setDisabled("undoBtn",!t||this.isAnimating||!o),this._setDisabled("redoBtn",!t||this.isAnimating||!r),this._setDisabled("cropBtn",!t||this.isAnimating),this._setDisabled("applyCropBtn",!0),this._setDisabled("cancelCropBtn",!0),this._setDisabled("imageInput",this.isAnimating),this._setDisabled("uploadArea",this.isAnimating)}_setDisabled(t,s){let e=document.getElementById(this.elements[t]);if(e){if("disabled"in e){e.disabled=!!s;return}s?(e.setAttribute("aria-disabled","true"),e.style.pointerEvents="none"):(e.removeAttribute("aria-disabled"),e.style.pointerEvents="")}}_isElementDisabled(t){return t?"disabled"in t?!!t.disabled:t.getAttribute("aria-disabled")==="true":!1}_updatePlaceholderStatus(){this.options.showPlaceholder&&this._setPlaceholderVisible(!this.originalImage)}_setPlaceholderVisible(t){this.placeholderElement&&(t?(this.placeholderElement.classList.remove("d-none"),this.placeholderElement.classList.add("d-flex"),this.containerElement.classList.add("d-none")):(this.placeholderElement.classList.remove("d-flex"),this.placeholderElement.classList.add("d-none"),this.containerElement.classList.remove("d-none")))}dispose(){try{for(let t in this._handlersByElementKey||{}){let s=this._handlersByElementKey[t]||[],e=document.getElementById(this.elements[t]);e&&s.forEach(i=>{try{e.removeEventListener(i.eventName,i.handler)}catch(n){}})}}catch(t){}if(this._cropRect){try{this.canvas.remove(this._cropRect)}catch(t){}this._cropRect=null}if(this.containerElement&&this._containerOriginalOverflow!==void 0)try{this.containerElement.style.overflow=this._containerOriginalOverflow}catch(t){}if(this.canvas){try{this.canvas.dispose()}catch(t){}this.canvas=null,this.canvasElement=null,this.isImageLoadedToCanvas=!1}this._handlersByElementKey={}}},S=class{constructor(){this.queue=[],this.running=!1}async add(t){return new Promise((s,e)=>{this.queue.push({fn:t,resolve:s,reject:e}),this.running||this.processQueue()})}async processQueue(){if(this.queue.length===0){this.running=!1;return}this.running=!0;let{fn:t,resolve:s,reject:e}=this.queue.shift();try{let i=await t();s(i)}catch(i){e(i)}this.processQueue()}},b=class{constructor(t,s){this.execute=t,this.undo=s}},I=class{constructor(t=50){this.history=[],this.currentIndex=-1,this.maxSize=t,this.pending=Promise.resolve()}enqueue(t){let s=this.pending.then(t,t);return this.pending=s.catch(()=>{}),s}execute(t){t.execute(),this.push(t)}push(t){this.currentIndex<this.history.length-1&&(this.history=this.history.slice(0,this.currentIndex+1)),this.history.push(t),this.history.length>this.maxSize?this.history.shift():this.currentIndex++}canUndo(){return this.currentIndex>=0}canRedo(){return this.currentIndex<this.history.length-1}undo(){return this.enqueue(async()=>{if(this.currentIndex>=0){let t=this.currentIndex;await this.history[t].undo(),this.currentIndex=t-1}})}redo(){return this.enqueue(async()=>{if(this.currentIndex<this.history.length-1){let t=this.currentIndex+1;await this.history[t].execute(),this.currentIndex=t}})}};var E=k;var L=M&&(M.fabric||M.default||M);x(L);var T=E;export{E as ImageEditor,T as default};
|
|
14
9
|
//# sourceMappingURL=image-editor.esm.min.js.map
|