@elixpo/lixsketch 5.6.9 → 5.6.11
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/dist/react/{AIRenderer-R5M2CIDO.js → AIRenderer-JNEZYDYQ.js} +4 -4
- package/dist/react/Arrow-QMR77LGQ.js +9 -0
- package/dist/react/Circle-5WL5HZA5.js +11 -0
- package/dist/react/{CopyPaste-PPDS3AD6.js → CopyPaste-V7AY56H3.js} +74 -30
- package/dist/react/CopyPaste-V7AY56H3.js.map +7 -0
- package/dist/react/{EventDispatcher-UV7LFSAS.js → EventDispatcher-E4OJCMY6.js} +154 -57
- package/dist/react/{EventDispatcher-UV7LFSAS.js.map → EventDispatcher-E4OJCMY6.js.map} +3 -3
- package/dist/react/Frame-OZCDVPMI.js +11 -0
- package/dist/react/FreehandStroke-QSSYWBFK.js +9 -0
- package/dist/react/IconShape-HXUV4VRT.js +10 -0
- package/dist/react/ImageShape-JGLT2UGG.js +10 -0
- package/dist/react/Line-YONPLUYT.js +11 -0
- package/dist/react/{MermaidFlowchartRenderer-EL3Q2MNW.js → MermaidFlowchartRenderer-FSH43RUP.js} +26 -7
- package/dist/react/{MermaidFlowchartRenderer-EL3Q2MNW.js.map → MermaidFlowchartRenderer-FSH43RUP.js.map} +2 -2
- package/dist/react/{MermaidSequenceRenderer-K4KHHEVC.js → MermaidSequenceRenderer-FRPNOF2V.js} +11 -9
- package/dist/react/{MermaidSequenceRenderer-K4KHHEVC.js.map → MermaidSequenceRenderer-FRPNOF2V.js.map} +2 -2
- package/dist/react/{MermaidStructuredRenderer-6LN3WISP.js → MermaidStructuredRenderer-BZGQLRIH.js} +13 -6
- package/dist/react/{MermaidStructuredRenderer-6LN3WISP.js.map → MermaidStructuredRenderer-BZGQLRIH.js.map} +2 -2
- package/dist/react/Rectangle-7KMA3SC6.js +11 -0
- package/dist/react/{SceneSerializer-H6KMQCO2.js → SceneSerializer-7O72LEZP.js} +13 -12
- package/dist/react/{SceneSerializer-H6KMQCO2.js.map → SceneSerializer-7O72LEZP.js.map} +1 -1
- package/dist/react/{Selection-CFWRGVKH.js → Selection-S4FYSZIF.js} +5 -5
- package/dist/react/{SketchEngine-UFLZJQXS.js → SketchEngine-VTWURP2K.js} +26 -26
- package/dist/react/{UndoRedo-RXO7YHA2.js → UndoRedo-YLQJ6DXW.js} +8 -2
- package/dist/react/{ZoomPan-RR7KUYZT.js → ZoomPan-AEKWKUCH.js} +2 -2
- package/dist/react/{arrowTool-DO327FKU.js → arrowTool-C4RDWQEX.js} +3 -3
- package/dist/react/{chunk-X5ENBMGL.js → chunk-2U47AU6Y.js} +3 -3
- package/dist/react/{chunk-X5ENBMGL.js.map → chunk-2U47AU6Y.js.map} +1 -1
- package/dist/react/{chunk-RK3NVAER.js → chunk-75OPJOWN.js} +7 -7
- package/dist/react/chunk-75OPJOWN.js.map +7 -0
- package/dist/react/{chunk-DODPOWNX.js → chunk-CWE5IFG7.js} +5 -5
- package/dist/react/{chunk-DODPOWNX.js.map → chunk-CWE5IFG7.js.map} +1 -1
- package/dist/react/{chunk-O7KXLFZN.js → chunk-IS2MKWGH.js} +8 -7
- package/dist/react/chunk-IS2MKWGH.js.map +7 -0
- package/dist/react/{chunk-ZNZAICWY.js → chunk-JEHOEQ6Z.js} +13 -5
- package/dist/react/chunk-JEHOEQ6Z.js.map +7 -0
- package/dist/react/{chunk-BOZEDUAF.js → chunk-JYBJXTLM.js} +40 -15
- package/dist/react/chunk-JYBJXTLM.js.map +7 -0
- package/dist/react/{chunk-6LWUR7XB.js → chunk-LXEHYCKH.js} +4 -4
- package/dist/react/{chunk-6LWUR7XB.js.map → chunk-LXEHYCKH.js.map} +1 -1
- package/dist/react/chunk-M7OYYJC6.js +17 -0
- package/dist/react/chunk-M7OYYJC6.js.map +7 -0
- package/dist/react/chunk-MS4TIQ6Z.js +131 -0
- package/dist/react/chunk-MS4TIQ6Z.js.map +7 -0
- package/dist/react/{chunk-2ALS5JGS.js → chunk-OCJN32IL.js} +2 -2
- package/dist/react/{chunk-KZBKYHZO.js → chunk-P7VIYR6R.js} +8 -5
- package/dist/react/chunk-P7VIYR6R.js.map +7 -0
- package/dist/react/{chunk-KC26KJW4.js → chunk-PX2635H5.js} +32 -10
- package/dist/react/chunk-PX2635H5.js.map +7 -0
- package/dist/react/{chunk-37PF7FG2.js → chunk-SDG4U7TP.js} +7 -6
- package/dist/react/chunk-SDG4U7TP.js.map +7 -0
- package/dist/react/{chunk-CGMUXYPJ.js → chunk-STJERZ25.js} +8 -4
- package/dist/react/chunk-STJERZ25.js.map +7 -0
- package/dist/react/{chunk-VZPH7OAM.js → chunk-TCWCC4Z4.js} +7 -3
- package/dist/react/chunk-TCWCC4Z4.js.map +7 -0
- package/dist/react/{chunk-VZX55VQL.js → chunk-TFCBCWL5.js} +90 -33
- package/dist/react/chunk-TFCBCWL5.js.map +7 -0
- package/dist/react/{chunk-GQLXUZHQ.js → chunk-TWHJ6PJK.js} +5 -3
- package/dist/react/chunk-TWHJ6PJK.js.map +7 -0
- package/dist/react/{chunk-NH3NVSWT.js → chunk-UCOK4V5Z.js} +4 -3
- package/dist/react/{chunk-NH3NVSWT.js.map → chunk-UCOK4V5Z.js.map} +2 -2
- package/dist/react/{chunk-W7XUY4GR.js → chunk-VJDNKJBX.js} +56 -4
- package/dist/react/chunk-VJDNKJBX.js.map +7 -0
- package/dist/react/{chunk-BT2EIJD4.js → chunk-WCA3FGWE.js} +6 -3
- package/dist/react/chunk-WCA3FGWE.js.map +7 -0
- package/dist/react/{chunk-I7TVGJFF.js → chunk-Y3FJMYPX.js} +4 -4
- package/dist/react/{chunk-I7TVGJFF.js.map → chunk-Y3FJMYPX.js.map} +1 -1
- package/dist/react/{chunk-7DD2JRBC.js → chunk-YCGLGY4C.js} +2 -2
- package/dist/react/{circleTool-NK4RVDAR.js → circleTool-QQV2QEVF.js} +4 -4
- package/dist/react/{codeTool-3WF4HEOW.js → codeTool-PTCPSZ4L.js} +5 -5
- package/dist/react/{frameTool-VCNV2NG2.js → frameTool-7GQPLU4Y.js} +4 -4
- package/dist/react/{freehandTool-TBAOD46K.js → freehandTool-3RJXTVAK.js} +4 -4
- package/dist/react/{iconTool-65JCAKYF.js → iconTool-DW5YJX7P.js} +5 -5
- package/dist/react/{imageTool-UQZUBOK2.js → imageTool-7GZQKWYT.js} +5 -5
- package/dist/react/index.js +68 -63
- package/dist/react/index.js.map +2 -2
- package/dist/react/{lineTool-762KBYOM.js → lineTool-5CY7BHND.js} +4 -4
- package/dist/react/{rectangleTool-IQK3HZK6.js → rectangleTool-DK4QL4QW.js} +4 -4
- package/dist/react/styles.css +4 -0
- package/dist/react/{textTool-ITG2SBJK.js → textTool-GP5QQYF3.js} +6 -6
- package/package.json +1 -1
- package/src/core/CopyPaste.js +66 -18
- package/src/core/EventDispatcher.js +71 -47
- package/src/core/MermaidFlowchartRenderer.js +34 -8
- package/src/core/MermaidSequenceRenderer.js +10 -8
- package/src/core/MermaidStructuredRenderer.js +12 -5
- package/src/core/ScreenSpaceControls.js +102 -13
- package/src/core/Selection.js +26 -7
- package/src/core/SelectionGesture.js +50 -0
- package/src/core/UndoRedo.js +108 -35
- package/src/react/components/sidebars/CircleSidebar.jsx +11 -5
- package/src/react/components/sidebars/IconSidebar.jsx +10 -4
- package/src/react/components/sidebars/RectangleSidebar.jsx +11 -5
- package/src/react/components/sidebars/ShapeSidebar.jsx +29 -37
- package/src/react/components/sidebars/TextSidebar.jsx +10 -4
- package/src/react/store/useUIStore.js +8 -1
- package/src/react/styles.css +13 -0
- package/src/react/utils/canvasBackgrounds.js +11 -2
- package/src/shapes/Arrow.js +4 -3
- package/src/shapes/Circle.js +58 -2
- package/src/shapes/Frame.js +11 -4
- package/src/shapes/FreehandStroke.js +2 -1
- package/src/shapes/Line.js +47 -20
- package/src/shapes/Rectangle.js +3 -1
- package/src/tools/arrowTool.js +1 -1
- package/src/tools/circleTool.js +5 -2
- package/src/tools/codeTool.js +1 -1
- package/src/tools/frameTool.js +3 -2
- package/src/tools/freehandTool.js +1 -1
- package/src/tools/iconTool.js +4 -3
- package/src/tools/imageTool.js +3 -2
- package/src/tools/lineTool.js +5 -1
- package/src/tools/rectangleTool.js +1 -1
- package/src/tools/shapeRecognitionTool.js +1 -1
- package/src/tools/textTool.js +2 -2
- package/src/utils/themeColors.js +13 -0
- package/dist/react/Arrow-EF7ALH2Y.js +0 -8
- package/dist/react/Circle-HMM5PKJ2.js +0 -10
- package/dist/react/CopyPaste-PPDS3AD6.js.map +0 -7
- package/dist/react/Frame-DELCMYV6.js +0 -11
- package/dist/react/FreehandStroke-WXIJKD5I.js +0 -9
- package/dist/react/IconShape-PZHMZSLR.js +0 -10
- package/dist/react/ImageShape-ZMBZARRI.js +0 -10
- package/dist/react/Line-VPVPL6ET.js +0 -10
- package/dist/react/Rectangle-4U4CD2ER.js +0 -10
- package/dist/react/chunk-37PF7FG2.js.map +0 -7
- package/dist/react/chunk-BOZEDUAF.js.map +0 -7
- package/dist/react/chunk-BT2EIJD4.js.map +0 -7
- package/dist/react/chunk-CGMUXYPJ.js.map +0 -7
- package/dist/react/chunk-GQLXUZHQ.js.map +0 -7
- package/dist/react/chunk-KC26KJW4.js.map +0 -7
- package/dist/react/chunk-KZBKYHZO.js.map +0 -7
- package/dist/react/chunk-O7KXLFZN.js.map +0 -7
- package/dist/react/chunk-PAKA6HUX.js +0 -59
- package/dist/react/chunk-PAKA6HUX.js.map +0 -7
- package/dist/react/chunk-RK3NVAER.js.map +0 -7
- package/dist/react/chunk-VZPH7OAM.js.map +0 -7
- package/dist/react/chunk-VZX55VQL.js.map +0 -7
- package/dist/react/chunk-W7XUY4GR.js.map +0 -7
- package/dist/react/chunk-ZNZAICWY.js.map +0 -7
- /package/dist/react/{AIRenderer-R5M2CIDO.js.map → AIRenderer-JNEZYDYQ.js.map} +0 -0
- /package/dist/react/{Arrow-EF7ALH2Y.js.map → Arrow-QMR77LGQ.js.map} +0 -0
- /package/dist/react/{Circle-HMM5PKJ2.js.map → Circle-5WL5HZA5.js.map} +0 -0
- /package/dist/react/{Frame-DELCMYV6.js.map → Frame-OZCDVPMI.js.map} +0 -0
- /package/dist/react/{FreehandStroke-WXIJKD5I.js.map → FreehandStroke-QSSYWBFK.js.map} +0 -0
- /package/dist/react/{IconShape-PZHMZSLR.js.map → IconShape-HXUV4VRT.js.map} +0 -0
- /package/dist/react/{ImageShape-ZMBZARRI.js.map → ImageShape-JGLT2UGG.js.map} +0 -0
- /package/dist/react/{Line-VPVPL6ET.js.map → Line-YONPLUYT.js.map} +0 -0
- /package/dist/react/{Rectangle-4U4CD2ER.js.map → Rectangle-7KMA3SC6.js.map} +0 -0
- /package/dist/react/{Selection-CFWRGVKH.js.map → Selection-S4FYSZIF.js.map} +0 -0
- /package/dist/react/{SketchEngine-UFLZJQXS.js.map → SketchEngine-VTWURP2K.js.map} +0 -0
- /package/dist/react/{UndoRedo-RXO7YHA2.js.map → UndoRedo-YLQJ6DXW.js.map} +0 -0
- /package/dist/react/{ZoomPan-RR7KUYZT.js.map → ZoomPan-AEKWKUCH.js.map} +0 -0
- /package/dist/react/{arrowTool-DO327FKU.js.map → arrowTool-C4RDWQEX.js.map} +0 -0
- /package/dist/react/{chunk-2ALS5JGS.js.map → chunk-OCJN32IL.js.map} +0 -0
- /package/dist/react/{chunk-7DD2JRBC.js.map → chunk-YCGLGY4C.js.map} +0 -0
- /package/dist/react/{circleTool-NK4RVDAR.js.map → circleTool-QQV2QEVF.js.map} +0 -0
- /package/dist/react/{codeTool-3WF4HEOW.js.map → codeTool-PTCPSZ4L.js.map} +0 -0
- /package/dist/react/{frameTool-VCNV2NG2.js.map → frameTool-7GQPLU4Y.js.map} +0 -0
- /package/dist/react/{freehandTool-TBAOD46K.js.map → freehandTool-3RJXTVAK.js.map} +0 -0
- /package/dist/react/{iconTool-65JCAKYF.js.map → iconTool-DW5YJX7P.js.map} +0 -0
- /package/dist/react/{imageTool-UQZUBOK2.js.map → imageTool-7GZQKWYT.js.map} +0 -0
- /package/dist/react/{lineTool-762KBYOM.js.map → lineTool-5CY7BHND.js.map} +0 -0
- /package/dist/react/{rectangleTool-IQK3HZK6.js.map → rectangleTool-DK4QL4QW.js.map} +0 -0
- /package/dist/react/{textTool-ITG2SBJK.js.map → textTool-GP5QQYF3.js.map} +0 -0
|
@@ -165,16 +165,16 @@ var SketchEngine = class {
|
|
|
165
165
|
{ Frame },
|
|
166
166
|
{ FreehandStroke }
|
|
167
167
|
] = await Promise.all([
|
|
168
|
-
import("./Rectangle-
|
|
169
|
-
import("./Circle-
|
|
170
|
-
import("./Arrow-
|
|
171
|
-
import("./Line-
|
|
168
|
+
import("./Rectangle-7KMA3SC6.js"),
|
|
169
|
+
import("./Circle-5WL5HZA5.js"),
|
|
170
|
+
import("./Arrow-QMR77LGQ.js"),
|
|
171
|
+
import("./Line-YONPLUYT.js"),
|
|
172
172
|
import("./TextShape-DY77FFI2.js"),
|
|
173
173
|
import("./CodeShape-TE74XP5V.js"),
|
|
174
|
-
import("./ImageShape-
|
|
175
|
-
import("./IconShape-
|
|
176
|
-
import("./Frame-
|
|
177
|
-
import("./FreehandStroke-
|
|
174
|
+
import("./ImageShape-JGLT2UGG.js"),
|
|
175
|
+
import("./IconShape-HXUV4VRT.js"),
|
|
176
|
+
import("./Frame-OZCDVPMI.js"),
|
|
177
|
+
import("./FreehandStroke-QSSYWBFK.js")
|
|
178
178
|
]);
|
|
179
179
|
window.Rectangle = Rectangle;
|
|
180
180
|
window.Circle = Circle;
|
|
@@ -210,16 +210,16 @@ var SketchEngine = class {
|
|
|
210
210
|
frameTool,
|
|
211
211
|
freehandTool
|
|
212
212
|
] = await Promise.all([
|
|
213
|
-
import("./rectangleTool-
|
|
214
|
-
import("./circleTool-
|
|
215
|
-
import("./arrowTool-
|
|
216
|
-
import("./lineTool-
|
|
217
|
-
import("./textTool-
|
|
218
|
-
import("./codeTool-
|
|
219
|
-
import("./imageTool-
|
|
220
|
-
import("./iconTool-
|
|
221
|
-
import("./frameTool-
|
|
222
|
-
import("./freehandTool-
|
|
213
|
+
import("./rectangleTool-DK4QL4QW.js"),
|
|
214
|
+
import("./circleTool-QQV2QEVF.js"),
|
|
215
|
+
import("./arrowTool-C4RDWQEX.js"),
|
|
216
|
+
import("./lineTool-5CY7BHND.js"),
|
|
217
|
+
import("./textTool-GP5QQYF3.js"),
|
|
218
|
+
import("./codeTool-PTCPSZ4L.js"),
|
|
219
|
+
import("./imageTool-7GZQKWYT.js"),
|
|
220
|
+
import("./iconTool-DW5YJX7P.js"),
|
|
221
|
+
import("./frameTool-7GQPLU4Y.js"),
|
|
222
|
+
import("./freehandTool-3RJXTVAK.js")
|
|
223
223
|
]);
|
|
224
224
|
this._modules.tools = {
|
|
225
225
|
rectangleTool,
|
|
@@ -243,11 +243,11 @@ var SketchEngine = class {
|
|
|
243
243
|
resizeShapes,
|
|
244
244
|
resizeCode
|
|
245
245
|
] = await Promise.all([
|
|
246
|
-
import("./EventDispatcher-
|
|
247
|
-
import("./UndoRedo-
|
|
248
|
-
import("./Selection-
|
|
249
|
-
import("./ZoomPan-
|
|
250
|
-
import("./CopyPaste-
|
|
246
|
+
import("./EventDispatcher-E4OJCMY6.js"),
|
|
247
|
+
import("./UndoRedo-YLQJ6DXW.js"),
|
|
248
|
+
import("./Selection-S4FYSZIF.js"),
|
|
249
|
+
import("./ZoomPan-AEKWKUCH.js"),
|
|
250
|
+
import("./CopyPaste-V7AY56H3.js"),
|
|
251
251
|
import("./EraserTrail-PA6IQLQN.js"),
|
|
252
252
|
import("./ResizeShapes-LKEQTITP.js"),
|
|
253
253
|
import("./ResizeCode-WAMDTKSW.js")
|
|
@@ -266,7 +266,7 @@ var SketchEngine = class {
|
|
|
266
266
|
eventDispatcher.initEventDispatcher(this.svg);
|
|
267
267
|
}
|
|
268
268
|
window.__sketchInteractionReady = true;
|
|
269
|
-
const sceneSerializer = await import("./SceneSerializer-
|
|
269
|
+
const sceneSerializer = await import("./SceneSerializer-7O72LEZP.js");
|
|
270
270
|
if (sceneSerializer.initSceneSerializer) sceneSerializer.initSceneSerializer();
|
|
271
271
|
await Promise.all([
|
|
272
272
|
import("./eraserTool-2GS2LQCS.js"),
|
|
@@ -279,7 +279,7 @@ var SketchEngine = class {
|
|
|
279
279
|
if (selection.multiSelection) window.multiSelection = selection.multiSelection;
|
|
280
280
|
if (selection.clearAllSelections) window.clearAllSelections = selection.clearAllSelections;
|
|
281
281
|
if (copyPaste.initCopyPaste) copyPaste.initCopyPaste();
|
|
282
|
-
const aiRenderer = await import("./AIRenderer-
|
|
282
|
+
const aiRenderer = await import("./AIRenderer-JNEZYDYQ.js");
|
|
283
283
|
if (aiRenderer.initAIRenderer) aiRenderer.initAIRenderer();
|
|
284
284
|
const graphEngine = await import("./GraphEngine-XH3RPYO4.js");
|
|
285
285
|
if (graphEngine.initGraphEngine) graphEngine.initGraphEngine();
|
|
@@ -441,4 +441,4 @@ export {
|
|
|
441
441
|
SketchEngine,
|
|
442
442
|
SketchEngine_default as default
|
|
443
443
|
};
|
|
444
|
-
//# sourceMappingURL=SketchEngine-
|
|
444
|
+
//# sourceMappingURL=SketchEngine-VTWURP2K.js.map
|
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import {
|
|
3
3
|
beginUndoBatch,
|
|
4
|
+
captureFrameChildStates,
|
|
5
|
+
captureShapeGeometry,
|
|
4
6
|
clearUndoHistory,
|
|
5
7
|
endUndoBatch,
|
|
6
8
|
getCurrentSelectedElement,
|
|
@@ -13,13 +15,16 @@ import {
|
|
|
13
15
|
pushFrameAttachmentAction,
|
|
14
16
|
pushOptionsChangeAction,
|
|
15
17
|
pushTransformAction,
|
|
18
|
+
rebindUndoHistory,
|
|
16
19
|
redo,
|
|
17
20
|
setTextReferences,
|
|
18
21
|
undo,
|
|
19
22
|
updateSelectedElement
|
|
20
|
-
} from "./chunk-
|
|
23
|
+
} from "./chunk-TFCBCWL5.js";
|
|
21
24
|
export {
|
|
22
25
|
beginUndoBatch,
|
|
26
|
+
captureFrameChildStates,
|
|
27
|
+
captureShapeGeometry,
|
|
23
28
|
clearUndoHistory,
|
|
24
29
|
endUndoBatch,
|
|
25
30
|
getCurrentSelectedElement,
|
|
@@ -32,9 +37,10 @@ export {
|
|
|
32
37
|
pushFrameAttachmentAction,
|
|
33
38
|
pushOptionsChangeAction,
|
|
34
39
|
pushTransformAction,
|
|
40
|
+
rebindUndoHistory,
|
|
35
41
|
redo,
|
|
36
42
|
setTextReferences,
|
|
37
43
|
undo,
|
|
38
44
|
updateSelectedElement
|
|
39
45
|
};
|
|
40
|
-
//# sourceMappingURL=UndoRedo-
|
|
46
|
+
//# sourceMappingURL=UndoRedo-YLQJ6DXW.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import {
|
|
3
3
|
installScreenSpaceControlSync
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-MS4TIQ6Z.js";
|
|
5
5
|
|
|
6
6
|
// src/core/ZoomPan.js
|
|
7
7
|
installScreenSpaceControlSync(freehandCanvas);
|
|
@@ -296,4 +296,4 @@ svg.addEventListener("wheel", (e) => {
|
|
|
296
296
|
`${currentViewBox.x} ${currentViewBox.y} ${currentViewBox.width} ${currentViewBox.height}`
|
|
297
297
|
);
|
|
298
298
|
});
|
|
299
|
-
//# sourceMappingURL=ZoomPan-
|
|
299
|
+
//# sourceMappingURL=ZoomPan-AEKWKUCH.js.map
|
|
@@ -5,8 +5,8 @@ import {
|
|
|
5
5
|
handleMouseMove,
|
|
6
6
|
handleMouseUp,
|
|
7
7
|
updateAttachedArrows
|
|
8
|
-
} from "./chunk-
|
|
9
|
-
import "./chunk-
|
|
8
|
+
} from "./chunk-2U47AU6Y.js";
|
|
9
|
+
import "./chunk-TFCBCWL5.js";
|
|
10
10
|
export {
|
|
11
11
|
cleanupAttachments,
|
|
12
12
|
handleMouseDown as handleMouseDownArrow,
|
|
@@ -14,4 +14,4 @@ export {
|
|
|
14
14
|
handleMouseUp as handleMouseUpArrow,
|
|
15
15
|
updateAttachedArrows
|
|
16
16
|
};
|
|
17
|
-
//# sourceMappingURL=arrowTool-
|
|
17
|
+
//# sourceMappingURL=arrowTool-C4RDWQEX.js.map
|
|
@@ -5,7 +5,7 @@ import {
|
|
|
5
5
|
pushFrameAttachmentAction,
|
|
6
6
|
pushOptionsChangeAction,
|
|
7
7
|
pushTransformAction
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-TFCBCWL5.js";
|
|
9
9
|
|
|
10
10
|
// src/core/SnapGuides.js
|
|
11
11
|
var SNAP_THRESHOLD = 6;
|
|
@@ -230,7 +230,7 @@ function clearSnapGuides() {
|
|
|
230
230
|
// src/tools/arrowTool.js
|
|
231
231
|
function getThemeStroke() {
|
|
232
232
|
if (typeof document === "undefined") return "#fff";
|
|
233
|
-
return document.body && document.body.classList.contains("theme-dark") ? "#fff" : "#
|
|
233
|
+
return document.body && document.body.classList.contains("theme-dark") ? "#fff" : "#000000";
|
|
234
234
|
}
|
|
235
235
|
var currentArrow = null;
|
|
236
236
|
var isResizing = false;
|
|
@@ -744,4 +744,4 @@ export {
|
|
|
744
744
|
updateAttachedArrows,
|
|
745
745
|
cleanupAttachments
|
|
746
746
|
};
|
|
747
|
-
//# sourceMappingURL=chunk-
|
|
747
|
+
//# sourceMappingURL=chunk-2U47AU6Y.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../src/core/SnapGuides.js", "../../src/tools/arrowTool.js"],
|
|
4
|
-
"sourcesContent": ["/**\n * SnapGuides - Shows thin red alignment guides when moving shapes\n * to help users align shapes with each other and the viewport.\n */\n\nconst SNAP_THRESHOLD = 6; // pixels \u2014 how close before snapping\nconst BREAK_THRESHOLD = 12; // pixels \u2014 how far mouse must move to break free\nconst GUIDE_COLOR = '#ff4444';\nconst GUIDE_WIDTH = 1;\n\nlet guideLayer = null;\n\n// Track active snaps so we can implement break-out\nlet activeSnapX = null; // { guideValue, mouseAtSnap }\nlet activeSnapY = null;\n\nfunction ensureGuideLayer() {\n if (guideLayer && guideLayer.parentNode) return guideLayer;\n const svg = window.svg;\n if (!svg) return null;\n\n guideLayer = document.createElementNS('http://www.w3.org/2000/svg', 'g');\n guideLayer.setAttribute('id', 'snap-guides');\n guideLayer.setAttribute('pointer-events', 'none');\n svg.appendChild(guideLayer);\n return guideLayer;\n}\n\nfunction clearGuides() {\n if (guideLayer) {\n while (guideLayer.firstChild) guideLayer.removeChild(guideLayer.firstChild);\n }\n}\n\nfunction drawGuide(x1, y1, x2, y2) {\n const layer = ensureGuideLayer();\n if (!layer) return;\n\n const line = document.createElementNS('http://www.w3.org/2000/svg', 'line');\n line.setAttribute('x1', x1);\n line.setAttribute('y1', y1);\n line.setAttribute('x2', x2);\n line.setAttribute('y2', y2);\n line.setAttribute('stroke', GUIDE_COLOR);\n line.setAttribute('stroke-width', GUIDE_WIDTH);\n line.setAttribute('stroke-dasharray', '4 2');\n layer.appendChild(line);\n}\n\n/**\n * Get the bounding box of a shape in canvas coordinates\n */\nfunction getShapeBounds(shape) {\n if (!shape) return null;\n\n const name = shape.shapeName;\n if (name === 'rectangle' || name === 'frame') {\n return {\n left: shape.x,\n top: shape.y,\n right: shape.x + shape.width,\n bottom: shape.y + shape.height,\n cx: shape.x + shape.width / 2,\n cy: shape.y + shape.height / 2,\n };\n }\n if (name === 'circle') {\n return {\n left: shape.x - shape.rx,\n top: shape.y - shape.ry,\n right: shape.x + shape.rx,\n bottom: shape.y + shape.ry,\n cx: shape.x,\n cy: shape.y,\n };\n }\n if (name === 'text' || name === 'code' || name === 'image' || name === 'icon') {\n const el = shape.group || shape.element;\n if (!el) return null;\n const bbox = el.getBBox();\n return {\n left: bbox.x,\n top: bbox.y,\n right: bbox.x + bbox.width,\n bottom: bbox.y + bbox.height,\n cx: bbox.x + bbox.width / 2,\n cy: bbox.y + bbox.height / 2,\n };\n }\n if (name === 'line' || name === 'arrow') {\n const sx = shape.startPoint?.x ?? 0;\n const sy = shape.startPoint?.y ?? 0;\n const ex = shape.endPoint?.x ?? 0;\n const ey = shape.endPoint?.y ?? 0;\n return {\n left: Math.min(sx, ex),\n top: Math.min(sy, ey),\n right: Math.max(sx, ex),\n bottom: Math.max(sy, ey),\n cx: (sx + ex) / 2,\n cy: (sy + ey) / 2,\n };\n }\n return null;\n}\n\n/**\n * Get the canvas viewport reference points for global alignment.\n */\nfunction getCanvasGuides() {\n const vb = window.currentViewBox;\n if (!vb) return [];\n\n return [\n { // Viewport center\n left: vb.x + vb.width / 2,\n top: vb.y + vb.height / 2,\n right: vb.x + vb.width / 2,\n bottom: vb.y + vb.height / 2,\n cx: vb.x + vb.width / 2,\n cy: vb.y + vb.height / 2,\n },\n { // Viewport edges\n left: vb.x,\n top: vb.y,\n right: vb.x + vb.width,\n bottom: vb.y + vb.height,\n cx: vb.x + vb.width / 2,\n cy: vb.y + vb.height / 2,\n },\n ];\n}\n\n/**\n * Calculate snap offsets and draw guides.\n * Returns { dx, dy } snap offset to apply.\n *\n * Uses a break-out system: once snapped, the shape stays on the guide\n * until the mouse moves BREAK_THRESHOLD away, then it breaks free.\n */\nexport function calculateSnap(movingShape, shiftKey = false, mouseX, mouseY) {\n clearGuides();\n\n const shapes = window.shapes;\n if (!shapes || !movingShape) return { dx: 0, dy: 0 };\n\n const moving = getShapeBounds(movingShape);\n if (!moving) return { dx: 0, dy: 0 };\n\n // Check if we should break out of an active snap\n if (activeSnapX && mouseX !== undefined) {\n if (Math.abs(mouseX - activeSnapX.mouseAtSnap) > BREAK_THRESHOLD) {\n activeSnapX = null;\n }\n }\n if (activeSnapY && mouseY !== undefined) {\n if (Math.abs(mouseY - activeSnapY.mouseAtSnap) > BREAK_THRESHOLD) {\n activeSnapY = null;\n }\n }\n\n let snapX = null;\n let snapY = null;\n let bestDistX = SNAP_THRESHOLD;\n let bestDistY = SNAP_THRESHOLD;\n\n const movingXs = [moving.left, moving.cx, moving.right];\n const movingYs = [moving.top, moving.cy, moving.bottom];\n\n const vb = window.currentViewBox;\n const extendY1 = vb ? vb.y : 0;\n const extendY2 = vb ? vb.y + vb.height : 10000;\n const extendX1 = vb ? vb.x : 0;\n const extendX2 = vb ? vb.x + vb.width : 10000;\n\n let otherShapeCount = 0;\n\n for (const shape of shapes) {\n if (shape === movingShape) continue;\n if (window.multiSelection && window.multiSelection.selectedShapes?.has(shape)) continue;\n\n const other = getShapeBounds(shape);\n if (!other) continue;\n otherShapeCount++;\n\n const otherXs = [other.left, other.cx, other.right];\n const otherYs = [other.top, other.cy, other.bottom];\n\n for (const mx of movingXs) {\n for (const ox of otherXs) {\n const dist = Math.abs(mx - ox);\n if (dist < bestDistX) {\n bestDistX = dist;\n snapX = { offset: ox - mx, x: ox, extendY1, extendY2 };\n }\n }\n }\n\n for (const my of movingYs) {\n for (const oy of otherYs) {\n const dist = Math.abs(my - oy);\n if (dist < bestDistY) {\n bestDistY = dist;\n snapY = { offset: oy - my, y: oy, extendX1, extendX2 };\n }\n }\n }\n }\n\n // Viewport guides when alone, no snap found, or shift held\n if (shiftKey || otherShapeCount === 0 || (!snapX && !snapY)) {\n const canvasGuides = getCanvasGuides();\n for (const guide of canvasGuides) {\n const guideXs = [guide.left, guide.cx, guide.right];\n const guideYs = [guide.top, guide.cy, guide.bottom];\n\n for (const mx of movingXs) {\n for (const gx of guideXs) {\n const dist = Math.abs(mx - gx);\n if (dist < bestDistX) {\n bestDistX = dist;\n snapX = { offset: gx - mx, x: gx, extendY1, extendY2 };\n }\n }\n }\n for (const my of movingYs) {\n for (const gy of guideYs) {\n const dist = Math.abs(my - gy);\n if (dist < bestDistY) {\n bestDistY = dist;\n snapY = { offset: gy - my, y: gy, extendX1, extendX2 };\n }\n }\n }\n }\n }\n\n let dx = 0;\n let dy = 0;\n\n // Apply X snap only if not broken out of a previous X snap\n if (snapX && !activeSnapX) {\n dx = snapX.offset;\n drawGuide(snapX.x, snapX.extendY1, snapX.x, snapX.extendY2);\n if (mouseX !== undefined) {\n activeSnapX = { guideValue: snapX.x, mouseAtSnap: mouseX };\n }\n } else if (activeSnapX) {\n // Still in an active snap \u2014 hold position by drawing guide but no offset\n drawGuide(activeSnapX.guideValue, extendY1, activeSnapX.guideValue, extendY2);\n }\n\n if (snapY && !activeSnapY) {\n dy = snapY.offset;\n drawGuide(snapY.extendX1, snapY.y, snapY.extendX2, snapY.y);\n if (mouseY !== undefined) {\n activeSnapY = { guideValue: snapY.y, mouseAtSnap: mouseY };\n }\n } else if (activeSnapY) {\n drawGuide(extendX1, activeSnapY.guideValue, extendX2, activeSnapY.guideValue);\n }\n\n return { dx, dy };\n}\n\n/**\n * Clear all snap guides and reset snap state. Call on mouseUp.\n */\nexport function clearSnapGuides() {\n clearGuides();\n activeSnapX = null;\n activeSnapY = null;\n}\n", "/* eslint-disable */\n// Arrow tool event handlers - extracted from drawArrow.js\nimport { pushCreateAction, pushDeleteAction, pushOptionsChangeAction, pushTransformAction, pushFrameAttachmentAction } from '../core/UndoRedo.js';\nimport { calculateSnap, clearSnapGuides } from '../core/SnapGuides.js';\n\n\nfunction getThemeStroke() { if (typeof document === \"undefined\") return \"#fff\"; return document.body && document.body.classList.contains(\"theme-dark\") ? \"#fff\" : \"#1a1a2e\"; }\n\nlet arrowStartX, arrowStartY;\nlet currentArrow = null;\nlet isResizing = false;\nlet isDragging = false;\nlet activeAnchor = null;\nlet isDrawingArrow = false;\nlet arrowStrokeColor = null;\nlet arrowStrokeThickness = 2;\nlet arrowOutlineStyle = \"solid\";\nlet arrowCurved = \"straight\";\nlet arrowCurveAmount = 20;\nlet arrowHeadLength = 10;\nlet arrowHeadAngleDeg = 30;\nlet arrowHeadStyle = \"default\";\nlet startX, startY;\nlet dragOldPosArrow = null;\nlet draggedShapeInitialFrameArrow = null;\nlet hoveredFrameArrow = null;\nlet arrowStrokeColorOptions = document.querySelectorAll(\".arrowStrokeSpan\");\nlet arrowStrokeThicknessValue = document.querySelectorAll(\".arrowStrokeThickSpan\");\nlet arrowOutlineStyleValue = document.querySelectorAll(\".arrowOutlineStyle\");\nlet arrowTypeStyleValue = document.querySelectorAll(\".arrowTypeStyle\");\nlet arrowHeadStyleValue = document.querySelectorAll(\".arrowHeadStyleSpan\");\nlet arrowCurveAmountOptions = document.querySelectorAll(\".arrowCurveSpan\");\n\n\nfunction getSVGCoordsFromMouse(e) {\n const viewBox = svg.viewBox.baseVal;\n const rect = svg.getBoundingClientRect();\n const mouseX = e.clientX - rect.left;\n const mouseY = e.clientY - rect.top;\n const svgX = viewBox.x + (mouseX / rect.width) * viewBox.width;\n const svgY = viewBox.y + (mouseY / rect.height) * viewBox.height;\n return { x: svgX, y: svgY };\n}\n\nfunction deleteCurrentShape() {\n if (currentShape && currentShape.shapeName === 'arrow') {\n const idx = shapes.indexOf(currentShape);\n if (idx !== -1) shapes.splice(idx, 1);\n if (currentShape.group.parentNode) {\n currentShape.group.parentNode.removeChild(currentShape.group);\n }\n pushDeleteAction(currentShape);\n currentShape = null;\n disableAllSideBars();\n }\n}\n\ndocument.addEventListener('keydown', (e) => {\n if (e.key === 'Delete' && currentShape && currentShape.shapeName === 'arrow') {\n deleteCurrentShape();\n }\n});\n\n\nconst handleMouseDown = (e) => {\n if (!isArrowToolActive && !isSelectionToolActive) return;\n\n const { x, y } = getSVGCoordsFromMouse(e);\n\n if (isArrowToolActive) {\n isDrawingArrow = true;\n currentArrow = new Arrow({ x, y }, { x, y }, {\n stroke: arrowStrokeColor ?? getThemeStroke(),\n strokeWidth: arrowStrokeThickness,\n arrowOutlineStyle: arrowOutlineStyle,\n arrowHeadStyle: arrowHeadStyle,\n arrowCurved: arrowCurved,\n arrowCurveAmount: arrowCurveAmount\n });\n shapes.push(currentArrow);\n currentShape = currentArrow;\n } else if (isSelectionToolActive) {\n let clickedOnShape = false;\n let clickedOnAnchor = false;\n\n if (currentShape && currentShape.shapeName === 'arrow' && currentShape.isSelected) {\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo && anchorInfo.type === 'anchor') {\n clickedOnAnchor = true;\n clickedOnShape = true;\n } \n if (currentShape.contains(x, y)) {\n isDragging = true;\n dragOldPosArrow = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n controlPoint1: currentShape.controlPoint1 ? { x: currentShape.controlPoint1.x, y: currentShape.controlPoint1.y } : null,\n controlPoint2: currentShape.controlPoint2 ? { x: currentShape.controlPoint2.x, y: currentShape.controlPoint2.y } : null,\n parentFrame: currentShape.parentFrame // Add this line\n };\n \n // Store initial frame state\n draggedShapeInitialFrameArrow = currentShape.parentFrame || null;\n \n // Temporarily remove from frame clipping if dragging\n if (currentShape.parentFrame) {\n currentShape.parentFrame.temporarilyRemoveFromFrame(currentShape);\n }\n \n startX = x;\n startY = y;\n clickedOnShape = true;\n }\n }\n\n if (!clickedOnShape) {\n let shapeToSelect = null;\n\n for (let i = shapes.length - 1; i >= 0; i--) {\n const shape = shapes[i];\n if (shape instanceof Arrow && shape.contains(x, y)) {\n shapeToSelect = shape;\n break;\n }\n }\n\n if (currentShape && currentShape !== shapeToSelect) {\n currentShape.removeSelection();\n currentShape = null;\n }\n\n if (shapeToSelect) {\n currentShape = shapeToSelect;\n currentShape.selectArrow();\n\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo && anchorInfo.type === 'anchor') {\n clickedOnAnchor = true;\n } else {\n isDragging = true;\n dragOldPosArrow = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n controlPoint1: currentShape.controlPoint1 ? { x: currentShape.controlPoint1.x, y: currentShape.controlPoint1.y } : null,\n controlPoint2: currentShape.controlPoint2 ? { x: currentShape.controlPoint2.x, y: currentShape.controlPoint2.y } : null\n };\n startX = x;\n startY = y;\n }\n clickedOnShape = true;\n }\n }\n\n if (!clickedOnShape && !clickedOnAnchor && currentShape) {\n currentShape.removeSelection();\n currentShape = null;\n }\n }\n};\n\n// Enhanced mouse move with better cursor feedback\nconst handleMouseMove = (e) => {\n const { x, y } = getSVGCoordsFromMouse(e);\n\n if (isDrawingArrow && currentArrow) {\n let endX = x, endY = y;\n if (e.shiftKey) {\n const dx = x - currentArrow.startPoint.x;\n const dy = y - currentArrow.startPoint.y;\n const angle = Math.atan2(dy, dx);\n const snapAngle = Math.round(angle / (Math.PI / 4)) * (Math.PI / 4);\n const dist = Math.sqrt(dx * dx + dy * dy);\n endX = currentArrow.startPoint.x + dist * Math.cos(snapAngle);\n endY = currentArrow.startPoint.y + dist * Math.sin(snapAngle);\n }\n currentArrow.endPoint = { x: endX, y: endY };\n\n // Check for potential attachment and show preview\n const nearbyShape = Arrow.findNearbyShape({ x: endX, y: endY });\n if (nearbyShape) {\n // Snap to attachment point\n currentArrow.endPoint = nearbyShape.attachment.point;\n svg.style.cursor = 'crosshair';\n\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n\n const preview = document.createElementNS(\"http://www.w3.org/2000/svg\", \"circle\");\n preview.setAttribute(\"cx\", nearbyShape.attachment.point.x);\n preview.setAttribute(\"cy\", nearbyShape.attachment.point.y);\n preview.setAttribute(\"r\", 6);\n preview.setAttribute(\"fill\", \"none\");\n preview.setAttribute(\"stroke\", \"#5B57D1\");\n preview.setAttribute(\"stroke-width\", 2);\n preview.setAttribute(\"class\", \"attachment-preview\");\n preview.setAttribute(\"opacity\", \"0.7\");\n svg.appendChild(preview);\n } else {\n // Remove preview if no nearby shape\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n }\n\n // Check for frame containment while drawing (but don't apply clipping yet)\n shapes.forEach(frame => {\n if (frame.shapeName === 'frame') {\n if (frame.isShapeInFrame(currentArrow)) {\n frame.highlightFrame();\n hoveredFrameArrow = frame;\n } else if (hoveredFrameArrow === frame) {\n frame.removeHighlight();\n hoveredFrameArrow = null;\n }\n }\n });\n\n // Update control points for curved arrows during drawing\n if (currentArrow.arrowCurved) {\n currentArrow.initializeCurveControlPoints();\n }\n currentArrow.draw();\n }\n\n else if (isDragging && currentShape && currentShape.isSelected) {\n const dx = x - startX;\n const dy = y - startY;\n currentShape.move(dx, dy);\n startX = x;\n startY = y;\n\n // Issue #24 bug #4: track containing frame during drag of an\n // existing arrow so mouseUp re-parents correctly. Without this\n // hoveredFrameArrow stays null and the arrow is detached the\n // moment the user nudges it inside its own parent frame.\n let newHover = null;\n for (const f of shapes) {\n if (f.shapeName !== 'frame') continue;\n if (f === currentShape) continue;\n if (typeof f.isShapeInFrame === 'function' && f.isShapeInFrame(currentShape)) {\n newHover = f;\n break;\n }\n }\n if (hoveredFrameArrow && hoveredFrameArrow !== newHover && typeof hoveredFrameArrow.removeHighlight === 'function') {\n hoveredFrameArrow.removeHighlight();\n }\n if (newHover && newHover !== hoveredFrameArrow && typeof newHover.highlightFrame === 'function') {\n newHover.highlightFrame();\n }\n hoveredFrameArrow = newHover;\n\n // Snap guides\n if (window.__sketchStoreApi && window.__sketchStoreApi.getState().snapToObjects) {\n const snap = calculateSnap(currentShape, e.shiftKey, e.clientX, e.clientY);\n if (snap.dx || snap.dy) {\n currentShape.move(snap.dx, snap.dy);\n }\n } else {\n clearSnapGuides();\n }\n\n svg.style.cursor = 'grabbing';\n } else if (isSelectionToolActive && currentShape && currentShape.isSelected) {\n // Provide visual feedback when hovering over anchors or the arrow\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo) {\n svg.style.cursor = 'grab';\n } else if (currentShape.contains(x, y)) {\n svg.style.cursor = 'move';\n } else {\n svg.style.cursor = 'default';\n }\n } else if (isSelectionToolActive) {\n // Check if hovering over any selectable arrow\n let hoveringOverArrow = false;\n for (let i = shapes.length - 1; i >= 0; i--) {\n const shape = shapes[i];\n if (shape instanceof Arrow && shape.contains(x, y)) {\n hoveringOverArrow = true;\n break;\n }\n }\n svg.style.cursor = hoveringOverArrow ? 'pointer' : 'default';\n }\n};\n\nconst handleMouseUp = (e) => {\nif (isDrawingArrow && currentArrow) {\n // Remove any attachment preview that might still be visible\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n\n // Check if arrow is too small\n const dx = currentArrow.endPoint.x - currentArrow.startPoint.x;\n const dy = currentArrow.endPoint.y - currentArrow.startPoint.y;\n const lengthSq = dx * dx + dy * dy;\n\n if (lengthSq < (5 / currentZoom) ** 2) {\n shapes.pop();\n if (currentArrow.group.parentNode) {\n currentArrow.group.parentNode.removeChild(currentArrow.group);\n }\n currentArrow = null;\n currentShape = null;\n } else {\n const startAttachment = Arrow.findNearbyShape(currentArrow.startPoint);\n const endAttachment = Arrow.findNearbyShape(currentArrow.endPoint);\n\n if (startAttachment) {\n currentArrow.attachToShape(true, startAttachment.shape, startAttachment.attachment);\n }\n\n if (endAttachment) {\n currentArrow.attachToShape(false, endAttachment.shape, endAttachment.attachment);\n }\n\n // Check for frame containment and track attachment\n const finalFrame = hoveredFrameArrow;\n if (finalFrame) {\n finalFrame.addShapeToFrame(currentArrow);\n // Track the attachment for undo\n pushFrameAttachmentAction(finalFrame, currentArrow, 'attach', null);\n }\n\n // Push create action for undo/redo\n pushCreateAction(currentArrow);\n\n // Auto-select the drawn arrow and switch to selection tool\n const drawnArrow = currentArrow;\n if (window.__sketchStoreApi) window.__sketchStoreApi.setActiveTool('select', { afterDraw: true });\n currentShape = drawnArrow;\n drawnArrow.selectArrow();\n }\n\n // Clear frame highlighting\n if (hoveredFrameArrow) {\n hoveredFrameArrow.removeHighlight();\n hoveredFrameArrow = null;\n }\n\n currentArrow = null;\n}\n\nif (isDragging && dragOldPosArrow && currentShape) {\n // Issue #34 bug #2: containment transfer happens later in this block,\n // so currentShape.parentFrame is still the OLD frame here. hoveredFrameArrow\n // tracks the actual destination during mousemove \u2014 use that as the truth.\n const newPos = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n parentFrame: hoveredFrameArrow || null,\n };\n const oldPos = {\n ...dragOldPosArrow,\n parentFrame: draggedShapeInitialFrameArrow // Add this line\n };\n \n const stateChanged = dragOldPosArrow.startPoint.x !== newPos.startPoint.x ||\n dragOldPosArrow.startPoint.y !== newPos.startPoint.y ||\n dragOldPosArrow.endPoint.x !== newPos.endPoint.x ||\n dragOldPosArrow.endPoint.y !== newPos.endPoint.y;\n \n const frameChanged = oldPos.parentFrame !== newPos.parentFrame;\n\n if (stateChanged || frameChanged) {\n pushTransformAction(currentShape, oldPos, newPos);\n }\n \n // Handle frame containment changes after drag\n if (isDragging) {\n const finalFrame = hoveredFrameArrow;\n \n // If shape moved to a different frame\n if (draggedShapeInitialFrameArrow !== finalFrame) {\n // Remove from initial frame\n if (draggedShapeInitialFrameArrow) {\n draggedShapeInitialFrameArrow.removeShapeFromFrame(currentShape);\n }\n \n // Add to new frame\n if (finalFrame) {\n finalFrame.addShapeToFrame(currentShape);\n }\n \n // Track the frame change for undo\n if (frameChanged) {\n pushFrameAttachmentAction(finalFrame || draggedShapeInitialFrameArrow, currentShape, \n finalFrame ? 'attach' : 'detach', draggedShapeInitialFrameArrow);\n }\n } else if (draggedShapeInitialFrameArrow) {\n // Shape stayed in same frame, restore clipping\n draggedShapeInitialFrameArrow.restoreToFrame(currentShape);\n }\n }\n \n draggedShapeInitialFrameArrow = null;\n dragOldPosArrow = null;\n}\n\n// Clear frame highlighting\nif (hoveredFrameArrow) {\n hoveredFrameArrow.removeHighlight();\n hoveredFrameArrow = null;\n}\n\nclearSnapGuides();\nisDrawingArrow = false;\nisResizing = false;\nisDragging = false;\nactiveAnchor = null;\nsvg.style.cursor = 'default';\n};\n\n// Remove old event listeners and add new ones\nsvg.removeEventListener('pointerdown', handleMouseDown);\nsvg.removeEventListener('pointermove', handleMouseMove);\nsvg.removeEventListener('pointerup', handleMouseUp);\n\n\n// Updated style handlers with undo/redo support\nconst updateSelectedArrowStyle = (styleChanges) => {\n if (currentShape instanceof Arrow && currentShape.isSelected) {\n const oldOptions = {\n ...currentShape.options,\n arrowOutlineStyle: currentShape.arrowOutlineStyle,\n arrowHeadStyle: currentShape.arrowHeadStyle,\n arrowCurved: currentShape.arrowCurved,\n arrowCurveAmount: currentShape.arrowCurveAmount\n };\n currentShape.updateStyle(styleChanges);\n pushOptionsChangeAction(currentShape, oldOptions);\n } else {\n if (styleChanges.stroke !== undefined) arrowStrokeColor = styleChanges.stroke;\n if (styleChanges.strokeWidth !== undefined) arrowStrokeThickness = styleChanges.strokeWidth;\n if (styleChanges.arrowOutlineStyle !== undefined) arrowOutlineStyle = styleChanges.arrowOutlineStyle;\n if (styleChanges.arrowHeadStyle !== undefined) arrowHeadStyle = styleChanges.arrowHeadStyle;\n if (styleChanges.arrowCurved !== undefined) arrowCurved = styleChanges.arrowCurved;\n if (styleChanges.arrowCurveAmount !== undefined) arrowCurveAmount = styleChanges.arrowCurveAmount;\n }\n};\n\narrowStrokeColorOptions.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowStrokeColorOptions.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newColor = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ stroke: newColor });\n });\n});\n\narrowStrokeThicknessValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowStrokeThicknessValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newThickness = parseInt(span.getAttribute(\"data-id\"));\n updateSelectedArrowStyle({ strokeWidth: newThickness });\n });\n});\n\narrowOutlineStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowOutlineStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newStyle = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ arrowOutlineStyle: newStyle });\n });\n});\n\narrowTypeStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowTypeStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n updateSelectedArrowStyle({ arrowCurved: span.getAttribute(\"data-id\") });\n });\n});\n\narrowCurveAmountOptions.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowCurveAmountOptions.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n updateSelectedArrowStyle({ arrowCurveAmount: parseInt(span.getAttribute(\"data-id\")) });\n });\n});\n\narrowHeadStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowHeadStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newHeadStyle = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ arrowHeadStyle: newHeadStyle });\n });\n});\n\nfunction detachSelectedArrow() {\n if (currentShape instanceof Arrow && currentShape.isSelected) {\n if (currentShape.attachedToStart || currentShape.attachedToEnd) {\n const oldState = {\n attachedToStart: currentShape.attachedToStart,\n attachedToEnd: currentShape.attachedToEnd,\n startPoint: { ...currentShape.startPoint },\n endPoint: { ...currentShape.endPoint }\n };\n\n currentShape.detachFromShape(true);\n currentShape.detachFromShape(false);\n currentShape.draw();\n\n // Add to undo/redo if needed\n }\n }\n}\n\nfunction updateAttachedArrows(shape) {\n if (!shape) return;\n\n // If a DOM element was passed (e.g. from text/code/image move), find the wrapper\n let targetShape = shape;\n if (shape.nodeType) {\n targetShape = shapes.find(s => s.group === shape || s.element === shape) || shape;\n }\n\n shapes.forEach(arrowShape => {\n if (arrowShape instanceof Arrow) {\n let needsUpdate = false;\n if (arrowShape.attachedToStart && arrowShape.attachedToStart.shape === targetShape) {\n needsUpdate = true;\n }\n if (arrowShape.attachedToEnd && arrowShape.attachedToEnd.shape === targetShape) {\n needsUpdate = true;\n }\n\n if (needsUpdate) {\n arrowShape.updateAttachments();\n }\n }\n });\n}\n\nfunction cleanupAttachments(deletedShape) {\n if (!deletedShape) return;\n\n // If a DOM element was passed, find the wrapper\n let targetShape = deletedShape;\n if (deletedShape.nodeType) {\n targetShape = shapes.find(s => s.group === deletedShape || s.element === deletedShape) || deletedShape;\n }\n\n shapes.forEach(shape => {\n if (shape instanceof Arrow) {\n let needsDraw = false;\n if (shape.attachedToStart && shape.attachedToStart.shape === targetShape) {\n shape.detachFromShape(true);\n needsDraw = true;\n }\n if (shape.attachedToEnd && shape.attachedToEnd.shape === targetShape) {\n shape.detachFromShape(false);\n needsDraw = true;\n }\n if (needsDraw) {\n shape.draw();\n }\n }\n });\n}\n\n// Add keyboard shortcut to detach arrows\ndocument.addEventListener('keydown', (e) => {\n if (e.key.toLowerCase() === 'd' && e.ctrlKey) {\n e.preventDefault();\n detachSelectedArrow();\n }\n});\n\n// Expose arrow tool settings on window for React sidebar bridge\nwindow.arrowToolSettings = {\n get strokeColor() { return arrowStrokeColor; },\n set strokeColor(v) { arrowStrokeColor = v; },\n get strokeWidth() { return arrowStrokeThickness; },\n set strokeWidth(v) { arrowStrokeThickness = v; },\n get outlineStyle() { return arrowOutlineStyle; },\n set outlineStyle(v) { arrowOutlineStyle = v; },\n get headStyle() { return arrowHeadStyle; },\n set headStyle(v) { arrowHeadStyle = v; },\n get arrowCurved() { return arrowCurved; },\n set arrowCurved(v) { arrowCurved = v; },\n get curveAmount() { return arrowCurveAmount; },\n set curveAmount(v) { arrowCurveAmount = v; },\n};\nwindow.updateSelectedArrowStyle = updateSelectedArrowStyle;\n\n// Export the cleanup function\n// Expose cleanupAttachments globally for centralized delete\nwindow.cleanupAttachments = cleanupAttachments;\n\nexport {\n handleMouseDown as handleMouseDownArrow,\n handleMouseMove as handleMouseMoveArrow,\n handleMouseUp as handleMouseUpArrow,\n cleanupAttachments,\n updateAttachedArrows\n};\n"],
|
|
4
|
+
"sourcesContent": ["/**\n * SnapGuides - Shows thin red alignment guides when moving shapes\n * to help users align shapes with each other and the viewport.\n */\n\nconst SNAP_THRESHOLD = 6; // pixels \u2014 how close before snapping\nconst BREAK_THRESHOLD = 12; // pixels \u2014 how far mouse must move to break free\nconst GUIDE_COLOR = '#ff4444';\nconst GUIDE_WIDTH = 1;\n\nlet guideLayer = null;\n\n// Track active snaps so we can implement break-out\nlet activeSnapX = null; // { guideValue, mouseAtSnap }\nlet activeSnapY = null;\n\nfunction ensureGuideLayer() {\n if (guideLayer && guideLayer.parentNode) return guideLayer;\n const svg = window.svg;\n if (!svg) return null;\n\n guideLayer = document.createElementNS('http://www.w3.org/2000/svg', 'g');\n guideLayer.setAttribute('id', 'snap-guides');\n guideLayer.setAttribute('pointer-events', 'none');\n svg.appendChild(guideLayer);\n return guideLayer;\n}\n\nfunction clearGuides() {\n if (guideLayer) {\n while (guideLayer.firstChild) guideLayer.removeChild(guideLayer.firstChild);\n }\n}\n\nfunction drawGuide(x1, y1, x2, y2) {\n const layer = ensureGuideLayer();\n if (!layer) return;\n\n const line = document.createElementNS('http://www.w3.org/2000/svg', 'line');\n line.setAttribute('x1', x1);\n line.setAttribute('y1', y1);\n line.setAttribute('x2', x2);\n line.setAttribute('y2', y2);\n line.setAttribute('stroke', GUIDE_COLOR);\n line.setAttribute('stroke-width', GUIDE_WIDTH);\n line.setAttribute('stroke-dasharray', '4 2');\n layer.appendChild(line);\n}\n\n/**\n * Get the bounding box of a shape in canvas coordinates\n */\nfunction getShapeBounds(shape) {\n if (!shape) return null;\n\n const name = shape.shapeName;\n if (name === 'rectangle' || name === 'frame') {\n return {\n left: shape.x,\n top: shape.y,\n right: shape.x + shape.width,\n bottom: shape.y + shape.height,\n cx: shape.x + shape.width / 2,\n cy: shape.y + shape.height / 2,\n };\n }\n if (name === 'circle') {\n return {\n left: shape.x - shape.rx,\n top: shape.y - shape.ry,\n right: shape.x + shape.rx,\n bottom: shape.y + shape.ry,\n cx: shape.x,\n cy: shape.y,\n };\n }\n if (name === 'text' || name === 'code' || name === 'image' || name === 'icon') {\n const el = shape.group || shape.element;\n if (!el) return null;\n const bbox = el.getBBox();\n return {\n left: bbox.x,\n top: bbox.y,\n right: bbox.x + bbox.width,\n bottom: bbox.y + bbox.height,\n cx: bbox.x + bbox.width / 2,\n cy: bbox.y + bbox.height / 2,\n };\n }\n if (name === 'line' || name === 'arrow') {\n const sx = shape.startPoint?.x ?? 0;\n const sy = shape.startPoint?.y ?? 0;\n const ex = shape.endPoint?.x ?? 0;\n const ey = shape.endPoint?.y ?? 0;\n return {\n left: Math.min(sx, ex),\n top: Math.min(sy, ey),\n right: Math.max(sx, ex),\n bottom: Math.max(sy, ey),\n cx: (sx + ex) / 2,\n cy: (sy + ey) / 2,\n };\n }\n return null;\n}\n\n/**\n * Get the canvas viewport reference points for global alignment.\n */\nfunction getCanvasGuides() {\n const vb = window.currentViewBox;\n if (!vb) return [];\n\n return [\n { // Viewport center\n left: vb.x + vb.width / 2,\n top: vb.y + vb.height / 2,\n right: vb.x + vb.width / 2,\n bottom: vb.y + vb.height / 2,\n cx: vb.x + vb.width / 2,\n cy: vb.y + vb.height / 2,\n },\n { // Viewport edges\n left: vb.x,\n top: vb.y,\n right: vb.x + vb.width,\n bottom: vb.y + vb.height,\n cx: vb.x + vb.width / 2,\n cy: vb.y + vb.height / 2,\n },\n ];\n}\n\n/**\n * Calculate snap offsets and draw guides.\n * Returns { dx, dy } snap offset to apply.\n *\n * Uses a break-out system: once snapped, the shape stays on the guide\n * until the mouse moves BREAK_THRESHOLD away, then it breaks free.\n */\nexport function calculateSnap(movingShape, shiftKey = false, mouseX, mouseY) {\n clearGuides();\n\n const shapes = window.shapes;\n if (!shapes || !movingShape) return { dx: 0, dy: 0 };\n\n const moving = getShapeBounds(movingShape);\n if (!moving) return { dx: 0, dy: 0 };\n\n // Check if we should break out of an active snap\n if (activeSnapX && mouseX !== undefined) {\n if (Math.abs(mouseX - activeSnapX.mouseAtSnap) > BREAK_THRESHOLD) {\n activeSnapX = null;\n }\n }\n if (activeSnapY && mouseY !== undefined) {\n if (Math.abs(mouseY - activeSnapY.mouseAtSnap) > BREAK_THRESHOLD) {\n activeSnapY = null;\n }\n }\n\n let snapX = null;\n let snapY = null;\n let bestDistX = SNAP_THRESHOLD;\n let bestDistY = SNAP_THRESHOLD;\n\n const movingXs = [moving.left, moving.cx, moving.right];\n const movingYs = [moving.top, moving.cy, moving.bottom];\n\n const vb = window.currentViewBox;\n const extendY1 = vb ? vb.y : 0;\n const extendY2 = vb ? vb.y + vb.height : 10000;\n const extendX1 = vb ? vb.x : 0;\n const extendX2 = vb ? vb.x + vb.width : 10000;\n\n let otherShapeCount = 0;\n\n for (const shape of shapes) {\n if (shape === movingShape) continue;\n if (window.multiSelection && window.multiSelection.selectedShapes?.has(shape)) continue;\n\n const other = getShapeBounds(shape);\n if (!other) continue;\n otherShapeCount++;\n\n const otherXs = [other.left, other.cx, other.right];\n const otherYs = [other.top, other.cy, other.bottom];\n\n for (const mx of movingXs) {\n for (const ox of otherXs) {\n const dist = Math.abs(mx - ox);\n if (dist < bestDistX) {\n bestDistX = dist;\n snapX = { offset: ox - mx, x: ox, extendY1, extendY2 };\n }\n }\n }\n\n for (const my of movingYs) {\n for (const oy of otherYs) {\n const dist = Math.abs(my - oy);\n if (dist < bestDistY) {\n bestDistY = dist;\n snapY = { offset: oy - my, y: oy, extendX1, extendX2 };\n }\n }\n }\n }\n\n // Viewport guides when alone, no snap found, or shift held\n if (shiftKey || otherShapeCount === 0 || (!snapX && !snapY)) {\n const canvasGuides = getCanvasGuides();\n for (const guide of canvasGuides) {\n const guideXs = [guide.left, guide.cx, guide.right];\n const guideYs = [guide.top, guide.cy, guide.bottom];\n\n for (const mx of movingXs) {\n for (const gx of guideXs) {\n const dist = Math.abs(mx - gx);\n if (dist < bestDistX) {\n bestDistX = dist;\n snapX = { offset: gx - mx, x: gx, extendY1, extendY2 };\n }\n }\n }\n for (const my of movingYs) {\n for (const gy of guideYs) {\n const dist = Math.abs(my - gy);\n if (dist < bestDistY) {\n bestDistY = dist;\n snapY = { offset: gy - my, y: gy, extendX1, extendX2 };\n }\n }\n }\n }\n }\n\n let dx = 0;\n let dy = 0;\n\n // Apply X snap only if not broken out of a previous X snap\n if (snapX && !activeSnapX) {\n dx = snapX.offset;\n drawGuide(snapX.x, snapX.extendY1, snapX.x, snapX.extendY2);\n if (mouseX !== undefined) {\n activeSnapX = { guideValue: snapX.x, mouseAtSnap: mouseX };\n }\n } else if (activeSnapX) {\n // Still in an active snap \u2014 hold position by drawing guide but no offset\n drawGuide(activeSnapX.guideValue, extendY1, activeSnapX.guideValue, extendY2);\n }\n\n if (snapY && !activeSnapY) {\n dy = snapY.offset;\n drawGuide(snapY.extendX1, snapY.y, snapY.extendX2, snapY.y);\n if (mouseY !== undefined) {\n activeSnapY = { guideValue: snapY.y, mouseAtSnap: mouseY };\n }\n } else if (activeSnapY) {\n drawGuide(extendX1, activeSnapY.guideValue, extendX2, activeSnapY.guideValue);\n }\n\n return { dx, dy };\n}\n\n/**\n * Clear all snap guides and reset snap state. Call on mouseUp.\n */\nexport function clearSnapGuides() {\n clearGuides();\n activeSnapX = null;\n activeSnapY = null;\n}\n", "/* eslint-disable */\n// Arrow tool event handlers - extracted from drawArrow.js\nimport { pushCreateAction, pushDeleteAction, pushOptionsChangeAction, pushTransformAction, pushFrameAttachmentAction } from '../core/UndoRedo.js';\nimport { calculateSnap, clearSnapGuides } from '../core/SnapGuides.js';\n\n\nfunction getThemeStroke() { if (typeof document === \"undefined\") return \"#fff\"; return document.body && document.body.classList.contains(\"theme-dark\") ? \"#fff\" : \"#000000\"; }\n\nlet arrowStartX, arrowStartY;\nlet currentArrow = null;\nlet isResizing = false;\nlet isDragging = false;\nlet activeAnchor = null;\nlet isDrawingArrow = false;\nlet arrowStrokeColor = null;\nlet arrowStrokeThickness = 2;\nlet arrowOutlineStyle = \"solid\";\nlet arrowCurved = \"straight\";\nlet arrowCurveAmount = 20;\nlet arrowHeadLength = 10;\nlet arrowHeadAngleDeg = 30;\nlet arrowHeadStyle = \"default\";\nlet startX, startY;\nlet dragOldPosArrow = null;\nlet draggedShapeInitialFrameArrow = null;\nlet hoveredFrameArrow = null;\nlet arrowStrokeColorOptions = document.querySelectorAll(\".arrowStrokeSpan\");\nlet arrowStrokeThicknessValue = document.querySelectorAll(\".arrowStrokeThickSpan\");\nlet arrowOutlineStyleValue = document.querySelectorAll(\".arrowOutlineStyle\");\nlet arrowTypeStyleValue = document.querySelectorAll(\".arrowTypeStyle\");\nlet arrowHeadStyleValue = document.querySelectorAll(\".arrowHeadStyleSpan\");\nlet arrowCurveAmountOptions = document.querySelectorAll(\".arrowCurveSpan\");\n\n\nfunction getSVGCoordsFromMouse(e) {\n const viewBox = svg.viewBox.baseVal;\n const rect = svg.getBoundingClientRect();\n const mouseX = e.clientX - rect.left;\n const mouseY = e.clientY - rect.top;\n const svgX = viewBox.x + (mouseX / rect.width) * viewBox.width;\n const svgY = viewBox.y + (mouseY / rect.height) * viewBox.height;\n return { x: svgX, y: svgY };\n}\n\nfunction deleteCurrentShape() {\n if (currentShape && currentShape.shapeName === 'arrow') {\n const idx = shapes.indexOf(currentShape);\n if (idx !== -1) shapes.splice(idx, 1);\n if (currentShape.group.parentNode) {\n currentShape.group.parentNode.removeChild(currentShape.group);\n }\n pushDeleteAction(currentShape);\n currentShape = null;\n disableAllSideBars();\n }\n}\n\ndocument.addEventListener('keydown', (e) => {\n if (e.key === 'Delete' && currentShape && currentShape.shapeName === 'arrow') {\n deleteCurrentShape();\n }\n});\n\n\nconst handleMouseDown = (e) => {\n if (!isArrowToolActive && !isSelectionToolActive) return;\n\n const { x, y } = getSVGCoordsFromMouse(e);\n\n if (isArrowToolActive) {\n isDrawingArrow = true;\n currentArrow = new Arrow({ x, y }, { x, y }, {\n stroke: arrowStrokeColor ?? getThemeStroke(),\n strokeWidth: arrowStrokeThickness,\n arrowOutlineStyle: arrowOutlineStyle,\n arrowHeadStyle: arrowHeadStyle,\n arrowCurved: arrowCurved,\n arrowCurveAmount: arrowCurveAmount\n });\n shapes.push(currentArrow);\n currentShape = currentArrow;\n } else if (isSelectionToolActive) {\n let clickedOnShape = false;\n let clickedOnAnchor = false;\n\n if (currentShape && currentShape.shapeName === 'arrow' && currentShape.isSelected) {\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo && anchorInfo.type === 'anchor') {\n clickedOnAnchor = true;\n clickedOnShape = true;\n } \n if (currentShape.contains(x, y)) {\n isDragging = true;\n dragOldPosArrow = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n controlPoint1: currentShape.controlPoint1 ? { x: currentShape.controlPoint1.x, y: currentShape.controlPoint1.y } : null,\n controlPoint2: currentShape.controlPoint2 ? { x: currentShape.controlPoint2.x, y: currentShape.controlPoint2.y } : null,\n parentFrame: currentShape.parentFrame // Add this line\n };\n \n // Store initial frame state\n draggedShapeInitialFrameArrow = currentShape.parentFrame || null;\n \n // Temporarily remove from frame clipping if dragging\n if (currentShape.parentFrame) {\n currentShape.parentFrame.temporarilyRemoveFromFrame(currentShape);\n }\n \n startX = x;\n startY = y;\n clickedOnShape = true;\n }\n }\n\n if (!clickedOnShape) {\n let shapeToSelect = null;\n\n for (let i = shapes.length - 1; i >= 0; i--) {\n const shape = shapes[i];\n if (shape instanceof Arrow && shape.contains(x, y)) {\n shapeToSelect = shape;\n break;\n }\n }\n\n if (currentShape && currentShape !== shapeToSelect) {\n currentShape.removeSelection();\n currentShape = null;\n }\n\n if (shapeToSelect) {\n currentShape = shapeToSelect;\n currentShape.selectArrow();\n\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo && anchorInfo.type === 'anchor') {\n clickedOnAnchor = true;\n } else {\n isDragging = true;\n dragOldPosArrow = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n controlPoint1: currentShape.controlPoint1 ? { x: currentShape.controlPoint1.x, y: currentShape.controlPoint1.y } : null,\n controlPoint2: currentShape.controlPoint2 ? { x: currentShape.controlPoint2.x, y: currentShape.controlPoint2.y } : null\n };\n startX = x;\n startY = y;\n }\n clickedOnShape = true;\n }\n }\n\n if (!clickedOnShape && !clickedOnAnchor && currentShape) {\n currentShape.removeSelection();\n currentShape = null;\n }\n }\n};\n\n// Enhanced mouse move with better cursor feedback\nconst handleMouseMove = (e) => {\n const { x, y } = getSVGCoordsFromMouse(e);\n\n if (isDrawingArrow && currentArrow) {\n let endX = x, endY = y;\n if (e.shiftKey) {\n const dx = x - currentArrow.startPoint.x;\n const dy = y - currentArrow.startPoint.y;\n const angle = Math.atan2(dy, dx);\n const snapAngle = Math.round(angle / (Math.PI / 4)) * (Math.PI / 4);\n const dist = Math.sqrt(dx * dx + dy * dy);\n endX = currentArrow.startPoint.x + dist * Math.cos(snapAngle);\n endY = currentArrow.startPoint.y + dist * Math.sin(snapAngle);\n }\n currentArrow.endPoint = { x: endX, y: endY };\n\n // Check for potential attachment and show preview\n const nearbyShape = Arrow.findNearbyShape({ x: endX, y: endY });\n if (nearbyShape) {\n // Snap to attachment point\n currentArrow.endPoint = nearbyShape.attachment.point;\n svg.style.cursor = 'crosshair';\n\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n\n const preview = document.createElementNS(\"http://www.w3.org/2000/svg\", \"circle\");\n preview.setAttribute(\"cx\", nearbyShape.attachment.point.x);\n preview.setAttribute(\"cy\", nearbyShape.attachment.point.y);\n preview.setAttribute(\"r\", 6);\n preview.setAttribute(\"fill\", \"none\");\n preview.setAttribute(\"stroke\", \"#5B57D1\");\n preview.setAttribute(\"stroke-width\", 2);\n preview.setAttribute(\"class\", \"attachment-preview\");\n preview.setAttribute(\"opacity\", \"0.7\");\n svg.appendChild(preview);\n } else {\n // Remove preview if no nearby shape\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n }\n\n // Check for frame containment while drawing (but don't apply clipping yet)\n shapes.forEach(frame => {\n if (frame.shapeName === 'frame') {\n if (frame.isShapeInFrame(currentArrow)) {\n frame.highlightFrame();\n hoveredFrameArrow = frame;\n } else if (hoveredFrameArrow === frame) {\n frame.removeHighlight();\n hoveredFrameArrow = null;\n }\n }\n });\n\n // Update control points for curved arrows during drawing\n if (currentArrow.arrowCurved) {\n currentArrow.initializeCurveControlPoints();\n }\n currentArrow.draw();\n }\n\n else if (isDragging && currentShape && currentShape.isSelected) {\n const dx = x - startX;\n const dy = y - startY;\n currentShape.move(dx, dy);\n startX = x;\n startY = y;\n\n // Issue #24 bug #4: track containing frame during drag of an\n // existing arrow so mouseUp re-parents correctly. Without this\n // hoveredFrameArrow stays null and the arrow is detached the\n // moment the user nudges it inside its own parent frame.\n let newHover = null;\n for (const f of shapes) {\n if (f.shapeName !== 'frame') continue;\n if (f === currentShape) continue;\n if (typeof f.isShapeInFrame === 'function' && f.isShapeInFrame(currentShape)) {\n newHover = f;\n break;\n }\n }\n if (hoveredFrameArrow && hoveredFrameArrow !== newHover && typeof hoveredFrameArrow.removeHighlight === 'function') {\n hoveredFrameArrow.removeHighlight();\n }\n if (newHover && newHover !== hoveredFrameArrow && typeof newHover.highlightFrame === 'function') {\n newHover.highlightFrame();\n }\n hoveredFrameArrow = newHover;\n\n // Snap guides\n if (window.__sketchStoreApi && window.__sketchStoreApi.getState().snapToObjects) {\n const snap = calculateSnap(currentShape, e.shiftKey, e.clientX, e.clientY);\n if (snap.dx || snap.dy) {\n currentShape.move(snap.dx, snap.dy);\n }\n } else {\n clearSnapGuides();\n }\n\n svg.style.cursor = 'grabbing';\n } else if (isSelectionToolActive && currentShape && currentShape.isSelected) {\n // Provide visual feedback when hovering over anchors or the arrow\n const anchorInfo = currentShape.isNearAnchor(x, y);\n if (anchorInfo) {\n svg.style.cursor = 'grab';\n } else if (currentShape.contains(x, y)) {\n svg.style.cursor = 'move';\n } else {\n svg.style.cursor = 'default';\n }\n } else if (isSelectionToolActive) {\n // Check if hovering over any selectable arrow\n let hoveringOverArrow = false;\n for (let i = shapes.length - 1; i >= 0; i--) {\n const shape = shapes[i];\n if (shape instanceof Arrow && shape.contains(x, y)) {\n hoveringOverArrow = true;\n break;\n }\n }\n svg.style.cursor = hoveringOverArrow ? 'pointer' : 'default';\n }\n};\n\nconst handleMouseUp = (e) => {\nif (isDrawingArrow && currentArrow) {\n // Remove any attachment preview that might still be visible\n const existingPreview = svg.querySelector('.attachment-preview');\n if (existingPreview) existingPreview.remove();\n\n // Check if arrow is too small\n const dx = currentArrow.endPoint.x - currentArrow.startPoint.x;\n const dy = currentArrow.endPoint.y - currentArrow.startPoint.y;\n const lengthSq = dx * dx + dy * dy;\n\n if (lengthSq < (5 / currentZoom) ** 2) {\n shapes.pop();\n if (currentArrow.group.parentNode) {\n currentArrow.group.parentNode.removeChild(currentArrow.group);\n }\n currentArrow = null;\n currentShape = null;\n } else {\n const startAttachment = Arrow.findNearbyShape(currentArrow.startPoint);\n const endAttachment = Arrow.findNearbyShape(currentArrow.endPoint);\n\n if (startAttachment) {\n currentArrow.attachToShape(true, startAttachment.shape, startAttachment.attachment);\n }\n\n if (endAttachment) {\n currentArrow.attachToShape(false, endAttachment.shape, endAttachment.attachment);\n }\n\n // Check for frame containment and track attachment\n const finalFrame = hoveredFrameArrow;\n if (finalFrame) {\n finalFrame.addShapeToFrame(currentArrow);\n // Track the attachment for undo\n pushFrameAttachmentAction(finalFrame, currentArrow, 'attach', null);\n }\n\n // Push create action for undo/redo\n pushCreateAction(currentArrow);\n\n // Auto-select the drawn arrow and switch to selection tool\n const drawnArrow = currentArrow;\n if (window.__sketchStoreApi) window.__sketchStoreApi.setActiveTool('select', { afterDraw: true });\n currentShape = drawnArrow;\n drawnArrow.selectArrow();\n }\n\n // Clear frame highlighting\n if (hoveredFrameArrow) {\n hoveredFrameArrow.removeHighlight();\n hoveredFrameArrow = null;\n }\n\n currentArrow = null;\n}\n\nif (isDragging && dragOldPosArrow && currentShape) {\n // Issue #34 bug #2: containment transfer happens later in this block,\n // so currentShape.parentFrame is still the OLD frame here. hoveredFrameArrow\n // tracks the actual destination during mousemove \u2014 use that as the truth.\n const newPos = {\n startPoint: { x: currentShape.startPoint.x, y: currentShape.startPoint.y },\n endPoint: { x: currentShape.endPoint.x, y: currentShape.endPoint.y },\n parentFrame: hoveredFrameArrow || null,\n };\n const oldPos = {\n ...dragOldPosArrow,\n parentFrame: draggedShapeInitialFrameArrow // Add this line\n };\n \n const stateChanged = dragOldPosArrow.startPoint.x !== newPos.startPoint.x ||\n dragOldPosArrow.startPoint.y !== newPos.startPoint.y ||\n dragOldPosArrow.endPoint.x !== newPos.endPoint.x ||\n dragOldPosArrow.endPoint.y !== newPos.endPoint.y;\n \n const frameChanged = oldPos.parentFrame !== newPos.parentFrame;\n\n if (stateChanged || frameChanged) {\n pushTransformAction(currentShape, oldPos, newPos);\n }\n \n // Handle frame containment changes after drag\n if (isDragging) {\n const finalFrame = hoveredFrameArrow;\n \n // If shape moved to a different frame\n if (draggedShapeInitialFrameArrow !== finalFrame) {\n // Remove from initial frame\n if (draggedShapeInitialFrameArrow) {\n draggedShapeInitialFrameArrow.removeShapeFromFrame(currentShape);\n }\n \n // Add to new frame\n if (finalFrame) {\n finalFrame.addShapeToFrame(currentShape);\n }\n \n // Track the frame change for undo\n if (frameChanged) {\n pushFrameAttachmentAction(finalFrame || draggedShapeInitialFrameArrow, currentShape, \n finalFrame ? 'attach' : 'detach', draggedShapeInitialFrameArrow);\n }\n } else if (draggedShapeInitialFrameArrow) {\n // Shape stayed in same frame, restore clipping\n draggedShapeInitialFrameArrow.restoreToFrame(currentShape);\n }\n }\n \n draggedShapeInitialFrameArrow = null;\n dragOldPosArrow = null;\n}\n\n// Clear frame highlighting\nif (hoveredFrameArrow) {\n hoveredFrameArrow.removeHighlight();\n hoveredFrameArrow = null;\n}\n\nclearSnapGuides();\nisDrawingArrow = false;\nisResizing = false;\nisDragging = false;\nactiveAnchor = null;\nsvg.style.cursor = 'default';\n};\n\n// Remove old event listeners and add new ones\nsvg.removeEventListener('pointerdown', handleMouseDown);\nsvg.removeEventListener('pointermove', handleMouseMove);\nsvg.removeEventListener('pointerup', handleMouseUp);\n\n\n// Updated style handlers with undo/redo support\nconst updateSelectedArrowStyle = (styleChanges) => {\n if (currentShape instanceof Arrow && currentShape.isSelected) {\n const oldOptions = {\n ...currentShape.options,\n arrowOutlineStyle: currentShape.arrowOutlineStyle,\n arrowHeadStyle: currentShape.arrowHeadStyle,\n arrowCurved: currentShape.arrowCurved,\n arrowCurveAmount: currentShape.arrowCurveAmount\n };\n currentShape.updateStyle(styleChanges);\n pushOptionsChangeAction(currentShape, oldOptions);\n } else {\n if (styleChanges.stroke !== undefined) arrowStrokeColor = styleChanges.stroke;\n if (styleChanges.strokeWidth !== undefined) arrowStrokeThickness = styleChanges.strokeWidth;\n if (styleChanges.arrowOutlineStyle !== undefined) arrowOutlineStyle = styleChanges.arrowOutlineStyle;\n if (styleChanges.arrowHeadStyle !== undefined) arrowHeadStyle = styleChanges.arrowHeadStyle;\n if (styleChanges.arrowCurved !== undefined) arrowCurved = styleChanges.arrowCurved;\n if (styleChanges.arrowCurveAmount !== undefined) arrowCurveAmount = styleChanges.arrowCurveAmount;\n }\n};\n\narrowStrokeColorOptions.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowStrokeColorOptions.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newColor = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ stroke: newColor });\n });\n});\n\narrowStrokeThicknessValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowStrokeThicknessValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newThickness = parseInt(span.getAttribute(\"data-id\"));\n updateSelectedArrowStyle({ strokeWidth: newThickness });\n });\n});\n\narrowOutlineStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowOutlineStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newStyle = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ arrowOutlineStyle: newStyle });\n });\n});\n\narrowTypeStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowTypeStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n updateSelectedArrowStyle({ arrowCurved: span.getAttribute(\"data-id\") });\n });\n});\n\narrowCurveAmountOptions.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowCurveAmountOptions.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n updateSelectedArrowStyle({ arrowCurveAmount: parseInt(span.getAttribute(\"data-id\")) });\n });\n});\n\narrowHeadStyleValue.forEach((span) => {\n span.addEventListener(\"click\", (event) => {\n event.stopPropagation();\n arrowHeadStyleValue.forEach((el) => el.classList.remove(\"selected\"));\n span.classList.add(\"selected\");\n const newHeadStyle = span.getAttribute(\"data-id\");\n updateSelectedArrowStyle({ arrowHeadStyle: newHeadStyle });\n });\n});\n\nfunction detachSelectedArrow() {\n if (currentShape instanceof Arrow && currentShape.isSelected) {\n if (currentShape.attachedToStart || currentShape.attachedToEnd) {\n const oldState = {\n attachedToStart: currentShape.attachedToStart,\n attachedToEnd: currentShape.attachedToEnd,\n startPoint: { ...currentShape.startPoint },\n endPoint: { ...currentShape.endPoint }\n };\n\n currentShape.detachFromShape(true);\n currentShape.detachFromShape(false);\n currentShape.draw();\n\n // Add to undo/redo if needed\n }\n }\n}\n\nfunction updateAttachedArrows(shape) {\n if (!shape) return;\n\n // If a DOM element was passed (e.g. from text/code/image move), find the wrapper\n let targetShape = shape;\n if (shape.nodeType) {\n targetShape = shapes.find(s => s.group === shape || s.element === shape) || shape;\n }\n\n shapes.forEach(arrowShape => {\n if (arrowShape instanceof Arrow) {\n let needsUpdate = false;\n if (arrowShape.attachedToStart && arrowShape.attachedToStart.shape === targetShape) {\n needsUpdate = true;\n }\n if (arrowShape.attachedToEnd && arrowShape.attachedToEnd.shape === targetShape) {\n needsUpdate = true;\n }\n\n if (needsUpdate) {\n arrowShape.updateAttachments();\n }\n }\n });\n}\n\nfunction cleanupAttachments(deletedShape) {\n if (!deletedShape) return;\n\n // If a DOM element was passed, find the wrapper\n let targetShape = deletedShape;\n if (deletedShape.nodeType) {\n targetShape = shapes.find(s => s.group === deletedShape || s.element === deletedShape) || deletedShape;\n }\n\n shapes.forEach(shape => {\n if (shape instanceof Arrow) {\n let needsDraw = false;\n if (shape.attachedToStart && shape.attachedToStart.shape === targetShape) {\n shape.detachFromShape(true);\n needsDraw = true;\n }\n if (shape.attachedToEnd && shape.attachedToEnd.shape === targetShape) {\n shape.detachFromShape(false);\n needsDraw = true;\n }\n if (needsDraw) {\n shape.draw();\n }\n }\n });\n}\n\n// Add keyboard shortcut to detach arrows\ndocument.addEventListener('keydown', (e) => {\n if (e.key.toLowerCase() === 'd' && e.ctrlKey) {\n e.preventDefault();\n detachSelectedArrow();\n }\n});\n\n// Expose arrow tool settings on window for React sidebar bridge\nwindow.arrowToolSettings = {\n get strokeColor() { return arrowStrokeColor; },\n set strokeColor(v) { arrowStrokeColor = v; },\n get strokeWidth() { return arrowStrokeThickness; },\n set strokeWidth(v) { arrowStrokeThickness = v; },\n get outlineStyle() { return arrowOutlineStyle; },\n set outlineStyle(v) { arrowOutlineStyle = v; },\n get headStyle() { return arrowHeadStyle; },\n set headStyle(v) { arrowHeadStyle = v; },\n get arrowCurved() { return arrowCurved; },\n set arrowCurved(v) { arrowCurved = v; },\n get curveAmount() { return arrowCurveAmount; },\n set curveAmount(v) { arrowCurveAmount = v; },\n};\nwindow.updateSelectedArrowStyle = updateSelectedArrowStyle;\n\n// Export the cleanup function\n// Expose cleanupAttachments globally for centralized delete\nwindow.cleanupAttachments = cleanupAttachments;\n\nexport {\n handleMouseDown as handleMouseDownArrow,\n handleMouseMove as handleMouseMoveArrow,\n handleMouseUp as handleMouseUpArrow,\n cleanupAttachments,\n updateAttachedArrows\n};\n"],
|
|
5
5
|
"mappings": "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",
|
|
6
6
|
"names": ["svg", "shapes"]
|
|
7
7
|
}
|
|
@@ -10,14 +10,14 @@ import {
|
|
|
10
10
|
setCodeLanguage,
|
|
11
11
|
updateCodeBackground,
|
|
12
12
|
wrapCodeElement
|
|
13
|
-
} from "./chunk-
|
|
13
|
+
} from "./chunk-CWE5IFG7.js";
|
|
14
14
|
import {
|
|
15
15
|
registerRotationAnchor
|
|
16
|
-
} from "./chunk-
|
|
16
|
+
} from "./chunk-MS4TIQ6Z.js";
|
|
17
17
|
import {
|
|
18
18
|
cleanupAttachments,
|
|
19
19
|
updateAttachedArrows
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-2U47AU6Y.js";
|
|
21
21
|
import {
|
|
22
22
|
pushCreateAction,
|
|
23
23
|
pushDeleteActionWithAttachments,
|
|
@@ -26,12 +26,12 @@ import {
|
|
|
26
26
|
pushTransformAction,
|
|
27
27
|
setTextReferences,
|
|
28
28
|
updateSelectedElement
|
|
29
|
-
} from "./chunk-
|
|
29
|
+
} from "./chunk-TFCBCWL5.js";
|
|
30
30
|
|
|
31
31
|
// src/tools/textTool.js
|
|
32
32
|
function getThemeStroke() {
|
|
33
33
|
if (typeof document === "undefined") return "#fff";
|
|
34
|
-
return document.body && document.body.classList.contains("theme-dark") ? "#fff" : "#
|
|
34
|
+
return document.body && document.body.classList.contains("theme-dark") ? "#fff" : "#000000";
|
|
35
35
|
}
|
|
36
36
|
var textSize = "20px";
|
|
37
37
|
var textFont = "lixFont";
|
|
@@ -372,7 +372,7 @@ function createSelectionFeedback(groupElement) {
|
|
|
372
372
|
selectionBox.setAttribute("fill", "none");
|
|
373
373
|
selectionBox.setAttribute("stroke", "#5B57D1");
|
|
374
374
|
selectionBox.setAttribute("stroke-width", "1.5");
|
|
375
|
-
selectionBox.setAttribute("stroke-dasharray",
|
|
375
|
+
selectionBox.setAttribute("stroke-dasharray", "4 2");
|
|
376
376
|
selectionBox.setAttribute("vector-effect", "non-scaling-stroke");
|
|
377
377
|
selectionBox.setAttribute("pointer-events", "none");
|
|
378
378
|
groupElement.appendChild(selectionBox);
|
|
@@ -1516,4 +1516,4 @@ export {
|
|
|
1516
1516
|
handleTextMouseUp,
|
|
1517
1517
|
updateCodeToggleForShape
|
|
1518
1518
|
};
|
|
1519
|
-
//# sourceMappingURL=chunk-
|
|
1519
|
+
//# sourceMappingURL=chunk-75OPJOWN.js.map
|