kritzel-stencil 0.0.159 → 0.0.161

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.
Files changed (171) hide show
  1. package/dist/cjs/{default-text-tool.config-BySzvIox.js → default-text-tool.config-zB3FPuXq.js} +270 -58
  2. package/dist/cjs/default-text-tool.config-zB3FPuXq.js.map +1 -0
  3. package/dist/cjs/index.cjs.js +2 -1
  4. package/dist/cjs/index.cjs.js.map +1 -1
  5. package/dist/cjs/kritzel-brush-style.cjs.entry.js +1 -1
  6. package/dist/cjs/kritzel-brush-style.entry.cjs.js.map +1 -1
  7. package/dist/cjs/kritzel-color_22.cjs.entry.js +108 -101
  8. package/dist/cjs/loader.cjs.js +1 -1
  9. package/dist/cjs/stencil.cjs.js +1 -1
  10. package/dist/collection/classes/core/store.class.js +3 -0
  11. package/dist/collection/classes/core/store.class.js.map +1 -1
  12. package/dist/collection/classes/handlers/resize.handler.js +54 -32
  13. package/dist/collection/classes/handlers/resize.handler.js.map +1 -1
  14. package/dist/collection/classes/handlers/rotation.handler.js +12 -8
  15. package/dist/collection/classes/handlers/rotation.handler.js.map +1 -1
  16. package/dist/collection/classes/objects/selection-group.class.js +91 -16
  17. package/dist/collection/classes/objects/selection-group.class.js.map +1 -1
  18. package/dist/collection/classes/registries/icon-registry.class.js +6 -1
  19. package/dist/collection/classes/registries/icon-registry.class.js.map +1 -1
  20. package/dist/collection/components/core/kritzel-cursor-trail/kritzel-cursor-trail.js +1 -1
  21. package/dist/collection/components/core/kritzel-editor/kritzel-editor.js +1 -1
  22. package/dist/collection/components/core/kritzel-engine/kritzel-engine.css +0 -14
  23. package/dist/collection/components/core/kritzel-engine/kritzel-engine.js +80 -10
  24. package/dist/collection/components/core/kritzel-engine/kritzel-engine.js.map +1 -1
  25. package/dist/collection/components/shared/kritzel-brush-style/kritzel-brush-style.css +0 -1
  26. package/dist/collection/components/shared/kritzel-color/kritzel-color.js +2 -2
  27. package/dist/collection/components/shared/kritzel-color-palette/kritzel-color-palette.css +1 -1
  28. package/dist/collection/components/shared/kritzel-color-palette/kritzel-color-palette.js +1 -1
  29. package/dist/collection/components/shared/kritzel-dropdown/kritzel-dropdown.css +1 -1
  30. package/dist/collection/components/shared/kritzel-font/kritzel-font.js +1 -1
  31. package/dist/collection/components/shared/kritzel-font-family/kritzel-font-family.css +1 -1
  32. package/dist/collection/components/shared/kritzel-font-family/kritzel-font-family.js +1 -1
  33. package/dist/collection/components/shared/kritzel-font-size/kritzel-font-size.css +1 -1
  34. package/dist/collection/components/shared/kritzel-font-size/kritzel-font-size.js +1 -1
  35. package/dist/collection/components/shared/kritzel-menu/kritzel-menu.js +1 -1
  36. package/dist/collection/components/shared/kritzel-menu-item/kritzel-menu-item.css +1 -2
  37. package/dist/collection/components/shared/kritzel-menu-item/kritzel-menu-item.js +2 -2
  38. package/dist/collection/components/shared/kritzel-portal/kritzel-portal.js +1 -1
  39. package/dist/collection/components/shared/kritzel-split-button/kritzel-split-button.css +1 -1
  40. package/dist/collection/components/shared/kritzel-split-button/kritzel-split-button.js +1 -1
  41. package/dist/collection/components/shared/kritzel-stroke-size/kritzel-stroke-size.css +1 -1
  42. package/dist/collection/components/shared/kritzel-stroke-size/kritzel-stroke-size.js +1 -1
  43. package/dist/collection/components/shared/kritzel-tooltip/kritzel-tooltip.js +4 -4
  44. package/dist/collection/components/ui/kritzel-context-menu/kritzel-context-menu.css +1 -2
  45. package/dist/collection/components/ui/kritzel-context-menu/kritzel-context-menu.js +1 -1
  46. package/dist/collection/components/ui/kritzel-control-brush-config/kritzel-control-brush-config.css +1 -1
  47. package/dist/collection/components/ui/kritzel-control-brush-config/kritzel-control-brush-config.js +2 -2
  48. package/dist/collection/components/ui/kritzel-control-text-config/kritzel-control-text-config.css +1 -1
  49. package/dist/collection/components/ui/kritzel-control-text-config/kritzel-control-text-config.js +2 -2
  50. package/dist/collection/components/ui/kritzel-controls/kritzel-controls.css +4 -4
  51. package/dist/collection/components/ui/kritzel-controls/kritzel-controls.js +3 -3
  52. package/dist/collection/components/ui/kritzel-utility-panel/kritzel-utility-panel.css +1 -1
  53. package/dist/collection/components/ui/kritzel-utility-panel/kritzel-utility-panel.js +1 -1
  54. package/dist/collection/configs/default-engine-config.js +6 -0
  55. package/dist/collection/configs/default-engine-config.js.map +1 -1
  56. package/dist/collection/helpers/cursor.helper.js +58 -0
  57. package/dist/collection/helpers/cursor.helper.js.map +1 -0
  58. package/dist/collection/index.js +1 -0
  59. package/dist/collection/index.js.map +1 -1
  60. package/dist/collection/interfaces/engine-state.interface.js.map +1 -1
  61. package/dist/components/index.js +2 -2
  62. package/dist/components/kritzel-brush-style.js +3 -3
  63. package/dist/components/kritzel-brush-style.js.map +1 -1
  64. package/dist/components/kritzel-color-palette.js +1 -1
  65. package/dist/components/kritzel-color.js +1 -1
  66. package/dist/components/kritzel-context-menu.js +1 -1
  67. package/dist/components/kritzel-control-brush-config.js +1 -1
  68. package/dist/components/kritzel-control-text-config.js +1 -1
  69. package/dist/components/kritzel-controls.js +1 -1
  70. package/dist/components/kritzel-cursor-trail.js +1 -1
  71. package/dist/components/kritzel-dropdown.js +1 -1
  72. package/dist/components/kritzel-editor.js +21 -21
  73. package/dist/components/kritzel-engine.js +1 -1
  74. package/dist/components/kritzel-font-family.js +1 -1
  75. package/dist/components/kritzel-font-size.js +1 -1
  76. package/dist/components/kritzel-font.js +1 -1
  77. package/dist/components/kritzel-icon.js +1 -1
  78. package/dist/components/kritzel-menu-item.js +1 -1
  79. package/dist/components/kritzel-menu.js +1 -1
  80. package/dist/components/kritzel-portal.js +1 -1
  81. package/dist/components/kritzel-split-button.js +1 -1
  82. package/dist/components/kritzel-stroke-size.js +1 -1
  83. package/dist/components/kritzel-tooltip.js +1 -1
  84. package/dist/components/kritzel-utility-panel.js +1 -1
  85. package/dist/components/kritzel-workspace-manager.js +1 -1
  86. package/dist/components/{p-CK6no3mi.js → p-58y59Acb.js} +6 -6
  87. package/dist/components/{p-CK6no3mi.js.map → p-58y59Acb.js.map} +1 -1
  88. package/dist/components/{p-CTP479Lf.js → p-9Fzdviju.js} +6 -6
  89. package/dist/components/{p-CTP479Lf.js.map → p-9Fzdviju.js.map} +1 -1
  90. package/dist/components/{p-DDmSxM5f.js → p-B6r22FSC.js} +5 -5
  91. package/dist/components/p-B6r22FSC.js.map +1 -0
  92. package/dist/components/{p-CLt3HMl6.js → p-B_3OZeom.js} +3 -3
  93. package/dist/components/{p-CLt3HMl6.js.map → p-B_3OZeom.js.map} +1 -1
  94. package/dist/components/{p-TdCTkEu0.js → p-BdZKPKnx.js} +7 -7
  95. package/dist/components/p-BdZKPKnx.js.map +1 -0
  96. package/dist/components/{p-CIXPLjCu.js → p-BdwB-S9G.js} +3 -3
  97. package/dist/components/p-BdwB-S9G.js.map +1 -0
  98. package/dist/components/{p-1lIHoOlH.js → p-BpXgwgnV.js} +18 -18
  99. package/dist/components/p-BpXgwgnV.js.map +1 -0
  100. package/dist/components/{p-D1uj4A4F.js → p-Brd9SxWS.js} +5 -5
  101. package/dist/components/p-Brd9SxWS.js.map +1 -0
  102. package/dist/components/{p-CsA9M6me.js → p-CC8KFHSe.js} +8 -8
  103. package/dist/components/p-CC8KFHSe.js.map +1 -0
  104. package/dist/components/{p-BgznZoBH.js → p-CFH6XRL5.js} +5 -5
  105. package/dist/components/p-CFH6XRL5.js.map +1 -0
  106. package/dist/components/{p-B4kxkVe-.js → p-CRGwaUcp.js} +5 -5
  107. package/dist/components/p-CRGwaUcp.js.map +1 -0
  108. package/dist/components/{p-uuRJU2R1.js → p-Ck4lGnmt.js} +3 -3
  109. package/dist/components/{p-uuRJU2R1.js.map → p-Ck4lGnmt.js.map} +1 -1
  110. package/dist/components/{p-BAplhrRJ.js → p-D7BLVRXX.js} +289 -75
  111. package/dist/components/p-D7BLVRXX.js.map +1 -0
  112. package/dist/components/{p-C2sWlNsJ.js → p-D_ygcWSz.js} +5 -5
  113. package/dist/components/p-D_ygcWSz.js.map +1 -0
  114. package/dist/components/p-DbKKCHKd.js +103 -0
  115. package/dist/components/p-DbKKCHKd.js.map +1 -0
  116. package/dist/components/{p-Ddh40W3x.js → p-Doixm8-N.js} +9 -9
  117. package/dist/components/p-Doixm8-N.js.map +1 -0
  118. package/dist/components/{p-BQg4YML7.js → p-DxNbcUzt.js} +12 -12
  119. package/dist/components/p-DxNbcUzt.js.map +1 -0
  120. package/dist/components/{p-D4yvhd1d.js → p-LAsVgL2e.js} +4 -4
  121. package/dist/components/{p-D4yvhd1d.js.map → p-LAsVgL2e.js.map} +1 -1
  122. package/dist/components/{p-D5Wq4x4r.js → p-OFrACpZf.js} +3 -3
  123. package/dist/components/{p-D5Wq4x4r.js.map → p-OFrACpZf.js.map} +1 -1
  124. package/dist/components/{p-DAfkuR8U.js → p-i0IlGLv2.js} +5 -5
  125. package/dist/components/p-i0IlGLv2.js.map +1 -0
  126. package/dist/esm/{default-text-tool.config-2YFQA3SF.js → default-text-tool.config-BvCgOiKA.js} +269 -59
  127. package/dist/esm/default-text-tool.config-BvCgOiKA.js.map +1 -0
  128. package/dist/esm/index.js +2 -2
  129. package/dist/esm/kritzel-brush-style.entry.js +1 -1
  130. package/dist/esm/kritzel-brush-style.entry.js.map +1 -1
  131. package/dist/esm/kritzel-color_22.entry.js +106 -99
  132. package/dist/esm/loader.js +1 -1
  133. package/dist/esm/stencil.js +1 -1
  134. package/dist/stencil/index.esm.js +1 -1
  135. package/dist/stencil/kritzel-brush-style.entry.esm.js.map +1 -1
  136. package/dist/stencil/p-385bab97.entry.js +2 -0
  137. package/dist/stencil/{p-d702c5af.entry.js.map → p-385bab97.entry.js.map} +1 -1
  138. package/dist/stencil/p-6d9756d9.entry.js +10 -0
  139. package/dist/stencil/p-6d9756d9.entry.js.map +1 -0
  140. package/dist/stencil/{p-2YFQA3SF.js → p-BvCgOiKA.js} +2 -2
  141. package/dist/stencil/p-BvCgOiKA.js.map +1 -0
  142. package/dist/stencil/stencil.esm.js +1 -1
  143. package/dist/types/classes/core/store.class.d.ts +1 -0
  144. package/dist/types/classes/objects/selection-group.class.d.ts +1 -0
  145. package/dist/types/components/core/kritzel-engine/kritzel-engine.d.ts +4 -0
  146. package/dist/types/components.d.ts +2 -0
  147. package/dist/types/helpers/cursor.helper.d.ts +22 -0
  148. package/dist/types/index.d.ts +1 -0
  149. package/dist/types/interfaces/engine-state.interface.d.ts +7 -0
  150. package/package.json +1 -1
  151. package/dist/cjs/default-text-tool.config-BySzvIox.js.map +0 -1
  152. package/dist/components/p-1lIHoOlH.js.map +0 -1
  153. package/dist/components/p-B4kxkVe-.js.map +0 -1
  154. package/dist/components/p-BAplhrRJ.js.map +0 -1
  155. package/dist/components/p-BQg4YML7.js.map +0 -1
  156. package/dist/components/p-BgznZoBH.js.map +0 -1
  157. package/dist/components/p-Bhtn9qay.js +0 -98
  158. package/dist/components/p-Bhtn9qay.js.map +0 -1
  159. package/dist/components/p-C2sWlNsJ.js.map +0 -1
  160. package/dist/components/p-CIXPLjCu.js.map +0 -1
  161. package/dist/components/p-CsA9M6me.js.map +0 -1
  162. package/dist/components/p-D1uj4A4F.js.map +0 -1
  163. package/dist/components/p-DAfkuR8U.js.map +0 -1
  164. package/dist/components/p-DDmSxM5f.js.map +0 -1
  165. package/dist/components/p-Ddh40W3x.js.map +0 -1
  166. package/dist/components/p-TdCTkEu0.js.map +0 -1
  167. package/dist/esm/default-text-tool.config-2YFQA3SF.js.map +0 -1
  168. package/dist/stencil/p-2YFQA3SF.js.map +0 -1
  169. package/dist/stencil/p-2e85a4af.entry.js +0 -10
  170. package/dist/stencil/p-2e85a4af.entry.js.map +0 -1
  171. package/dist/stencil/p-d702c5af.entry.js +0 -2
