kritzel-stencil 0.0.168 → 0.0.170

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 (100) hide show
  1. package/dist/cjs/{default-line-tool.config-CK85ewK0.js → default-line-tool.config-JuTDR6PF.js} +515 -10
  2. package/dist/cjs/default-line-tool.config-JuTDR6PF.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-color_22.cjs.entry.js +120 -6
  6. package/dist/cjs/loader.cjs.js +1 -1
  7. package/dist/cjs/stencil.cjs.js +1 -1
  8. package/dist/collection/classes/core/core.class.js +89 -1
  9. package/dist/collection/classes/core/core.class.js.map +1 -1
  10. package/dist/collection/classes/core/reviver.class.js +4 -0
  11. package/dist/collection/classes/core/reviver.class.js.map +1 -1
  12. package/dist/collection/classes/handlers/key.handler.js +3 -0
  13. package/dist/collection/classes/handlers/key.handler.js.map +1 -1
  14. package/dist/collection/classes/handlers/move.handler.js +63 -0
  15. package/dist/collection/classes/handlers/move.handler.js.map +1 -1
  16. package/dist/collection/classes/handlers/rotation.handler.js +2 -0
  17. package/dist/collection/classes/handlers/rotation.handler.js.map +1 -1
  18. package/dist/collection/classes/handlers/selection.handler.js +23 -5
  19. package/dist/collection/classes/handlers/selection.handler.js.map +1 -1
  20. package/dist/collection/classes/objects/group.class.js +394 -0
  21. package/dist/collection/classes/objects/group.class.js.map +1 -0
  22. package/dist/collection/classes/objects/line.class.js +2 -1
  23. package/dist/collection/classes/objects/line.class.js.map +1 -1
  24. package/dist/collection/classes/objects/selection-group.class.js +20 -0
  25. package/dist/collection/classes/objects/selection-group.class.js.map +1 -1
  26. package/dist/collection/classes/registries/icon-registry.class.js +2 -0
  27. package/dist/collection/classes/registries/icon-registry.class.js.map +1 -1
  28. package/dist/collection/components/core/kritzel-editor/kritzel-editor.js +17 -2
  29. package/dist/collection/components/core/kritzel-editor/kritzel-editor.js.map +1 -1
  30. package/dist/collection/components/core/kritzel-engine/kritzel-engine.js +43 -3
  31. package/dist/collection/components/core/kritzel-engine/kritzel-engine.js.map +1 -1
  32. package/dist/collection/helpers/event.helper.js +10 -2
  33. package/dist/collection/helpers/event.helper.js.map +1 -1
  34. package/dist/collection/index.js +1 -0
  35. package/dist/collection/index.js.map +1 -1
  36. package/dist/components/index.js +3 -3
  37. package/dist/components/kritzel-brush-style.js +1 -1
  38. package/dist/components/kritzel-context-menu.js +1 -1
  39. package/dist/components/kritzel-control-brush-config.js +1 -1
  40. package/dist/components/kritzel-control-text-config.js +1 -1
  41. package/dist/components/kritzel-controls.js +1 -1
  42. package/dist/components/kritzel-editor.js +27 -12
  43. package/dist/components/kritzel-editor.js.map +1 -1
  44. package/dist/components/kritzel-engine.js +1 -1
  45. package/dist/components/kritzel-icon.js +1 -1
  46. package/dist/components/kritzel-menu-item.js +1 -1
  47. package/dist/components/kritzel-menu.js +1 -1
  48. package/dist/components/kritzel-split-button.js +1 -1
  49. package/dist/components/kritzel-utility-panel.js +1 -1
  50. package/dist/components/kritzel-workspace-manager.js +1 -1
  51. package/dist/components/{p-BG2m-Sq9.js → p-9Sbn9-7-.js} +611 -16
  52. package/dist/components/p-9Sbn9-7-.js.map +1 -0
  53. package/dist/components/{p-Bwv1dxAB.js → p-BUsg2vtg.js} +12 -4
  54. package/dist/components/{p-Bwv1dxAB.js.map → p-BUsg2vtg.js.map} +1 -1
  55. package/dist/components/{p-BoazmhlG.js → p-C6-tSCMR.js} +3 -3
  56. package/dist/components/{p-BoazmhlG.js.map → p-C6-tSCMR.js.map} +1 -1
  57. package/dist/components/{p-Cv4BGNPb.js → p-CIts5Uma.js} +4 -2
  58. package/dist/components/p-CIts5Uma.js.map +1 -0
  59. package/dist/components/{p-BSBMBjhq.js → p-CQd5oYXp.js} +3 -3
  60. package/dist/components/{p-BSBMBjhq.js.map → p-CQd5oYXp.js.map} +1 -1
  61. package/dist/components/{p-D8L0t-Ro.js → p-Co5HWjr6.js} +3 -3
  62. package/dist/components/{p-D8L0t-Ro.js.map → p-Co5HWjr6.js.map} +1 -1
  63. package/dist/components/{p-5OECjGHq.js → p-DG7VXGxX.js} +3 -3
  64. package/dist/components/{p-5OECjGHq.js.map → p-DG7VXGxX.js.map} +1 -1
  65. package/dist/components/{p-D1YAsWrL.js → p-D_uh1RUI.js} +3 -3
  66. package/dist/components/{p-D1YAsWrL.js.map → p-D_uh1RUI.js.map} +1 -1
  67. package/dist/components/{p-xcQV8l_c.js → p-cv2RCdI1.js} +7 -7
  68. package/dist/components/{p-xcQV8l_c.js.map → p-cv2RCdI1.js.map} +1 -1
  69. package/dist/components/{p-BmdYFhLx.js → p-nZdy-Ii5.js} +4 -4
  70. package/dist/components/{p-BmdYFhLx.js.map → p-nZdy-Ii5.js.map} +1 -1
  71. package/dist/components/{p-CiM-IPaD.js → p-y25EBKEA.js} +5 -5
  72. package/dist/components/{p-CiM-IPaD.js.map → p-y25EBKEA.js.map} +1 -1
  73. package/dist/esm/{default-line-tool.config-kK3fdCJH.js → default-line-tool.config-CuBm2vpW.js} +515 -11
  74. package/dist/esm/default-line-tool.config-CuBm2vpW.js.map +1 -0
  75. package/dist/esm/index.js +2 -2
  76. package/dist/esm/kritzel-color_22.entry.js +120 -6
  77. package/dist/esm/loader.js +1 -1
  78. package/dist/esm/stencil.js +1 -1
  79. package/dist/stencil/index.esm.js +1 -1
  80. package/dist/stencil/p-CuBm2vpW.js +2 -0
  81. package/dist/stencil/p-CuBm2vpW.js.map +1 -0
  82. package/dist/stencil/p-c9201236.entry.js +10 -0
  83. package/dist/stencil/p-c9201236.entry.js.map +1 -0
  84. package/dist/stencil/stencil.esm.js +1 -1
  85. package/dist/types/classes/core/core.class.d.ts +11 -1
  86. package/dist/types/classes/handlers/move.handler.d.ts +11 -0
  87. package/dist/types/classes/objects/group.class.d.ts +97 -0
  88. package/dist/types/classes/objects/selection-group.class.d.ts +5 -0
  89. package/dist/types/components/core/kritzel-engine/kritzel-engine.d.ts +2 -0
  90. package/dist/types/components.d.ts +4 -2
  91. package/dist/types/index.d.ts +1 -0
  92. package/package.json +1 -1
  93. package/dist/cjs/default-line-tool.config-CK85ewK0.js.map +0 -1
  94. package/dist/components/p-BG2m-Sq9.js.map +0 -1
  95. package/dist/components/p-Cv4BGNPb.js.map +0 -1
  96. package/dist/esm/default-line-tool.config-kK3fdCJH.js.map +0 -1
  97. package/dist/stencil/p-8ee3959e.entry.js +0 -10
  98. package/dist/stencil/p-8ee3959e.entry.js.map +0 -1
  99. package/dist/stencil/p-kK3fdCJH.js +0 -2
  100. package/dist/stencil/p-kK3fdCJH.js.map +0 -1
