@markup-canvas/core 1.2.6 → 1.2.8

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/README.md CHANGED
@@ -194,7 +194,7 @@ iframe.contentWindow.postMessage({
194
194
  - `panLeft(distance?)`, `panRight(distance?)`, `panUp(distance?)`, `panDown(distance?)` - Pan operations
195
195
  - `fitToScreen()` - Fit content to viewport
196
196
  - `centerContent()` - Center content
197
- - `scrollToPoint(x, y)` - Pan to specific coordinates
197
+ - `panToPoint(x, y)` - Pan to specific coordinates
198
198
 
199
199
  **Rulers & Grid:**
200
200
  - `toggleRulers()`, `showRulers()`, `hideRulers()`
@@ -259,7 +259,7 @@ canvas.resetZoom(); // Reset to 100%
259
259
  canvas.setZoom(2.0); // Set specific zoom level
260
260
 
261
261
  // Pan controls
262
- canvas.scrollToPoint(x, y); // Pan to specific coordinates
262
+ canvas.panToPoint(x, y); // Pan to specific coordinates
263
263
  canvas.centerContent(); // Center the content
264
264
 
265
265
  // Fit to screen
@@ -65,7 +65,7 @@ export declare class MarkupCanvas {
65
65
  height: number;
66
66
  };
67
67
  isPointVisible(x: number, y: number): boolean;
68
- scrollToPoint(x: number, y: number): boolean;
68
+ panToPoint(x: number, y: number): boolean;
69
69
  getConfig(): Required<MarkupCanvasConfig>;
70
70
  updateConfig(newConfig: Partial<MarkupCanvasConfig>): void;
71
71
  updateThemeMode(mode: "light" | "dark"): void;
@@ -2,5 +2,5 @@ export { centerContent } from "./centerContent.js";
2
2
  export { panDown } from "./panDown.js";
3
3
  export { panLeft } from "./panLeft.js";
4
4
  export { panRight } from "./panRight.js";
5
+ export { panToPoint } from "./panToPoint.js";
5
6
  export { panUp } from "./panUp.js";
6
- export { scrollToPoint } from "./scrollToPoint.js";
@@ -0,0 +1,2 @@
1
+ import type { Canvas, MarkupCanvasConfig, Transform } from "@/types/index.js";
2
+ export declare function panToPoint(canvas: Canvas, config: Required<MarkupCanvasConfig>, x: number, y: number, updateTransform: (newTransform: Partial<Transform>) => boolean, transformLayer: HTMLElement): boolean;
@@ -1,2 +1,2 @@
1
1
  import type { MarkupCanvasConfig } from "@/types";
2
- export declare const EDITOR_PRESET: Required<MarkupCanvasConfig>;
2
+ export declare const EDITOR_PRESET: MarkupCanvasConfig;
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Markup Canvas
3
3
  * High-performance markup canvas with zoom and pan capabilities
4
- * @version 1.2.6
4
+ * @version 1.2.8
5
5
  */
6
6
  'use strict';
7
7
 
@@ -265,6 +265,9 @@ const DEFAULT_CONFIG = {
265
265
  width: 8000,
266
266
  height: 8000,
267
267
  enableAcceleration: true,
268
+ // Initial view transform
269
+ initialZoom: 1,
270
+ initialPan: { x: 0, y: 0 },
268
271
  // Global Instance Access
269
272
  name: "markupCanvas",
270
273
  enablePostMessageAPI: false,
@@ -460,15 +463,7 @@ function panRight(canvas, config, updateTransform) {
460
463
  return updateTransform(newTransform);
461
464
  }
462
465
 
463
- function panUp(canvas, config, updateTransform) {
464
- const panDistance = config.keyboardPanStep;
465
- const newTransform = {
466
- translateY: canvas.transform.translateY + panDistance,
467
- };
468
- return updateTransform(newTransform);
469
- }
470
-
471
- function scrollToPoint(canvas, config, x, y, updateTransform, transformLayer) {
466
+ function panToPoint(canvas, config, x, y, updateTransform, transformLayer) {
472
467
  return withTransition(transformLayer, config, () => {
473
468
  const bounds = getCanvasBounds(canvas, config);
474
469
  const centerX = bounds.width / 2;
@@ -483,6 +478,14 @@ function scrollToPoint(canvas, config, x, y, updateTransform, transformLayer) {
483
478
  });
484
479
  }
485
480
 
481
+ function panUp(canvas, config, updateTransform) {
482
+ const panDistance = config.keyboardPanStep;
483
+ const newTransform = {
484
+ translateY: canvas.transform.translateY + panDistance,
485
+ };
486
+ return updateTransform(newTransform);
487
+ }
488
+
486
489
  function createMatrixString(matrix) {
487
490
  return `matrix3d(${matrix.m11}, ${matrix.m12}, ${matrix.m13}, ${matrix.m14}, ${matrix.m21}, ${matrix.m22}, ${matrix.m23}, ${matrix.m24}, ${matrix.m31}, ${matrix.m32}, ${matrix.m33}, ${matrix.m34}, ${matrix.m41}, ${matrix.m42}, ${matrix.m43}, ${matrix.m44})`;
488
491
  }
@@ -1376,8 +1379,8 @@ function setupPostMessageEvents(canvas) {
1376
1379
  else if (action === "centerContent") {
1377
1380
  canvas.centerContent();
1378
1381
  }
1379
- else if (action === "scrollToPoint") {
1380
- canvas.scrollToPoint(args[0], args[1]);
1382
+ else if (action === "panToPoint") {
1383
+ canvas.panToPoint(args[0], args[1]);
1381
1384
  }
1382
1385
  else if (action === "resetView") {
1383
1386
  canvas.resetView();
@@ -2146,7 +2149,7 @@ function bindCanvasToWindow(canvas, config) {
2146
2149
  right: canvas.panRight.bind(canvas),
2147
2150
  up: canvas.panUp.bind(canvas),
2148
2151
  down: canvas.panDown.bind(canvas),
2149
- toPoint: canvas.scrollToPoint.bind(canvas),
2152
+ toPoint: canvas.panToPoint.bind(canvas),
2150
2153
  toCenter: canvas.centerContent.bind(canvas),
2151
2154
  },
2152
2155
  // Mouse drag group
@@ -2261,6 +2264,12 @@ class MarkupCanvas {
2261
2264
  }
2262
2265
  this.setupEventHandlers();
2263
2266
  this._isReady = true;
2267
+ if (options.initialZoom !== undefined) {
2268
+ this.setZoom(options.initialZoom);
2269
+ }
2270
+ if (options.initialPan !== undefined) {
2271
+ this.panToPoint(options.initialPan.x, options.initialPan.y);
2272
+ }
2264
2273
  // Emit ready event
2265
2274
  this.event.emit("ready", this);
2266
2275
  }
@@ -2446,8 +2455,8 @@ class MarkupCanvas {
2446
2455
  isPointVisible(x, y) {
2447
2456
  return isPointVisible(this, x, y);
2448
2457
  }
2449
- scrollToPoint(x, y) {
2450
- return scrollToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2458
+ panToPoint(x, y) {
2459
+ return panToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2451
2460
  }
2452
2461
  // Configuration access
2453
2462
  getConfig() {
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Markup Canvas
3
3
  * High-performance markup canvas with zoom and pan capabilities
4
- * @version 1.2.6
4
+ * @version 1.2.8
5
5
  */
6
6
  const EDITOR_PRESET = {
7
7
  // Canvas dimensions
@@ -261,6 +261,9 @@ const DEFAULT_CONFIG = {
261
261
  width: 8000,
262
262
  height: 8000,
263
263
  enableAcceleration: true,
264
+ // Initial view transform
265
+ initialZoom: 1,
266
+ initialPan: { x: 0, y: 0 },
264
267
  // Global Instance Access
265
268
  name: "markupCanvas",
266
269
  enablePostMessageAPI: false,
@@ -456,15 +459,7 @@ function panRight(canvas, config, updateTransform) {
456
459
  return updateTransform(newTransform);
457
460
  }
458
461
 
459
- function panUp(canvas, config, updateTransform) {
460
- const panDistance = config.keyboardPanStep;
461
- const newTransform = {
462
- translateY: canvas.transform.translateY + panDistance,
463
- };
464
- return updateTransform(newTransform);
465
- }
466
-
467
- function scrollToPoint(canvas, config, x, y, updateTransform, transformLayer) {
462
+ function panToPoint(canvas, config, x, y, updateTransform, transformLayer) {
468
463
  return withTransition(transformLayer, config, () => {
469
464
  const bounds = getCanvasBounds(canvas, config);
470
465
  const centerX = bounds.width / 2;
@@ -479,6 +474,14 @@ function scrollToPoint(canvas, config, x, y, updateTransform, transformLayer) {
479
474
  });
480
475
  }
481
476
 
477
+ function panUp(canvas, config, updateTransform) {
478
+ const panDistance = config.keyboardPanStep;
479
+ const newTransform = {
480
+ translateY: canvas.transform.translateY + panDistance,
481
+ };
482
+ return updateTransform(newTransform);
483
+ }
484
+
482
485
  function createMatrixString(matrix) {
483
486
  return `matrix3d(${matrix.m11}, ${matrix.m12}, ${matrix.m13}, ${matrix.m14}, ${matrix.m21}, ${matrix.m22}, ${matrix.m23}, ${matrix.m24}, ${matrix.m31}, ${matrix.m32}, ${matrix.m33}, ${matrix.m34}, ${matrix.m41}, ${matrix.m42}, ${matrix.m43}, ${matrix.m44})`;
484
487
  }
@@ -1372,8 +1375,8 @@ function setupPostMessageEvents(canvas) {
1372
1375
  else if (action === "centerContent") {
1373
1376
  canvas.centerContent();
1374
1377
  }
1375
- else if (action === "scrollToPoint") {
1376
- canvas.scrollToPoint(args[0], args[1]);
1378
+ else if (action === "panToPoint") {
1379
+ canvas.panToPoint(args[0], args[1]);
1377
1380
  }
1378
1381
  else if (action === "resetView") {
1379
1382
  canvas.resetView();
@@ -2142,7 +2145,7 @@ function bindCanvasToWindow(canvas, config) {
2142
2145
  right: canvas.panRight.bind(canvas),
2143
2146
  up: canvas.panUp.bind(canvas),
2144
2147
  down: canvas.panDown.bind(canvas),
2145
- toPoint: canvas.scrollToPoint.bind(canvas),
2148
+ toPoint: canvas.panToPoint.bind(canvas),
2146
2149
  toCenter: canvas.centerContent.bind(canvas),
2147
2150
  },
2148
2151
  // Mouse drag group
@@ -2257,6 +2260,12 @@ class MarkupCanvas {
2257
2260
  }
2258
2261
  this.setupEventHandlers();
2259
2262
  this._isReady = true;
2263
+ if (options.initialZoom !== undefined) {
2264
+ this.setZoom(options.initialZoom);
2265
+ }
2266
+ if (options.initialPan !== undefined) {
2267
+ this.panToPoint(options.initialPan.x, options.initialPan.y);
2268
+ }
2260
2269
  // Emit ready event
2261
2270
  this.event.emit("ready", this);
2262
2271
  }
@@ -2442,8 +2451,8 @@ class MarkupCanvas {
2442
2451
  isPointVisible(x, y) {
2443
2452
  return isPointVisible(this, x, y);
2444
2453
  }
2445
- scrollToPoint(x, y) {
2446
- return scrollToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2454
+ panToPoint(x, y) {
2455
+ return panToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2447
2456
  }
2448
2457
  // Configuration access
2449
2458
  getConfig() {
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Markup Canvas
3
3
  * High-performance markup canvas with zoom and pan capabilities
4
- * @version 1.2.6
4
+ * @version 1.2.8
5
5
  */
6
6
  (function (global, factory) {
7
7
  typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
@@ -206,6 +206,9 @@
206
206
  width: 8000,
207
207
  height: 8000,
208
208
  enableAcceleration: true,
209
+ // Initial view transform
210
+ initialZoom: 1,
211
+ initialPan: { x: 0, y: 0 },
209
212
  // Global Instance Access
210
213
  name: "markupCanvas",
211
214
  enablePostMessageAPI: false,
@@ -401,15 +404,7 @@
401
404
  return updateTransform(newTransform);
402
405
  }
403
406
 
404
- function panUp(canvas, config, updateTransform) {
405
- const panDistance = config.keyboardPanStep;
406
- const newTransform = {
407
- translateY: canvas.transform.translateY + panDistance,
408
- };
409
- return updateTransform(newTransform);
410
- }
411
-
412
- function scrollToPoint(canvas, config, x, y, updateTransform, transformLayer) {
407
+ function panToPoint(canvas, config, x, y, updateTransform, transformLayer) {
413
408
  return withTransition(transformLayer, config, () => {
414
409
  const bounds = getCanvasBounds(canvas, config);
415
410
  const centerX = bounds.width / 2;
@@ -424,6 +419,14 @@
424
419
  });
425
420
  }
426
421
 
422
+ function panUp(canvas, config, updateTransform) {
423
+ const panDistance = config.keyboardPanStep;
424
+ const newTransform = {
425
+ translateY: canvas.transform.translateY + panDistance,
426
+ };
427
+ return updateTransform(newTransform);
428
+ }
429
+
427
430
  function createMatrixString(matrix) {
428
431
  return `matrix3d(${matrix.m11}, ${matrix.m12}, ${matrix.m13}, ${matrix.m14}, ${matrix.m21}, ${matrix.m22}, ${matrix.m23}, ${matrix.m24}, ${matrix.m31}, ${matrix.m32}, ${matrix.m33}, ${matrix.m34}, ${matrix.m41}, ${matrix.m42}, ${matrix.m43}, ${matrix.m44})`;
429
432
  }
@@ -1317,8 +1320,8 @@
1317
1320
  else if (action === "centerContent") {
1318
1321
  canvas.centerContent();
1319
1322
  }
1320
- else if (action === "scrollToPoint") {
1321
- canvas.scrollToPoint(args[0], args[1]);
1323
+ else if (action === "panToPoint") {
1324
+ canvas.panToPoint(args[0], args[1]);
1322
1325
  }
1323
1326
  else if (action === "resetView") {
1324
1327
  canvas.resetView();
@@ -2087,7 +2090,7 @@
2087
2090
  right: canvas.panRight.bind(canvas),
2088
2091
  up: canvas.panUp.bind(canvas),
2089
2092
  down: canvas.panDown.bind(canvas),
2090
- toPoint: canvas.scrollToPoint.bind(canvas),
2093
+ toPoint: canvas.panToPoint.bind(canvas),
2091
2094
  toCenter: canvas.centerContent.bind(canvas),
2092
2095
  },
2093
2096
  // Mouse drag group
@@ -2202,6 +2205,12 @@
2202
2205
  }
2203
2206
  this.setupEventHandlers();
2204
2207
  this._isReady = true;
2208
+ if (options.initialZoom !== undefined) {
2209
+ this.setZoom(options.initialZoom);
2210
+ }
2211
+ if (options.initialPan !== undefined) {
2212
+ this.panToPoint(options.initialPan.x, options.initialPan.y);
2213
+ }
2205
2214
  // Emit ready event
2206
2215
  this.event.emit("ready", this);
2207
2216
  }
@@ -2387,8 +2396,8 @@
2387
2396
  isPointVisible(x, y) {
2388
2397
  return isPointVisible(this, x, y);
2389
2398
  }
2390
- scrollToPoint(x, y) {
2391
- return scrollToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2399
+ panToPoint(x, y) {
2400
+ return panToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
2392
2401
  }
2393
2402
  // Configuration access
2394
2403
  getConfig() {
@@ -1 +1 @@
1
- !function(e,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(e="undefined"!=typeof globalThis?globalThis:e||self).MarkupCanvas=t()}(this,function(){"use strict";function e(e,t,n){if(!n?.inverse)return{x:e,y:t};try{const r=n.inverse(),o=new DOMPoint(e,t).matrixTransform(r);return{x:o.x,y:o.y}}catch(n){return console.warn("Canvas to content conversion failed:",n),{x:e,y:t}}}function t(e,t){return Math.max(t.minZoom,Math.min(t.maxZoom,e))}function n(e,t,n){return new DOMMatrix([e,0,0,e,t,n])}const r="canvas-container",o="transform-layer",a="content-layer";function s(e,n,r,o,a){const s=a.enableRulers?-a.rulerSize:0,i=r||{scale:1,translateX:s,translateY:s},{scale:l,translateX:c,translateY:u}=i,d=t(l*o,a);if(Math.abs(d-l)<.001)return{scale:l,translateX:c,translateY:u};return{scale:d,translateX:e-(e-c)/l*d,translateY:n-(n-u)/l*d}}function i(e){return e.getBounds().visibleArea}function l(e,n){return n(n=>t(n,e))}const c=new Map;function u(e,t,n){return e[t]?n():null}function d(e){let t=null,n=null;const r=(...r)=>{n=r,null===t&&(t=requestAnimationFrame(()=>{n&&e(...n),t=null,n=null}))};return r.cleanup=()=>{null!==t&&(cancelAnimationFrame(t),t=null,n=null)},r}function h(e,t,n){return n(null!==e.container.querySelector(".canvas-ruler")?t:0)}function g(e,t,n,r,o){const a=null!==e.container.querySelector(".canvas-ruler");return o(a?t-r:t,a?n-r:n)}function m(e,t){if("dark"===e.themeMode){return e[`${t}Dark`]}return e[t]}const f={width:8e3,height:8e3,enableAcceleration:!0,name:"markupCanvas",enablePostMessageAPI:!1,enableZoom:!0,enablePan:!0,enableTouch:!0,enableKeyboard:!0,bindKeyboardEventsTo:"document",zoomSpeed:1.5,minZoom:.05,maxZoom:80,enableTransition:!0,transitionDuration:.2,enableAdaptiveSpeed:!0,enableLeftDrag:!0,enableMiddleDrag:!0,requireSpaceForMouseDrag:!1,keyboardPanStep:50,keyboardFastMultiplier:20,keyboardZoomStep:.2,enableClickToZoom:!0,clickZoomLevel:1,requireOptionForClickZoom:!1,enableRulers:!0,enableGrid:!1,showRulers:!0,showGrid:!1,rulerFontSize:9,rulerFontFamily:"Monaco, Menlo, monospace",rulerUnits:"px",rulerSize:20,canvasBackgroundColor:"rgba(250, 250, 250, 1)",canvasBackgroundColorDark:"rgba(40, 40, 40, 1)",rulerBackgroundColor:"rgba(255, 255, 255, 0.95)",rulerBorderColor:"rgba(240, 240, 240, 1)",rulerTextColor:"rgba(102, 102, 102, 1)",rulerTickColor:"rgba(204, 204, 204, 1)",gridColor:"rgba(232, 86, 193, 0.5)",rulerBackgroundColorDark:"rgba(30, 30, 30, 0.95)",rulerBorderColorDark:"rgba(68, 68, 68, 1)",rulerTextColorDark:"rgba(170, 170, 170, 1)",rulerTickColorDark:"rgba(104, 104, 104, 1)",gridColorDark:"rgba(232, 86, 193, 0.5)",themeMode:"light"};function p(t,r){try{const o=t.container,a=t.transform||{scale:1,translateX:0,translateY:0},s=o.getBoundingClientRect(),i=s.width||o.clientWidth||0,l=s.height||o.clientHeight||0,c=h({container:o},r.rulerSize,e=>Math.max(0,i-e)),u=h({container:o},r.rulerSize,e=>Math.max(0,l-e)),d=r.width||f.width,g=r.height||f.height,m=function(t,r,o,a,s){const i=e(0,0,n(s.scale,s.translateX,s.translateY)),l=e(t,r,n(s.scale,s.translateX,s.translateY));return{x:Math.max(0,Math.min(o,i.x)),y:Math.max(0,Math.min(a,i.y)),width:Math.max(0,Math.min(o-i.x,l.x-i.x)),height:Math.max(0,Math.min(a-i.y,l.y-i.y))}}(c,u,d,g,a);return{width:c,height:u,contentWidth:d,contentHeight:g,scale:a.scale,translateX:a.translateX,translateY:a.translateY,visibleArea:m,scaledContentWidth:d*a.scale,scaledContentHeight:g*a.scale,canPanLeft:a.translateX<0,canPanRight:a.translateX+d*a.scale>c,canPanUp:a.translateY<0,canPanDown:a.translateY+g*a.scale>u,canZoomIn:a.scale<3.5,canZoomOut:a.scale>.1}}catch(e){return console.error("Failed to calculate canvas bounds:",e),{width:0,height:0,contentWidth:0,contentHeight:0,scale:1,translateX:0,translateY:0,visibleArea:{x:0,y:0,width:0,height:0},scaledContentWidth:0,scaledContentHeight:0,canPanLeft:!1,canPanRight:!1,canPanUp:!1,canPanDown:!1,canZoomIn:!1,canZoomOut:!1}}}function v(e,t){try{if(t.enableTransition){window.__markupCanvasTransitionTimeout&&(clearTimeout(window.__markupCanvasTransitionTimeout),window.__markupCanvasTransitionTimeout=void 0);return function(e,t,n){const r=c.get(e);r&&clearTimeout(r);const o=window.setTimeout(()=>{n(),c.delete(e)},t);c.set(e,o)}("disableTransition",1e3*(t.transitionDuration??.2),()=>{e.style.transition="none",window.__markupCanvasTransitionTimeout=void 0}),!0}return!1}catch(e){return console.error("Failed to disable transitions:",e),!0}}function y(e,t,n){!function(e,t){try{return!!t.enableTransition&&(window.__markupCanvasTransitionTimeout&&(clearTimeout(window.__markupCanvasTransitionTimeout),window.__markupCanvasTransitionTimeout=void 0),e.style.transition=`transform ${t.transitionDuration}s linear`,!0)}catch(e){return console.error("Failed to enable transitions:",e),!1}}(e,t);try{return n()}finally{v(e,t)}}function b(e,t,n){const r=t.keyboardPanStep;return n({translateY:e.transform.translateY-r})}function w(e,t,n){const r=t.keyboardPanStep;return n({translateX:e.transform.translateX+r})}function k(e,t,n){const r=t.keyboardPanStep;return n({translateX:e.transform.translateX-r})}function x(e,t,n){const r=t.keyboardPanStep;return n({translateY:e.transform.translateY+r})}function T(e,t){if(!e?.style||!t)return!1;try{return e.style.transform=function(e){return`matrix3d(${e.m11}, ${e.m12}, ${e.m13}, ${e.m14}, ${e.m21}, ${e.m22}, ${e.m23}, ${e.m24}, ${e.m31}, ${e.m32}, ${e.m33}, ${e.m34}, ${e.m41}, ${e.m42}, ${e.m43}, ${e.m44})`}(t),!0}catch(e){return console.warn("Transform application failed:",e),!1}}function C(e,t){e.transform={...e.transform,...t};const r=n(e.transform.scale,e.transform.translateX,e.transform.translateY);return T(e.transformLayer,r)}function M(e={}){const t={...f,...e};return("number"!=typeof t.width||t.width<=0)&&(console.warn("Invalid width, using default"),t.width=f.width),("number"!=typeof t.height||t.height<=0)&&(console.warn("Invalid height, using default"),t.height=f.height),("number"!=typeof t.zoomSpeed||t.zoomSpeed<=0)&&(console.warn("Invalid zoomSpeed, using default"),t.zoomSpeed=f.zoomSpeed),("number"!=typeof t.minZoom||t.minZoom<=0)&&(console.warn("Invalid minZoom, using default"),t.minZoom=f.minZoom),("number"!=typeof t.maxZoom||t.maxZoom<=t.minZoom)&&(console.warn("Invalid maxZoom, using default"),t.maxZoom=f.maxZoom),("number"!=typeof t.keyboardPanStep||t.keyboardPanStep<=0)&&(console.warn("Invalid keyboardPanStep, using default"),t.keyboardPanStep=f.keyboardPanStep),("number"!=typeof t.keyboardFastMultiplier||t.keyboardFastMultiplier<=0)&&(console.warn("Invalid keyboardFastMultiplier, using default"),t.keyboardFastMultiplier=f.keyboardFastMultiplier),("number"!=typeof t.clickZoomLevel||t.clickZoomLevel<=0)&&(console.warn("Invalid clickZoomLevel, using default"),t.clickZoomLevel=f.clickZoomLevel),("number"!=typeof t.rulerFontSize||t.rulerFontSize<=0)&&(console.warn("Invalid rulerFontSize, using default"),t.rulerFontSize=f.rulerFontSize),("number"!=typeof t.rulerSize||t.rulerSize<=0)&&(console.warn("Invalid rulerSize, using default"),t.rulerSize=f.rulerSize),t}function S(e,t,n,r){const o=M({...t,themeMode:r}),a=m(o,"canvasBackgroundColor");e.style.backgroundColor=a,n&&n.updateTheme(o)}function D(e){try{const t=e.getBounds();return{x:t.width/2,y:t.height/2}}catch(e){return console.warn("Failed to calculate viewport center:",e),{x:0,y:0}}}function z(e,t){const n=Array.from(e.children);let r=e.querySelector(`.${o}`);r||(r=document.createElement("div"),r.className=o,e.appendChild(r)),function(e,t){e.style.position="absolute";const n=t.rulerSize;e.style.top=`${n}px`,e.style.left=`${n}px`,e.style.width=`${t.width}px`,e.style.height=`${t.height}px`,e.style.transformOrigin="0 0"}(r,t);let s=r.querySelector(`.${a}`);return s||(s=document.createElement("div"),s.className=a,r.appendChild(s),function(e,t,n){e.forEach(e=>{e===n||e.classList.contains(o)||t.appendChild(e)})}(n,s,r)),function(e){e.style.position="relative",e.style.width="100%",e.style.height="100%",e.style.pointerEvents="auto"}(s),{transformLayer:r,contentLayer:s}}function L(e,t){if("static"===getComputedStyle(e).position&&(e.style.position="relative"),e.style.overflow="hidden",e.style.cursor="grab",e.style.overscrollBehavior="none",t){const n=m(t,"canvasBackgroundColor");e.style.backgroundColor=n}e.hasAttribute("tabindex")||e.setAttribute("tabindex","0"),function(e){const t=e.getBoundingClientRect(),n=getComputedStyle(e);0===t.height&&"auto"===n.height&&console.error("MarkupCanvas: Container height is 0. Please set a height on your container element using CSS.","Examples: height: 100vh, height: 500px, or use flexbox/grid layout.",e),0===t.width&&"auto"===n.width&&console.error("MarkupCanvas: Container width is 0. Please set a width on your container element using CSS.","Examples: width: 100vw, width: 800px, or use flexbox/grid layout.",e)}(e),e.classList.contains(r)||e.classList.add(r)}function R(e,t){if(!e?.appendChild)return console.error("Invalid container element provided to createCanvas"),null;try{L(e,t);const{transformLayer:r,contentLayer:o}=z(e,t);u(t,"enableAcceleration",()=>{!function(e){try{return e.style.transform=e.style.transform||"translateZ(0)",e.style.backfaceVisibility="hidden",!0}catch(e){return console.error("Failed to enable hardware acceleration:",e),!1}}(r)});const a=t.enableRulers?-t.rulerSize:0,s={scale:1,translateX:a,translateY:a},i=n(s.scale,s.translateX,s.translateY);T(r,i);return{container:e,transformLayer:r,contentLayer:o,transform:s}}catch(e){return console.error("Failed to create canvas:",e),null}}class P{constructor(){this.listeners=new Map}setEmitInterceptor(e){this.emitInterceptor=e}on(e,t){this.listeners.has(e)||this.listeners.set(e,new Set),this.listeners.get(e).add(t)}off(e,t){const n=this.listeners.get(e);n&&n.delete(t)}emit(e,t){this.emitInterceptor?.(e,t);const n=this.listeners.get(e);n&&n.forEach(n=>{try{n(t)}catch(t){console.error(`Error in event handler for "${String(e)}":`,t)}})}removeAllListeners(){this.listeners.clear()}}function E(e,t){const n=t.transform;e.emit("transform",n),e.emit("zoom",n.scale),e.emit("pan",{x:n.translateX,y:n.translateY})}const Y=300,X=5;function $(e,t){if(!e?.getBounds)return t;try{const n=e.getBounds(),r=n.width*n.height;return t*(r/2073600)**1}catch(e){return console.warn("Failed to calculate adaptive zoom speed, using base speed:",e),t}}function I(e,t,n,r,o){n?t.requireSpaceForMouseDrag?e.container.style.cursor=r?"grab":"default":e.container.style.cursor=o?"grabbing":"grab":e.container.style.cursor="default"}function B(e,t,n,r,o){o.setIsDragging(!1),o.setDragButton(-1),I(e,t,n,r,!1)}function F(e,t,n,r,o,a,s,i,l,c){a&&e.button===s&&B(t,n,r,o,{setIsDragging:c.setIsDragging,setDragButton:c.setDragButton}),r&&0===e.button&&n.enableClickToZoom&&i>0&&function(e,t,n,r,o,a){const s=Date.now()-r,i=e.altKey,l=!n.requireOptionForClickZoom||i;if(s<Y&&!o&&!a&&l){e.preventDefault();const r=t.container.getBoundingClientRect(),o=e.clientX-r.left,a=e.clientY-r.top,{clickX:s,clickY:i}=g(t,o,a,n.rulerSize,(e,t)=>({clickX:e,clickY:t})),l=t.canvasToContent(s,i),c=r.width/2,u=r.height/2,d=n.clickZoomLevel,h={scale:d,translateX:c-l.x*d,translateY:u-l.y*d};y(t.transformLayer,t.config,()=>{t.updateTransform(h)})}}(e,t,n,i,l,a),0===e.button&&function(e){e.setMouseDownTime(0),e.setHasDragged(!1)}({setMouseDownTime:c.setMouseDownTime,setHasDragged:c.setHasDragged})}function Z(e,t,n=!0){let r=!0,o=!1,a=0,s=0,i=-1,l=!1,c=0,u=0,h=0,g=!1;const m={setIsDragging:e=>{o=e},setDragButton:e=>{i=e},setIsSpacePressed:e=>{l=e},setMouseDownTime:e=>{c=e},setMouseDownX:e=>{u=e},setMouseDownY:e=>{h=e},setHasDragged:e=>{g=e},setLastMouseX:e=>{a=e},setLastMouseY:e=>{s=e}},f=n=>{!function(e,t,n,r,o,a){n.requireSpaceForMouseDrag&&" "===e.key&&(a.setIsSpacePressed(!0),I(t,n,r,!0,o))}(n,e,t,r,o,{setIsSpacePressed:m.setIsSpacePressed})},p=n=>{!function(e,t,n,r,o,a){n.requireSpaceForMouseDrag&&" "===e.key&&(a.setIsSpacePressed(!1),I(t,n,r,!1,o),o&&B(t,n,r,!1,{setIsDragging:a.setIsDragging,setDragButton:a.setDragButton}))}(n,e,t,r,o,{setIsSpacePressed:m.setIsSpacePressed,setIsDragging:m.setIsDragging,setDragButton:m.setDragButton})},v=n=>{!function(e,t,n,r,o,a){const s=0===e.button,i=1===e.button;if(s&&(a.setMouseDownTime(Date.now()),a.setMouseDownX(e.clientX),a.setMouseDownY(e.clientY),a.setHasDragged(!1)),!r)return;(!n.requireSpaceForMouseDrag||o)&&(s&&n.enableLeftDrag||i&&n.enableMiddleDrag)&&(e.preventDefault(),a.setDragButton(e.button),a.setLastMouseX(e.clientX),a.setLastMouseY(e.clientY),I(t,n,r,o,!1))}(n,e,t,r,l,m)},y=n=>{!function(e,t,n,r,o,a,s,i,l,c,u,h){if(s>0){const t=Math.abs(e.clientX-i),s=Math.abs(e.clientY-l);if(t>X||s>X){h.setHasDragged(!0);const e=!n.requireSpaceForMouseDrag||a;!o&&r&&e&&h.setIsDragging(!0)}}if(!o||!r)return;e.preventDefault(),d((...e)=>{const n=e[0];if(!o||!r)return;const a=n.clientX-c,s=n.clientY-u,i={translateX:t.transform.translateX+a,translateY:t.transform.translateY+s};t.updateTransform(i),h.setLastMouseX(n.clientX),h.setLastMouseY(n.clientY)})(e)}(n,e,t,r,o,l,c,u,h,a,s,{setHasDragged:m.setHasDragged,setIsDragging:m.setIsDragging,setLastMouseX:m.setLastMouseX,setLastMouseY:m.setLastMouseY})},b=n=>{F(n,e,t,r,l,o,i,c,g,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton,setMouseDownTime:m.setMouseDownTime,setHasDragged:m.setHasDragged})},w=()=>{!function(e,t,n,r,o,a){o&&B(e,t,n,r,a)}(e,t,r,l,o,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton})};e.container.addEventListener("mousedown",v),document.addEventListener("mousemove",y),document.addEventListener("mouseup",b),e.container.addEventListener("mouseleave",w),t.requireSpaceForMouseDrag&&(document.addEventListener("keydown",f),document.addEventListener("keyup",p)),I(e,t,r,l,o);const k=()=>{e.container.removeEventListener("mousedown",v),document.removeEventListener("mousemove",y),document.removeEventListener("mouseup",b),e.container.removeEventListener("mouseleave",w),t.requireSpaceForMouseDrag&&(document.removeEventListener("keydown",f),document.removeEventListener("keyup",p))};return n?{cleanup:k,enable:()=>(r=!0,I(e,t,r,l,o),!0),disable:()=>(r=!1,o&&B(e,t,r,l,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton}),I(e,t,r,l,o),!0),isEnabled:()=>r}:k}function O(e){const t=t=>{const n=t.data;if("markup-canvas"!==n.source)return;const r=e.config.name||"markupCanvas";if(n.canvasName!==r)return;const o=n.action,a=n.args||[];try{if("zoomIn"===o)e.zoomIn(a[0]);else if("zoomOut"===o)e.zoomOut(a[0]);else if("setZoom"===o){const t=a[0];if("number"!=typeof t||t<=0)throw new Error(`Invalid zoom level: ${t}. Must be a positive number.`);e.setZoom(t)}else if("resetZoom"===o)e.resetZoom();else if("panLeft"===o)e.panLeft(a[0]);else if("panRight"===o)e.panRight(a[0]);else if("panUp"===o)e.panUp(a[0]);else if("panDown"===o)e.panDown(a[0]);else if("fitToScreen"===o)e.fitToScreen();else if("centerContent"===o)e.centerContent();else if("scrollToPoint"===o)e.scrollToPoint(a[0],a[1]);else if("resetView"===o)e.resetView();else if("resetViewToCenter"===o)e.resetViewToCenter();else if("toggleRulers"===o)e.toggleRulers();else if("showRulers"===o)e.showRulers();else if("hideRulers"===o)e.hideRulers();else if("toggleGrid"===o)e.toggleGrid();else if("showGrid"===o)e.showGrid();else if("hideGrid"===o)e.hideGrid();else if("updateThemeMode"===o){const t=a[0];if("light"!==t&&"dark"!==t)throw new Error(`Invalid theme mode: ${t}`);e.updateThemeMode(t)}else if("toggleThemeMode"===o){const t="light"===e.getConfig().themeMode?"dark":"light";e.updateThemeMode(t)}else if("updateTransition"===o){const t=a[0];if("boolean"!=typeof t)throw new Error(`Invalid transition enabled value: ${t}. Must be a boolean.`);e.updateTransition(t)}else{if("toggleTransitionMode"!==o)throw new Error(`Unknown action: ${o}`);e.toggleTransitionMode()}}catch(e){!function(e,t,n){window.postMessage({source:"markup-canvas-error",canvasName:e,action:t,error:n,timestamp:Date.now()},"*")}(r,o,e instanceof Error?e.message:String(e))}};return"undefined"!=typeof window&&window.addEventListener("message",t),()=>{"undefined"!=typeof window&&window.removeEventListener("message",t)}}function V(e,t){return{x:(e.clientX+t.clientX)/2,y:(e.clientY+t.clientY)/2}}function A(e,t){const n=e.clientX-t.clientX,r=e.clientY-t.clientY;return Math.sqrt(n*n+r*r)}function _(e,t,n,r){const o=s(n,r,e.transform,t,e.config);return e.updateTransform(o)}function G(e,t,n){e.preventDefault();const r=Array.from(e.touches);d((...e)=>{const r=e[0];if(1===r.length){if(1===n.touches.length){const e=r[0].clientX-n.touches[0].clientX,o=r[0].clientY-n.touches[0].clientY,a={translateX:t.transform.translateX+e,translateY:t.transform.translateY+o};t.updateTransform(a)}}else if(2===r.length){const e=A(r[0],r[1]),o=V(r[0],r[1]);if(n.lastDistance>0){const r=e/n.lastDistance,a=t.container.getBoundingClientRect();let s=o.x-a.left,i=o.y-a.top;const l=function(e,t,n,r){return h(e,t,e=>{const t={...n,x:n.x-e,y:n.y-e};return r(t)})}(t,t.config.rulerSize,{x:s,y:i},e=>e);s=l.x,i=l.y,_(t,r,s,i)}n.lastDistance=e,n.lastCenter=o}n.touches=r})(r)}function H(e){const t={touches:[],lastDistance:0,lastCenter:{}},n=e=>{!function(e,t){e.preventDefault(),t.touches=Array.from(e.touches),2===t.touches.length&&(t.lastDistance=A(t.touches[0],t.touches[1]),t.lastCenter=V(t.touches[0],t.touches[1]))}(e,t)},r=n=>{G(n,e,t)},o=e=>{!function(e,t){t.touches=Array.from(e.touches),t.touches.length<2&&(t.lastDistance=0)}(e,t)};return e.container.addEventListener("touchstart",n,{passive:!1}),e.container.addEventListener("touchmove",r,{passive:!1}),e.container.addEventListener("touchend",o,{passive:!1}),()=>{e.container.removeEventListener("touchstart",n),e.container.removeEventListener("touchmove",r),e.container.removeEventListener("touchend",o)}}function N(e){const t=e.ctrlKey||e.metaKey,n=[0===e.deltaMode,Math.abs(e.deltaY)<50,e.deltaY%1!=0,Math.abs(e.deltaX)>0&&Math.abs(e.deltaY)>0].filter(Boolean).length>=2;return{isTrackpad:n,isMouseWheel:!n,isTrackpadScroll:n&&!t,isTrackpadPinch:n&&t,isZoomGesture:t}}function K(e,t){const n=(e=>d((...t)=>{const n=t[0];if(!n||!e?.updateTransform)return!1;try{const t=e.transform,r=1,o=n.deltaX*r,a=n.deltaY*r,s={scale:t.scale,translateX:t.translateX-o,translateY:t.translateY-a};return v(e.transformLayer,e.config),e.updateTransform(s)}catch(e){return console.error("Error handling trackpad pan:",e),!1}}))(e),r=r=>N(r).isTrackpadScroll?n(r):function(e,t,n){if(!e||"number"!=typeof e.deltaY)return console.warn("Invalid wheel event provided"),!1;if(!t?.updateTransform)return console.warn("Invalid canvas provided to handleWheelEvent"),!1;try{e.preventDefault();const r=t.container.getBoundingClientRect(),o=e.clientX-r.left,a=e.clientY-r.top,{mouseX:s,mouseY:i}=g(t,o,a,n.rulerSize,(e,t)=>({mouseX:e,mouseY:t})),l=n.zoomSpeed,c=N(e);if(!c.isZoomGesture)return!1;let u=n.enableAdaptiveSpeed?$(t,l):l;if(c.isTrackpadPinch){const e=.05*n.zoomSpeed;u=n.enableAdaptiveSpeed?$(t,e):e}return _(t,(e.deltaY<0?1:-1)>0?1+u:1/(1+u),s,i)}catch(e){return console.error("Error handling wheel event:",e),!1}}(r,e,t);return e.container.addEventListener("wheel",r,{passive:!1}),()=>{e.container.removeEventListener("wheel",r)}}const q=100,U=1e3,W=1001,j=4,J=4,Q=100,ee=100,te=20,ne=200;function re(e,t){const n=function(e){const t=document.createElement("div");return t.className="canvas-ruler horizontal-ruler",t.style.cssText=`\n\tposition: absolute;\n\ttop: 0;\n\tleft: ${e.rulerSize}px;\n\tright: 0;\n\theight: ${e.rulerSize}px;\n\tbackground: var(--ruler-background-color);\n\tborder-bottom: 1px solid var(--ruler-border-color);\n\tborder-right: 1px solid var(--ruler-border-color);\n\tz-index: ${U};\n\tpointer-events: none;\n\tfont-family: ${e.rulerFontFamily};\n\tfont-size: ${e.rulerFontSize}px;\n\tcolor: var(--ruler-text-color);\n\toverflow: hidden;\n `,t}(t),r=function(e){const t=document.createElement("div");return t.className="canvas-ruler vertical-ruler",t.style.cssText=`\n\tposition: absolute;\n\ttop: ${e.rulerSize}px;\n\tleft: 0;\n\tbottom: 0;\n\twidth: ${e.rulerSize}px;\n\tbackground: var(--ruler-background-color);\n\tborder-right: 1px solid var(--ruler-border-color);\n\tborder-bottom: 1px solid var(--ruler-border-color);\n\tz-index: ${U};\n\tpointer-events: none;\n\tfont-family: ${e.rulerFontFamily};\n\tfont-size: ${e.rulerFontSize}px;\n\tcolor: var(--ruler-text-color);\n\toverflow: hidden;\n `,t}(t),o=function(e){const t=document.createElement("div");return t.className="canvas-ruler corner-box",t.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: 0;\n\t\tleft: 0;\n\t\twidth: ${e.rulerSize}px;\n\t\theight: ${e.rulerSize}px;\n\t\tbackground: var(--ruler-background-color);\n\t\tborder-right: 1px solid var(--ruler-border-color);\n\t\tborder-bottom: 1px solid var(--ruler-border-color);\n\t\tz-index: ${W};\n\t\tdisplay: flex;\n\t\talign-items: center;\n\t\tjustify-content: center;\n\t\tfont-family: ${e.rulerFontFamily};\n\t\tfont-size: ${e.rulerFontSize-2}px;\n\t\tcolor: var(--ruler-text-color);\n\t\tpointer-events: none;\n\t`,t.textContent=e.rulerUnits,t}(t),a=t.enableGrid?function(e){const t=document.createElement("div");return t.className="canvas-ruler grid-overlay",t.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: ${e.rulerSize}px;\n\t\tleft: ${e.rulerSize}px;\n\t\tright: 0;\n\t\tbottom: 0;\n\t\tpointer-events: none;\n\t\tz-index: ${q};\n\t\tbackground-image: \n\t\t\tlinear-gradient(var(--grid-color) 1px, transparent 1px),\n\t\t\tlinear-gradient(90deg, var(--grid-color) 1px, transparent 1px);\n\t\tbackground-size: 100px 100px;\n\t\topacity: 0.5;\n\t`,t}(t):void 0;return e.appendChild(n),e.appendChild(r),e.appendChild(o),a&&e.appendChild(a),{horizontalRuler:n,verticalRuler:r,cornerBox:o,gridOverlay:a}}function oe(e,t){const n=e/Math.max(5,Math.min(20,t/50)),r=10**Math.floor(Math.log10(n)),o=n/r;let a;return a=o<=1?1:o<=2?2:o<=5?5:10,a*r}function ae(e,t,n,r,o){const a=document.createElement("div");a.className="tick",a.style.cssText=`\n\t\tposition: absolute;\n\t\tleft: ${n}px;\n\t\tbottom: 0;\n\t\twidth: 1px;\n\t\theight: ${j}px;\n\t\tbackground: var(--ruler-tick-color);\n\t`,e.appendChild(a);if(t%Q===0){const r=document.createElement("div");r.style.cssText=`\n\t\t\tposition: absolute;\n\t\t\tleft: ${n}px;\n\t\t\tbottom: ${j+2}px;\n\t\t\tfont-size: ${o.rulerFontSize}px;\n\t\t\tline-height: 1;\n\t\t\tcolor: var(--ruler-text-color);\n\t\t\twhite-space: nowrap;\n\t\t\tpointer-events: none;\n\t\t`,r.textContent=Math.round(t).toString(),e.appendChild(r)}}function se(e,t,n,r,o){const a=document.createElement("div");a.className="tick",a.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: ${n}px;\n\t\tright: 0;\n\t\twidth: ${J}px;\n\t\theight: 1px;\n\t\tbackground: var(--ruler-tick-color);\n\t`,e.appendChild(a);if(t%Q===0){const r=document.createElement("div");r.style.cssText=`\n\t\t\tposition: absolute;\n\t\t\ttop: ${n-6}px;\n\t\t\tright: ${J+6}px;\n\t\t\tfont-size: ${o.rulerFontSize}px;\n\t\t\tline-height: 1;\n\t\t\tcolor: var(--ruler-text-color);\n\t\t\twhite-space: nowrap;\n\t\t\tpointer-events: none;\n\t\t\ttransform: rotate(-90deg);\n\t\t\ttransform-origin: right center;\n\t\t`,r.textContent=Math.round(t).toString(),e.appendChild(r)}}function ie(e,t,n,r,o){const a=e.getBounds(),s=a.scale||1,i=a.translateX||0,l=a.translateY||0,c=a.width-o.rulerSize,u=a.height-o.rulerSize,d=-i/s,h=-l/s,g=h+u/s;!function(e,t,n,r,o,a){const s=r,i=oe(n-t,s),l=document.createDocumentFragment(),c=Math.floor(t/i)*i,u=Math.ceil(n/i)*i;for(let e=c;e<=u;e+=i){const n=(e-t)*o;n>=-50&&n<=s+50&&ae(l,e,n,0,a)}e.innerHTML="",e.appendChild(l)}(t,d,d+c/s,c,s,o),function(e,t,n,r,o,a){const s=r,i=oe(n-t,s),l=document.createDocumentFragment(),c=Math.floor(t/i)*i,u=Math.ceil(n/i)*i;for(let e=c;e<=u;e+=i){const n=(e-t)*o;n>=-50&&n<=s+50&&se(l,e,n,0,a)}e.innerHTML="",e.appendChild(l)}(n,h,g,u,s,o),r&&function(e,t,n,r){let o=ee*t;for(;o<te;)o*=2;for(;o>ne;)o/=2;e.style.backgroundSize=`${o}px ${o}px`,e.style.backgroundPosition=`${n%o}px ${r%o}px`}(r,s,i,l)}function le(e,t){const n=m(t,"rulerBackgroundColor"),r=m(t,"rulerBorderColor"),o=m(t,"rulerTextColor"),a=m(t,"rulerTickColor"),s=m(t,"gridColor");e.horizontalRuler&&(e.horizontalRuler.style.setProperty("--ruler-background-color",n),e.horizontalRuler.style.setProperty("--ruler-border-color",r),e.horizontalRuler.style.setProperty("--ruler-text-color",o),e.horizontalRuler.style.setProperty("--ruler-tick-color",a)),e.verticalRuler&&(e.verticalRuler.style.setProperty("--ruler-background-color",n),e.verticalRuler.style.setProperty("--ruler-border-color",r),e.verticalRuler.style.setProperty("--ruler-text-color",o),e.verticalRuler.style.setProperty("--ruler-tick-color",a)),e.cornerBox&&(e.cornerBox.style.setProperty("--ruler-background-color",n),e.cornerBox.style.setProperty("--ruler-border-color",r),e.cornerBox.style.setProperty("--ruler-text-color",o)),e.gridOverlay&&e.gridOverlay.style.setProperty("--grid-color",s)}function ce(e,t){if(!e?.container)return console.error("Invalid canvas provided to createRulers"),null;let n,r=null,o=!1;const a=()=>{!o&&n.horizontalRuler&&n.verticalRuler&&ie(e,n.horizontalRuler,n.verticalRuler,n.gridOverlay,t)};try{return n=re(e.container,t),r=function(e,t){const n=d(t),r=e.updateTransform;e.updateTransform=function(e){const t=r.call(this,e);return n(),t};const o=d(t);return window.addEventListener("resize",o),()=>{window.removeEventListener("resize",o),e.updateTransform=r,n.cleanup(),o.cleanup()}}(e,a),le(n,t),a(),t.showRulers||(n.horizontalRuler.style.display="none",n.verticalRuler.style.display="none",n.cornerBox.style.display="none"),!t.showGrid&&n.gridOverlay&&(n.gridOverlay.style.display="none"),{horizontalRuler:n.horizontalRuler,verticalRuler:n.verticalRuler,cornerBox:n.cornerBox,gridOverlay:n.gridOverlay,update:a,updateTheme:e=>{o||le(n,e)},show:()=>{n.horizontalRuler&&(n.horizontalRuler.style.display="block"),n.verticalRuler&&(n.verticalRuler.style.display="block"),n.cornerBox&&(n.cornerBox.style.display="flex")},hide:()=>{n.horizontalRuler&&(n.horizontalRuler.style.display="none"),n.verticalRuler&&(n.verticalRuler.style.display="none"),n.cornerBox&&(n.cornerBox.style.display="none"),n.gridOverlay&&(n.gridOverlay.style.display="none")},toggleGrid:()=>{if(n.gridOverlay){const e="none"!==n.gridOverlay.style.display;n.gridOverlay.style.display=e?"none":"block"}},destroy:()=>{o=!0,r&&r(),n.horizontalRuler?.parentNode&&n.horizontalRuler.parentNode.removeChild(n.horizontalRuler),n.verticalRuler?.parentNode&&n.verticalRuler.parentNode.removeChild(n.verticalRuler),n.cornerBox?.parentNode&&n.cornerBox.parentNode.removeChild(n.cornerBox),n.gridOverlay?.parentNode&&n.gridOverlay.parentNode.removeChild(n.gridOverlay)}}}catch(e){return console.error("Failed to create rulers:",e),null}}return class{constructor(e,t={}){if(this.cleanupCallbacks=[],this.rulers=null,this.dragSetup=null,this.event=new P,this._isReady=!1,!e)throw new Error("Container element is required");this.config=M(t);const n=R(e,this.config);if(!n)throw new Error("Failed to create canvas");if(this.canvas=n,u(this.config,"enableRulers",()=>{this.rulers=ce(this,this.config),this.cleanupCallbacks.push(()=>{this.rulers&&this.rulers.destroy()})}),t.themeMode&&S(this.canvas.container,this.config,this.rulers,t.themeMode),this.event.setEmitInterceptor((e,t)=>{!function(e,t,n){if("undefined"==typeof window)return;let r=t;"ready"===e&&(r={ready:!0});const o=n.name||"markupCanvas";window.postMessage({source:"markup-canvas",action:e,data:r,timestamp:Date.now(),canvasName:o},"*"),window.parent&&window.parent.postMessage({source:"markup-canvas",action:e,data:r,timestamp:Date.now(),canvasName:o},"*")}(e,t,this.config)}),function(e,t){if("undefined"==typeof window)return;const n=t.name||"markupCanvas",r=window,o={config:{get current(){return e.config},get:e.getConfig.bind(e),update:e.updateConfig.bind(e)},transform:{update:e.updateTransform.bind(e),reset:e.reset.bind(e)},zoom:{get current(){return e.transform.scale||1},set:e.setZoom.bind(e),toPoint:e.zoomToPoint.bind(e),in:e.zoomIn.bind(e),out:e.zoomOut.bind(e),reset:e.resetZoom.bind(e),resetToCenter:e.resetViewToCenter.bind(e),fitToScreen:e.fitToScreen.bind(e)},pan:{left:e.panLeft.bind(e),right:e.panRight.bind(e),up:e.panUp.bind(e),down:e.panDown.bind(e),toPoint:e.scrollToPoint.bind(e),toCenter:e.centerContent.bind(e)},mouseDrag:{enable:e.enableMouseDrag.bind(e),disable:e.disableMouseDrag.bind(e),isEnabled:e.isMouseDragEnabled.bind(e)},grid:{toggle:e.toggleGrid.bind(e),show:e.showGrid.bind(e),hide:e.hideGrid.bind(e),isVisible:e.isGridVisible.bind(e)},rulers:{toggle:e.toggleRulers.bind(e),show:e.showRulers.bind(e),hide:e.hideRulers.bind(e),isVisible:e.areRulersVisible.bind(e)},canvas:{canvasToContent:e.canvasToContent.bind(e),getVisibleArea:e.getVisibleArea.bind(e),isPointVisible:e.isPointVisible.bind(e),getBounds:e.getBounds.bind(e)},theme:{get current(){return e.config.themeMode},update:e.updateThemeMode.bind(e),toggle:e.toggleThemeMode.bind(e)},transition:{get current(){return e.config.enableTransition},set:e.updateTransition.bind(e),toggle:e.toggleTransitionMode.bind(e)},event:e.event,lifecycle:{cleanup:e.cleanup.bind(e),destroy:e.destroy.bind(e)},state:{get isReady(){return e.isReady},get isTransforming(){return e.isTransforming},get visibleBounds(){return e.visibleBounds},get transform(){return e.transform}}};r[n]=o,r.__markupCanvasInstances||(r.__markupCanvasInstances=new Map),r.__markupCanvasInstances.set(n,o)}(this,this.config),this.config.enablePostMessageAPI){const e=O(this);this.cleanupCallbacks.push(e)}this.setupEventHandlers(),this._isReady=!0,this.event.emit("ready",this)}setupEventHandlers(){try{u(this.config,"enableZoom",()=>{const e=K(this,this.config);this.cleanupCallbacks.push(e)}),(this.config.enablePan||this.config.enableClickToZoom)&&(this.dragSetup=Z(this,this.config,!0),this.cleanupCallbacks.push(this.dragSetup.cleanup)),u(this.config,"enableKeyboard",()=>{const e=function(e,t){function n(n){if(!(n instanceof KeyboardEvent))return;if("canvas"===t.bindKeyboardEventsTo&&document.activeElement!==e.container)return;let r=!1;const o={};switch(n.key){case"ArrowLeft":o.translateX=e.transform.translateX+t.keyboardPanStep,r=!0;break;case"ArrowRight":o.translateX=e.transform.translateX-t.keyboardPanStep,r=!0;break;case"ArrowUp":o.translateY=e.transform.translateY+t.keyboardPanStep,r=!0;break;case"ArrowDown":o.translateY=e.transform.translateY-t.keyboardPanStep,r=!0;break;case"=":case"+":{const n=t.enableAdaptiveSpeed?$(e,t.keyboardZoomStep):t.keyboardZoomStep;e.zoomIn(n),r=!0}break;case"-":{const n=t.enableAdaptiveSpeed?$(e,t.keyboardZoomStep):t.keyboardZoomStep;e.zoomOut(n),r=!0}break;case"0":n.ctrlKey?(e.resetView&&e.resetView(),r=!0):(n.metaKey||n.ctrlKey)&&(e.resetViewToCenter&&e.resetViewToCenter(),r=!0);break;case"g":case"G":n.shiftKey&&e.toggleGrid&&e.toggleGrid(),r=n.shiftKey;break;case"r":case"R":!n.shiftKey||n.metaKey||n.ctrlKey||n.altKey||!e.toggleRulers||(e.toggleRulers(),r=!0)}r&&(n.preventDefault(),Object.keys(o).length>0&&e.updateTransform(o))}const r="canvas"===t.bindKeyboardEventsTo?e.container:document;return r.addEventListener("keydown",n),()=>{r.removeEventListener("keydown",n)}}(this,this.config);this.cleanupCallbacks.push(e)}),u(this.config,"enableTouch",()=>{const e=H(this);this.cleanupCallbacks.push(e)})}catch(e){throw console.error("Failed to set up event handlers:",e),this.cleanup(),e}}get container(){return this.canvas.container}get transformLayer(){return this.canvas.transformLayer}get contentLayer(){return this.canvas.contentLayer}get transform(){return this.canvas.transform}get isReady(){return this._isReady}get isTransforming(){return this.dragSetup?.isEnabled()||!1}get visibleBounds(){return i(this)}getBounds(){return p(this.canvas,this.config)}updateTransform(e){const t=C(this.canvas,e);return t&&E(this.event,this.canvas),t}reset(){const e=C(this.canvas,{scale:1,translateX:0,translateY:0});return e&&E(this.event,this.canvas),e}setZoom(e){return function(e,t,n,r,o){return y(t,n,()=>l(n,t=>{const n=t(o),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}canvasToContent(t,r){return e(t,r,n(this.canvas.transform.scale,this.canvas.transform.translateX,this.canvas.transform.translateY))}zoomToPoint(e,t,n){const r=function(e,t,n,r,o,a){return y(t,n,()=>{const t=s(r,o,e.transform,a/e.transform.scale,n);return C(e,t)})}(this.canvas,this.transformLayer,this.config,e,t,n);return r&&E(this.event,this.canvas),r}resetView(){return e=this.canvas,t=this.transformLayer,n=this.config,y(t,n,()=>h(e,n.rulerSize,t=>C(e,{scale:1,translateX:-1*t,translateY:-1*t})));var e,t,n}resetViewToCenter(){return function(e,t,n,r){return y(t,n,()=>l(n,t=>{const n=t(1),o=D(e);return r(o.x,o.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this))}panLeft(e){return w(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&w(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panRight(e){return k(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&k(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panUp(e){return x(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&x(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panDown(e){return b(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&b(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}zoomIn(e=.5){return function(e,t,n,r,o=.5){return y(t,n,()=>l(n,t=>{const n=t(e.transform.scale*(1+o)),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}zoomOut(e=.5){return function(e,t,n,r,o=.5){return y(t,n,()=>l(n,t=>{const n=t(e.transform.scale*(1-o)),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}resetZoom(){return this.resetViewToCenter()}enableMouseDrag(){return this.dragSetup?.enable()??!1}disableMouseDrag(){return this.dragSetup?.disable()??!1}isMouseDragEnabled(){return this.dragSetup?.isEnabled()??!1}toggleGrid(){const e=(t=this.rulers,!!t?.toggleGrid&&(t.toggleGrid(),!0));var t;return e&&this.event.emit("gridVisibility",this.isGridVisible()),e}showGrid(){const e=(t=this.rulers,!!t?.gridOverlay&&(t.gridOverlay.style.display="block",!0));var t;return e&&this.event.emit("gridVisibility",!0),e}hideGrid(){const e=(t=this.rulers,!!t?.gridOverlay&&(t.gridOverlay.style.display="none",!0));var t;return e&&this.event.emit("gridVisibility",!1),e}isGridVisible(){return e=this.rulers,!!e?.gridOverlay&&"none"!==e.gridOverlay.style.display;var e}toggleRulers(){const e=function(e,t){if(e)return t()?e.hide():e.show(),!0;return!1}(this.rulers,()=>this.areRulersVisible());return e&&this.event.emit("rulersVisibility",this.areRulersVisible()),e}showRulers(){const e=!!(t=this.rulers)&&(t.show(),!0);var t;return e&&this.event.emit("rulersVisibility",!0),e}hideRulers(){const e=!!(t=this.rulers)&&(t.hide(),!0);var t;return e&&this.event.emit("rulersVisibility",!1),e}areRulersVisible(){return e=this.rulers,!!e?.horizontalRuler&&"none"!==e.horizontalRuler.style.display;var e}centerContent(){return e=this.canvas,t=this.config,n=this.updateTransform.bind(this),y(this.transformLayer,t,()=>{const r=p(e,t),o=(r.width-r.contentWidth*e.transform.scale)/2,a=(r.height-r.contentHeight*e.transform.scale)/2;return n({translateX:o,translateY:a})});var e,t,n}fitToScreen(){return e=this.canvas,t=this.transformLayer,n=this.config,y(t,n,()=>{const t=p(e,n),r=t.width/n.width,o=t.height/n.height,a=l(n,e=>e(.9*Math.min(r,o))),s=n.width*a,i=n.height*a,c=(t.width-s)/2,u=(t.height-i)/2;return C(e,{scale:a,translateX:c,translateY:u})});var e,t,n}getVisibleArea(){return i(this)}isPointVisible(e,t){return function(e,t,n){const r=i(e);return t>=r.x&&t<=r.x+r.width&&n>=r.y&&n<=r.y+r.height}(this,e,t)}scrollToPoint(e,t){return function(e,t,n,r,o,a){return y(a,t,()=>{const a=p(e,t),s=a.width/2,i=a.height/2,l=s-n*e.transform.scale,c=i-r*e.transform.scale;return o({translateX:l,translateY:c})})}(this.canvas,this.config,e,t,this.updateTransform.bind(this),this.transformLayer)}getConfig(){return{...this.config}}updateConfig(e){this.config=M({...this.config,...e})}updateThemeMode(e){this.config=M({...this.config,themeMode:e}),S(this.canvas.container,this.config,this.rulers,e)}toggleThemeMode(){const e="light"===this.config.themeMode?"dark":"light";return this.updateThemeMode(e),e}updateTransition(e){this.config=M({...this.config,enableTransition:e})}toggleTransitionMode(){const e=function(e){return!e}(this.config.enableTransition);return this.updateTransition(e),e}cleanup(){!function(e){if("undefined"==typeof window)return;const t=e.name||"markupCanvas",n=window;delete n[t],n.__markupCanvasInstances&&n.__markupCanvasInstances.delete(t)}(this.config),this.cleanupCallbacks.forEach(e=>{try{e()}catch(e){console.warn("Error during cleanup:",e)}}),this.cleanupCallbacks=[],this.removeAllListeners()}on(e,t){this.event.on(e,t)}off(e,t){this.event.off(e,t)}emit(e,t){this.event.emit(e,t)}removeAllListeners(){this.event.removeAllListeners()}destroy(){this.cleanup(),window.__markupCanvasTransitionTimeout&&clearTimeout(window.__markupCanvasTransitionTimeout)}}});
1
+ !function(e,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(e="undefined"!=typeof globalThis?globalThis:e||self).MarkupCanvas=t()}(this,function(){"use strict";function e(e,t,n){if(!n?.inverse)return{x:e,y:t};try{const r=n.inverse(),o=new DOMPoint(e,t).matrixTransform(r);return{x:o.x,y:o.y}}catch(n){return console.warn("Canvas to content conversion failed:",n),{x:e,y:t}}}function t(e,t){return Math.max(t.minZoom,Math.min(t.maxZoom,e))}function n(e,t,n){return new DOMMatrix([e,0,0,e,t,n])}const r="canvas-container",o="transform-layer",a="content-layer";function i(e,n,r,o,a){const i=a.enableRulers?-a.rulerSize:0,s=r||{scale:1,translateX:i,translateY:i},{scale:l,translateX:c,translateY:u}=s,d=t(l*o,a);if(Math.abs(d-l)<.001)return{scale:l,translateX:c,translateY:u};return{scale:d,translateX:e-(e-c)/l*d,translateY:n-(n-u)/l*d}}function s(e){return e.getBounds().visibleArea}function l(e,n){return n(n=>t(n,e))}const c=new Map;function u(e,t,n){return e[t]?n():null}function d(e){let t=null,n=null;const r=(...r)=>{n=r,null===t&&(t=requestAnimationFrame(()=>{n&&e(...n),t=null,n=null}))};return r.cleanup=()=>{null!==t&&(cancelAnimationFrame(t),t=null,n=null)},r}function h(e,t,n){return n(null!==e.container.querySelector(".canvas-ruler")?t:0)}function g(e,t,n,r,o){const a=null!==e.container.querySelector(".canvas-ruler");return o(a?t-r:t,a?n-r:n)}function m(e,t){if("dark"===e.themeMode){return e[`${t}Dark`]}return e[t]}const f={width:8e3,height:8e3,enableAcceleration:!0,initialZoom:1,initialPan:{x:0,y:0},name:"markupCanvas",enablePostMessageAPI:!1,enableZoom:!0,enablePan:!0,enableTouch:!0,enableKeyboard:!0,bindKeyboardEventsTo:"document",zoomSpeed:1.5,minZoom:.05,maxZoom:80,enableTransition:!0,transitionDuration:.2,enableAdaptiveSpeed:!0,enableLeftDrag:!0,enableMiddleDrag:!0,requireSpaceForMouseDrag:!1,keyboardPanStep:50,keyboardFastMultiplier:20,keyboardZoomStep:.2,enableClickToZoom:!0,clickZoomLevel:1,requireOptionForClickZoom:!1,enableRulers:!0,enableGrid:!1,showRulers:!0,showGrid:!1,rulerFontSize:9,rulerFontFamily:"Monaco, Menlo, monospace",rulerUnits:"px",rulerSize:20,canvasBackgroundColor:"rgba(250, 250, 250, 1)",canvasBackgroundColorDark:"rgba(40, 40, 40, 1)",rulerBackgroundColor:"rgba(255, 255, 255, 0.95)",rulerBorderColor:"rgba(240, 240, 240, 1)",rulerTextColor:"rgba(102, 102, 102, 1)",rulerTickColor:"rgba(204, 204, 204, 1)",gridColor:"rgba(232, 86, 193, 0.5)",rulerBackgroundColorDark:"rgba(30, 30, 30, 0.95)",rulerBorderColorDark:"rgba(68, 68, 68, 1)",rulerTextColorDark:"rgba(170, 170, 170, 1)",rulerTickColorDark:"rgba(104, 104, 104, 1)",gridColorDark:"rgba(232, 86, 193, 0.5)",themeMode:"light"};function p(t,r){try{const o=t.container,a=t.transform||{scale:1,translateX:0,translateY:0},i=o.getBoundingClientRect(),s=i.width||o.clientWidth||0,l=i.height||o.clientHeight||0,c=h({container:o},r.rulerSize,e=>Math.max(0,s-e)),u=h({container:o},r.rulerSize,e=>Math.max(0,l-e)),d=r.width||f.width,g=r.height||f.height,m=function(t,r,o,a,i){const s=e(0,0,n(i.scale,i.translateX,i.translateY)),l=e(t,r,n(i.scale,i.translateX,i.translateY));return{x:Math.max(0,Math.min(o,s.x)),y:Math.max(0,Math.min(a,s.y)),width:Math.max(0,Math.min(o-s.x,l.x-s.x)),height:Math.max(0,Math.min(a-s.y,l.y-s.y))}}(c,u,d,g,a);return{width:c,height:u,contentWidth:d,contentHeight:g,scale:a.scale,translateX:a.translateX,translateY:a.translateY,visibleArea:m,scaledContentWidth:d*a.scale,scaledContentHeight:g*a.scale,canPanLeft:a.translateX<0,canPanRight:a.translateX+d*a.scale>c,canPanUp:a.translateY<0,canPanDown:a.translateY+g*a.scale>u,canZoomIn:a.scale<3.5,canZoomOut:a.scale>.1}}catch(e){return console.error("Failed to calculate canvas bounds:",e),{width:0,height:0,contentWidth:0,contentHeight:0,scale:1,translateX:0,translateY:0,visibleArea:{x:0,y:0,width:0,height:0},scaledContentWidth:0,scaledContentHeight:0,canPanLeft:!1,canPanRight:!1,canPanUp:!1,canPanDown:!1,canZoomIn:!1,canZoomOut:!1}}}function v(e,t){try{if(t.enableTransition){window.__markupCanvasTransitionTimeout&&(clearTimeout(window.__markupCanvasTransitionTimeout),window.__markupCanvasTransitionTimeout=void 0);return function(e,t,n){const r=c.get(e);r&&clearTimeout(r);const o=window.setTimeout(()=>{n(),c.delete(e)},t);c.set(e,o)}("disableTransition",1e3*(t.transitionDuration??.2),()=>{e.style.transition="none",window.__markupCanvasTransitionTimeout=void 0}),!0}return!1}catch(e){return console.error("Failed to disable transitions:",e),!0}}function y(e,t,n){!function(e,t){try{return!!t.enableTransition&&(window.__markupCanvasTransitionTimeout&&(clearTimeout(window.__markupCanvasTransitionTimeout),window.__markupCanvasTransitionTimeout=void 0),e.style.transition=`transform ${t.transitionDuration}s linear`,!0)}catch(e){return console.error("Failed to enable transitions:",e),!1}}(e,t);try{return n()}finally{v(e,t)}}function b(e,t,n){const r=t.keyboardPanStep;return n({translateY:e.transform.translateY-r})}function w(e,t,n){const r=t.keyboardPanStep;return n({translateX:e.transform.translateX+r})}function k(e,t,n){const r=t.keyboardPanStep;return n({translateX:e.transform.translateX-r})}function x(e,t,n){const r=t.keyboardPanStep;return n({translateY:e.transform.translateY+r})}function T(e,t){if(!e?.style||!t)return!1;try{return e.style.transform=function(e){return`matrix3d(${e.m11}, ${e.m12}, ${e.m13}, ${e.m14}, ${e.m21}, ${e.m22}, ${e.m23}, ${e.m24}, ${e.m31}, ${e.m32}, ${e.m33}, ${e.m34}, ${e.m41}, ${e.m42}, ${e.m43}, ${e.m44})`}(t),!0}catch(e){return console.warn("Transform application failed:",e),!1}}function C(e,t){e.transform={...e.transform,...t};const r=n(e.transform.scale,e.transform.translateX,e.transform.translateY);return T(e.transformLayer,r)}function M(e={}){const t={...f,...e};return("number"!=typeof t.width||t.width<=0)&&(console.warn("Invalid width, using default"),t.width=f.width),("number"!=typeof t.height||t.height<=0)&&(console.warn("Invalid height, using default"),t.height=f.height),("number"!=typeof t.zoomSpeed||t.zoomSpeed<=0)&&(console.warn("Invalid zoomSpeed, using default"),t.zoomSpeed=f.zoomSpeed),("number"!=typeof t.minZoom||t.minZoom<=0)&&(console.warn("Invalid minZoom, using default"),t.minZoom=f.minZoom),("number"!=typeof t.maxZoom||t.maxZoom<=t.minZoom)&&(console.warn("Invalid maxZoom, using default"),t.maxZoom=f.maxZoom),("number"!=typeof t.keyboardPanStep||t.keyboardPanStep<=0)&&(console.warn("Invalid keyboardPanStep, using default"),t.keyboardPanStep=f.keyboardPanStep),("number"!=typeof t.keyboardFastMultiplier||t.keyboardFastMultiplier<=0)&&(console.warn("Invalid keyboardFastMultiplier, using default"),t.keyboardFastMultiplier=f.keyboardFastMultiplier),("number"!=typeof t.clickZoomLevel||t.clickZoomLevel<=0)&&(console.warn("Invalid clickZoomLevel, using default"),t.clickZoomLevel=f.clickZoomLevel),("number"!=typeof t.rulerFontSize||t.rulerFontSize<=0)&&(console.warn("Invalid rulerFontSize, using default"),t.rulerFontSize=f.rulerFontSize),("number"!=typeof t.rulerSize||t.rulerSize<=0)&&(console.warn("Invalid rulerSize, using default"),t.rulerSize=f.rulerSize),t}function S(e,t,n,r){const o=M({...t,themeMode:r}),a=m(o,"canvasBackgroundColor");e.style.backgroundColor=a,n&&n.updateTheme(o)}function D(e){try{const t=e.getBounds();return{x:t.width/2,y:t.height/2}}catch(e){return console.warn("Failed to calculate viewport center:",e),{x:0,y:0}}}function z(e,t){const n=Array.from(e.children);let r=e.querySelector(`.${o}`);r||(r=document.createElement("div"),r.className=o,e.appendChild(r)),function(e,t){e.style.position="absolute";const n=t.rulerSize;e.style.top=`${n}px`,e.style.left=`${n}px`,e.style.width=`${t.width}px`,e.style.height=`${t.height}px`,e.style.transformOrigin="0 0"}(r,t);let i=r.querySelector(`.${a}`);return i||(i=document.createElement("div"),i.className=a,r.appendChild(i),function(e,t,n){e.forEach(e=>{e===n||e.classList.contains(o)||t.appendChild(e)})}(n,i,r)),function(e){e.style.position="relative",e.style.width="100%",e.style.height="100%",e.style.pointerEvents="auto"}(i),{transformLayer:r,contentLayer:i}}function L(e,t){if("static"===getComputedStyle(e).position&&(e.style.position="relative"),e.style.overflow="hidden",e.style.cursor="grab",e.style.overscrollBehavior="none",t){const n=m(t,"canvasBackgroundColor");e.style.backgroundColor=n}e.hasAttribute("tabindex")||e.setAttribute("tabindex","0"),function(e){const t=e.getBoundingClientRect(),n=getComputedStyle(e);0===t.height&&"auto"===n.height&&console.error("MarkupCanvas: Container height is 0. Please set a height on your container element using CSS.","Examples: height: 100vh, height: 500px, or use flexbox/grid layout.",e),0===t.width&&"auto"===n.width&&console.error("MarkupCanvas: Container width is 0. Please set a width on your container element using CSS.","Examples: width: 100vw, width: 800px, or use flexbox/grid layout.",e)}(e),e.classList.contains(r)||e.classList.add(r)}function R(e,t){if(!e?.appendChild)return console.error("Invalid container element provided to createCanvas"),null;try{L(e,t);const{transformLayer:r,contentLayer:o}=z(e,t);u(t,"enableAcceleration",()=>{!function(e){try{return e.style.transform=e.style.transform||"translateZ(0)",e.style.backfaceVisibility="hidden",!0}catch(e){return console.error("Failed to enable hardware acceleration:",e),!1}}(r)});const a=t.enableRulers?-t.rulerSize:0,i={scale:1,translateX:a,translateY:a},s=n(i.scale,i.translateX,i.translateY);T(r,s);return{container:e,transformLayer:r,contentLayer:o,transform:i}}catch(e){return console.error("Failed to create canvas:",e),null}}class P{constructor(){this.listeners=new Map}setEmitInterceptor(e){this.emitInterceptor=e}on(e,t){this.listeners.has(e)||this.listeners.set(e,new Set),this.listeners.get(e).add(t)}off(e,t){const n=this.listeners.get(e);n&&n.delete(t)}emit(e,t){this.emitInterceptor?.(e,t);const n=this.listeners.get(e);n&&n.forEach(n=>{try{n(t)}catch(t){console.error(`Error in event handler for "${String(e)}":`,t)}})}removeAllListeners(){this.listeners.clear()}}function E(e,t){const n=t.transform;e.emit("transform",n),e.emit("zoom",n.scale),e.emit("pan",{x:n.translateX,y:n.translateY})}const Y=300,X=5;function $(e,t){if(!e?.getBounds)return t;try{const n=e.getBounds(),r=n.width*n.height;return t*(r/2073600)**1}catch(e){return console.warn("Failed to calculate adaptive zoom speed, using base speed:",e),t}}function I(e,t,n,r,o){n?t.requireSpaceForMouseDrag?e.container.style.cursor=r?"grab":"default":e.container.style.cursor=o?"grabbing":"grab":e.container.style.cursor="default"}function B(e,t,n,r,o){o.setIsDragging(!1),o.setDragButton(-1),I(e,t,n,r,!1)}function Z(e,t,n,r,o,a,i,s,l,c){a&&e.button===i&&B(t,n,r,o,{setIsDragging:c.setIsDragging,setDragButton:c.setDragButton}),r&&0===e.button&&n.enableClickToZoom&&s>0&&function(e,t,n,r,o,a){const i=Date.now()-r,s=e.altKey,l=!n.requireOptionForClickZoom||s;if(i<Y&&!o&&!a&&l){e.preventDefault();const r=t.container.getBoundingClientRect(),o=e.clientX-r.left,a=e.clientY-r.top,{clickX:i,clickY:s}=g(t,o,a,n.rulerSize,(e,t)=>({clickX:e,clickY:t})),l=t.canvasToContent(i,s),c=r.width/2,u=r.height/2,d=n.clickZoomLevel,h={scale:d,translateX:c-l.x*d,translateY:u-l.y*d};y(t.transformLayer,t.config,()=>{t.updateTransform(h)})}}(e,t,n,s,l,a),0===e.button&&function(e){e.setMouseDownTime(0),e.setHasDragged(!1)}({setMouseDownTime:c.setMouseDownTime,setHasDragged:c.setHasDragged})}function F(e,t,n=!0){let r=!0,o=!1,a=0,i=0,s=-1,l=!1,c=0,u=0,h=0,g=!1;const m={setIsDragging:e=>{o=e},setDragButton:e=>{s=e},setIsSpacePressed:e=>{l=e},setMouseDownTime:e=>{c=e},setMouseDownX:e=>{u=e},setMouseDownY:e=>{h=e},setHasDragged:e=>{g=e},setLastMouseX:e=>{a=e},setLastMouseY:e=>{i=e}},f=n=>{!function(e,t,n,r,o,a){n.requireSpaceForMouseDrag&&" "===e.key&&(a.setIsSpacePressed(!0),I(t,n,r,!0,o))}(n,e,t,r,o,{setIsSpacePressed:m.setIsSpacePressed})},p=n=>{!function(e,t,n,r,o,a){n.requireSpaceForMouseDrag&&" "===e.key&&(a.setIsSpacePressed(!1),I(t,n,r,!1,o),o&&B(t,n,r,!1,{setIsDragging:a.setIsDragging,setDragButton:a.setDragButton}))}(n,e,t,r,o,{setIsSpacePressed:m.setIsSpacePressed,setIsDragging:m.setIsDragging,setDragButton:m.setDragButton})},v=n=>{!function(e,t,n,r,o,a){const i=0===e.button,s=1===e.button;if(i&&(a.setMouseDownTime(Date.now()),a.setMouseDownX(e.clientX),a.setMouseDownY(e.clientY),a.setHasDragged(!1)),!r)return;(!n.requireSpaceForMouseDrag||o)&&(i&&n.enableLeftDrag||s&&n.enableMiddleDrag)&&(e.preventDefault(),a.setDragButton(e.button),a.setLastMouseX(e.clientX),a.setLastMouseY(e.clientY),I(t,n,r,o,!1))}(n,e,t,r,l,m)},y=n=>{!function(e,t,n,r,o,a,i,s,l,c,u,h){if(i>0){const t=Math.abs(e.clientX-s),i=Math.abs(e.clientY-l);if(t>X||i>X){h.setHasDragged(!0);const e=!n.requireSpaceForMouseDrag||a;!o&&r&&e&&h.setIsDragging(!0)}}if(!o||!r)return;e.preventDefault(),d((...e)=>{const n=e[0];if(!o||!r)return;const a=n.clientX-c,i=n.clientY-u,s={translateX:t.transform.translateX+a,translateY:t.transform.translateY+i};t.updateTransform(s),h.setLastMouseX(n.clientX),h.setLastMouseY(n.clientY)})(e)}(n,e,t,r,o,l,c,u,h,a,i,{setHasDragged:m.setHasDragged,setIsDragging:m.setIsDragging,setLastMouseX:m.setLastMouseX,setLastMouseY:m.setLastMouseY})},b=n=>{Z(n,e,t,r,l,o,s,c,g,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton,setMouseDownTime:m.setMouseDownTime,setHasDragged:m.setHasDragged})},w=()=>{!function(e,t,n,r,o,a){o&&B(e,t,n,r,a)}(e,t,r,l,o,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton})};e.container.addEventListener("mousedown",v),document.addEventListener("mousemove",y),document.addEventListener("mouseup",b),e.container.addEventListener("mouseleave",w),t.requireSpaceForMouseDrag&&(document.addEventListener("keydown",f),document.addEventListener("keyup",p)),I(e,t,r,l,o);const k=()=>{e.container.removeEventListener("mousedown",v),document.removeEventListener("mousemove",y),document.removeEventListener("mouseup",b),e.container.removeEventListener("mouseleave",w),t.requireSpaceForMouseDrag&&(document.removeEventListener("keydown",f),document.removeEventListener("keyup",p))};return n?{cleanup:k,enable:()=>(r=!0,I(e,t,r,l,o),!0),disable:()=>(r=!1,o&&B(e,t,r,l,{setIsDragging:m.setIsDragging,setDragButton:m.setDragButton}),I(e,t,r,l,o),!0),isEnabled:()=>r}:k}function O(e){const t=t=>{const n=t.data;if("markup-canvas"!==n.source)return;const r=e.config.name||"markupCanvas";if(n.canvasName!==r)return;const o=n.action,a=n.args||[];try{if("zoomIn"===o)e.zoomIn(a[0]);else if("zoomOut"===o)e.zoomOut(a[0]);else if("setZoom"===o){const t=a[0];if("number"!=typeof t||t<=0)throw new Error(`Invalid zoom level: ${t}. Must be a positive number.`);e.setZoom(t)}else if("resetZoom"===o)e.resetZoom();else if("panLeft"===o)e.panLeft(a[0]);else if("panRight"===o)e.panRight(a[0]);else if("panUp"===o)e.panUp(a[0]);else if("panDown"===o)e.panDown(a[0]);else if("fitToScreen"===o)e.fitToScreen();else if("centerContent"===o)e.centerContent();else if("panToPoint"===o)e.panToPoint(a[0],a[1]);else if("resetView"===o)e.resetView();else if("resetViewToCenter"===o)e.resetViewToCenter();else if("toggleRulers"===o)e.toggleRulers();else if("showRulers"===o)e.showRulers();else if("hideRulers"===o)e.hideRulers();else if("toggleGrid"===o)e.toggleGrid();else if("showGrid"===o)e.showGrid();else if("hideGrid"===o)e.hideGrid();else if("updateThemeMode"===o){const t=a[0];if("light"!==t&&"dark"!==t)throw new Error(`Invalid theme mode: ${t}`);e.updateThemeMode(t)}else if("toggleThemeMode"===o){const t="light"===e.getConfig().themeMode?"dark":"light";e.updateThemeMode(t)}else if("updateTransition"===o){const t=a[0];if("boolean"!=typeof t)throw new Error(`Invalid transition enabled value: ${t}. Must be a boolean.`);e.updateTransition(t)}else{if("toggleTransitionMode"!==o)throw new Error(`Unknown action: ${o}`);e.toggleTransitionMode()}}catch(e){!function(e,t,n){window.postMessage({source:"markup-canvas-error",canvasName:e,action:t,error:n,timestamp:Date.now()},"*")}(r,o,e instanceof Error?e.message:String(e))}};return"undefined"!=typeof window&&window.addEventListener("message",t),()=>{"undefined"!=typeof window&&window.removeEventListener("message",t)}}function V(e,t){return{x:(e.clientX+t.clientX)/2,y:(e.clientY+t.clientY)/2}}function A(e,t){const n=e.clientX-t.clientX,r=e.clientY-t.clientY;return Math.sqrt(n*n+r*r)}function _(e,t,n,r){const o=i(n,r,e.transform,t,e.config);return e.updateTransform(o)}function G(e,t,n){e.preventDefault();const r=Array.from(e.touches);d((...e)=>{const r=e[0];if(1===r.length){if(1===n.touches.length){const e=r[0].clientX-n.touches[0].clientX,o=r[0].clientY-n.touches[0].clientY,a={translateX:t.transform.translateX+e,translateY:t.transform.translateY+o};t.updateTransform(a)}}else if(2===r.length){const e=A(r[0],r[1]),o=V(r[0],r[1]);if(n.lastDistance>0){const r=e/n.lastDistance,a=t.container.getBoundingClientRect();let i=o.x-a.left,s=o.y-a.top;const l=function(e,t,n,r){return h(e,t,e=>{const t={...n,x:n.x-e,y:n.y-e};return r(t)})}(t,t.config.rulerSize,{x:i,y:s},e=>e);i=l.x,s=l.y,_(t,r,i,s)}n.lastDistance=e,n.lastCenter=o}n.touches=r})(r)}function H(e){const t={touches:[],lastDistance:0,lastCenter:{}},n=e=>{!function(e,t){e.preventDefault(),t.touches=Array.from(e.touches),2===t.touches.length&&(t.lastDistance=A(t.touches[0],t.touches[1]),t.lastCenter=V(t.touches[0],t.touches[1]))}(e,t)},r=n=>{G(n,e,t)},o=e=>{!function(e,t){t.touches=Array.from(e.touches),t.touches.length<2&&(t.lastDistance=0)}(e,t)};return e.container.addEventListener("touchstart",n,{passive:!1}),e.container.addEventListener("touchmove",r,{passive:!1}),e.container.addEventListener("touchend",o,{passive:!1}),()=>{e.container.removeEventListener("touchstart",n),e.container.removeEventListener("touchmove",r),e.container.removeEventListener("touchend",o)}}function N(e){const t=e.ctrlKey||e.metaKey,n=[0===e.deltaMode,Math.abs(e.deltaY)<50,e.deltaY%1!=0,Math.abs(e.deltaX)>0&&Math.abs(e.deltaY)>0].filter(Boolean).length>=2;return{isTrackpad:n,isMouseWheel:!n,isTrackpadScroll:n&&!t,isTrackpadPinch:n&&t,isZoomGesture:t}}function K(e,t){const n=(e=>d((...t)=>{const n=t[0];if(!n||!e?.updateTransform)return!1;try{const t=e.transform,r=1,o=n.deltaX*r,a=n.deltaY*r,i={scale:t.scale,translateX:t.translateX-o,translateY:t.translateY-a};return v(e.transformLayer,e.config),e.updateTransform(i)}catch(e){return console.error("Error handling trackpad pan:",e),!1}}))(e),r=r=>N(r).isTrackpadScroll?n(r):function(e,t,n){if(!e||"number"!=typeof e.deltaY)return console.warn("Invalid wheel event provided"),!1;if(!t?.updateTransform)return console.warn("Invalid canvas provided to handleWheelEvent"),!1;try{e.preventDefault();const r=t.container.getBoundingClientRect(),o=e.clientX-r.left,a=e.clientY-r.top,{mouseX:i,mouseY:s}=g(t,o,a,n.rulerSize,(e,t)=>({mouseX:e,mouseY:t})),l=n.zoomSpeed,c=N(e);if(!c.isZoomGesture)return!1;let u=n.enableAdaptiveSpeed?$(t,l):l;if(c.isTrackpadPinch){const e=.05*n.zoomSpeed;u=n.enableAdaptiveSpeed?$(t,e):e}return _(t,(e.deltaY<0?1:-1)>0?1+u:1/(1+u),i,s)}catch(e){return console.error("Error handling wheel event:",e),!1}}(r,e,t);return e.container.addEventListener("wheel",r,{passive:!1}),()=>{e.container.removeEventListener("wheel",r)}}const q=100,U=1e3,W=1001,j=4,J=4,Q=100,ee=100,te=20,ne=200;function re(e,t){const n=function(e){const t=document.createElement("div");return t.className="canvas-ruler horizontal-ruler",t.style.cssText=`\n\tposition: absolute;\n\ttop: 0;\n\tleft: ${e.rulerSize}px;\n\tright: 0;\n\theight: ${e.rulerSize}px;\n\tbackground: var(--ruler-background-color);\n\tborder-bottom: 1px solid var(--ruler-border-color);\n\tborder-right: 1px solid var(--ruler-border-color);\n\tz-index: ${U};\n\tpointer-events: none;\n\tfont-family: ${e.rulerFontFamily};\n\tfont-size: ${e.rulerFontSize}px;\n\tcolor: var(--ruler-text-color);\n\toverflow: hidden;\n `,t}(t),r=function(e){const t=document.createElement("div");return t.className="canvas-ruler vertical-ruler",t.style.cssText=`\n\tposition: absolute;\n\ttop: ${e.rulerSize}px;\n\tleft: 0;\n\tbottom: 0;\n\twidth: ${e.rulerSize}px;\n\tbackground: var(--ruler-background-color);\n\tborder-right: 1px solid var(--ruler-border-color);\n\tborder-bottom: 1px solid var(--ruler-border-color);\n\tz-index: ${U};\n\tpointer-events: none;\n\tfont-family: ${e.rulerFontFamily};\n\tfont-size: ${e.rulerFontSize}px;\n\tcolor: var(--ruler-text-color);\n\toverflow: hidden;\n `,t}(t),o=function(e){const t=document.createElement("div");return t.className="canvas-ruler corner-box",t.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: 0;\n\t\tleft: 0;\n\t\twidth: ${e.rulerSize}px;\n\t\theight: ${e.rulerSize}px;\n\t\tbackground: var(--ruler-background-color);\n\t\tborder-right: 1px solid var(--ruler-border-color);\n\t\tborder-bottom: 1px solid var(--ruler-border-color);\n\t\tz-index: ${W};\n\t\tdisplay: flex;\n\t\talign-items: center;\n\t\tjustify-content: center;\n\t\tfont-family: ${e.rulerFontFamily};\n\t\tfont-size: ${e.rulerFontSize-2}px;\n\t\tcolor: var(--ruler-text-color);\n\t\tpointer-events: none;\n\t`,t.textContent=e.rulerUnits,t}(t),a=t.enableGrid?function(e){const t=document.createElement("div");return t.className="canvas-ruler grid-overlay",t.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: ${e.rulerSize}px;\n\t\tleft: ${e.rulerSize}px;\n\t\tright: 0;\n\t\tbottom: 0;\n\t\tpointer-events: none;\n\t\tz-index: ${q};\n\t\tbackground-image: \n\t\t\tlinear-gradient(var(--grid-color) 1px, transparent 1px),\n\t\t\tlinear-gradient(90deg, var(--grid-color) 1px, transparent 1px);\n\t\tbackground-size: 100px 100px;\n\t\topacity: 0.5;\n\t`,t}(t):void 0;return e.appendChild(n),e.appendChild(r),e.appendChild(o),a&&e.appendChild(a),{horizontalRuler:n,verticalRuler:r,cornerBox:o,gridOverlay:a}}function oe(e,t){const n=e/Math.max(5,Math.min(20,t/50)),r=10**Math.floor(Math.log10(n)),o=n/r;let a;return a=o<=1?1:o<=2?2:o<=5?5:10,a*r}function ae(e,t,n,r,o){const a=document.createElement("div");a.className="tick",a.style.cssText=`\n\t\tposition: absolute;\n\t\tleft: ${n}px;\n\t\tbottom: 0;\n\t\twidth: 1px;\n\t\theight: ${j}px;\n\t\tbackground: var(--ruler-tick-color);\n\t`,e.appendChild(a);if(t%Q===0){const r=document.createElement("div");r.style.cssText=`\n\t\t\tposition: absolute;\n\t\t\tleft: ${n}px;\n\t\t\tbottom: ${j+2}px;\n\t\t\tfont-size: ${o.rulerFontSize}px;\n\t\t\tline-height: 1;\n\t\t\tcolor: var(--ruler-text-color);\n\t\t\twhite-space: nowrap;\n\t\t\tpointer-events: none;\n\t\t`,r.textContent=Math.round(t).toString(),e.appendChild(r)}}function ie(e,t,n,r,o){const a=document.createElement("div");a.className="tick",a.style.cssText=`\n\t\tposition: absolute;\n\t\ttop: ${n}px;\n\t\tright: 0;\n\t\twidth: ${J}px;\n\t\theight: 1px;\n\t\tbackground: var(--ruler-tick-color);\n\t`,e.appendChild(a);if(t%Q===0){const r=document.createElement("div");r.style.cssText=`\n\t\t\tposition: absolute;\n\t\t\ttop: ${n-6}px;\n\t\t\tright: ${J+6}px;\n\t\t\tfont-size: ${o.rulerFontSize}px;\n\t\t\tline-height: 1;\n\t\t\tcolor: var(--ruler-text-color);\n\t\t\twhite-space: nowrap;\n\t\t\tpointer-events: none;\n\t\t\ttransform: rotate(-90deg);\n\t\t\ttransform-origin: right center;\n\t\t`,r.textContent=Math.round(t).toString(),e.appendChild(r)}}function se(e,t,n,r,o){const a=e.getBounds(),i=a.scale||1,s=a.translateX||0,l=a.translateY||0,c=a.width-o.rulerSize,u=a.height-o.rulerSize,d=-s/i,h=-l/i,g=h+u/i;!function(e,t,n,r,o,a){const i=r,s=oe(n-t,i),l=document.createDocumentFragment(),c=Math.floor(t/s)*s,u=Math.ceil(n/s)*s;for(let e=c;e<=u;e+=s){const n=(e-t)*o;n>=-50&&n<=i+50&&ae(l,e,n,0,a)}e.innerHTML="",e.appendChild(l)}(t,d,d+c/i,c,i,o),function(e,t,n,r,o,a){const i=r,s=oe(n-t,i),l=document.createDocumentFragment(),c=Math.floor(t/s)*s,u=Math.ceil(n/s)*s;for(let e=c;e<=u;e+=s){const n=(e-t)*o;n>=-50&&n<=i+50&&ie(l,e,n,0,a)}e.innerHTML="",e.appendChild(l)}(n,h,g,u,i,o),r&&function(e,t,n,r){let o=ee*t;for(;o<te;)o*=2;for(;o>ne;)o/=2;e.style.backgroundSize=`${o}px ${o}px`,e.style.backgroundPosition=`${n%o}px ${r%o}px`}(r,i,s,l)}function le(e,t){const n=m(t,"rulerBackgroundColor"),r=m(t,"rulerBorderColor"),o=m(t,"rulerTextColor"),a=m(t,"rulerTickColor"),i=m(t,"gridColor");e.horizontalRuler&&(e.horizontalRuler.style.setProperty("--ruler-background-color",n),e.horizontalRuler.style.setProperty("--ruler-border-color",r),e.horizontalRuler.style.setProperty("--ruler-text-color",o),e.horizontalRuler.style.setProperty("--ruler-tick-color",a)),e.verticalRuler&&(e.verticalRuler.style.setProperty("--ruler-background-color",n),e.verticalRuler.style.setProperty("--ruler-border-color",r),e.verticalRuler.style.setProperty("--ruler-text-color",o),e.verticalRuler.style.setProperty("--ruler-tick-color",a)),e.cornerBox&&(e.cornerBox.style.setProperty("--ruler-background-color",n),e.cornerBox.style.setProperty("--ruler-border-color",r),e.cornerBox.style.setProperty("--ruler-text-color",o)),e.gridOverlay&&e.gridOverlay.style.setProperty("--grid-color",i)}function ce(e,t){if(!e?.container)return console.error("Invalid canvas provided to createRulers"),null;let n,r=null,o=!1;const a=()=>{!o&&n.horizontalRuler&&n.verticalRuler&&se(e,n.horizontalRuler,n.verticalRuler,n.gridOverlay,t)};try{return n=re(e.container,t),r=function(e,t){const n=d(t),r=e.updateTransform;e.updateTransform=function(e){const t=r.call(this,e);return n(),t};const o=d(t);return window.addEventListener("resize",o),()=>{window.removeEventListener("resize",o),e.updateTransform=r,n.cleanup(),o.cleanup()}}(e,a),le(n,t),a(),t.showRulers||(n.horizontalRuler.style.display="none",n.verticalRuler.style.display="none",n.cornerBox.style.display="none"),!t.showGrid&&n.gridOverlay&&(n.gridOverlay.style.display="none"),{horizontalRuler:n.horizontalRuler,verticalRuler:n.verticalRuler,cornerBox:n.cornerBox,gridOverlay:n.gridOverlay,update:a,updateTheme:e=>{o||le(n,e)},show:()=>{n.horizontalRuler&&(n.horizontalRuler.style.display="block"),n.verticalRuler&&(n.verticalRuler.style.display="block"),n.cornerBox&&(n.cornerBox.style.display="flex")},hide:()=>{n.horizontalRuler&&(n.horizontalRuler.style.display="none"),n.verticalRuler&&(n.verticalRuler.style.display="none"),n.cornerBox&&(n.cornerBox.style.display="none"),n.gridOverlay&&(n.gridOverlay.style.display="none")},toggleGrid:()=>{if(n.gridOverlay){const e="none"!==n.gridOverlay.style.display;n.gridOverlay.style.display=e?"none":"block"}},destroy:()=>{o=!0,r&&r(),n.horizontalRuler?.parentNode&&n.horizontalRuler.parentNode.removeChild(n.horizontalRuler),n.verticalRuler?.parentNode&&n.verticalRuler.parentNode.removeChild(n.verticalRuler),n.cornerBox?.parentNode&&n.cornerBox.parentNode.removeChild(n.cornerBox),n.gridOverlay?.parentNode&&n.gridOverlay.parentNode.removeChild(n.gridOverlay)}}}catch(e){return console.error("Failed to create rulers:",e),null}}return class{constructor(e,t={}){if(this.cleanupCallbacks=[],this.rulers=null,this.dragSetup=null,this.event=new P,this._isReady=!1,!e)throw new Error("Container element is required");this.config=M(t);const n=R(e,this.config);if(!n)throw new Error("Failed to create canvas");if(this.canvas=n,u(this.config,"enableRulers",()=>{this.rulers=ce(this,this.config),this.cleanupCallbacks.push(()=>{this.rulers&&this.rulers.destroy()})}),t.themeMode&&S(this.canvas.container,this.config,this.rulers,t.themeMode),this.event.setEmitInterceptor((e,t)=>{!function(e,t,n){if("undefined"==typeof window)return;let r=t;"ready"===e&&(r={ready:!0});const o=n.name||"markupCanvas";window.postMessage({source:"markup-canvas",action:e,data:r,timestamp:Date.now(),canvasName:o},"*"),window.parent&&window.parent.postMessage({source:"markup-canvas",action:e,data:r,timestamp:Date.now(),canvasName:o},"*")}(e,t,this.config)}),function(e,t){if("undefined"==typeof window)return;const n=t.name||"markupCanvas",r=window,o={config:{get current(){return e.config},get:e.getConfig.bind(e),update:e.updateConfig.bind(e)},transform:{update:e.updateTransform.bind(e),reset:e.reset.bind(e)},zoom:{get current(){return e.transform.scale||1},set:e.setZoom.bind(e),toPoint:e.zoomToPoint.bind(e),in:e.zoomIn.bind(e),out:e.zoomOut.bind(e),reset:e.resetZoom.bind(e),resetToCenter:e.resetViewToCenter.bind(e),fitToScreen:e.fitToScreen.bind(e)},pan:{left:e.panLeft.bind(e),right:e.panRight.bind(e),up:e.panUp.bind(e),down:e.panDown.bind(e),toPoint:e.panToPoint.bind(e),toCenter:e.centerContent.bind(e)},mouseDrag:{enable:e.enableMouseDrag.bind(e),disable:e.disableMouseDrag.bind(e),isEnabled:e.isMouseDragEnabled.bind(e)},grid:{toggle:e.toggleGrid.bind(e),show:e.showGrid.bind(e),hide:e.hideGrid.bind(e),isVisible:e.isGridVisible.bind(e)},rulers:{toggle:e.toggleRulers.bind(e),show:e.showRulers.bind(e),hide:e.hideRulers.bind(e),isVisible:e.areRulersVisible.bind(e)},canvas:{canvasToContent:e.canvasToContent.bind(e),getVisibleArea:e.getVisibleArea.bind(e),isPointVisible:e.isPointVisible.bind(e),getBounds:e.getBounds.bind(e)},theme:{get current(){return e.config.themeMode},update:e.updateThemeMode.bind(e),toggle:e.toggleThemeMode.bind(e)},transition:{get current(){return e.config.enableTransition},set:e.updateTransition.bind(e),toggle:e.toggleTransitionMode.bind(e)},event:e.event,lifecycle:{cleanup:e.cleanup.bind(e),destroy:e.destroy.bind(e)},state:{get isReady(){return e.isReady},get isTransforming(){return e.isTransforming},get visibleBounds(){return e.visibleBounds},get transform(){return e.transform}}};r[n]=o,r.__markupCanvasInstances||(r.__markupCanvasInstances=new Map),r.__markupCanvasInstances.set(n,o)}(this,this.config),this.config.enablePostMessageAPI){const e=O(this);this.cleanupCallbacks.push(e)}this.setupEventHandlers(),this._isReady=!0,void 0!==t.initialZoom&&this.setZoom(t.initialZoom),void 0!==t.initialPan&&this.panToPoint(t.initialPan.x,t.initialPan.y),this.event.emit("ready",this)}setupEventHandlers(){try{u(this.config,"enableZoom",()=>{const e=K(this,this.config);this.cleanupCallbacks.push(e)}),(this.config.enablePan||this.config.enableClickToZoom)&&(this.dragSetup=F(this,this.config,!0),this.cleanupCallbacks.push(this.dragSetup.cleanup)),u(this.config,"enableKeyboard",()=>{const e=function(e,t){function n(n){if(!(n instanceof KeyboardEvent))return;if("canvas"===t.bindKeyboardEventsTo&&document.activeElement!==e.container)return;let r=!1;const o={};switch(n.key){case"ArrowLeft":o.translateX=e.transform.translateX+t.keyboardPanStep,r=!0;break;case"ArrowRight":o.translateX=e.transform.translateX-t.keyboardPanStep,r=!0;break;case"ArrowUp":o.translateY=e.transform.translateY+t.keyboardPanStep,r=!0;break;case"ArrowDown":o.translateY=e.transform.translateY-t.keyboardPanStep,r=!0;break;case"=":case"+":{const n=t.enableAdaptiveSpeed?$(e,t.keyboardZoomStep):t.keyboardZoomStep;e.zoomIn(n),r=!0}break;case"-":{const n=t.enableAdaptiveSpeed?$(e,t.keyboardZoomStep):t.keyboardZoomStep;e.zoomOut(n),r=!0}break;case"0":n.ctrlKey?(e.resetView&&e.resetView(),r=!0):(n.metaKey||n.ctrlKey)&&(e.resetViewToCenter&&e.resetViewToCenter(),r=!0);break;case"g":case"G":n.shiftKey&&e.toggleGrid&&e.toggleGrid(),r=n.shiftKey;break;case"r":case"R":!n.shiftKey||n.metaKey||n.ctrlKey||n.altKey||!e.toggleRulers||(e.toggleRulers(),r=!0)}r&&(n.preventDefault(),Object.keys(o).length>0&&e.updateTransform(o))}const r="canvas"===t.bindKeyboardEventsTo?e.container:document;return r.addEventListener("keydown",n),()=>{r.removeEventListener("keydown",n)}}(this,this.config);this.cleanupCallbacks.push(e)}),u(this.config,"enableTouch",()=>{const e=H(this);this.cleanupCallbacks.push(e)})}catch(e){throw console.error("Failed to set up event handlers:",e),this.cleanup(),e}}get container(){return this.canvas.container}get transformLayer(){return this.canvas.transformLayer}get contentLayer(){return this.canvas.contentLayer}get transform(){return this.canvas.transform}get isReady(){return this._isReady}get isTransforming(){return this.dragSetup?.isEnabled()||!1}get visibleBounds(){return s(this)}getBounds(){return p(this.canvas,this.config)}updateTransform(e){const t=C(this.canvas,e);return t&&E(this.event,this.canvas),t}reset(){const e=C(this.canvas,{scale:1,translateX:0,translateY:0});return e&&E(this.event,this.canvas),e}setZoom(e){return function(e,t,n,r,o){return y(t,n,()=>l(n,t=>{const n=t(o),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}canvasToContent(t,r){return e(t,r,n(this.canvas.transform.scale,this.canvas.transform.translateX,this.canvas.transform.translateY))}zoomToPoint(e,t,n){const r=function(e,t,n,r,o,a){return y(t,n,()=>{const t=i(r,o,e.transform,a/e.transform.scale,n);return C(e,t)})}(this.canvas,this.transformLayer,this.config,e,t,n);return r&&E(this.event,this.canvas),r}resetView(){return e=this.canvas,t=this.transformLayer,n=this.config,y(t,n,()=>h(e,n.rulerSize,t=>C(e,{scale:1,translateX:-1*t,translateY:-1*t})));var e,t,n}resetViewToCenter(){return function(e,t,n,r){return y(t,n,()=>l(n,t=>{const n=t(1),o=D(e);return r(o.x,o.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this))}panLeft(e){return w(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&w(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panRight(e){return k(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&k(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panUp(e){return x(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&x(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}panDown(e){return b(this.canvas,this.config,this.updateTransform.bind(this))||!!e&&b(this.canvas,{...this.config,keyboardPanStep:e},this.updateTransform.bind(this))}zoomIn(e=.5){return function(e,t,n,r,o=.5){return y(t,n,()=>l(n,t=>{const n=t(e.transform.scale*(1+o)),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}zoomOut(e=.5){return function(e,t,n,r,o=.5){return y(t,n,()=>l(n,t=>{const n=t(e.transform.scale*(1-o)),a=D(e);return r(a.x,a.y,n)}))}(this,this.transformLayer,this.config,this.zoomToPoint.bind(this),e)}resetZoom(){return this.resetViewToCenter()}enableMouseDrag(){return this.dragSetup?.enable()??!1}disableMouseDrag(){return this.dragSetup?.disable()??!1}isMouseDragEnabled(){return this.dragSetup?.isEnabled()??!1}toggleGrid(){const e=(t=this.rulers,!!t?.toggleGrid&&(t.toggleGrid(),!0));var t;return e&&this.event.emit("gridVisibility",this.isGridVisible()),e}showGrid(){const e=(t=this.rulers,!!t?.gridOverlay&&(t.gridOverlay.style.display="block",!0));var t;return e&&this.event.emit("gridVisibility",!0),e}hideGrid(){const e=(t=this.rulers,!!t?.gridOverlay&&(t.gridOverlay.style.display="none",!0));var t;return e&&this.event.emit("gridVisibility",!1),e}isGridVisible(){return e=this.rulers,!!e?.gridOverlay&&"none"!==e.gridOverlay.style.display;var e}toggleRulers(){const e=function(e,t){if(e)return t()?e.hide():e.show(),!0;return!1}(this.rulers,()=>this.areRulersVisible());return e&&this.event.emit("rulersVisibility",this.areRulersVisible()),e}showRulers(){const e=!!(t=this.rulers)&&(t.show(),!0);var t;return e&&this.event.emit("rulersVisibility",!0),e}hideRulers(){const e=!!(t=this.rulers)&&(t.hide(),!0);var t;return e&&this.event.emit("rulersVisibility",!1),e}areRulersVisible(){return e=this.rulers,!!e?.horizontalRuler&&"none"!==e.horizontalRuler.style.display;var e}centerContent(){return e=this.canvas,t=this.config,n=this.updateTransform.bind(this),y(this.transformLayer,t,()=>{const r=p(e,t),o=(r.width-r.contentWidth*e.transform.scale)/2,a=(r.height-r.contentHeight*e.transform.scale)/2;return n({translateX:o,translateY:a})});var e,t,n}fitToScreen(){return e=this.canvas,t=this.transformLayer,n=this.config,y(t,n,()=>{const t=p(e,n),r=t.width/n.width,o=t.height/n.height,a=l(n,e=>e(.9*Math.min(r,o))),i=n.width*a,s=n.height*a,c=(t.width-i)/2,u=(t.height-s)/2;return C(e,{scale:a,translateX:c,translateY:u})});var e,t,n}getVisibleArea(){return s(this)}isPointVisible(e,t){return function(e,t,n){const r=s(e);return t>=r.x&&t<=r.x+r.width&&n>=r.y&&n<=r.y+r.height}(this,e,t)}panToPoint(e,t){return function(e,t,n,r,o,a){return y(a,t,()=>{const a=p(e,t),i=a.width/2,s=a.height/2,l=i-n*e.transform.scale,c=s-r*e.transform.scale;return o({translateX:l,translateY:c})})}(this.canvas,this.config,e,t,this.updateTransform.bind(this),this.transformLayer)}getConfig(){return{...this.config}}updateConfig(e){this.config=M({...this.config,...e})}updateThemeMode(e){this.config=M({...this.config,themeMode:e}),S(this.canvas.container,this.config,this.rulers,e)}toggleThemeMode(){const e="light"===this.config.themeMode?"dark":"light";return this.updateThemeMode(e),e}updateTransition(e){this.config=M({...this.config,enableTransition:e})}toggleTransitionMode(){const e=function(e){return!e}(this.config.enableTransition);return this.updateTransition(e),e}cleanup(){!function(e){if("undefined"==typeof window)return;const t=e.name||"markupCanvas",n=window;delete n[t],n.__markupCanvasInstances&&n.__markupCanvasInstances.delete(t)}(this.config),this.cleanupCallbacks.forEach(e=>{try{e()}catch(e){console.warn("Error during cleanup:",e)}}),this.cleanupCallbacks=[],this.removeAllListeners()}on(e,t){this.event.on(e,t)}off(e,t){this.event.off(e,t)}emit(e,t){this.event.emit(e,t)}removeAllListeners(){this.event.removeAllListeners()}destroy(){this.cleanup(),window.__markupCanvasTransitionTimeout&&clearTimeout(window.__markupCanvasTransitionTimeout)}}});
@@ -2,6 +2,11 @@ export interface MarkupCanvasConfig {
2
2
  width?: number;
3
3
  height?: number;
4
4
  enableAcceleration?: boolean;
5
+ initialZoom?: number;
6
+ initialPan?: {
7
+ x: number;
8
+ y: number;
9
+ };
5
10
  name?: string;
6
11
  enablePostMessageAPI?: boolean;
7
12
  enableZoom?: boolean;
@@ -33,7 +33,7 @@ export interface MouseDragControls {
33
33
  disable: () => boolean;
34
34
  isEnabled: () => boolean;
35
35
  }
36
- export type PostMessageAction = "zoomIn" | "zoomOut" | "setZoom" | "resetZoom" | "panLeft" | "panRight" | "panUp" | "panDown" | "fitToScreen" | "centerContent" | "scrollToPoint" | "resetView" | "resetViewToCenter" | "toggleRulers" | "showRulers" | "hideRulers" | "toggleGrid" | "showGrid" | "hideGrid" | "updateThemeMode" | "toggleThemeMode" | "updateTransition" | "toggleTransitionMode";
36
+ export type PostMessageAction = "zoomIn" | "zoomOut" | "setZoom" | "resetZoom" | "panLeft" | "panRight" | "panUp" | "panDown" | "fitToScreen" | "centerContent" | "panToPoint" | "resetView" | "resetViewToCenter" | "toggleRulers" | "showRulers" | "hideRulers" | "toggleGrid" | "showGrid" | "hideGrid" | "updateThemeMode" | "toggleThemeMode" | "updateTransition" | "toggleTransitionMode";
37
37
  export interface PostMessageRequest {
38
38
  source: "markup-canvas";
39
39
  canvasName: string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@markup-canvas/core",
3
- "version": "1.2.6",
3
+ "version": "1.2.8",
4
4
  "description": "High-performance canvas-like container with pan and zoom capabilities",
5
5
  "type": "module",
6
6
  "main": "dist/markup-canvas.cjs.js",
@@ -1,4 +1,4 @@
1
- import { centerContent, panDown, panLeft, panRight, panUp, scrollToPoint } from "@/lib/actions/pan/index.js";
1
+ import { centerContent, panDown, panLeft, panRight, panToPoint, panUp } from "@/lib/actions/pan/index.js";
2
2
  import { resetTransform, updateTransform } from "@/lib/actions/transform/index.js";
3
3
  import { hideGrid, isGridVisible, showGrid, toggleGrid, toggleTransition, updateThemeMode } from "@/lib/actions/ui/index.js";
4
4
  import { areRulersVisible, hideRulers, showRulers, toggleRulers } from "@/lib/actions/ui/rulers/index.js";
@@ -78,6 +78,13 @@ export class MarkupCanvas {
78
78
 
79
79
  this._isReady = true;
80
80
 
81
+ if (options.initialZoom !== undefined) {
82
+ this.setZoom(options.initialZoom);
83
+ }
84
+ if (options.initialPan !== undefined) {
85
+ this.panToPoint(options.initialPan.x, options.initialPan.y);
86
+ }
87
+
81
88
  // Emit ready event
82
89
  this.event.emit("ready", this);
83
90
  }
@@ -312,8 +319,8 @@ export class MarkupCanvas {
312
319
  return isPointVisible(this, x, y);
313
320
  }
314
321
 
315
- scrollToPoint(x: number, y: number): boolean {
316
- return scrollToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
322
+ panToPoint(x: number, y: number): boolean {
323
+ return panToPoint(this.canvas, this.config, x, y, this.updateTransform.bind(this), this.transformLayer);
317
324
  }
318
325
 
319
326
  // Configuration access
@@ -2,5 +2,5 @@ export { centerContent } from "./centerContent.js";
2
2
  export { panDown } from "./panDown.js";
3
3
  export { panLeft } from "./panLeft.js";
4
4
  export { panRight } from "./panRight.js";
5
+ export { panToPoint } from "./panToPoint.js";
5
6
  export { panUp } from "./panUp.js";
6
- export { scrollToPoint } from "./scrollToPoint.js";
@@ -2,7 +2,7 @@ import { getCanvasBounds } from "@/lib/canvas/getCanvasBounds.js";
2
2
  import { withTransition } from "@/lib/transition/withTransition.js";
3
3
  import type { Canvas, MarkupCanvasConfig, Transform } from "@/types/index.js";
4
4
 
5
- export function scrollToPoint(
5
+ export function panToPoint(
6
6
  canvas: Canvas,
7
7
  config: Required<MarkupCanvasConfig>,
8
8
  x: number,
@@ -6,6 +6,10 @@ export const DEFAULT_CONFIG: Required<MarkupCanvasConfig> = {
6
6
  height: 8000,
7
7
  enableAcceleration: true,
8
8
 
9
+ // Initial view transform
10
+ initialZoom: 1,
11
+ initialPan: { x: 0, y: 0 },
12
+
9
13
  // Global Instance Access
10
14
  name: "markupCanvas",
11
15
  enablePostMessageAPI: false,
@@ -1,6 +1,6 @@
1
1
  import type { MarkupCanvasConfig } from "@/types";
2
2
 
3
- export const EDITOR_PRESET: Required<MarkupCanvasConfig> = {
3
+ export const EDITOR_PRESET: MarkupCanvasConfig = {
4
4
  // Canvas dimensions
5
5
  width: 4000,
6
6
  height: 4000,
@@ -45,8 +45,8 @@ export function setupPostMessageEvents(canvas: MarkupCanvas): () => void {
45
45
  canvas.fitToScreen();
46
46
  } else if (action === "centerContent") {
47
47
  canvas.centerContent();
48
- } else if (action === "scrollToPoint") {
49
- canvas.scrollToPoint(args[0] as number, args[1] as number);
48
+ } else if (action === "panToPoint") {
49
+ canvas.panToPoint(args[0] as number, args[1] as number);
50
50
  } else if (action === "resetView") {
51
51
  canvas.resetView();
52
52
  } else if (action === "resetViewToCenter") {
@@ -43,7 +43,7 @@ export function bindCanvasToWindow(canvas: MarkupCanvas, config: Required<Markup
43
43
  right: canvas.panRight.bind(canvas),
44
44
  up: canvas.panUp.bind(canvas),
45
45
  down: canvas.panDown.bind(canvas),
46
- toPoint: canvas.scrollToPoint.bind(canvas),
46
+ toPoint: canvas.panToPoint.bind(canvas),
47
47
  toCenter: canvas.centerContent.bind(canvas),
48
48
  },
49
49
 
@@ -4,6 +4,10 @@ export interface MarkupCanvasConfig {
4
4
  height?: number;
5
5
  enableAcceleration?: boolean;
6
6
 
7
+ // Initial view transform
8
+ initialZoom?: number;
9
+ initialPan?: { x: number; y: number };
10
+
7
11
  // Global Instance Access
8
12
  name?: string;
9
13
 
@@ -43,7 +43,7 @@ export type PostMessageAction =
43
43
  | "panDown"
44
44
  | "fitToScreen"
45
45
  | "centerContent"
46
- | "scrollToPoint"
46
+ | "panToPoint"
47
47
  | "resetView"
48
48
  | "resetViewToCenter"
49
49
  | "toggleRulers"
@@ -1,2 +0,0 @@
1
- import type { Canvas, MarkupCanvasConfig, Transform } from "@/types/index.js";
2
- export declare function scrollToPoint(canvas: Canvas, config: Required<MarkupCanvasConfig>, x: number, y: number, updateTransform: (newTransform: Partial<Transform>) => boolean, transformLayer: HTMLElement): boolean;