@@ -1,12 +1,12 @@
1
1
  import { p as proxyCustomElement, H, c as createEvent, h, d as Host } from './p-CwkUrTy1.js';
2
2
  import { K as KritzelMouseButton } from './p-D8W6LE-c.js';
3
3
  import { e as KritzelBaseObject, f as KritzelBaseTool, g as KritzelEventHelper, h as KritzelToolRegistry, c as KritzelTextTool, b as KritzelBrushTool, K as KritzelText, a as KritzelPath, d as KritzelKeyboardHelper } from './p-CBYBurdY.js';
4
- import { K as KritzelContextMenu, d as defineCustomElement$3 } from './p-C2sWlNsJ.js';
4
+ import { K as KritzelContextMenu, d as defineCustomElement$3 } from './p-D_ygcWSz.js';
5
5
  import { O as ObjectHelper } from './p-B0kd2rUI.js';
6
+ import { K as KritzelIconRegistry, d as defineCustomElement$1 } from './p-DbKKCHKd.js';
6
7
  import { K as KritzelWorkspace } from './p-n789Y3S-.js';
7
8
  import { K as KritzelDevicesHelper } from './p-l10It7Nm.js';
8
- import { d as defineCustomElement$2 } from './p-CLt3HMl6.js';
9
- import { d as defineCustomElement$1 } from './p-Bhtn9qay.js';
9
+ import { d as defineCustomElement$2 } from './p-B_3OZeom.js';
10
10
 
11
11
  var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {};
12
12
 
@@ -236,6 +236,63 @@ class KritzelImageTool extends KritzelBaseTool {
236
236
  }
237
237
  }
238
238
 