@@ -1,2 +1,2 @@
1
- import{p as e,b as t}from"./p-SGde3HXB.js";export{s as setNonce}from"./p-SGde3HXB.js";import{g as o}from"./p-DQuL1Twl.js";var n=()=>{const t=import.meta.url;const o={};if(t!==""){o.resourcesUrl=new URL(".",t).href}return e(o)};n().then((async e=>{await o();return t([["p-8ee3959e",[[768,"kritzel-editor",{scaleMax:[2,"scale-max"],scaleMin:[2,"scale-min"],controls:[16],globalContextMenuItems:[16],objectContextMenuItems:[16],customSvgIcons:[16],isControlsVisible:[4,"is-controls-visible"],isUtilityPanelVisible:[4,"is-utility-panel-visible"],syncConfig:[16],isEngineReady:[32],isControlsReady:[32],isWorkspaceManagerReady:[32],workspaces:[32],activeWorkspace:[32],isVirtualKeyboardOpen:[32],undoState:[32],getObjectById:[64],addObject:[64],updateObject:[64],removeObject:[64],getSelectedObjects:[64],selectObjects:[64],selectAllObjectsInViewport:[64],clearSelection:[64],centerObjectInViewport:[64],createWorkspace:[64],updateWorkspace:[64],deleteWorkspace:[64],getWorkspaces:[64],getActiveWorkspace:[64]},[[0,"dblclick","onTouchStart"]],{isEngineReady:["onIsEngineReady"],isControlsReady:["onIsControlsReady"],workspaces:["onWorkspacesChange"]}],[769,"kritzel-controls",{controls:[16],activeControl:[1040],isUtilityPanelVisible:[4,"is-utility-panel-visible"],undoState:[16],firstConfig:[32],isTooltipVisible:[32],isTouchDevice:[32],selectedSubOptions:[32],openSubMenuControl:[32],closeTooltip:[64]},[[4,"click","handleDocumentClick"],[8,"keydown","handleKeyDown"],[4,"activeToolChange","handleActiveToolChange"]]],[769,"kritzel-workspace-manager",{activeWorkspace:[1040],workspaces:[16],childMenuAnchor:[32],openChildMenuItem:[32],newWorkspace:[32],editingItemId:[32]},[[8,"wheel","handleWheel"]]],[769,"kritzel-engine",{workspace:[16],syncConfig:[16],activeTool:[16],globalContextMenuItems:[16],objectContextMenuItems:[16],scaleMax:[1026,"scale-max"],scaleMin:[1026,"scale-min"],cursorTarget:[16],forceUpdate:[32],registerTool:[64],changeActiveTool:[64],disable:[64],enable:[64],delete:[64],copy:[64],paste:[64],bringForward:[64],sendBackward:[64],bringToFront:[64],sendToBack:[64],undo:[64],redo:[64],hideContextMenu:[64],getObjectById:[64],addObject:[64],updateObject:[64],removeObject:[64],getSelectedObjects:[64],selectObjects:[64],selectAllObjectsInViewport:[64],clearSelection:[64],centerObjectInViewport:[64],getCopiedObjects:[64],createWorkspace:[64],updateWorkspace:[64],deleteWorkspace:[64],getWorkspaces:[64],getActiveWorkspace:[64]},[[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"]],{workspace:["onWorkspaceChange"],scaleMax:["validateScaleMax"],scaleMin:["validateScaleMin"],cursorTarget:["onCursorTargetChange"]}],[769,"kritzel-control-text-config",{tool:[1040],isExpanded:[1028,"is-expanded"]}],[769,"kritzel-control-brush-config",{tool:[1040],isExpanded:[1028,"is-expanded"],palette:[32]},null,{tool:["handleToolChange"]}],[769,"kritzel-split-button",{buttonIcon:[1,"button-icon"],dropdownIcon:[1,"dropdown-icon"],items:[16],mainButtonDisabled:[4,"main-button-disabled"],menuButtonDisabled:[4,"menu-button-disabled"],isMenuOpen:[32],isTouchDevice:[32],anchorElement:[32],menuScrollTop:[32],open:[64],focusMenu:[64]}],[769,"kritzel-context-menu",{items:[16],objects:[16],processedItems:[32]},[[9,"pointerdown","handleOutsideClick"]],{items:["onItemsChanged"]}],[769,"kritzel-utility-panel",{undoState:[16]}],[769,"kritzel-cursor-trail",{core:[16],cursorTrailPoints:[32],isLeftButtonDown:[32]},[[9,"pointerdown","handleMouseDown"],[9,"pointermove","handlePointerMove"],[9,"pointerup","handlePointerUp"]]],[769,"kritzel-tooltip",{isVisible:[4,"is-visible"],anchorElement:[16],arrowSize:[2,"arrow-size"],offsetY:[2,"offset-y"],showArrow:[4,"show-arrow"],positionX:[32],positionY:[32],arrowOffset:[32],focusContent:[64]},[[4,"click","handleOutsideClick"],[9,"resize","handleWindowResize"]]],[769,"kritzel-font-family",{fontOptions:[16],selectedFontFamily:[1025,"selected-font-family"]}],[769,"kritzel-font-size",{sizes:[16],selectedSize:[1026,"selected-size"],fontFamily:[1,"font-family"]}],[769,"kritzel-stroke-size",{sizes:[16],selectedSize:[1026,"selected-size"]}],[769,"kritzel-color-palette",{colors:[16],selectedColor:[1025,"selected-color"],isExpanded:[4,"is-expanded"],isOpaque:[4,"is-opaque"]}],[769,"kritzel-font",{fontFamily:[1,"font-family"],size:[2],color:[1]}],[769,"kritzel-menu",{items:[16],parent:[16],selectedIndex:[32],setScrollTop:[64],setFocus:[64]}],[769,"kritzel-menu-item",{item:[16],parent:[16],isDirty:[32]},null,{item:["onItemChange"]}],[769,"kritzel-dropdown",{options:[16],value:[1],width:[1],selectStyles:[8,"select-styles"],internalValue:[32],hasSuffixContent:[32],hasPrefixContent:[32]},null,{options:["optionsChanged"],value:["externalValueChanged"]}],[769,"kritzel-portal",{anchor:[16],offsetX:[2,"offset-x"],offsetY:[2,"offset-y"],autoFocus:[4,"auto-focus"]},[[8,"click","handleOutsideClick"],[8,"keydown","handleKeyDown"],[11,"resize","handleResize"],[11,"scroll","handleWindowScroll"]],{anchor:["anchorChanged"]}],[769,"kritzel-color",{value:[1],size:[2]}],[769,"kritzel-icon",{name:[1],label:[1],size:[2]}]]],["p-385bab97",[[769,"kritzel-brush-style",{type:[1],brushOptions:[16]}]]]],e)}));
1
+ import{p as e,b as t}from"./p-SGde3HXB.js";export{s as setNonce}from"./p-SGde3HXB.js";import{g as o}from"./p-DQuL1Twl.js";var n=()=>{const t=import.meta.url;const o={};if(t!==""){o.resourcesUrl=new URL(".",t).href}return e(o)};n().then((async e=>{await o();return t([["p-c9201236",[[768,"kritzel-editor",{scaleMax:[2,"scale-max"],scaleMin:[2,"scale-min"],controls:[16],globalContextMenuItems:[16],objectContextMenuItems:[16],customSvgIcons:[16],isControlsVisible:[4,"is-controls-visible"],isUtilityPanelVisible:[4,"is-utility-panel-visible"],syncConfig:[16],isEngineReady:[32],isControlsReady:[32],isWorkspaceManagerReady:[32],workspaces:[32],activeWorkspace:[32],isVirtualKeyboardOpen:[32],undoState:[32],getObjectById:[64],addObject:[64],updateObject:[64],removeObject:[64],getSelectedObjects:[64],selectObjects:[64],selectAllObjectsInViewport:[64],clearSelection:[64],centerObjectInViewport:[64],createWorkspace:[64],updateWorkspace:[64],deleteWorkspace:[64],getWorkspaces:[64],getActiveWorkspace:[64]},[[0,"dblclick","onTouchStart"]],{isEngineReady:["onIsEngineReady"],isControlsReady:["onIsControlsReady"],workspaces:["onWorkspacesChange"]}],[769,"kritzel-controls",{controls:[16],activeControl:[1040],isUtilityPanelVisible:[4,"is-utility-panel-visible"],undoState:[16],firstConfig:[32],isTooltipVisible:[32],isTouchDevice:[32],selectedSubOptions:[32],openSubMenuControl:[32],closeTooltip:[64]},[[4,"click","handleDocumentClick"],[8,"keydown","handleKeyDown"],[4,"activeToolChange","handleActiveToolChange"]]],[769,"kritzel-workspace-manager",{activeWorkspace:[1040],workspaces:[16],childMenuAnchor:[32],openChildMenuItem:[32],newWorkspace:[32],editingItemId:[32]},[[8,"wheel","handleWheel"]]],[769,"kritzel-engine",{workspace:[16],syncConfig:[16],activeTool:[16],globalContextMenuItems:[16],objectContextMenuItems:[16],scaleMax:[1026,"scale-max"],scaleMin:[1026,"scale-min"],cursorTarget:[16],forceUpdate:[32],registerTool:[64],changeActiveTool:[64],disable:[64],enable:[64],delete:[64],copy:[64],paste:[64],bringForward:[64],sendBackward:[64],bringToFront:[64],sendToBack:[64],group:[64],ungroup:[64],undo:[64],redo:[64],hideContextMenu:[64],getObjectById:[64],addObject:[64],updateObject:[64],removeObject:[64],getSelectedObjects:[64],selectObjects:[64],selectAllObjectsInViewport:[64],clearSelection:[64],centerObjectInViewport:[64],getCopiedObjects:[64],createWorkspace:[64],updateWorkspace:[64],deleteWorkspace:[64],getWorkspaces:[64],getActiveWorkspace:[64]},[[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"]],{workspace:["onWorkspaceChange"],scaleMax:["validateScaleMax"],scaleMin:["validateScaleMin"],cursorTarget:["onCursorTargetChange"]}],[769,"kritzel-control-text-config",{tool:[1040],isExpanded:[1028,"is-expanded"]}],[769,"kritzel-control-brush-config",{tool:[1040],isExpanded:[1028,"is-expanded"],palette:[32]},null,{tool:["handleToolChange"]}],[769,"kritzel-split-button",{buttonIcon:[1,"button-icon"],dropdownIcon:[1,"dropdown-icon"],items:[16],mainButtonDisabled:[4,"main-button-disabled"],menuButtonDisabled:[4,"menu-button-disabled"],isMenuOpen:[32],isTouchDevice:[32],anchorElement:[32],menuScrollTop:[32],open:[64],focusMenu:[64]}],[769,"kritzel-context-menu",{items:[16],objects:[16],processedItems:[32]},[[9,"pointerdown","handleOutsideClick"]],{items:["onItemsChanged"]}],[769,"kritzel-utility-panel",{undoState:[16]}],[769,"kritzel-cursor-trail",{core:[16],cursorTrailPoints:[32],isLeftButtonDown:[32]},[[9,"pointerdown","handleMouseDown"],[9,"pointermove","handlePointerMove"],[9,"pointerup","handlePointerUp"]]],[769,"kritzel-tooltip",{isVisible:[4,"is-visible"],anchorElement:[16],arrowSize:[2,"arrow-size"],offsetY:[2,"offset-y"],showArrow:[4,"show-arrow"],positionX:[32],positionY:[32],arrowOffset:[32],focusContent:[64]},[[4,"click","handleOutsideClick"],[9,"resize","handleWindowResize"]]],[769,"kritzel-font-family",{fontOptions:[16],selectedFontFamily:[1025,"selected-font-family"]}],[769,"kritzel-font-size",{sizes:[16],selectedSize:[1026,"selected-size"],fontFamily:[1,"font-family"]}],[769,"kritzel-stroke-size",{sizes:[16],selectedSize:[1026,"selected-size"]}],[769,"kritzel-color-palette",{colors:[16],selectedColor:[1025,"selected-color"],isExpanded:[4,"is-expanded"],isOpaque:[4,"is-opaque"]}],[769,"kritzel-font",{fontFamily:[1,"font-family"],size:[2],color:[1]}],[769,"kritzel-menu",{items:[16],parent:[16],selectedIndex:[32],setScrollTop:[64],setFocus:[64]}],[769,"kritzel-menu-item",{item:[16],parent:[16],isDirty:[32]},null,{item:["onItemChange"]}],[769,"kritzel-dropdown",{options:[16],value:[1],width:[1],selectStyles:[8,"select-styles"],internalValue:[32],hasSuffixContent:[32],hasPrefixContent:[32]},null,{options:["optionsChanged"],value:["externalValueChanged"]}],[769,"kritzel-portal",{anchor:[16],offsetX:[2,"offset-x"],offsetY:[2,"offset-y"],autoFocus:[4,"auto-focus"]},[[8,"click","handleOutsideClick"],[8,"keydown","handleKeyDown"],[11,"resize","handleResize"],[11,"scroll","handleWindowScroll"]],{anchor:["anchorChanged"]}],[769,"kritzel-color",{value:[1],size:[2]}],[769,"kritzel-icon",{name:[1],label:[1],size:[2]}]]],["p-385bab97",[[769,"kritzel-brush-style",{type:[1],brushOptions:[16]}]]]],e)}));
2
2
  //# sourceMappingURL=stencil.esm.js.map
@@ -43,7 +43,7 @@ export declare class KritzelCore {
43
43
  deleteWorkspace(workspace: KritzelWorkspace): void;
44
44
  updateWorkspaceViewport(translateX: number, translateY: number, scale: number): void;
45
45
  addObject(object: KritzelBaseObject<any>): void;
46
- removeObject(object: KritzelBaseObject<any>): void;
46
+ removeObject(object: KritzelBaseObject<any>, preserveChildren?: boolean): void;
47
47
  updateObject<T extends KritzelBaseObject<any>>(object: T, updatedProperties: Partial<T>): void;
48
48
  addSelectionGroup(selectionGroup: KritzelSelectionGroup): void;
49
49
  removeSelectionGroup(): void;
@@ -59,6 +59,16 @@ export declare class KritzelCore {
59
59
  sendBackward(object?: KritzelBaseObject<any>): void;
60
60
  bringToFront(object?: KritzelBaseObject<any>): void;
61
61
  sendToBack(object?: KritzelBaseObject<any>): void;
62
+ /**
63
+ * Groups the currently selected objects into a KritzelGroup.
64
+ * Requires at least 2 objects to be selected.
65
+ */
66
+ group(): void;
67
+ /**
68
+ * Ungroups any KritzelGroup objects in the current selection.
69
+ * Children are extracted and become top-level objects.
70
+ */
71
+ ungroup(): void;
62
72
  selectObjects(objects: KritzelBaseObject<any>[]): void;
63
73
  selectAllObjectsInViewport(): void;
64
74
  clearSelection(): void;
@@ -7,6 +7,11 @@ export declare class KritzelMoveHandler extends KritzelBaseHandler {
7
7
  startY: number;
8
8
  endX: number;
9
9
  endY: number;
10
+ /** Initial position when drag started (for calculating total accumulated distance) */
11
+ private initialDragX;
12
+ private initialDragY;
13
+ /** Set of line IDs that have been disconnected from anchors during this drag */
14
+ private disconnectedLineIds;
10
15
  hasMoved: boolean;
11
16
  private trackedPointerId;
12
17
  constructor(core: KritzelCore);
@@ -15,4 +20,10 @@ export declare class KritzelMoveHandler extends KritzelBaseHandler {
15
20
  handlePointerDown(event: PointerEvent): void;
16
21
  handlePointerMove(event: PointerEvent): void;
17
22
  handlePointerUp(event: PointerEvent): void;
23
+ /**
24
+ * Checks if the total accumulated drag distance exceeds the anchor disconnect threshold.
25
+ * If so, disconnects all anchors from any KritzelLine objects in the selection group.
26
+ * This allows anchored lines to be freely moved after dragging beyond the threshold.
27
+ */
28
+ private checkAndDisconnectAnchors;
18
29
  }
@@ -0,0 +1,97 @@
1
+ import { KritzelCore } from '../core/core.class';
2
+ import { KritzelBaseObject } from './base-object.class';
3
+ import { KritzelPolygon } from '../../interfaces/polygon.interface';
4
+ /**
5
+ * KritzelGroup represents a permanent grouping of objects that act as a single unit.
6
+ *
7
+ * Unlike KritzelSelectionGroup (which is ephemeral and used for temporary multi-selection),
8
+ * KritzelGroup is persisted and saved with the workspace. Grouped objects move, resize,
9
+ * rotate, copy, and delete together as one unit.
10
+ *
11
+ * Key features:
12
+ * - Supports nested groups (groups can contain other groups)
13
+ * - Clicking any child selects the entire group
14
+ * - Can be ungrouped to restore children to top-level objects
15
+ */
16
+ export declare class KritzelGroup extends KritzelBaseObject<HTMLElement> {
17
+ __class__: string;
18
+ /**
19
+ * IDs of child objects within this group.
20
+ * Children can be any KritzelBaseObject, including other KritzelGroups for nesting.
21
+ */
22
+ childIds: string[];
23
+ /**
24
+ * Snapshots of child states for transformation operations (resize, rotate).
25
+ * Similar pattern to KritzelSelectionGroup.
26
+ */
27
+ private unchangedChildSnapshots;
28
+ private snapshotRotation;
29
+ private snapshotTranslateX;
30
+ private snapshotTranslateY;
31
+ private snapshotTotalWidth;
32
+ private snapshotTotalHeight;
33
+ private snapshotScale;
34
+ /**
35
+ * Retrieves the actual child objects from the store by their IDs.
36
+ */
37
+ get children(): KritzelBaseObject<any>[];
38
+ /**
39
+ * Returns the number of children in this group.
40
+ */
41
+ get length(): number;
42
+ /**
43
+ * Creates a new empty KritzelGroup.
44
+ */
45
+ static create(core: KritzelCore): KritzelGroup;
46
+ /**
47
+ * Creates a KritzelGroup from an array of objects.
48
+ * The objects are added as children and their bounding box is calculated.
49
+ */
50
+ static createFromObjects(core: KritzelCore, objects: KritzelBaseObject<any>[]): KritzelGroup;
51
+ /**
52
+ * Finds the parent KritzelGroup that contains the given object as a child.
53
+ * Returns null if the object is not a child of any group.
54
+ */
55
+ static findParentGroup(core: KritzelCore, objectId: string): KritzelGroup | null;
56
+ /**
57
+ * Adds a child object to this group.
58
+ */
59
+ addChild(object: KritzelBaseObject<any>): void;
60
+ /**
61
+ * Removes a child object from this group.
62
+ */
63
+ removeChild(objectId: string): void;
64
+ /**
65
+ * Ungroups this group, returning all children to top-level objects.
66
+ * The group itself should be removed after calling this.
67
+ */
68
+ ungroup(): KritzelBaseObject<any>[];
69
+ /**
70
+ * Finalizes the group after children have been positioned (e.g., after paste).
71
+ * Refreshes the bounding box and captures child snapshots.
72
+ */
73
+ finalize(): void;
74
+ /**
75
+ * Recalculates the group's bounding box based on its children.
76
+ */
77
+ refreshBoundingBox(): void;
78
+ /**
79
+ * Captures snapshots of child states for transformation operations.
80
+ */
81
+ private captureChildSnapshots;
82
+ move(startX: number, startY: number, endX: number, endY: number): void;
83
+ resize(x: number, y: number, width: number, height: number): void;
84
+ rotate(value: number): void;
85
+ private getOffsetXToCenterFromSnapshot;
86
+ private getOffsetYToCenterFromSnapshot;
87
+ hitTest(x: number, y: number): boolean;
88
+ hitTestPolygon(polygon: KritzelPolygon): boolean;
89
+ copy(): KritzelGroup;
90
+ serialize(): any;
91
+ deserialize<T>(object: any): T;
92
+ update(): void;
93
+ /**
94
+ * Updates the workspace ID for this group and all its children.
95
+ */
96
+ updateWorkspaceId(workspaceId: string): void;
97
+ }
@@ -24,6 +24,11 @@ export declare class KritzelSelectionGroup extends KritzelBaseObject<HTMLElement
24
24
  get length(): number;
25
25
  static create(core: KritzelCore): KritzelSelectionGroup;
26
26
  addOrRemove(object: KritzelBaseObject<any>): void;
27
+ /**
28
+ * Prepares the selection group and its children for a transform interaction (rotate/resize).
29
+ * Ensures snapshot state is aligned with the current visual state.
30
+ */
31
+ beginTransform(): void;
27
32
  deselectAllChildren(): void;
28
33
  updateWorkspaceId(workspaceId: string): void;
29
34
  updateZIndices(startZIndex: number): void;
@@ -57,6 +57,8 @@ export declare class KritzelEngine {
57
57
  sendBackward(object?: KritzelBaseObject<any>): Promise<void>;
58
58
  bringToFront(object?: KritzelBaseObject<any>): Promise<void>;
59
59
  sendToBack(object?: KritzelBaseObject<any>): Promise<void>;
60
+ group(): Promise<void>;
61
+ ungroup(): Promise<void>;
60
62
  undo(): Promise<void>;
61
63
  redo(): Promise<void>;
62
64
  hideContextMenu(): Promise<void>;
@@ -158,7 +158,7 @@ export namespace Components {
158
158
  */
159
159
  "isUtilityPanelVisible": boolean;
160
160
  /**
161
- * @default [ { label: 'Copy', icon: 'copy', action: () => this.engineRef.copy() }, { label: 'Paste', icon: 'paste', disabled: async () => (await this.engineRef.getCopiedObjects()).length === 0, action: (menu, _) => this.engineRef.paste(menu.x, menu.y), }, { label: 'Delete', icon: 'delete', action: () => this.engineRef.delete() }, { label: 'Bring to Front', icon: 'bring-to-front', action: () => this.engineRef.bringToFront() }, { label: 'Send to Back', icon: 'send-to-back', action: () => this.engineRef.sendToBack() }, ]
161
+ * @default [ { label: 'Copy', icon: 'copy', action: () => this.engineRef.copy() }, { label: 'Paste', icon: 'paste', disabled: async () => (await this.engineRef.getCopiedObjects()).length === 0, action: (menu, _) => this.engineRef.paste(menu.x, menu.y), }, { label: 'Delete', icon: 'delete', action: () => this.engineRef.delete() }, { label: 'Bring to Front', icon: 'bring-to-front', action: () => this.engineRef.bringToFront() }, { label: 'Send to Back', icon: 'send-to-back', action: () => this.engineRef.sendToBack() }, { label: 'Group', icon: 'group', disabled: async () => (await this.engineRef.getSelectedObjects()).length < 2, action: () => this.engineRef.group(), }, { label: 'Ungroup', icon: 'ungroup', disabled: async () => { const selectedObjects = await this.engineRef.getSelectedObjects(); return !selectedObjects.some(obj => obj.__class__ === 'KritzelGroup'); }, action: () => this.engineRef.ungroup(), }, ]
162
162
  */
163
163
  "objectContextMenuItems": ContextMenuItem[];
164
164
  "removeObject": <T extends KritzelBaseObject>(object: T) => Promise<T | null>;
@@ -197,6 +197,7 @@ export namespace Components {
197
197
  "getSelectedObjects": () => Promise<KritzelBaseObject<any>[]>;
198
198
  "getWorkspaces": () => Promise<KritzelWorkspace[]>;
199
199
  "globalContextMenuItems": ContextMenuItem[];
200
+ "group": () => Promise<void>;
200
201
  "hideContextMenu": () => Promise<void>;
201
202
  "objectContextMenuItems": ContextMenuItem[];
202
203
  "paste": (x: number, y: number) => Promise<void>;
@@ -217,6 +218,7 @@ export namespace Components {
217
218
  "sendToBack": (object?: KritzelBaseObject<any>) => Promise<void>;
218
219
  "syncConfig"?: KritzelSyncConfig;
219
220
  "undo": () => Promise<void>;
221
+ "ungroup": () => Promise<void>;
220
222
  "updateObject": <T extends KritzelBaseObject>(object: T, updatedProperties: Partial<T>) => Promise<T | null>;
221
223
  "updateWorkspace": (workspace: KritzelWorkspace) => Promise<void>;
222
224
  "workspace"?: KritzelWorkspace;
@@ -951,7 +953,7 @@ declare namespace LocalJSX {
951
953
  */
952
954
  "isUtilityPanelVisible"?: boolean;
953
955
  /**
954
- * @default [ { label: 'Copy', icon: 'copy', action: () => this.engineRef.copy() }, { label: 'Paste', icon: 'paste', disabled: async () => (await this.engineRef.getCopiedObjects()).length === 0, action: (menu, _) => this.engineRef.paste(menu.x, menu.y), }, { label: 'Delete', icon: 'delete', action: () => this.engineRef.delete() }, { label: 'Bring to Front', icon: 'bring-to-front', action: () => this.engineRef.bringToFront() }, { label: 'Send to Back', icon: 'send-to-back', action: () => this.engineRef.sendToBack() }, ]
956
+ * @default [ { label: 'Copy', icon: 'copy', action: () => this.engineRef.copy() }, { label: 'Paste', icon: 'paste', disabled: async () => (await this.engineRef.getCopiedObjects()).length === 0, action: (menu, _) => this.engineRef.paste(menu.x, menu.y), }, { label: 'Delete', icon: 'delete', action: () => this.engineRef.delete() }, { label: 'Bring to Front', icon: 'bring-to-front', action: () => this.engineRef.bringToFront() }, { label: 'Send to Back', icon: 'send-to-back', action: () => this.engineRef.sendToBack() }, { label: 'Group', icon: 'group', disabled: async () => (await this.engineRef.getSelectedObjects()).length < 2, action: () => this.engineRef.group(), }, { label: 'Ungroup', icon: 'ungroup', disabled: async () => { const selectedObjects = await this.engineRef.getSelectedObjects(); return !selectedObjects.some(obj => obj.__class__ === 'KritzelGroup'); }, action: () => this.engineRef.ungroup(), }, ]
955
957
  */
956
958
  "objectContextMenuItems"?: ContextMenuItem[];
957
959
  "onIsReady"?: (event: KritzelEditorCustomEvent<HTMLElement>) => void;
@@ -12,6 +12,7 @@ export * from './classes/objects/text.class';
12
12
  export * from './classes/objects/path.class';
13
13
  export * from './classes/objects/image.class';
14
14
  export * from './classes/objects/line.class';
15
+ export * from './classes/objects/group.class';
15
16
  export * from './classes/tools/brush-tool.class';
16
17
  export * from './classes/tools/line-tool.class';
17
18
  export * from './classes/tools/eraser-tool.class';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kritzel-stencil",
3
- "version": "0.0.168",
3
+ "version": "0.0.170",
4
4
  "description": "Stencil Component Starter",
5
5
  "main": "dist/index.cjs.js",
6
6
  "module": "dist/index.js",