239
+ class KritzelCursorHelper {
240
+ static _pointerCursor = null;
241
+ /**
242
+ * Returns the custom pointer cursor CSS value.
243
+ * This can be used instead of `cursor: pointer` for consistent styling.
244
+ */
245
+ static getPointerCursor() {
246
+ if (!this._pointerCursor) {
247
+ this._pointerCursor = this.getCursor({ iconName: 'pointer' });
248
+ }
249
+ return this._pointerCursor;
250
+ }
251
+ /**
252
+ * Returns a custom cursor CSS value with support for rotation.
253
+ * The icon is retrieved from the KritzelIconRegistry.
254
+ */
255
+ static getCursor(options) {
256
+ const iconName = options.iconName === 'default' ? 'mouse-pointer' : options.iconName;
257
+ const iconSvg = KritzelIconRegistry.get(iconName);
258
+ if (!iconSvg) {
259
+ console.warn(`Icon "${iconName}" not found in registry.`);
260
+ return 'auto';
261
+ }
262
+ const size = options.size || 24;
263
+ const rotation = options.rotation || 0;
264
+ const color = options.color || 'black';
265
+ // Default cursor (mouse-pointer) has hotspot at (4, 4), others at center
266
+ const hotspot = options.hotspot || (options.iconName === 'default' ? { x: 4, y: 4 } : { x: size / 2, y: size / 2 });
267
+ // Modify the SVG string to set size and color
268
+ // We replace width and height to match the requested size
269
+ // We replace currentColor with the requested color
270
+ let content = iconSvg
271
+ .replace(/width="\d+"/, `width="${size}"`)
272
+ .replace(/height="\d+"/, `height="${size}"`)
273
+ .replace(/currentColor/g, color);
274
+ // Create the SVG string
275
+ // We rotate around the center of the SVG canvas
276
+ const center = size / 2;
277
+ // We use a group to apply the rotation
278
+ const svg = `
279
+ <svg xmlns="http://www.w3.org/2000/svg" width="${size}" height="${size}" viewBox="0 0 ${size} ${size}">
280
+ <g transform="rotate(${rotation} ${center} ${center})">
281
+ ${content}
282
+ </g>
283
+ </svg>
284
+ `;
285
+ // Encode the SVG for use in a data URI
286
+ // We need to be careful with encoding to ensure it works across browsers
287
+ const encodedSvg = encodeURIComponent(svg.replace(/\s+/g, ' ').trim())
288
+ .replace(/'/g, '%27')
289
+ .replace(/"/g, '%22');
290
+ const dataUri = `data:image/svg+xml;charset=utf-8,${encodedSvg}`;
291
+ // Return the cursor style string
292
+ return `url('${dataUri}') ${hotspot.x} ${hotspot.y}, auto`;
293
+ }
294
+ }
295
+
239
296
  class KritzelBaseHandler {
240
297
  _core;
241
298
  constructor(core) {
@@ -471,32 +528,43 @@ class KritzelResizeHandler extends KritzelBaseHandler {
471
528
  if (!this.hasResized) {
472
529
  return;
473
530
  }
531
+ const rotation = selectionGroup.rotation;
532
+ const sin = Math.sin(rotation);
533
+ const cos = Math.cos(rotation);
534
+ const objectScale = selectionGroup.scale || 1;
535
+ const currentScale = this._core.store.state.scale;
536
+ // Calculate delta in local unrotated space
537
+ // We rotate the screen delta by -rotation to align with the object's axes
538
+ const localDx = (dx * cos + dy * sin) / currentScale;
539
+ const localDy = (-dx * sin + dy * cos) / currentScale;
540
+ // Calculate the center of the selection group before resize
541
+ const initialCenterX = this.initialSize.x + this.initialSize.width / objectScale / 2;
542
+ const initialCenterY = this.initialSize.y + this.initialSize.height / objectScale / 2;
543
+ // The center moves by half of the screen delta (scaled)
544
+ // This is true regardless of rotation because the resize happens symmetrically around the center
545
+ // relative to the fixed point logic
546
+ const newCenterX = initialCenterX + dx / currentScale / 2;
547
+ const newCenterY = initialCenterY + dy / currentScale / 2;
474
548
  switch (this._core.store.state.resizeHandleType) {
475
549
  case KritzelHandleType.TopLeft:
476
- this.newSize.width = this.initialSize.width - dx;
477
- this.newSize.height = this.initialSize.height - dy;
478
- this.newSize.x = dx / this._core.store.state.scale + this.initialSize.x;
479
- this.newSize.y = dy / this._core.store.state.scale + this.initialSize.y;
550
+ this.newSize.width = this.initialSize.width - localDx * objectScale;
551
+ this.newSize.height = this.initialSize.height - localDy * objectScale;
480
552
  break;
481
553
  case KritzelHandleType.TopRight:
482
- this.newSize.width = this.initialSize.width + dx;
483
- this.newSize.height = this.initialSize.height - dy;
484
- this.newSize.x = this.initialSize.x;
485
- this.newSize.y = dy / this._core.store.state.scale + this.initialSize.y;
554
+ this.newSize.width = this.initialSize.width + localDx * objectScale;
555
+ this.newSize.height = this.initialSize.height - localDy * objectScale;
486
556
  break;
487
557
  case KritzelHandleType.BottomLeft:
488
- this.newSize.width = this.initialSize.width - dx;
489
- this.newSize.height = this.initialSize.height + dy;
490
- this.newSize.x = dx / this._core.store.state.scale + this.initialSize.x;
491
- this.newSize.y = this.initialSize.y;
558
+ this.newSize.width = this.initialSize.width - localDx * objectScale;
559
+ this.newSize.height = this.initialSize.height + localDy * objectScale;
492
560
  break;
493
561
  case KritzelHandleType.BottomRight:
494
- this.newSize.width = this.initialSize.width + dx;
495
- this.newSize.height = this.initialSize.height + dy;
496
- this.newSize.x = this.initialSize.x;
497
- this.newSize.y = this.initialSize.y;
562
+ this.newSize.width = this.initialSize.width + localDx * objectScale;
563
+ this.newSize.height = this.initialSize.height + localDy * objectScale;
498
564
  break;
499
565
  }
566
+ this.newSize.x = newCenterX - this.newSize.width / objectScale / 2;
567
+ this.newSize.y = newCenterY - this.newSize.height / objectScale / 2;
500
568
  selectionGroup.resize(this.newSize.x, this.newSize.y, this.newSize.width, this.newSize.height);
501
569
  }
502
570
  }
@@ -522,32 +590,43 @@ class KritzelResizeHandler extends KritzelBaseHandler {
522
590
  if (!this.hasResized) {
523
591
  return;
524
592
  }
593
+ const rotation = selectionGroup.rotation;
594
+ const sin = Math.sin(rotation);
595
+ const cos = Math.cos(rotation);
596
+ const objectScale = selectionGroup.scale || 1;
597
+ const currentScale = this._core.store.state.scale;
598
+ // Calculate delta in local unrotated space
599
+ // We rotate the screen delta by -rotation to align with the object's axes
600
+ const localDx = (dx * cos + dy * sin) / currentScale;
601
+ const localDy = (-dx * sin + dy * cos) / currentScale;
602
+ // Calculate the center of the selection group before resize
603
+ const initialCenterX = this.initialSize.x + this.initialSize.width / objectScale / 2;
604
+ const initialCenterY = this.initialSize.y + this.initialSize.height / objectScale / 2;
605
+ // The center moves by half of the screen delta (scaled)
606
+ // This is true regardless of rotation because the resize happens symmetrically around the center
607
+ // relative to the fixed point logic
608
+ const newCenterX = initialCenterX + dx / currentScale / 2;
609
+ const newCenterY = initialCenterY + dy / currentScale / 2;
525
610
  switch (this._core.store.state.resizeHandleType) {
526
611
  case KritzelHandleType.TopLeft:
527
- this.newSize.width = this.initialSize.width - dx;
528
- this.newSize.height = this.initialSize.height - dy;
529
- this.newSize.x = dx / this._core.store.state.scale + this.initialSize.x;
530
- this.newSize.y = dy / this._core.store.state.scale + this.initialSize.y;
612
+ this.newSize.width = this.initialSize.width - localDx * objectScale;
613
+ this.newSize.height = this.initialSize.height - localDy * objectScale;
531
614
  break;
532
615
  case KritzelHandleType.TopRight:
533
- this.newSize.width = this.initialSize.width + dx;
534
- this.newSize.height = this.initialSize.height - dy;
535
- this.newSize.x = this.initialSize.x;
536
- this.newSize.y = dy / this._core.store.state.scale + this.initialSize.y;
616
+ this.newSize.width = this.initialSize.width + localDx * objectScale;
617
+ this.newSize.height = this.initialSize.height - localDy * objectScale;
537
618
  break;
538
619
  case KritzelHandleType.BottomLeft:
539
- this.newSize.width = this.initialSize.width - dx;
540
- this.newSize.height = this.initialSize.height + dy;
541
- this.newSize.x = dx / this._core.store.state.scale + this.initialSize.x;
542
- this.newSize.y = this.initialSize.y;
620
+ this.newSize.width = this.initialSize.width - localDx * objectScale;
621
+ this.newSize.height = this.initialSize.height + localDy * objectScale;
543
622
  break;
544
623
  case KritzelHandleType.BottomRight:
545
- this.newSize.width = this.initialSize.width + dx;
546
- this.newSize.height = this.initialSize.height + dy;
547
- this.newSize.x = this.initialSize.x;
548
- this.newSize.y = this.initialSize.y;
624
+ this.newSize.width = this.initialSize.width + localDx * objectScale;
625
+ this.newSize.height = this.initialSize.height + localDy * objectScale;
549
626
  break;
550
627
  }
628
+ this.newSize.x = newCenterX - this.newSize.width / objectScale / 2;
629
+ this.newSize.y = newCenterY - this.newSize.height / objectScale / 2;
551
630
  selectionGroup.resize(this.newSize.x, this.newSize.y, this.newSize.width, this.newSize.height);
552
631
  }
553
632
  }
@@ -600,8 +679,9 @@ class KritzelRotationHandler extends KritzelBaseHandler {
600
679
  const clientX = event.clientX - this._core.store.offsetX;
601
680
  const clientY = event.clientY - this._core.store.offsetY;
602
681
  this._core.store.state.isRotating = true;
603
- const centerX = selectionGroup.translateX + selectionGroup.width / 2 / this._core.store.state.scale;
604
- const centerY = selectionGroup.translateY + selectionGroup.height / 2 / this._core.store.state.scale;
682
+ const objectScale = selectionGroup.scale || 1;
683
+ const centerX = selectionGroup.translateX + selectionGroup.width / 2 / objectScale;
684
+ const centerY = selectionGroup.translateY + selectionGroup.height / 2 / objectScale;
605
685
  const cursorX = (clientX - this._core.store.state.translateX) / this._core.store.state.scale;
606
686
  const cursorY = (clientY - this._core.store.state.translateY) / this._core.store.state.scale;
607
687
  this.initialSelectionGroupRotation = selectionGroup.rotation;
@@ -622,8 +702,9 @@ class KritzelRotationHandler extends KritzelBaseHandler {
622
702
  const clientX = Math.round(firstTouch.clientX - this._core.store.offsetX);
623
703
  const clientY = Math.round(firstTouch.clientY - this._core.store.offsetY);
624
704
  this._core.store.state.isRotating = true;
625
- const centerX = selectionGroup.translateX + selectionGroup.width / 2 / this._core.store.state.scale;
626
- const centerY = selectionGroup.translateY + selectionGroup.height / 2 / this._core.store.state.scale;
705
+ const objectScale = selectionGroup.scale || 1;
706
+ const centerX = selectionGroup.translateX + selectionGroup.width / 2 / objectScale;
707
+ const centerY = selectionGroup.translateY + selectionGroup.height / 2 / objectScale;
627
708
  const cursorX = (clientX - this._core.store.state.translateX) / this._core.store.state.scale;
628
709
  const cursorY = (clientY - this._core.store.state.translateY) / this._core.store.state.scale;
629
710
  this.initialSelectionGroupRotation = selectionGroup.rotation;
@@ -640,8 +721,9 @@ class KritzelRotationHandler extends KritzelBaseHandler {
640
721
  if (this._core.store.state.isRotating && selectionGroup) {
641
722
  const clientX = event.clientX - this._core.store.offsetX;
642
723
  const clientY = event.clientY - this._core.store.offsetY;
643
- const groupCenterX = selectionGroup.translateX + selectionGroup.width / 2 / this._core.store.state.scale;
644
- const groupCenterY = selectionGroup.translateY + selectionGroup.height / 2 / this._core.store.state.scale;
724
+ const objectScale = selectionGroup.scale || 1;
725
+ const groupCenterX = selectionGroup.translateX + selectionGroup.width / 2 / objectScale;
726
+ const groupCenterY = selectionGroup.translateY + selectionGroup.height / 2 / objectScale;
645
727
  const cursorX = (clientX - this._core.store.state.translateX) / this._core.store.state.scale;
646
728
  const cursorY = (clientY - this._core.store.state.translateY) / this._core.store.state.scale;
647
729
  const currentRotation = Math.atan2(groupCenterY - cursorY, groupCenterX - cursorX);
@@ -659,8 +741,9 @@ class KritzelRotationHandler extends KritzelBaseHandler {
659
741
  if (this._core.store.state.isRotating && selectionGroup) {
660
742
  const clientX = Math.round(firstTouch.clientX - this._core.store.offsetX);
661
743
  const clientY = Math.round(firstTouch.clientY - this._core.store.offsetY);
662
- const groupCenterX = selectionGroup.translateX + selectionGroup.width / 2 / this._core.store.state.scale;
663
- const groupCenterY = selectionGroup.translateY + selectionGroup.height / 2 / this._core.store.state.scale;
744
+ const objectScale = selectionGroup.scale || 1;
745
+ const groupCenterX = selectionGroup.translateX + selectionGroup.width / 2 / objectScale;
746
+ const groupCenterY = selectionGroup.translateY + selectionGroup.height / 2 / objectScale;
664
747
  const cursorX = (clientX - this._core.store.state.translateX) / this._core.store.state.scale;
665
748
  const cursorY = (clientY - this._core.store.state.translateY) / this._core.store.state.scale;
666
749
  const currentRotation = Math.atan2(groupCenterY - cursorY, groupCenterX - cursorX);
@@ -717,6 +800,7 @@ class KritzelSelectionGroup extends KritzelBaseObject {
717
800
  objectIds = [];
718
801
  // Store snapshots of object state for transformations (rotation, resize)
719
802
  unchangedObjectSnapshots = new Map();
803
+ snapshotRotation = 0;
720
804
  minX;
721
805
  maxX;
722
806
  minY;
@@ -787,6 +871,7 @@ class KritzelSelectionGroup extends KritzelBaseObject {
787
871
  */
788
872
  captureUnchangedSnapshots() {
789
873
  this.unchangedObjectSnapshots.clear();
874
+ this.snapshotRotation = this.rotation;
790
875
  this.objects.forEach(obj => {
791
876
  this.unchangedObjectSnapshots.set(obj.id, {
792
877
  id: obj.id,
@@ -846,14 +931,56 @@ class KritzelSelectionGroup extends KritzelBaseObject {
846
931
  resize(x, y, width, height) {
847
932
  const widthScaleFactor = width / this.width;
848
933
  const heightScaleFactor = height / this.height;
849
- const deltaX = x - this.translateX;
850
- const deltaY = y - this.translateY;
934
+ // Calculate old center
935
+ const oldCenterX = this.translateX + this.totalWidth / 2 / this.scale;
936
+ const oldCenterY = this.translateY + this.totalHeight / 2 / this.scale;
937
+ // Calculate new center
938
+ const newTotalWidth = width + this.padding * 2;
939
+ const newTotalHeight = height + this.padding * 2;
940
+ const newCenterX = x + newTotalWidth / 2 / this.scale;
941
+ const newCenterY = y + newTotalHeight / 2 / this.scale;
942
+ const rotation = this.rotation;
943
+ const cos = Math.cos(-rotation);
944
+ const sin = Math.sin(-rotation);
945
+ const cosR = Math.cos(rotation);
946
+ const sinR = Math.sin(rotation);
851
947
  this._core.store.state.objects.transaction(() => {
852
948
  this.objects.forEach(child => {
853
- const updatedWidth = child.width * widthScaleFactor;
854
- const updatedHeight = child.height * heightScaleFactor;
855
- const updatedX = child.translateX + deltaX + (child.translateX - this.translateX) * (widthScaleFactor - 1);
856
- const updatedY = child.translateY + deltaY + (child.translateY - this.translateY) * (heightScaleFactor - 1);
949
+ // Calculate child center
950
+ const childCenterX = child.translateX + child.totalWidth / 2 / child.scale;
951
+ const childCenterY = child.translateY + child.totalHeight / 2 / child.scale;
952
+ // Vector from old group center to child center
953
+ const dx = childCenterX - oldCenterX;
954
+ const dy = childCenterY - oldCenterY;
955
+ // Rotate to local space (align with group axes)
956
+ const localX = dx * cos - dy * sin;
957
+ const localY = dx * sin + dy * cos;
958
+ // Scale in local space
959
+ const scaledLocalX = localX * widthScaleFactor;
960
+ const scaledLocalY = localY * heightScaleFactor;
961
+ // Rotate back to world space
962
+ const rotatedX = scaledLocalX * cosR - scaledLocalY * sinR;
963
+ const rotatedY = scaledLocalX * sinR + scaledLocalY * cosR;
964
+ // New child center
965
+ const newChildCenterX = newCenterX + rotatedX;
966
+ const newChildCenterY = newCenterY + rotatedY;
967
+ // New child top-left
968
+ // Calculate relative rotation
969
+ const relativeRotation = child.rotation - rotation;
970
+ const cosRel = Math.cos(relativeRotation);
971
+ const sinRel = Math.sin(relativeRotation);
972
+ // Project the group's scale factors onto the child's local axes
973
+ // We use absolute values because scaling is magnitude-based
974
+ // If the child is aligned (0 deg), cos=1, sin=0 -> scales match
975
+ // If the child is 90 deg, cos=0, sin=1 -> scales swap
976
+ const newChildWidthScale = Math.sqrt(Math.pow(widthScaleFactor * cosRel, 2) + Math.pow(heightScaleFactor * sinRel, 2));
977
+ const newChildHeightScale = Math.sqrt(Math.pow(widthScaleFactor * sinRel, 2) + Math.pow(heightScaleFactor * cosRel, 2));
978
+ const updatedWidth = child.width * newChildWidthScale;
979
+ const updatedHeight = child.height * newChildHeightScale;
980
+ const updatedTotalWidth = updatedWidth + child.padding * 2;
981
+ const updatedTotalHeight = updatedHeight + child.padding * 2;
982
+ const updatedX = newChildCenterX - updatedTotalWidth / 2 / child.scale;
983
+ const updatedY = newChildCenterY - updatedTotalHeight / 2 / child.scale;
857
984
  child.resize(updatedX, updatedY, updatedWidth, updatedHeight);
858
985
  });
859
986
  // Refresh dimensions and update the SelectionGroup to propagate changes to other tabs
@@ -866,7 +993,7 @@ class KritzelSelectionGroup extends KritzelBaseObject {
866
993
  this.rotation = value;
867
994
  const centerX = this.translateX + this.totalWidth / 2 / this.scale;
868
995
  const centerY = this.translateY + this.totalHeight / 2 / this.scale;
869
- const angle = value;
996
+ const angle = value - this.snapshotRotation;
870
997
  const cos = Math.cos(angle);
871
998
  const sin = Math.sin(angle);
872
999
  this._core.store.state.objects.transaction(() => {
@@ -882,7 +1009,7 @@ class KritzelSelectionGroup extends KritzelBaseObject {
882
1009
  const rotatedY = sin * offsetX + cos * offsetY;
883
1010
  child.translateX = centerX + rotatedX - child.totalWidth / 2 / child.scale;
884
1011
  child.translateY = centerY + rotatedY - child.totalHeight / 2 / child.scale;
885
- child.rotate(this.objects.length === 1 ? value : value + unchangedSnapshot.rotation);
1012
+ child.rotate(this.objects.length === 1 ? value : unchangedSnapshot.rotation + angle);
886
1013
  });
887
1014
  });
888
1015
  }
@@ -913,14 +1040,45 @@ class KritzelSelectionGroup extends KritzelBaseObject {
913
1040
  this.height = (this.maxY - this.minY - this.padding) * this.scale;
914
1041
  }
915
1042
  else {
916
- this.minX = Math.min(...this.objects.map(obj => obj.minXRotated));
917
- this.maxX = Math.max(...this.objects.map(obj => obj.maxXRotated));
918
- this.minY = Math.min(...this.objects.map(obj => obj.minYRotated));
919
- this.maxY = Math.max(...this.objects.map(obj => obj.maxYRotated));
920
- this.translateX = this.minX - this.padding;
921
- this.translateY = this.minY - this.padding;
922
- this.width = (this.maxX - this.minX - this.padding) * this.scale;
923
- this.height = (this.maxY - this.minY - this.padding) * this.scale;
1043
+ const rotation = this.rotation;
1044
+ const cos = Math.cos(-rotation);
1045
+ const sin = Math.sin(-rotation);
1046
+ let minX = Infinity;
1047
+ let maxX = -Infinity;
1048
+ let minY = Infinity;
1049
+ let maxY = -Infinity;
1050
+ this.objects.forEach(obj => {
1051
+ const polygon = obj.rotatedPolygon;
1052
+ const corners = [polygon.topLeft, polygon.topRight, polygon.bottomRight, polygon.bottomLeft];
1053
+ corners.forEach(corner => {
1054
+ // Rotate corner into local space (aligned with group rotation)
1055
+ const rx = corner.x * cos - corner.y * sin;
1056
+ const ry = corner.x * sin + corner.y * cos;
1057
+ if (rx < minX)
1058
+ minX = rx;
1059
+ if (rx > maxX)
1060
+ maxX = rx;
1061
+ if (ry < minY)
1062
+ minY = ry;
1063
+ if (ry > maxY)
1064
+ maxY = ry;
1065
+ });
1066
+ });
1067
+ // Dimensions in world units (unrotated)
1068
+ const worldWidth = maxX - minX;
1069
+ const worldHeight = maxY - minY;
1070
+ this.width = (worldWidth - this.padding) * this.scale;
1071
+ this.height = (worldHeight - this.padding) * this.scale;
1072
+ // Center of the box in rotated space
1073
+ const cRx = (minX + maxX) / 2;
1074
+ const cRy = (minY + maxY) / 2;
1075
+ // Rotate center back to world space
1076
+ const cosR = Math.cos(rotation);
1077
+ const sinR = Math.sin(rotation);
1078
+ const cx = cRx * cosR - cRy * sinR;
1079
+ const cy = cRx * sinR + cRy * cosR;
1080
+ this.translateX = cx - (this.width / this.scale + 2 * this.padding) / 2;
1081
+ this.translateY = cy - (this.height / this.scale + 2 * this.padding) / 2;
924
1082
  }
925
1083
  this._core.store.state.objects.update(this);
926
1084
  }
@@ -33890,8 +34048,10 @@ const DEFAULT_ENGINE_CONFIG = {
33890
34048
  isPanning: false,
33891
34049
  isSelecting: false,
33892
34050
  isResizing: false,
34051
+ isResizeHandleHovered: false,
33893
34052
  isResizeHandleSelected: false,
33894
34053
  isRotating: false,
34054
+ isRotationHandleHovered: false,
33895
34055
  isRotationHandleSelected: false,
33896
34056
  isDragging: false,
33897
34057
  isDrawing: false,
@@ -33927,6 +34087,10 @@ const DEFAULT_ENGINE_CONFIG = {
33927
34087
  longTouchDelay: 300,
33928
34088
  pointers: new Map(),
33929
34089
  workspaces: [],
34090
+ cursor: {
34091
+ icon: 'default',
34092
+ iconActive: 'default'
34093
+ }
33930
34094
  };
33931
34095
 
33932
34096
  class KritzelCustomElement extends KritzelBaseObject {
@@ -34521,6 +34685,9 @@ class KritzelStore {
34521
34685
  get isDisabled() {
34522
34686
  return this._state.isEnabled === false || this._state.isReady === false || this._state.activeWorkspace === null;
34523
34687
  }
34688
+ get isPointerDown() {
34689
+ return this._state.pointers.size > 0;
34690
+ }
34524
34691
  constructor(state) {
34525
34692
  this._state = state;
34526
34693
  this._state.objects = new KritzelObjectMap();
@@ -35005,7 +35172,7 @@ class KritzelCore {
35005
35172
  }
35006
35173
  }
35007
35174
 
35008
- const kritzelEngineCss = ":host{display:block;position:relative;height:100%;width:100%;overflow:hidden;background-color:var(--kritzel-engine-background-color, #ffffff)}:host,:host *{touch-action:none;user-select:none}.ProseMirror{outline:none}p,h1,h2,h3,h4,h5,h6,blockquote,pre{margin:0;padding:0}.debug-panel{position:absolute;pointer-events:none;top:0;right:0}.origin{position:relative;top:0;left:0;height:0;width:0;pointer-events:none;-webkit-transform-origin:top left;-moz-transform-origin:top left;transform-origin:top left;overflow:visible}.object{overflow:visible}.resize-handle-overlay.top-left,.resize-handle-overlay.bottom-right{cursor:nwse-resize}.resize-handle-overlay.top-right,.resize-handle-overlay.bottom-left{cursor:nesw-resize}.rotation-handle-overlay{cursor:grab}.PlaygroundEditorTheme__quote{margin:0;margin-left:20px;margin-bottom:10px;font-size:15px;color:rgb(101, 103, 107);border-left-color:rgb(206, 208, 212);border-left-width:4px;border-left-style:solid;padding-left:16px}";
35175
+ const kritzelEngineCss = ":host{display:block;position:relative;height:100%;width:100%;overflow:hidden;background-color:var(--kritzel-engine-background-color, #ffffff)}:host,:host *{touch-action:none;user-select:none}.ProseMirror{outline:none}p,h1,h2,h3,h4,h5,h6,blockquote,pre{margin:0;padding:0}.debug-panel{position:absolute;pointer-events:none;top:0;right:0}.origin{position:relative;top:0;left:0;height:0;width:0;pointer-events:none;-webkit-transform-origin:top left;-moz-transform-origin:top left;transform-origin:top left;overflow:visible}.object{overflow:visible}.PlaygroundEditorTheme__quote{margin:0;margin-left:20px;margin-bottom:10px;font-size:15px;color:rgb(101, 103, 107);border-left-color:rgb(206, 208, 212);border-left-width:4px;border-left-style:solid;padding-left:16px}";
35009
35176
 
35010
35177
  const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine extends H {
35011
35178
  get host() { return this; }
@@ -35044,6 +35211,15 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35044
35211
  this.core.store.state.scaleMin = newValue;
35045
35212
  }
35046
35213
  }
35214
+ cursorTarget;
35215
+ onCursorTargetChange(newValue) {
35216
+ // Reset cursor on old target
35217
+ if (this.cursorTargetElement) {
35218
+ this.cursorTargetElement.style.cursor = '';
35219
+ }
35220
+ // Set new target (defaults to document.body)
35221
+ this.cursorTargetElement = newValue || document.body;
35222
+ }
35047
35223
  isEngineReady;
35048
35224
  activeToolChange;
35049
35225
  workspacesChange;
@@ -35084,7 +35260,9 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35084
35260
  if (this.core.store.isDisabled) {
35085
35261
  return;
35086
35262
  }
35087
- this.core.store.state.pointers.set(ev.pointerId, ev);
35263
+ if (this.core.store.state.pointers.has(ev.pointerId)) {
35264
+ this.core.store.state.pointers.set(ev.pointerId, ev);
35265
+ }
35088
35266
  if (this.core.store.state.pointers.size > 1) {
35089
35267
  this.throttledPointerMoveMulti(ev);
35090
35268
  }
@@ -35097,6 +35275,10 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35097
35275
  }
35098
35276
  this.core.store.state.pointers.delete(ev.pointerId);
35099
35277
  this.host.releasePointerCapture(ev.pointerId);
35278
+ // Reset cursor to default when all pointers are released
35279
+ if (this.core.store.state.pointers.size === 0) {
35280
+ this.core.store.state.cursor = { icon: 'default', iconActive: 'default' };
35281
+ }
35100
35282
  this.viewport.handlePointerUp(ev);
35101
35283
  this.core.store.state?.activeTool?.handlePointerUp(ev);
35102
35284
  }
@@ -35106,6 +35288,10 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35106
35288
  }
35107
35289
  this.host.releasePointerCapture(ev.pointerId);
35108
35290
  this.core.store.state.pointers.delete(ev.pointerId);
35291
+ // Reset cursor to default when all pointers are released
35292
+ if (this.core.store.state.pointers.size === 0) {
35293
+ this.core.store.state.cursor = { icon: 'default', iconActive: 'default' };
35294
+ }
35109
35295
  this.viewport.handlePointerUp(ev);
35110
35296
  this.core.store.state?.activeTool?.handlePointerUp(ev);
35111
35297
  }
@@ -35280,6 +35466,7 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35280
35466
  contextMenuHandler;
35281
35467
  keyHandler;
35282
35468
  contextMenuElement = null;
35469
+ cursorTargetElement = null;
35283
35470
  get isSelecting() {
35284
35471
  return this.core.store.state.activeTool instanceof KritzelSelectionTool && this.core.store.state.isSelecting;
35285
35472
  }
@@ -35303,6 +35490,12 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35303
35490
  disconnectedCallback() {
35304
35491
  this.throttledWheel.cancel();
35305
35492
  this.throttledPointerMoveMulti.cancel();
35493
+ // Reset cursor on target element
35494
+ if (this.cursorTargetElement) {
35495
+ this.cursorTargetElement.style.cursor = '';
35496
+ this.cursorTargetElement.style.removeProperty('--kritzel-pointer-cursor');
35497
+ this.cursorTargetElement = null;
35498
+ }
35306
35499
  }
35307
35500
  componentWillLoad() {
35308
35501
  this.validateScaleMax(this.scaleMax);
@@ -35312,6 +35505,10 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35312
35505
  this.contextMenuHandler = new KritzelContextMenuHandler(this.core, this.globalContextMenuItems, this.objectContextMenuItems);
35313
35506
  this.keyHandler = new KritzelKeyHandler(this.core);
35314
35507
  this.viewport = new KritzelViewport(this.core, this.host);
35508
+ // Set cursor target element (use prop value or default to document.body)
35509
+ this.cursorTargetElement = this.cursorTarget || document.body;
35510
+ // Set the pointer cursor CSS variable for child components to use
35511
+ this.cursorTargetElement.style.setProperty('--kritzel-pointer-cursor', KritzelCursorHelper.getPointerCursor());
35315
35512
  // Set sync configuration if provided
35316
35513
  if (this.syncConfig) {
35317
35514
  this.core.setSyncConfig(this.syncConfig);
@@ -35353,6 +35550,20 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35353
35550
  KritzelKeyboardHelper.forceHideKeyboard();
35354
35551
  this.core.rerender();
35355
35552
  }
35553
+ updateCursor() {
35554
+ const state = this.core.store.state;
35555
+ const isPointerDown = this.core.store.isPointerDown;
35556
+ const icon = state.cursor?.icon;
35557
+ const iconActive = state.cursor?.iconActive ?? icon;
35558
+ const rotation = state.cursor?.rotation;
35559
+ const cursor = KritzelCursorHelper.getCursor({
35560
+ iconName: isPointerDown ? iconActive : icon,
35561
+ rotation: rotation,
35562
+ });
35563
+ if (this.cursorTargetElement) {
35564
+ this.cursorTargetElement.style.cursor = cursor;
35565
+ }
35566
+ }
35356
35567
  render() {
35357
35568
  const computedStyle = window.getComputedStyle(this.host);
35358
35569
  const baseHandleSizePx = computedStyle.getPropertyValue('--kritzel-selection-handle-size').trim() || '6px';
@@ -35369,7 +35580,8 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35369
35580
  depth: 100,
35370
35581
  };
35371
35582
  const visibleObjects = this.core.store.state.objects.query(viewportBounds);
35372
- return (h(Host, { key: '1a76bcddde5f1aa68dd20a73af61f6f89ab08c78' }, this.core.store.state.debugInfo.showViewportInfo && (h("div", { key: '9be109e44187d7d2072e115533b3c58a36351993', class: "debug-panel" }, h("div", { key: 'de16ca51bc04f851ef65a9a937829916041abd1c' }, "ActiveWorkspaceId: ", this.core.store.state?.activeWorkspace?.id), h("div", { key: '299b05d4091d6c883ee637207e242e3fdb93f19c' }, "ActiveWorkspaceName: ", this.core.store.state?.activeWorkspace?.name), h("div", { key: '9ef3f04b7fcb42ec87d8b7e6b9f5e914918fd780' }, "TranslateX: ", this.core.store.state?.translateX), h("div", { key: 'cd920e869be5112c7dbe7d494f9fa06902c3d30a' }, "TranslateY: ", this.core.store.state?.translateY), h("div", { key: 'd8d28322f8cc2b5cf9a3da2c97c91e3115f53ddc' }, "ViewportWidth: ", this.core.store.state?.viewportWidth), h("div", { key: 'e8d920e10b020b359533682452f76489bc8e9f2d' }, "ViewportHeight: ", this.core.store.state?.viewportHeight), h("div", { key: '768280f7bf01703c9f6ea22b06b89fe7130006a4' }, "PointerCount: ", this.core.store.state.pointers.size), h("div", { key: 'ff0f5e860a9987abaf8c81b95d1476af19d9b186' }, "Scale: ", this.core.store.state?.scale), h("div", { key: 'a672fbf63576a1776f4d3960d9f36493a4308a79' }, "ActiveTool: ", this.core.store.state?.activeTool?.name), h("div", { key: 'd562bff5d582e3df38e0a62229c8c7b0700b9fa0' }, "HasViewportChanged: ", this.core.store.state?.hasViewportChanged ? 'true' : 'false'), h("div", { key: 'd6b2646e7fd0abb5d39928c51ad340ccf306db01' }, "IsEnabled: ", this.core.store.state?.isEnabled ? 'true' : 'false'), h("div", { key: '453e3d3691aad984895241734c70de61cbcd60ec' }, "IsScaling: ", this.core.store.state?.isScaling ? 'true' : 'false'), h("div", { key: '156668df87ea5001c7348c1c141f1c8601fe23da' }, "IsPanning: ", this.core.store.state?.isPanning ? 'true' : 'false'), h("div", { key: '86f956f35a84961c17685ebfd7cb73e92f04cd45' }, "IsSelecting: ", this.isSelecting ? 'true' : 'false'), h("div", { key: '73581c5791434983308d49e5c41f82836729a75d' }, "IsSelectionActive: ", this.isSelectionActive ? 'true' : 'false'), h("div", { key: '23f3eef374052545b7e99b0cb58a00011b421188' }, "IsResizeHandleSelected: ", this.core.store.state.isResizeHandleSelected ? 'true' : 'false'), h("div", { key: '51842e9f6e95413e6defbe6f81f43c1c7559be3e' }, "IsRotationHandleSelected: ", this.core.store.state.isRotationHandleSelected ? 'true' : 'false'), h("div", { key: 'b835c25cb75bc6f6d29a71ba25b18735f60319f8' }, "IsDrawing: ", this.core.store.state.isDrawing ? 'true' : 'false'), h("div", { key: '9a9740f44f06d57f2f9a1fce94ca2330a9c14e29' }, "IsWriting: ", this.core.store.state.isWriting ? 'true' : 'false'), h("div", { key: '9b97322077152d4fbcb98bc650ee7d0555f8d06d' }, "PointerX: ", this.core.store.state?.pointerX), h("div", { key: '9eddc79647458ca7b72e3241709fc36276587159' }, "PointerY: ", this.core.store.state?.pointerY), h("div", { key: '426ac2bf30669cc79beda5c2e5136eba5c29c578' }, "SelectedObjects: ", this.core.store.selectionGroup?.objects.length || 0), h("div", { key: '8544b6e8aaeacee60fe9597ec13af11c938eaacf' }, "ViewportCenter: (", viewportCenterX.toFixed(2), ", ", viewportCenterY.toFixed(2), ")"))), h("div", { key: '5101eecff40329a93b5ac6eb09830f1067ebaa90', id: "origin", class: "origin", style: {
35583
+ this.updateCursor();
35584
+ return (h(Host, { key: '192c356c5476b2b3cf370b05efd5742776423200' }, this.core.store.state.debugInfo.showViewportInfo && (h("div", { key: 'fae1b053c1eda01726f6b583a8dd167bb1c34aa1', class: "debug-panel" }, h("div", { key: '0e0fab7c39c1c8116831cf7b228914b0c40fb338' }, "ActiveWorkspaceId: ", this.core.store.state?.activeWorkspace?.id), h("div", { key: '770d284f5104919c5c6a36e653971d3662e9428b' }, "ActiveWorkspaceName: ", this.core.store.state?.activeWorkspace?.name), h("div", { key: '4937256ccf074a0a2fffb9c8c32a8c6ba41d3fb4' }, "TranslateX: ", this.core.store.state?.translateX), h("div", { key: '447d95aed0dda6e212e7c67ff4bc0a2e574131fd' }, "TranslateY: ", this.core.store.state?.translateY), h("div", { key: '548a04b16f68873e5fc0a2767146b52e83b9f0f8' }, "ViewportWidth: ", this.core.store.state?.viewportWidth), h("div", { key: '16a92abf89f1b438f14f311dd248ae82e1ac1982' }, "ViewportHeight: ", this.core.store.state?.viewportHeight), h("div", { key: '92a2abc5a757c64d764f3e1ee525556eb6a88852' }, "PointerCount: ", this.core.store.state.pointers.size), h("div", { key: '7677d4fd149ef2507626e50502d7c2b74fb294af' }, "Scale: ", this.core.store.state?.scale), h("div", { key: '3120c7ff85fd9f8ef14fb313b9aae6f2fc817f75' }, "ActiveTool: ", this.core.store.state?.activeTool?.name), h("div", { key: '100cd8a8c221d66046d9ff869b23809ca2568d12' }, "HasViewportChanged: ", this.core.store.state?.hasViewportChanged ? 'true' : 'false'), h("div", { key: '2efec039f635eec81d172113d55284eb9002f339' }, "IsEnabled: ", this.core.store.state?.isEnabled ? 'true' : 'false'), h("div", { key: 'f1df2fbf86a1944831c26a23e8c0baadd5ba1c56' }, "IsScaling: ", this.core.store.state?.isScaling ? 'true' : 'false'), h("div", { key: '10098cd2ffd07200fc8a12941ffd91fc1fac4de8' }, "IsPanning: ", this.core.store.state?.isPanning ? 'true' : 'false'), h("div", { key: '75043ccdac3ef3b02dae17b758813132174c2034' }, "IsSelecting: ", this.isSelecting ? 'true' : 'false'), h("div", { key: '59217b67d572cc60fc8381bcc930a952fea2faaa' }, "IsSelectionActive: ", this.isSelectionActive ? 'true' : 'false'), h("div", { key: 'c4a7d64031d3b430673adb6adcb7f525f7a47ddc' }, "IsResizeHandleSelected: ", this.core.store.state.isResizeHandleSelected ? 'true' : 'false'), h("div", { key: 'd62bef9cab424e77781a3d5639552b8122e92238' }, "IsRotationHandleSelected: ", this.core.store.state.isRotationHandleSelected ? 'true' : 'false'), h("div", { key: 'ab5dbbc947b335a1396a945328a5939d690d8cd0' }, "IsRotationHandleHovered: ", this.core.store.state.isRotationHandleHovered ? 'true' : 'false'), h("div", { key: 'fb2c19a0cdc070ecbf28e51b08112a73ffcf2817' }, "IsDrawing: ", this.core.store.state.isDrawing ? 'true' : 'false'), h("div", { key: '2d5519541aeb9a6423524463a03d1626f5eaf6ca' }, "IsWriting: ", this.core.store.state.isWriting ? 'true' : 'false'), h("div", { key: 'f86b578263c68ac194d6b3d606a1cb31717b1792' }, "IsPointerDown: ", this.core.store.isPointerDown ? 'true' : 'false'), h("div", { key: '52ed5379ef3e9a18cbabe14be8106055a8f71ede' }, "PointerX: ", this.core.store.state?.pointerX), h("div", { key: '6b97e5f6c90666283fb5cfed0cf0e3b7bc0fffe3' }, "PointerY: ", this.core.store.state?.pointerY), h("div", { key: '5f80b9d4121974ee1e8afe89925b6b38b840e90f' }, "SelectedObjects: ", this.core.store.selectionGroup?.objects.length || 0), h("div", { key: '8a280b4454677f5dc29e4a2a39fd4f7cfc8c26df' }, "ViewportCenter: (", viewportCenterX.toFixed(2), ", ", viewportCenterY.toFixed(2), ")"))), h("div", { key: '660dd95852906f5c049b9527b26ea0af3fa04274', id: "origin", class: "origin", style: {
35373
35585
  transform: `matrix(${this.core.store.state?.scale}, 0, 0, ${this.core.store.state?.scale}, ${this.core.store.state?.translateX}, ${this.core.store.state?.translateY})`,
35374
35586
  } }, visibleObjects?.map(object => {
35375
35587
  return (h("div", { key: object.id, style: {
@@ -35467,25 +35679,25 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35467
35679
  } }), h("circle", { class: "resize-handle-overlay top-left", cx: "0", cy: "0", r: `${(baseHandleTouchSize * object.scale) / this.core.store.state?.scale}`, style: {
35468
35680
  fill: 'transparent',
35469
35681
  paintOrder: 'fill',
35470
- } }), h("circle", { class: "resize-handle top-right", cx: object.totalWidth, cy: "0", r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35682
+ }, onPointerEnter: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'move-vertical', rotation: object.rotationDegrees - 45 }), onPointerLeave: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'default', iconActive: 'default' }) }), h("circle", { class: "resize-handle top-right", cx: object.totalWidth, cy: "0", r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35471
35683
  fill: 'var(--kritzel-selection-handle-color, #000000)',
35472
35684
  paintOrder: 'fill',
35473
35685
  } }), h("circle", { class: "resize-handle-overlay top-right", cx: object.totalWidth, cy: "0", r: `${(baseHandleTouchSize * object.scale) / this.core.store.state?.scale}`, style: {
35474
35686
  fill: 'transparent',
35475
35687
  paintOrder: 'fill',
35476
- } }), h("circle", { class: "resize-handle bottom-left", cx: "0", cy: object.totalHeight, r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35688
+ }, onPointerEnter: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'move-vertical', rotation: object.rotationDegrees + 45 }), onPointerLeave: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'default', iconActive: 'default' }) }), h("circle", { class: "resize-handle bottom-left", cx: "0", cy: object.totalHeight, r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35477
35689
  fill: 'var(--kritzel-selection-handle-color, #000000)',
35478
35690
  paintOrder: 'fill',
35479
35691
  } }), h("circle", { class: "resize-handle-overlay bottom-left", cx: "0", cy: object.totalHeight, r: `${(baseHandleTouchSize * object.scale) / this.core.store.state?.scale}`, style: {
35480
35692
  fill: 'transparent',
35481
35693
  paintOrder: 'fill',
35482
- } }), h("circle", { class: "resize-handle bottom-right", cx: object.totalWidth, cy: object.totalHeight, r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35694
+ }, onPointerEnter: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'move-vertical', rotation: object.rotationDegrees + 45 }), onPointerLeave: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'default', iconActive: 'default' }) }), h("circle", { class: "resize-handle bottom-right", cx: object.totalWidth, cy: object.totalHeight, r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
35483
35695
  fill: 'var(--kritzel-selection-handle-color, #000000)',
35484
35696
  paintOrder: 'fill',
35485
35697
  } }), h("circle", { class: "resize-handle-overlay bottom-right", cx: object.totalWidth, cy: object.totalHeight, r: `${(baseHandleTouchSize * object.scale) / this.core.store.state?.scale}`, style: {
35486
35698
  fill: 'transparent',
35487
35699
  paintOrder: 'fill',
35488
- } }), h("line", { x1: object.totalWidth / 2, y1: "0", x2: object.totalWidth / 2, y2: -((15 * object.scale) / this.core.store.state?.scale), style: {
35700
+ }, onPointerEnter: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'move-vertical', rotation: object.rotationDegrees - 45 }), onPointerLeave: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'default', iconActive: 'default' }) }), h("line", { x1: object.totalWidth / 2, y1: "0", x2: object.totalWidth / 2, y2: -((15 * object.scale) / this.core.store.state?.scale), style: {
35489
35701
  stroke: 'var(--kritzel-selection-border-color, #007AFF)',
35490
35702
  strokeWidth: `calc(var(--kritzel-selection-border-width, 2px) * ${object.scale} / ${this.core.store.state?.scale})`,
35491
35703
  } }), h("circle", { class: "rotation-handle", cx: object.totalWidth / 2, cy: -((15 * object.scale) / this.core.store.state?.scale), r: `${(baseHandleSize * object.scale) / this.core.store.state?.scale}`, style: {
@@ -35493,10 +35705,9 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35493
35705
  paintOrder: 'fill',
35494
35706
  } }), h("circle", { class: "rotation-handle-overlay", cx: object.totalWidth / 2, cy: -((15 * object.scale) / this.core.store.state?.scale), r: `${(baseHandleTouchSize * object.scale) / this.core.store.state?.scale}`, style: {
35495
35707
  fill: 'transparent',
35496
- cursor: 'grab',
35497
35708
  paintOrder: 'fill',
35498
- } }))))));
35499
- })), this.core.store.state.isContextMenuVisible && (h("kritzel-context-menu", { key: '8270193062df51aa5e358bd31c0851f54e4644d1', class: "context-menu", ref: el => (this.contextMenuElement = el), items: this.core.store.state.contextMenuItems, objects: this.core.store.selectionGroup?.objects || [], style: {
35709
+ }, onPointerEnter: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'hand', iconActive: 'hand-grab' }), onPointerLeave: () => !this.core.store.isPointerDown && (this.core.store.state.cursor = { icon: 'default', iconActive: 'default' }) }))))));
35710
+ })), this.core.store.state.isContextMenuVisible && (h("kritzel-context-menu", { key: '0da13416f8f2cf2f0eb6fcbb8eacb942dda0efb5', class: "context-menu", ref: el => (this.contextMenuElement = el), items: this.core.store.state.contextMenuItems, objects: this.core.store.selectionGroup?.objects || [], style: {
35500
35711
  position: 'fixed',
35501
35712
  left: `${this.core.store.state.contextMenuX}px`,
35502
35713
  top: `${this.core.store.state.contextMenuY}px`,
@@ -35507,12 +35718,13 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35507
35718
  y: (-this.core.store.state.translateY + this.core.store.state.contextMenuY) / this.core.store.state.scale,
35508
35719
  }, this.core.store.selectionGroup?.objects);
35509
35720
  this.hideContextMenu();
35510
- }, onClose: () => this.hideContextMenu() })), this.core.store.state?.activeTool instanceof KritzelEraserTool && !this.core.store.state.isScaling && h("kritzel-cursor-trail", { key: '7d199fcf652dee0cd12fff8a558b455c361e019f', core: this.core })));
35721
+ }, onClose: () => this.hideContextMenu() })), this.core.store.state?.activeTool instanceof KritzelEraserTool && !this.core.store.state.isScaling && h("kritzel-cursor-trail", { key: '609dd8438a2678eaa3ce0a73858d9236c9371f96', core: this.core })));
35511
35722
  }
35512
35723
  static get watchers() { return {
35513
35724
  "workspace": ["onWorkspaceChange"],
35514
35725
  "scaleMax": ["validateScaleMax"],
35515
- "scaleMin": ["validateScaleMin"]
35726
+ "scaleMin": ["validateScaleMin"],
35727
+ "cursorTarget": ["onCursorTargetChange"]
35516
35728
  }; }
35517
35729
  static get style() { return kritzelEngineCss; }
35518
35730
  }, [769, "kritzel-engine", {
@@ -35523,6 +35735,7 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35523
35735
  "objectContextMenuItems": [16],
35524
35736
  "scaleMax": [1026, "scale-max"],
35525
35737
  "scaleMin": [1026, "scale-min"],
35738
+ "cursorTarget": [16],
35526
35739
  "forceUpdate": [32],
35527
35740
  "registerTool": [64],
35528
35741
  "changeActiveTool": [64],
@@ -35556,7 +35769,8 @@ const KritzelEngine = /*@__PURE__*/ proxyCustomElement(class KritzelEngine exten
35556
35769
  }, [[0, "wheel", "handleWheel"], [0, "pointerdown", "handlePointerDown"], [0, "pointermove", "handlePointerMove"], [0, "pointerup", "handlePointerUp"], [0, "pointercancel", "handlePointerCancel"], [0, "longpress", "handleLongPress"], [0, "contextmenu", "handleContextMenu"], [9, "resize", "handleResize"], [8, "keydown", "handleKeyDown"], [8, "keyup", "handleKeyUp"], [4, "dblclick", "preventDoubleTapZoomOnTouchDevices"]], {
35557
35770
  "workspace": ["onWorkspaceChange"],
35558
35771
  "scaleMax": ["validateScaleMax"],
35559
- "scaleMin": ["validateScaleMin"]
35772
+ "scaleMin": ["validateScaleMin"],
35773
+ "cursorTarget": ["onCursorTargetChange"]
35560
35774
  }]);
35561
35775
  function defineCustomElement() {
35562
35776
  if (typeof customElements === "undefined") {
@@ -35587,7 +35801,7 @@ function defineCustomElement() {
35587
35801
  } });
35588
35802
  }
35589
35803
 
35590
- export { isNode as A, min$2 as B, pow as C, HocuspocusProviderWebsocket as D, KritzelEraserTool as E, KritzelImageTool as F, KritzelSelectionTool as G, HocuspocusProvider as H, IndexedDBSyncProvider as I, KritzelAppStateMap as J, KritzelImage as K, ABSOLUTE_SCALE_MAX as L, ABSOLUTE_SCALE_MIN as M, defineCustomElement as N, Observable$1 as O, KritzelEngine as P, writeVarUint8Array$2 as a, readVarUint8Array$2 as b, applyUpdate as c, encodeStateVector as d, encodeStateAsUpdate as e, createEncoder$1 as f, createDecoder$1 as g, create$8 as h, fromBase64 as i, toBase64 as j, createUint8ArrayFromArrayBuffer as k, offChange as l, readVarString$2 as m, floor$2 as n, onChange as o, getUnixTime$1 as p, equalityDeep$1 as q, readVarUint$2 as r, setIfUndefined$1 as s, toUint8Array$1 as t, writeVarString$2 as u, varStorage as v, writeVarUint$2 as w, map as x, ObservableV2 as y, length$3 as z };
35591
- //# sourceMappingURL=p-BAplhrRJ.js.map
35804
+ export { isNode as A, min$2 as B, pow as C, HocuspocusProviderWebsocket as D, KritzelEraserTool as E, KritzelImageTool as F, KritzelCursorHelper as G, HocuspocusProvider as H, KritzelSelectionTool as I, IndexedDBSyncProvider as J, KritzelImage as K, KritzelAppStateMap as L, ABSOLUTE_SCALE_MAX as M, ABSOLUTE_SCALE_MIN as N, Observable$1 as O, defineCustomElement as P, KritzelEngine as Q, writeVarUint8Array$2 as a, readVarUint8Array$2 as b, applyUpdate as c, encodeStateVector as d, encodeStateAsUpdate as e, createEncoder$1 as f, createDecoder$1 as g, create$8 as h, fromBase64 as i, toBase64 as j, createUint8ArrayFromArrayBuffer as k, offChange as l, readVarString$2 as m, floor$2 as n, onChange as o, getUnixTime$1 as p, equalityDeep$1 as q, readVarUint$2 as r, setIfUndefined$1 as s, toUint8Array$1 as t, writeVarString$2 as u, varStorage as v, writeVarUint$2 as w, map as x, ObservableV2 as y, length$3 as z };
35805
+ //# sourceMappingURL=p-D7BLVRXX.js.map
35592
35806
 
35593
- //# sourceMappingURL=p-BAplhrRJ.js.map
35807
+ //# sourceMappingURL=p-D7BLVRXX.js.map