@mx-sose-front/mx-sose-graph 1.1.8 → 1.2.1
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/assets/edgeWorker-b57ca007.js +2 -0
- package/dist/assets/edgeWorker-b57ca007.js.map +1 -0
- package/dist/index.d.ts +994 -31
- package/dist/index.esm.js +9541 -5145
- package/dist/index.esm.js.map +1 -1
- package/dist/index.umd.js +1 -1
- package/dist/index.umd.js.map +1 -1
- package/dist/style.css +1 -1
- package/package.json +1 -1
- package/src/components/Common/Tree.vue +451 -0
- package/src/components/Common/index.ts +2 -0
- package/src/components/DiagramListTooltip/DiagramListTooltip.vue +1 -2
- package/src/components/Edge/Edge.vue +172 -169
- package/src/components/Gantt/Gantt.vue +1544 -0
- package/src/components/GanttContextMenu/GanttContextMenu.vue +304 -0
- package/src/components/InteractionLayer.vue +343 -147
- package/src/components/Matrix/Matrix.vue +808 -0
- package/src/components/Matrix/index.ts +168 -0
- package/src/components/Shape/ConceptualRole.vue +2 -34
- package/src/components/Table/Table.vue +1193 -0
- package/src/constants/edgeShapeKeys.ts +8 -5
- package/src/constants/index.ts +279 -51
- package/src/hooks/index.ts +2 -0
- package/src/hooks/useChartRowSelection.ts +456 -0
- package/src/hooks/useResize.ts +2 -2
- package/src/hooks/useVirtualScroll.ts +258 -0
- package/src/index.ts +1 -1
- package/src/render/shape-renderer.ts +62 -2
- package/src/statics/icons/childIcons/AV-1/346/246/202/350/277/260/344/270/216/346/221/230/350/246/201/344/277/241/346/201/257/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/AV-1/346/246/202/350/277/260/346/221/230/350/246/201/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/AV-2/351/233/206/346/210/220/345/255/227/345/205/270/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/AV-2/351/233/206/346/210/220/345/255/227/345/205/270/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-1/346/204/277/346/231/257/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-1/346/204/277/346/231/257/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-2/350/203/275/345/212/233/345/210/206/347/261/273/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-2/350/203/275/345/212/233/345/210/206/347/261/273/345/233/276@3x-2.png +0 -0
- package/src/statics/icons/childIcons/CV-2/350/203/275/345/212/233/345/210/206/347/261/273/345/233/276@3x-3.png +0 -0
- package/src/statics/icons/childIcons/CV-2/350/203/275/345/212/233/345/210/206/347/261/273/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-3/350/203/275/345/212/233/345/210/206/346/256/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-3/350/203/275/345/212/233/351/230/266/346/256/265/347/224/230/347/211/271/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-4/350/203/275/345/212/233/344/276/235/350/265/226/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-4/350/203/275/345/212/233/344/276/235/350/265/226/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-5/350/203/275/345/212/233/345/210/260/347/273/204/347/273/207/347/232/204/345/274/200/345/217/221/346/230/240/345/260/204/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-5/350/203/275/345/212/233/345/210/260/347/273/204/347/273/207/347/232/204/346/230/240/345/260/204/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-6/350/203/275/345/212/233/345/210/260/344/270/232/345/212/241/346/264/273/345/212/250/346/230/240/345/260/204/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-6/350/203/275/345/212/233/345/210/260/344/275/234/346/210/230/346/264/273/345/212/250/347/232/204/346/230/240/345/260/204/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-7/350/203/275/345/212/233/345/210/260/346/234/215/345/212/241/346/230/240/345/260/204/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/CV-7/350/203/275/345/212/233/345/210/260/346/234/215/345/212/241/347/232/204/346/230/240/345/260/204/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/DIV-1/346/246/202/345/277/265/346/225/260/346/215/256/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/DIV-1/346/246/202/345/277/265/346/225/260/346/215/256/346/250/241/345/236/213/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/DIV-2/351/200/273/350/276/221/346/225/260/346/215/256/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/DIV-2/351/200/273/350/276/221/346/225/260/346/215/256/346/250/241/345/236/213/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/DIV-3/347/211/251/347/220/206/346/225/260/346/215/256/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-1/350/207/252/347/224/261/345/210/206/347/261/273/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-1/351/253/230/347/272/247/344/275/234/346/210/230/346/246/202/345/277/265/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-1/351/253/230/347/272/247/344/275/234/346/210/230/346/246/202/345/277/265/345/233/276/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-2/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/345/206/205/351/203/250/346/217/217/350/277/260/345/233/276@3x-2.png +0 -0
- package/src/statics/icons/childIcons/OV-2/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/345/206/205/351/203/250/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-2/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-2/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-3/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-3/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-3/345/237/272/347/241/200/350/247/222/350/211/262/344/275/234/346/210/230/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-4/347/273/204/347/273/207/345/205/263/347/263/273/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-4/347/273/204/347/273/207/345/205/263/347/263/273/345/233/276/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-5a/344/275/234/346/210/230/346/264/273/345/212/250/345/210/206/350/247/243/346/240/221/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-5a/344/275/234/346/210/230/346/264/273/345/212/250/345/210/206/350/247/243/346/240/221/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-5b/344/275/234/346/210/230/346/264/273/345/212/250/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-5b/344/275/234/346/210/230/346/264/273/345/212/250/346/250/241/345/236/213/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6a/344/275/234/346/210/230/350/247/204/345/210/231/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6a/344/275/234/346/210/230/350/265/204/346/272/220/345/217/202/346/225/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6b/347/212/266/346/200/201/350/275/254/346/215/242/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6b/347/212/266/346/200/201/350/275/254/346/215/242/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6c/344/272/213/344/273/266/350/277/275/350/270/252/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/OV-6c/344/275/234/346/210/230/344/272/213/344/273/266/350/267/237/350/270/252/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-1/351/241/271/347/233/256/347/273/204/345/220/210/345/205/263/347/263/273/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-1/351/241/271/347/233/256/347/273/204/345/220/210/345/205/263/347/263/273/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-2/351/241/271/347/233/256/346/227/266/351/227/264/350/277/233/345/272/246/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-2/351/241/271/347/233/256/346/227/266/351/227/264/350/277/233/345/272/246/347/224/230/347/211/271/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-3/351/241/271/347/233/256/344/270/216/350/203/275/345/212/233/346/230/240/345/260/204/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/PV-3/351/241/271/347/233/256/344/270/216/350/203/275/345/212/233/347/232/204/346/230/240/345/260/204/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-1 /347/263/273/347/273/237/346/216/245/345/217/243/345/206/205/351/203/250/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-1 /347/263/273/347/273/237/346/216/245/345/217/243/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10a /347/263/273/347/273/237/345/217/202/346/225/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10a /347/263/273/347/273/237/350/247/204/345/210/231/346/250/241/345/236/213/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10a/347/263/273/347/273/237/350/247/204/345/210/231/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10b /347/263/273/347/273/237/347/212/266/346/200/201/350/275/254/346/215/242/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10b/347/263/273/347/273/237/347/212/266/346/200/201/350/275/254/346/215/242/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10c /347/263/273/347/273/237/344/272/213/344/273/266/350/267/237/350/270/252/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-10c/347/263/273/347/273/237/344/272/213/344/273/266-/350/277/275/350/270/252/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-1/347/263/273/347/273/237/346/216/245/345/217/243/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-2 /347/263/273/347/273/237/345/206/205/351/203/250/350/265/204/346/272/220/346/265/201/345/212/250/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-2 /347/263/273/347/273/237/350/265/204/346/272/220/346/265/201/345/212/250/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-2/347/263/273/347/273/237/350/265/204/346/272/220/346/265/201/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-3 /347/263/273/347/273/237 - /347/263/273/347/273/237/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-3/347/263/273/347/273/237-/347/263/273/347/273/237/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-4 /347/263/273/347/273/237/345/212/237/350/203/275/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-4 /347/263/273/347/273/237/345/212/237/350/203/275/346/265/201/347/250/213/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-4/347/263/273/347/273/237/345/212/237/350/203/275/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-5a /344/270/232/345/212/241/346/264/273/345/212/250/345/210/260/347/263/273/347/273/237/345/212/237/350/203/275/347/232/204/345/217/257/350/277/275/346/272/257/346/200/247/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-5a/344/275/234/346/210/230/346/264/273/345/212/250/345/210/260/347/263/273/347/273/237/345/212/237/350/203/275/345/217/257/350/277/275/350/270/252/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-5b /344/270/232/345/212/241/346/264/273/345/212/250/345/210/260/347/263/273/347/273/237/347/232/204/345/217/257/350/277/275/346/272/257/346/200/247/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-5b/344/275/234/346/210/230/346/264/273/345/212/250/345/210/260/347/263/273/347/273/237/345/217/257/350/277/275/350/270/252/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-6 /347/263/273/347/273/237/350/265/204/346/272/220/346/265/201/345/212/250/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-6/347/263/273/347/273/237/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-7 /347/263/273/347/273/237/345/256/236/351/231/205/345/272/246/351/207/217/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-7/347/263/273/347/273/237/345/272/246/351/207/217/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-8 /347/263/273/347/273/237/346/274/224/350/277/233/346/217/217/350/277/260/347/224/230/347/211/271/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-8/347/263/273/347/273/237/346/274/224/350/277/233/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-9 /347/263/273/347/273/237/346/212/200/346/234/257/344/270/216/346/212/200/350/203/275/351/242/204/346/265/213/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/SV-9/347/263/273/347/273/237/346/212/200/346/234/257/344/270/216/346/212/200/350/203/275/351/242/204/346/265/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/StdV-1 /346/240/207/345/207/206/351/205/215/347/275/256/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/StdV-1/346/240/207/345/207/206/351/205/215/347/275/256/346/226/207/344/273/266/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/StdV-2 /346/240/207/345/207/206/351/242/204/346/265/213/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/StdV-2/346/240/207/345/207/206/351/242/204/346/265/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10a /346/234/215/345/212/241/345/217/202/346/225/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10a/346/234/215/345/212/241/350/247/204/345/210/231/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10b /346/234/215/345/212/241/347/212/266/346/200/201/350/275/254/346/215/242/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10b/346/234/215/345/212/241/347/212/266/346/200/201/350/275/254/346/215/242/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10c /346/234/215/345/212/241/344/272/213/344/273/266/350/267/237/350/270/252/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-10c/346/234/215/345/212/241/344/272/213/344/273/266-/350/277/275/350/270/252/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-1/346/234/215/345/212/241/344/270/212/344/270/213/346/226/207/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-1/346/234/215/345/212/241/350/203/214/346/231/257/346/250/241/345/236/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-2 /346/234/215/345/212/241/350/265/204/346/272/220/346/265/201/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-2/346/234/215/345/212/241/350/265/204/346/272/220/346/265/201/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-3a /347/263/273/347/273/237 -/346/234/215/345/212/241/347/237/251/351/230/265@3x-2.png +0 -0
- package/src/statics/icons/childIcons/SvcV-3a /347/263/273/347/273/237 -/346/234/215/345/212/241/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-3a/347/263/273/347/273/237-/346/234/215/345/212/241/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-3b/346/234/215/345/212/241-/346/234/215/345/212/241/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-4 /346/234/215/345/212/241/345/212/237/350/203/275/346/217/217/350/277/260/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-4 /346/234/215/345/212/241/345/212/237/350/203/275/346/265/201/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-4/346/234/215/345/212/241/345/212/237/350/203/275/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-5/344/275/234/346/210/230/346/264/273/345/212/250/345/210/260/346/234/215/345/212/241/345/217/257/350/277/275/350/270/252/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-6 /346/234/215/345/212/241/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-6/346/234/215/345/212/241/350/265/204/346/272/220/346/265/201/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-7 /346/234/215/345/212/241/345/205/270/345/236/213/345/272/246/351/207/217/347/237/251/351/230/265@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-7/346/234/215/345/212/241/345/272/246/351/207/217/347/237/251/351/230/265/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-8 /346/234/215/345/212/241/346/274/224/350/277/233/347/224/230/347/211/271/345/233/276@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-8/346/234/215/345/212/241/346/274/224/350/277/233/346/217/217/350/277/260/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-9 /346/234/215/345/212/241/346/212/200/346/234/257/344/270/216/346/212/200/350/203/275/351/242/204/346/265/213/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons/SvcV-9/346/234/215/345/212/241/346/212/200/346/234/257/344/270/216/346/212/200/350/203/275/351/242/204/346/265/213/345/214/205@3x.png +0 -0
- package/src/statics/icons/childIcons//344/275/223/347/263/273/346/236/266/346/236/204@3x.png +0 -0
- package/src/statics/icons/childIcons//344/275/234/346/210/230/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//345/205/250/346/231/257/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//345/205/254/345/217/270@3x.png +0 -0
- package/src/statics/icons/childIcons//345/215/217/350/256/256@3x.png +0 -0
- package/src/statics/icons/childIcons//345/215/217/350/256/256/345/261/202@3x.png +0 -0
- package/src/statics/icons/childIcons//345/215/217/350/256/256/346/240/210@3x.png +0 -0
- package/src/statics/icons/childIcons//345/221/275/344/273/244@3x.png +0 -0
- package/src/statics/icons/childIcons//346/210/230/347/225/245/346/246/202/345/277/265/350/241/250@3x.png +0 -0
- package/src/statics/icons/childIcons//346/216/247/345/210/266@3x.png +0 -0
- package/src/statics/icons/childIcons//346/224/257/346/214/201@3x.png +0 -0
- package/src/statics/icons/childIcons//346/225/260/346/215/256/344/277/241/346/201/257/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//346/234/215/345/212/241/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//346/240/207/345/207/206@3x.png +0 -0
- package/src/statics/icons/childIcons//346/240/207/345/207/206/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//347/263/273/347/273/237/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//350/203/275/345/212/233/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/childIcons//351/241/271/347/233/256/350/247/206/350/247/222@3x.png +0 -0
- package/src/statics/icons/createMenu/down.png +0 -0
- package/src/statics/icons/createMenu/remove.png +0 -0
- package/src/statics/icons/createMenu/up.png +0 -0
- package/src/store/graphStore.ts +238 -45
- package/src/types/index.ts +87 -4
- package/src/utils/batchAutoExpand.ts +9 -10
- package/src/utils/containers.ts +72 -17
- package/src/utils/contextMenuUtils.ts +7 -7
- package/src/utils/dateUtils.ts +160 -0
- package/src/utils/diagram.ts +10 -8
- package/src/utils/drag.ts +6 -5
- package/src/utils/edgeUtils.ts +344 -427
- package/src/utils/edgeWorker.ts +471 -0
- package/src/utils/hittest.ts +37 -38
- package/src/utils/index.ts +3 -0
- package/src/utils/keyboardUtils.ts +5 -5
- package/src/utils/packageOutline.ts +96 -0
- package/src/utils/rafThrottle.ts +162 -0
- package/src/utils/workerManager.ts +335 -0
- package/src/view/graph.vue +47 -33
- /package/src/statics/icons/childIcons//346/210/230/347/225/{245@3x.png" → 245/345/261/202@3x.png"} +0 -0
|
@@ -11,7 +11,21 @@
|
|
|
11
11
|
@model-type-property-id-click="clickModelTypePropertyIdButton" />
|
|
12
12
|
</template>
|
|
13
13
|
<!-- 命中容器的高亮矩形(虚线框) -->
|
|
14
|
-
<
|
|
14
|
+
<svg
|
|
15
|
+
v-if="hoverRect && hoverOutlineIsPackage"
|
|
16
|
+
:class="[
|
|
17
|
+
'hover-container-outline-svg',
|
|
18
|
+
{
|
|
19
|
+
'is-invalid': graphStore.hoverNestable === false,
|
|
20
|
+
'is-valid': graphStore.hoverNestable === true,
|
|
21
|
+
},
|
|
22
|
+
]"
|
|
23
|
+
:style="hoverPackageOutline.style"
|
|
24
|
+
:viewBox="`0 0 ${hoverPackageOutline.width} ${hoverPackageOutline.height}`"
|
|
25
|
+
>
|
|
26
|
+
<path class="outline-path" :d="hoverPackageOutline.path" />
|
|
27
|
+
</svg>
|
|
28
|
+
<div v-else-if="hoverRect" :class="[
|
|
15
29
|
'hover-container-outline',
|
|
16
30
|
{
|
|
17
31
|
'is-invalid': graphStore.hoverNestable === false,
|
|
@@ -51,7 +65,16 @@
|
|
|
51
65
|
</div>
|
|
52
66
|
|
|
53
67
|
<!-- 高亮覆盖层 - 独立于 connect-layer,支持连线模式和拖拽模式 -->
|
|
54
|
-
<
|
|
68
|
+
<svg
|
|
69
|
+
v-if="highlightOverlayBounds && highlightOverlayIsPackage"
|
|
70
|
+
class="highlight-overlay-svg"
|
|
71
|
+
:class="highlightOverlayColor"
|
|
72
|
+
:style="highlightPackageOutline.style"
|
|
73
|
+
:viewBox="`0 0 ${highlightPackageOutline.width} ${highlightPackageOutline.height}`"
|
|
74
|
+
>
|
|
75
|
+
<path class="outline-path" :d="highlightPackageOutline.path" />
|
|
76
|
+
</svg>
|
|
77
|
+
<div v-else-if="highlightOverlayBounds" class="highlight-overlay" :class="highlightOverlayColor" :style="{
|
|
55
78
|
left: highlightOverlayBounds.x + 'px',
|
|
56
79
|
top: highlightOverlayBounds.y + 'px',
|
|
57
80
|
width: highlightOverlayBounds.width + 'px',
|
|
@@ -84,6 +107,7 @@ import NameEditor from "./NameEditor/NameEditor.vue";
|
|
|
84
107
|
// 工具:几何/命中/样式/拖拽
|
|
85
108
|
import {
|
|
86
109
|
toLocalPoint,
|
|
110
|
+
inBounds,
|
|
87
111
|
getBounds,
|
|
88
112
|
getDiagramRect,
|
|
89
113
|
rectFromPoints,
|
|
@@ -95,7 +119,6 @@ import {
|
|
|
95
119
|
} from "../utils/geom";
|
|
96
120
|
import { pickTarget } from "../utils/hittest";
|
|
97
121
|
import {
|
|
98
|
-
adjustCanvasToFitAllShapes,
|
|
99
122
|
actionButtonsStyle,
|
|
100
123
|
getMarqueeStyle,
|
|
101
124
|
getLayerStyle,
|
|
@@ -120,6 +143,11 @@ import { useNameEdit } from "../hooks/useNameEdit";
|
|
|
120
143
|
import { guardOperate } from "../utils/license-guard";
|
|
121
144
|
import { useResize } from "../hooks/useResize";
|
|
122
145
|
import { useHighlight, type IHighlightUtils } from "../hooks/useHighlight";
|
|
146
|
+
import { createRAFThrottle, createRAFDebounce } from "../utils/rafThrottle";
|
|
147
|
+
import {
|
|
148
|
+
buildPackageOutlineOverlay,
|
|
149
|
+
PACKAGE_OUTLINE_PADDING,
|
|
150
|
+
} from "../utils/packageOutline";
|
|
123
151
|
|
|
124
152
|
const props = defineProps<InteractionLayerProps>();
|
|
125
153
|
|
|
@@ -138,7 +166,7 @@ const cursorStyle = ref<"default" | "pointer">("default");
|
|
|
138
166
|
const resizeGhostShadow = computed<Shape[]>(() => {
|
|
139
167
|
const out: Shape[] = [];
|
|
140
168
|
for (const id in groupGhost.value) {
|
|
141
|
-
const s = graphStore.
|
|
169
|
+
const s = graphStore.shapeMap.get(id);
|
|
142
170
|
if (!s) continue;
|
|
143
171
|
out.push({
|
|
144
172
|
...s,
|
|
@@ -152,11 +180,18 @@ const resizeGhostShadow = computed<Shape[]>(() => {
|
|
|
152
180
|
const hoverRect = computed(() => {
|
|
153
181
|
const id = graphStore.hoverContainerId;
|
|
154
182
|
if (!id) return null;
|
|
155
|
-
const s = graphStore.
|
|
183
|
+
const s = graphStore.shapeMap.get(id);
|
|
156
184
|
if (!s) return null;
|
|
157
185
|
const b = getBounds(s);
|
|
158
186
|
return { x: b.x, y: b.y, width: b.width, height: b.height };
|
|
159
187
|
});
|
|
188
|
+
|
|
189
|
+
// 当前 hover 到的原始容器图元,用来判断是否需要切换成包轮廓覆盖层。
|
|
190
|
+
const hoverOutlineShape = computed(() => {
|
|
191
|
+
const id = graphStore.hoverContainerId;
|
|
192
|
+
if (!id) return null;
|
|
193
|
+
return graphStore.shapeMap.get(id) ?? null;
|
|
194
|
+
});
|
|
160
195
|
// 把拖动缩放预览框合并,
|
|
161
196
|
const allGhosts = computed<Shape[]>(() => {
|
|
162
197
|
const byId = new Map<string, Shape>();
|
|
@@ -222,9 +257,10 @@ const { isResizing, groupGhost, startResize } = useResize(
|
|
|
222
257
|
|
|
223
258
|
// 是否在画布内
|
|
224
259
|
const isMouseInside = ref(false);
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
260
|
+
|
|
261
|
+
// 创建 RAF 节流实例用于鼠标移动事件
|
|
262
|
+
const mouseMoveThrottle = createRAFThrottle();
|
|
263
|
+
|
|
228
264
|
// 拖拽清理函数
|
|
229
265
|
let offDrag: (() => void) | null = null;
|
|
230
266
|
|
|
@@ -244,33 +280,30 @@ const emitMouse = (evt: MouseEvent, inside: boolean) => {
|
|
|
244
280
|
// 对外抛出
|
|
245
281
|
eventBus.emit("canvas-mouse-move", payload);
|
|
246
282
|
};
|
|
283
|
+
|
|
247
284
|
// 鼠标进入画布
|
|
248
285
|
const onMouseEnter = () => {
|
|
249
286
|
isMouseInside.value = true;
|
|
250
287
|
eventBus.emit("canvas-mouse-enter", { inside: true });
|
|
251
288
|
};
|
|
289
|
+
|
|
252
290
|
// 鼠标离开画布区域
|
|
253
291
|
const onMouseLeave = () => {
|
|
254
292
|
isMouseInside.value = false;
|
|
255
|
-
//
|
|
256
|
-
|
|
257
|
-
rafId = null;
|
|
258
|
-
latestEvt = null;
|
|
293
|
+
// 取消待执行的 RAF
|
|
294
|
+
mouseMoveThrottle.cancel();
|
|
259
295
|
// 通知外部隐藏坐标
|
|
260
296
|
eventBus.emit("canvas-mouse-leave", { inside: false });
|
|
261
297
|
};
|
|
262
|
-
|
|
298
|
+
|
|
299
|
+
// 鼠标移动过程中 - 使用 RAF 节流优化
|
|
263
300
|
const onMouseMove = (evt: MouseEvent) => {
|
|
264
301
|
if (!isMouseInside.value) return;
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
if (rafId) return;
|
|
268
|
-
rafId = requestAnimationFrame(() => {
|
|
269
|
-
rafId = null;
|
|
302
|
+
// 使用 RAF 节流,同一帧内多次调用会合并为最后一次
|
|
303
|
+
mouseMoveThrottle.throttle((latestEvt: MouseEvent) => {
|
|
270
304
|
if (!latestEvt) return;
|
|
271
305
|
emitMouse(latestEvt, true);
|
|
272
|
-
|
|
273
|
-
});
|
|
306
|
+
})(evt);
|
|
274
307
|
};
|
|
275
308
|
|
|
276
309
|
// 框选状态
|
|
@@ -306,10 +339,95 @@ const highlightUtils: IHighlightUtils = {
|
|
|
306
339
|
// 保持兼容性:highlightedShape 计算属性
|
|
307
340
|
const highlightedShape = computed(() => {
|
|
308
341
|
if (!highlightedShapeId.value) return null;
|
|
309
|
-
return graphStore.
|
|
342
|
+
return graphStore.shapeMap.get(highlightedShapeId.value) ?? null;
|
|
310
343
|
});
|
|
344
|
+
|
|
345
|
+
// 包图元使用“文件夹轮廓”高亮,其他图元继续沿用默认矩形覆盖层。
|
|
346
|
+
const isPackageShape = (shape: Shape | null | undefined) => {
|
|
347
|
+
return !!shape?.shapeKey && !!props.packages?.includes(shape.shapeKey);
|
|
348
|
+
};
|
|
349
|
+
|
|
350
|
+
// 拖拽嵌套时,只有命中的容器是包图元才切换到 SVG 轮廓。
|
|
351
|
+
const hoverOutlineIsPackage = computed(() =>
|
|
352
|
+
isPackageShape(hoverOutlineShape.value),
|
|
353
|
+
);
|
|
354
|
+
|
|
355
|
+
// hover 覆盖层会额外向外扩一点,尽量保持和原矩形框接近的视觉反馈。
|
|
356
|
+
const hoverPackageOutline = computed(() =>
|
|
357
|
+
buildPackageOutlineOverlay({
|
|
358
|
+
bounds: hoverRect.value,
|
|
359
|
+
strokeWidth: 2,
|
|
360
|
+
padding: PACKAGE_OUTLINE_PADDING,
|
|
361
|
+
zIndex: 999,
|
|
362
|
+
}),
|
|
363
|
+
);
|
|
364
|
+
|
|
365
|
+
const highlightOverlayIsPackage = computed(() =>
|
|
366
|
+
isPackageShape(highlightedShape.value),
|
|
367
|
+
);
|
|
368
|
+
|
|
369
|
+
// 连线目标高亮复用同一套几何工具,只是描边更粗,且不额外外扩。
|
|
370
|
+
const highlightPackageOutline = computed(() =>
|
|
371
|
+
buildPackageOutlineOverlay({
|
|
372
|
+
bounds: highlightOverlayBounds.value,
|
|
373
|
+
strokeWidth: 3,
|
|
374
|
+
zIndex: 1001,
|
|
375
|
+
}),
|
|
376
|
+
);
|
|
377
|
+
|
|
378
|
+
const getCurrentTargetModels = () => {
|
|
379
|
+
if (connectMode.value === "action") {
|
|
380
|
+
return (
|
|
381
|
+
props.connectShapeData?.scenarioMenus?.find(
|
|
382
|
+
(menu) => menu.code === props.connectShapeData?.shapeKey
|
|
383
|
+
)?.targetModels ?? props.connectShapeData?.targetModels
|
|
384
|
+
);
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
return props.connectShapeData?.targetModels;
|
|
388
|
+
};
|
|
389
|
+
|
|
390
|
+
const resolveConnectTargetAtPoint = (pt: { x: number; y: number }) => {
|
|
391
|
+
const hit = pickTarget(graphStore.shapes, pt);
|
|
392
|
+
|
|
393
|
+
if (
|
|
394
|
+
["shape", "pin"].includes(hit.kind) &&
|
|
395
|
+
hit.shape?.id &&
|
|
396
|
+
hit.shape.id !== props.connectShapeData?.sourceId
|
|
397
|
+
) {
|
|
398
|
+
return hit.shape;
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
const hoveredShape = highlightedShape.value;
|
|
402
|
+
if (
|
|
403
|
+
!hoveredShape?.id ||
|
|
404
|
+
hoveredShape.id === props.connectShapeData?.sourceId
|
|
405
|
+
) {
|
|
406
|
+
return null;
|
|
407
|
+
}
|
|
408
|
+
|
|
409
|
+
const bounds = getBounds(hoveredShape);
|
|
410
|
+
const minSide = Math.min(bounds.width, bounds.height);
|
|
411
|
+
const padding = minSide <= 30 ? 8 : minSide <= 40 ? 6 : 0;
|
|
412
|
+
|
|
413
|
+
if (
|
|
414
|
+
inBounds(pt, {
|
|
415
|
+
x: bounds.x - padding,
|
|
416
|
+
y: bounds.y - padding,
|
|
417
|
+
width: bounds.width + padding * 2,
|
|
418
|
+
height: bounds.height + padding * 2,
|
|
419
|
+
})
|
|
420
|
+
) {
|
|
421
|
+
return hoveredShape;
|
|
422
|
+
}
|
|
423
|
+
|
|
424
|
+
return null;
|
|
425
|
+
};
|
|
426
|
+
|
|
311
427
|
const sourceShape = ref<Shape | null>(null);
|
|
312
428
|
const recordClickPoint = ref({ x: 0, y: 0 });
|
|
429
|
+
// 等待后端创建图元中,冻结连线预览
|
|
430
|
+
const pendingActionButton = ref(false);
|
|
313
431
|
|
|
314
432
|
// 正在交互:缩放中 或 元素拖动中
|
|
315
433
|
const isBusy = computed(
|
|
@@ -388,9 +506,9 @@ const onLayerClick = (evt: MouseEvent) => {
|
|
|
388
506
|
}
|
|
389
507
|
recordClickPoint.value = toLocalPoint(evt, layerRef.value);
|
|
390
508
|
// 获取 sourceShape(先获取,确保存在)
|
|
391
|
-
const foundSourceShape =
|
|
392
|
-
|
|
393
|
-
|
|
509
|
+
const foundSourceShape = props.connectShapeData?.sourceId
|
|
510
|
+
? graphStore.shapeMap.get(props.connectShapeData.sourceId)
|
|
511
|
+
: undefined;
|
|
394
512
|
if (!foundSourceShape) {
|
|
395
513
|
// 如果找不到 sourceShape,不处理
|
|
396
514
|
handleConnectLayerClick(evt);
|
|
@@ -404,11 +522,8 @@ const onLayerClick = (evt: MouseEvent) => {
|
|
|
404
522
|
const clickX = localPoint.x;
|
|
405
523
|
const clickY = localPoint.y;
|
|
406
524
|
|
|
407
|
-
|
|
408
|
-
const hasShapeAtPoint =
|
|
409
|
-
x: clickX,
|
|
410
|
-
y: clickY,
|
|
411
|
-
});
|
|
525
|
+
const clickedTargetShape = resolveConnectTargetAtPoint(localPoint);
|
|
526
|
+
const hasShapeAtPoint = !!clickedTargetShape;
|
|
412
527
|
|
|
413
528
|
// 修改:无论是否在action模式下,只要在连接状态且点击空白处,都创建新图元
|
|
414
529
|
if (!hasShapeAtPoint) {
|
|
@@ -465,9 +580,12 @@ const onLayerClick = (evt: MouseEvent) => {
|
|
|
465
580
|
y: newShapeY,
|
|
466
581
|
diagramId: diagramId,
|
|
467
582
|
});
|
|
583
|
+
// 冻结连线预览,避免等待后端返回期间预览线跟着鼠标走
|
|
584
|
+
pendingActionButton.value = true;
|
|
585
|
+
showLine.value = false;
|
|
468
586
|
return;
|
|
469
587
|
} else {
|
|
470
|
-
handleConnectLayerClick(evt);
|
|
588
|
+
handleConnectLayerClick(evt, clickedTargetShape, localPoint);
|
|
471
589
|
return;
|
|
472
590
|
}
|
|
473
591
|
}
|
|
@@ -611,16 +729,14 @@ const onLayerMouseDown = (evt: MouseEvent) => {
|
|
|
611
729
|
// 如果是 pin 类型,需要在移动过程中将“指针位置”校正为吸附后的指针坐标
|
|
612
730
|
let targetPt = curr;
|
|
613
731
|
if (ids.length === 1) {
|
|
614
|
-
const draggedShape = graphStore.
|
|
615
|
-
(x) => x.id === ids[0]
|
|
616
|
-
);
|
|
732
|
+
const draggedShape = graphStore.shapeMap.get(ids[0]);
|
|
617
733
|
if (
|
|
618
734
|
draggedShape &&
|
|
619
735
|
draggedShape.shapeType === "pin" &&
|
|
620
736
|
draggedShape.parenShapeId
|
|
621
737
|
) {
|
|
622
|
-
const parentShape = graphStore.
|
|
623
|
-
|
|
738
|
+
const parentShape = graphStore.shapeMap.get(
|
|
739
|
+
draggedShape.parenShapeId
|
|
624
740
|
);
|
|
625
741
|
if (parentShape) {
|
|
626
742
|
// 使用移动专用的吸附方法:根据 dragOffset 计算应传入 moveDraggedShape 的指针坐标
|
|
@@ -683,14 +799,9 @@ const startMarquee = (anchor: { x: number; y: number }) => {
|
|
|
683
799
|
//缓存 bounds,避免 move 中每次 getBounds(s)
|
|
684
800
|
b: getBounds(s),
|
|
685
801
|
}));
|
|
686
|
-
//
|
|
687
|
-
|
|
802
|
+
// 创建 RAF 节流实例用于框选
|
|
803
|
+
const marqueeThrottle = createRAFThrottle();
|
|
688
804
|
let latestPoint = anchorClamped;
|
|
689
|
-
const updateRect = () => {
|
|
690
|
-
raf = 0;
|
|
691
|
-
// 根据“锚点 & 当前点”得到框选矩形
|
|
692
|
-
marqueeRect.value = rectFromPoints(marqueeAnchor.value!, latestPoint);
|
|
693
|
-
};
|
|
694
805
|
// 拖拽生命周期
|
|
695
806
|
offDrag?.();
|
|
696
807
|
offDrag = null;
|
|
@@ -707,16 +818,16 @@ const startMarquee = (anchor: { x: number; y: number }) => {
|
|
|
707
818
|
edges
|
|
708
819
|
);
|
|
709
820
|
|
|
710
|
-
//
|
|
711
|
-
//
|
|
712
|
-
|
|
713
|
-
|
|
821
|
+
// 根据"锚点 & 当前点"得到框选矩形(会自动处理反向拖拽)
|
|
822
|
+
// 使用 RAF 节流更新,避免 mousemove 触发过多响应式刷新
|
|
823
|
+
marqueeThrottle.throttle(() => {
|
|
824
|
+
marqueeRect.value = rectFromPoints(marqueeAnchor.value!, latestPoint);
|
|
825
|
+
})();
|
|
714
826
|
},
|
|
715
827
|
// 结束框选,清理预览
|
|
716
828
|
() => {
|
|
717
|
-
//
|
|
718
|
-
|
|
719
|
-
updateRect();
|
|
829
|
+
// 刷新最后一次更新
|
|
830
|
+
marqueeThrottle.flush();
|
|
720
831
|
|
|
721
832
|
const rect = marqueeRect.value!;
|
|
722
833
|
const right = rect.x + rect.width;
|
|
@@ -763,6 +874,10 @@ const isConnectAllowed = ref(false);
|
|
|
763
874
|
// 处理右键点击事件
|
|
764
875
|
const handleContextMenu = (event: MouseEvent) => {
|
|
765
876
|
return guardOperate(async () => {
|
|
877
|
+
// 连线状态下不允许出现右键菜单
|
|
878
|
+
if (isConnecting.value) {
|
|
879
|
+
return;
|
|
880
|
+
}
|
|
766
881
|
// 如果图元正在移动或缩放,则不显示菜单
|
|
767
882
|
if (graphStore.isDragging || isResizing.value) {
|
|
768
883
|
return;
|
|
@@ -795,14 +910,6 @@ const closeMenu = () => {
|
|
|
795
910
|
contextMenuTarget.value = null;
|
|
796
911
|
};
|
|
797
912
|
|
|
798
|
-
watch(
|
|
799
|
-
() => graphStore.shapes,
|
|
800
|
-
() => {
|
|
801
|
-
nextTick(adjustCanvasToFitAllShapes);
|
|
802
|
-
},
|
|
803
|
-
{ deep: true, immediate: true }
|
|
804
|
-
);
|
|
805
|
-
|
|
806
913
|
// 监听图元状态
|
|
807
914
|
watch(shouldCloseMenu, (shouldClose) => {
|
|
808
915
|
if (shouldClose && showContextMenu.value) {
|
|
@@ -811,13 +918,13 @@ watch(shouldCloseMenu, (shouldClose) => {
|
|
|
811
918
|
});
|
|
812
919
|
watch(
|
|
813
920
|
() => props.actionButtonShapeDataId,
|
|
814
|
-
(newVal) => {
|
|
921
|
+
async (newVal) => {
|
|
815
922
|
if (newVal) {
|
|
816
|
-
const foundShape = graphStore.
|
|
923
|
+
const foundShape = graphStore.shapeMap.get(newVal);
|
|
817
924
|
if (foundShape) {
|
|
818
925
|
// 连接 sourceShape 和新 shape
|
|
819
926
|
if (sourceShape.value) {
|
|
820
|
-
const connectionData = EdgeUtils.
|
|
927
|
+
const connectionData = await EdgeUtils.completeConnectionAsync(
|
|
821
928
|
sourceShape.value,
|
|
822
929
|
foundShape,
|
|
823
930
|
{ x: recordClickPoint.value.x, y: recordClickPoint.value.y },
|
|
@@ -851,40 +958,54 @@ watch(
|
|
|
851
958
|
}
|
|
852
959
|
graphStore.setConnectMode("connect");
|
|
853
960
|
isConnecting.value = false;
|
|
961
|
+
pendingActionButton.value = false;
|
|
854
962
|
clearHighlightTimeout();
|
|
963
|
+
} else {
|
|
964
|
+
// connectionData 为 null(如源和目标相同),也需要重置
|
|
965
|
+
pendingActionButton.value = false;
|
|
855
966
|
}
|
|
967
|
+
} else {
|
|
968
|
+
pendingActionButton.value = false;
|
|
856
969
|
}
|
|
970
|
+
} else {
|
|
971
|
+
pendingActionButton.value = false;
|
|
857
972
|
}
|
|
858
973
|
// 处理 actionButtonShapeData 的逻辑
|
|
859
974
|
}
|
|
860
975
|
}
|
|
861
976
|
);
|
|
862
977
|
|
|
863
|
-
// 鼠标移动事件处理
|
|
978
|
+
// 鼠标移动事件处理 - 使用 RAF 节流优化
|
|
864
979
|
const handleMouseMove = (event: MouseEvent) => {
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
980
|
+
// 使用 RAF 节流,同一帧内多次调用会合并为最后一次
|
|
981
|
+
connectMouseMoveThrottle.throttle((evt: MouseEvent) => {
|
|
982
|
+
const { clientX, clientY } = evt;
|
|
983
|
+
const localPoint = toLocalPoint(evt, layerRef.value);
|
|
984
|
+
// 使用工具类检查是否在画布内
|
|
985
|
+
if (EdgeUtils.isWithinCanvas(clientX, clientY)) {
|
|
986
|
+
mousePosition.value = { x: localPoint.x, y: localPoint.y };
|
|
870
987
|
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
988
|
+
// 只有在连接状态下才显示线条
|
|
989
|
+
if (isConnecting.value && !pendingActionButton.value) {
|
|
990
|
+
showLine.value = true;
|
|
991
|
+
updateConnectPointToNearest(localPoint.x, localPoint.y);
|
|
992
|
+
checkHoverTarget(localPoint.x, localPoint.y);
|
|
993
|
+
}
|
|
994
|
+
} else {
|
|
995
|
+
if (isConnecting.value) {
|
|
996
|
+
showLine.value = false;
|
|
997
|
+
}
|
|
998
|
+
highlightShape(null, false); // 使用highlightShape函数取消高亮,恢复原始样式
|
|
880
999
|
}
|
|
881
|
-
|
|
882
|
-
}
|
|
1000
|
+
})(event);
|
|
883
1001
|
};
|
|
884
1002
|
|
|
885
1003
|
// 用于跟踪上一次的hoverShape,避免重复发射事件
|
|
886
1004
|
let lastHoverShapeId: string | null = null;
|
|
887
1005
|
|
|
1006
|
+
// 创建 RAF 节流实例用于连线时的鼠标移动
|
|
1007
|
+
const connectMouseMoveThrottle = createRAFThrottle();
|
|
1008
|
+
|
|
888
1009
|
// 用于防抖 edge-check 事件和高亮,只有鼠标停留一段时间后才触发
|
|
889
1010
|
let edgeCheckDebounceTimer: ReturnType<typeof setTimeout> | null = null;
|
|
890
1011
|
const EDGE_CHECK_DEBOUNCE_DELAY = 150; // 150ms 防抖延迟
|
|
@@ -904,12 +1025,7 @@ const checkHoverTarget = (x: number, y: number) => {
|
|
|
904
1025
|
|
|
905
1026
|
if (hoverShape) {
|
|
906
1027
|
// 检查连接有效性
|
|
907
|
-
|
|
908
|
-
if (connectMode.value === "action") {
|
|
909
|
-
targetModels = props.connectShapeData?.scenarioMenus?.find(
|
|
910
|
-
(menu) => menu.code === props.connectShapeData?.shapeKey
|
|
911
|
-
)?.targetModels;
|
|
912
|
-
}
|
|
1028
|
+
const targetModels = getCurrentTargetModels();
|
|
913
1029
|
let isAllowed = true;
|
|
914
1030
|
if (
|
|
915
1031
|
targetModels &&
|
|
@@ -921,8 +1037,8 @@ const checkHoverTarget = (x: number, y: number) => {
|
|
|
921
1037
|
}
|
|
922
1038
|
// 检查parenShapeId是否匹配(无论hoverShape是否改变都要检查)
|
|
923
1039
|
if (props.connectShapeData?.sourceId) {
|
|
924
|
-
const sourceShape = graphStore.
|
|
925
|
-
|
|
1040
|
+
const sourceShape = graphStore.shapeMap.get(
|
|
1041
|
+
props.connectShapeData.sourceId
|
|
926
1042
|
);
|
|
927
1043
|
if (
|
|
928
1044
|
sourceShape &&
|
|
@@ -1003,15 +1119,14 @@ const checkHoverTarget = (x: number, y: number) => {
|
|
|
1003
1119
|
const updateConnectPointToNearest = (mouseX: number, mouseY: number) => {
|
|
1004
1120
|
if (!props.connectShapeData?.sourceId || !props.diagramBounds) return;
|
|
1005
1121
|
|
|
1006
|
-
const sourceShape =
|
|
1007
|
-
|
|
1008
|
-
|
|
1122
|
+
const sourceShape = props.connectShapeData?.sourceId
|
|
1123
|
+
? graphStore.shapeMap.get(props.connectShapeData.sourceId)
|
|
1124
|
+
: undefined;
|
|
1009
1125
|
|
|
1010
|
-
//
|
|
1126
|
+
// 使用同步版本,避免 Worker 异步延迟导致连线跟不上鼠标
|
|
1011
1127
|
const nearestPoint = EdgeUtils.findNearestConnectPoint(
|
|
1012
1128
|
{ x: mouseX, y: mouseY },
|
|
1013
|
-
sourceShape
|
|
1014
|
-
props.diagramBounds
|
|
1129
|
+
sourceShape
|
|
1015
1130
|
);
|
|
1016
1131
|
|
|
1017
1132
|
if (
|
|
@@ -1061,30 +1176,47 @@ watch(
|
|
|
1061
1176
|
);
|
|
1062
1177
|
|
|
1063
1178
|
// 处理连接层点击事件
|
|
1064
|
-
const handleConnectLayerClick = (
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1179
|
+
const handleConnectLayerClick = (
|
|
1180
|
+
event: MouseEvent,
|
|
1181
|
+
resolvedShape?: Shape | null,
|
|
1182
|
+
localPointArg?: { x: number; y: number }
|
|
1183
|
+
) => {
|
|
1184
|
+
const localPoint = localPointArg ?? toLocalPoint(event, layerRef.value);
|
|
1185
|
+
const clickedShape = resolvedShape ?? resolveConnectTargetAtPoint(localPoint);
|
|
1068
1186
|
|
|
1069
|
-
if (
|
|
1070
|
-
["shape", "pin"].includes(hit.kind) &&
|
|
1071
|
-
hit.shape?.id &&
|
|
1072
|
-
props.connectShapeData?.sourceId &&
|
|
1073
|
-
hit.shape?.id !== props.connectShapeData.sourceId
|
|
1074
|
-
) {
|
|
1187
|
+
if (clickedShape?.id && props.connectShapeData?.sourceId) {
|
|
1075
1188
|
event.stopPropagation();
|
|
1076
|
-
completeConnection(
|
|
1189
|
+
completeConnection(clickedShape, localPoint);
|
|
1190
|
+
}
|
|
1191
|
+
};
|
|
1192
|
+
|
|
1193
|
+
const tryCompleteConnectionFromShapeClick = (shape: Shape) => {
|
|
1194
|
+
if (!isConnecting.value || !props.connectShapeData?.sourceId) {
|
|
1195
|
+
return false;
|
|
1196
|
+
}
|
|
1197
|
+
|
|
1198
|
+
if (!shape?.id || shape.id === props.connectShapeData.sourceId) {
|
|
1199
|
+
return false;
|
|
1077
1200
|
}
|
|
1201
|
+
|
|
1202
|
+
const bounds = getBounds(shape);
|
|
1203
|
+
const clickPoint = {
|
|
1204
|
+
x: bounds.x + bounds.width / 2,
|
|
1205
|
+
y: bounds.y + bounds.height / 2,
|
|
1206
|
+
};
|
|
1207
|
+
|
|
1208
|
+
completeConnection(shape, clickPoint);
|
|
1209
|
+
return true;
|
|
1078
1210
|
};
|
|
1079
1211
|
|
|
1080
1212
|
// 完成连接
|
|
1081
|
-
const completeConnection = (
|
|
1213
|
+
const completeConnection = async (
|
|
1082
1214
|
clickedShape: Shape,
|
|
1083
1215
|
clickPoint: { x: number; y: number }
|
|
1084
1216
|
) => {
|
|
1085
|
-
const sourceShape =
|
|
1086
|
-
|
|
1087
|
-
|
|
1217
|
+
const sourceShape = props.connectShapeData?.sourceId
|
|
1218
|
+
? graphStore.shapeMap.get(props.connectShapeData.sourceId)
|
|
1219
|
+
: undefined;
|
|
1088
1220
|
|
|
1089
1221
|
// 如果高亮是红色的情况直接返回
|
|
1090
1222
|
if (!isConnectAllowed.value) {
|
|
@@ -1110,7 +1242,7 @@ const completeConnection = (
|
|
|
1110
1242
|
return;
|
|
1111
1243
|
}
|
|
1112
1244
|
// 检查目标图元类型是否符合targetModels要求
|
|
1113
|
-
const targetModels =
|
|
1245
|
+
const targetModels = getCurrentTargetModels();
|
|
1114
1246
|
if (targetModels && Array.isArray(targetModels) && targetModels.length > 0) {
|
|
1115
1247
|
const clickedShapeType = clickedShape.shapeKey || "";
|
|
1116
1248
|
if (!targetModels.includes(clickedShapeType)) {
|
|
@@ -1123,13 +1255,15 @@ const completeConnection = (
|
|
|
1123
1255
|
}
|
|
1124
1256
|
}
|
|
1125
1257
|
|
|
1126
|
-
//
|
|
1127
|
-
const
|
|
1128
|
-
(
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1258
|
+
// 检查是否已存在相同类型的边(通过 edgesByNodeId 索引快速查找)
|
|
1259
|
+
const candidateEdges = props.connectShapeData?.sourceId
|
|
1260
|
+
? (graphStore.edgesByNodeId.get(props.connectShapeData.sourceId) ?? [])
|
|
1261
|
+
: [];
|
|
1262
|
+
const existingEdge = candidateEdges.find(
|
|
1263
|
+
(edge) =>
|
|
1264
|
+
edge.sourceId === props.connectShapeData?.sourceId &&
|
|
1265
|
+
edge.targetId === clickedShape.id &&
|
|
1266
|
+
edge.shapeKey === props.connectShapeData?.shapeKey
|
|
1133
1267
|
);
|
|
1134
1268
|
|
|
1135
1269
|
// 如果边已存在,错误提示并返回
|
|
@@ -1143,7 +1277,7 @@ const completeConnection = (
|
|
|
1143
1277
|
return;
|
|
1144
1278
|
}
|
|
1145
1279
|
// 使用工具类完成连接,传递当前的shapes列表以支持差异化路由
|
|
1146
|
-
const connectionData = EdgeUtils.
|
|
1280
|
+
const connectionData = await EdgeUtils.completeConnectionAsync(
|
|
1147
1281
|
sourceShape,
|
|
1148
1282
|
clickedShape,
|
|
1149
1283
|
clickPoint,
|
|
@@ -1190,9 +1324,9 @@ const handleMouseLeave = () => {
|
|
|
1190
1324
|
// 初始化连接点位置
|
|
1191
1325
|
const initializeConnectPoint = () => {
|
|
1192
1326
|
if (props.connectShapeData?.sourceId && props.diagramBounds) {
|
|
1193
|
-
const sourceShape =
|
|
1194
|
-
|
|
1195
|
-
|
|
1327
|
+
const sourceShape = props.connectShapeData?.sourceId
|
|
1328
|
+
? graphStore.shapeMap.get(props.connectShapeData.sourceId)
|
|
1329
|
+
: undefined;
|
|
1196
1330
|
|
|
1197
1331
|
// 使用工具类初始化连接点,传递当前鼠标位置和diagramBounds
|
|
1198
1332
|
// 这样可以确保即使是第一次连线,也能计算出图元边界上的合适连接点,而不是使用中心点
|
|
@@ -1400,13 +1534,13 @@ const continueExternalCreateDrag = async (payload: {
|
|
|
1400
1534
|
if (!externalCreateDragState.creatingId) return;
|
|
1401
1535
|
|
|
1402
1536
|
let targetPt = pt;
|
|
1403
|
-
const s = graphStore.
|
|
1404
|
-
|
|
1537
|
+
const s = graphStore.shapeMap.get(
|
|
1538
|
+
externalCreateDragState.creatingId!
|
|
1405
1539
|
);
|
|
1406
1540
|
if (s && s.shapeType === "pin") {
|
|
1407
1541
|
if (graphStore.hoverContainerId && graphStore.hoverNestable !== false) {
|
|
1408
|
-
const parent = graphStore.
|
|
1409
|
-
|
|
1542
|
+
const parent = graphStore.shapeMap.get(
|
|
1543
|
+
graphStore.hoverContainerId
|
|
1410
1544
|
);
|
|
1411
1545
|
if (parent) {
|
|
1412
1546
|
const { x: adjustedX, y: adjustedY } = snapPinToParentEdge(
|
|
@@ -1439,16 +1573,13 @@ const finishExternalCreateDrag = async (payload: {
|
|
|
1439
1573
|
isInsideCanvasClient(payload.clientX, payload.clientY, layerRef.value)
|
|
1440
1574
|
) {
|
|
1441
1575
|
let targetPt = pt;
|
|
1442
|
-
const s0 =
|
|
1443
|
-
|
|
1444
|
-
|
|
1576
|
+
const s0: any = externalCreateDragState.creatingId
|
|
1577
|
+
? graphStore.shapeMap.get(externalCreateDragState.creatingId)
|
|
1578
|
+
: undefined;
|
|
1445
1579
|
// 推断这次 drop 的“候选父节点”
|
|
1446
1580
|
let parent: Shape | null = null;
|
|
1447
1581
|
if (graphStore.hoverContainerId && graphStore.hoverNestable !== false) {
|
|
1448
|
-
parent =
|
|
1449
|
-
(graphStore.shapes as any[]).find(
|
|
1450
|
-
(x: any) => x.id === graphStore.hoverContainerId
|
|
1451
|
-
) || null;
|
|
1582
|
+
parent = graphStore.shapeMap.get(graphStore.hoverContainerId) ?? null;
|
|
1452
1583
|
}
|
|
1453
1584
|
// pin:松手瞬间就先算好最终吸附坐标
|
|
1454
1585
|
if (s0 && s0.shapeType === "pin" && parent) {
|
|
@@ -1462,9 +1593,9 @@ const finishExternalCreateDrag = async (payload: {
|
|
|
1462
1593
|
|
|
1463
1594
|
graphStore.moveDraggedShape(targetPt, { hitPointer: pt });
|
|
1464
1595
|
await nextTick();
|
|
1465
|
-
const s: any =
|
|
1466
|
-
|
|
1467
|
-
|
|
1596
|
+
const s: any = externalCreateDragState.creatingId
|
|
1597
|
+
? graphStore.shapeMap.get(externalCreateDragState.creatingId)
|
|
1598
|
+
: undefined;
|
|
1468
1599
|
if ((s && s.shapeType == "shape") || s.shapeType == "pin") {
|
|
1469
1600
|
const pure = _.omit(s, ["inert"]);
|
|
1470
1601
|
pure.bounds = {
|
|
@@ -1580,7 +1711,7 @@ const keyboardHandler = createKeyboardHandler({
|
|
|
1580
1711
|
onCopy: () => {
|
|
1581
1712
|
// 获取当前选中的图元
|
|
1582
1713
|
const selectedShapes = graphStore.selectedIds
|
|
1583
|
-
.map((id) => graphStore.
|
|
1714
|
+
.map((id) => graphStore.shapeMap.get(id))
|
|
1584
1715
|
.filter(Boolean) as Shape[];
|
|
1585
1716
|
|
|
1586
1717
|
if (selectedShapes.length === 0) {
|
|
@@ -1593,7 +1724,7 @@ const keyboardHandler = createKeyboardHandler({
|
|
|
1593
1724
|
onCut: () => {
|
|
1594
1725
|
// 获取当前选中的图元
|
|
1595
1726
|
const selectedShapes = graphStore.selectedIds
|
|
1596
|
-
.map((id) => graphStore.
|
|
1727
|
+
.map((id) => graphStore.shapeMap.get(id))
|
|
1597
1728
|
.filter(Boolean) as Shape[];
|
|
1598
1729
|
|
|
1599
1730
|
if (selectedShapes.length === 0) {
|
|
@@ -1643,32 +1774,57 @@ const flushMoveDraggedShape = () => {
|
|
|
1643
1774
|
}
|
|
1644
1775
|
};
|
|
1645
1776
|
|
|
1777
|
+
type InteractionCleanup = () => void;
|
|
1778
|
+
|
|
1779
|
+
const interactionCleanups: InteractionCleanup[] = [];
|
|
1780
|
+
|
|
1781
|
+
const registerWindowListener = <K extends keyof WindowEventMap>(
|
|
1782
|
+
event: K,
|
|
1783
|
+
handler: (event: WindowEventMap[K]) => void,
|
|
1784
|
+
) => {
|
|
1785
|
+
window.addEventListener(event, handler as EventListener);
|
|
1786
|
+
interactionCleanups.push(() => window.removeEventListener(event, handler as EventListener));
|
|
1787
|
+
};
|
|
1788
|
+
|
|
1789
|
+
const registerDocumentListener = <K extends keyof DocumentEventMap>(
|
|
1790
|
+
event: K,
|
|
1791
|
+
handler: (event: DocumentEventMap[K]) => void,
|
|
1792
|
+
) => {
|
|
1793
|
+
document.addEventListener(event, handler as EventListener);
|
|
1794
|
+
interactionCleanups.push(() => document.removeEventListener(event, handler as EventListener));
|
|
1795
|
+
};
|
|
1796
|
+
|
|
1797
|
+
const registerEventBusListener = (event: string, handler: (...args: any[]) => void) => {
|
|
1798
|
+
eventBus.on(event, handler);
|
|
1799
|
+
interactionCleanups.push(() => eventBus.off(event, handler));
|
|
1800
|
+
};
|
|
1801
|
+
|
|
1802
|
+
const handleSelectShapes = (ids: string[]) => {
|
|
1803
|
+
graphStore.clearSelection();
|
|
1804
|
+
graphStore.selectMany(ids);
|
|
1805
|
+
};
|
|
1806
|
+
|
|
1646
1807
|
onMounted(() => {
|
|
1647
|
-
|
|
1808
|
+
registerWindowListener("keydown", keyboardHandler);
|
|
1648
1809
|
// 添加连接层相关的事件监听
|
|
1649
1810
|
if (props.connectShapeData) {
|
|
1650
|
-
|
|
1651
|
-
|
|
1811
|
+
registerDocumentListener("mousemove", handleMouseMove);
|
|
1812
|
+
registerDocumentListener("mouseleave", handleMouseLeave);
|
|
1652
1813
|
initializeConnectPoint();
|
|
1653
1814
|
}
|
|
1654
1815
|
|
|
1655
1816
|
//拖动结束后更新情景菜单
|
|
1656
|
-
|
|
1817
|
+
registerEventBusListener("shape-drag-end-updateScenarioMenu", actionButtonsStyle);
|
|
1657
1818
|
|
|
1658
1819
|
// 监听选择图元事件
|
|
1659
|
-
|
|
1660
|
-
graphStore.clearSelection();
|
|
1661
|
-
graphStore.selectMany(ids);
|
|
1662
|
-
});
|
|
1820
|
+
registerEventBusListener("select-shapes", handleSelectShapes);
|
|
1663
1821
|
});
|
|
1664
1822
|
onUnmounted(() => {
|
|
1665
1823
|
offDrag?.();
|
|
1824
|
+
while (interactionCleanups.length > 0) {
|
|
1825
|
+
interactionCleanups.pop()?.();
|
|
1826
|
+
}
|
|
1666
1827
|
// 清理连接层相关的事件监听
|
|
1667
|
-
document.removeEventListener("mousemove", handleMouseMove);
|
|
1668
|
-
document.removeEventListener("mouseleave", handleMouseLeave);
|
|
1669
|
-
window.removeEventListener("keydown", keyboardHandler);
|
|
1670
|
-
eventBus.off("shape-drag-end-updateScenarioMenu", actionButtonsStyle);
|
|
1671
|
-
if (rafId) cancelAnimationFrame(rafId);
|
|
1672
1828
|
if (dragMoveRafId) cancelAnimationFrame(dragMoveRafId);
|
|
1673
1829
|
dragMoveRafId = null;
|
|
1674
1830
|
latestDragMove = null;
|
|
@@ -1677,6 +1833,7 @@ defineExpose({
|
|
|
1677
1833
|
continueExternalCreateDrag,
|
|
1678
1834
|
finishExternalCreateDrag,
|
|
1679
1835
|
handleEdgeClick,
|
|
1836
|
+
tryCompleteConnectionFromShapeClick,
|
|
1680
1837
|
getBoundingClientRect: () => layerRef.value?.getBoundingClientRect(),
|
|
1681
1838
|
});
|
|
1682
1839
|
</script>
|
|
@@ -1702,17 +1859,37 @@ defineExpose({
|
|
|
1702
1859
|
top: 6px;
|
|
1703
1860
|
}
|
|
1704
1861
|
|
|
1862
|
+
.hover-container-outline-svg {
|
|
1863
|
+
position: absolute;
|
|
1864
|
+
pointer-events: none;
|
|
1865
|
+
}
|
|
1866
|
+
|
|
1867
|
+
.hover-container-outline-svg .outline-path {
|
|
1868
|
+
fill: transparent;
|
|
1869
|
+
stroke-width: 2px;
|
|
1870
|
+
stroke-linejoin: round;
|
|
1871
|
+
}
|
|
1872
|
+
|
|
1705
1873
|
/* 允许嵌套(后端 ok) */
|
|
1706
1874
|
.hover-container-outline.is-valid {
|
|
1707
1875
|
border: 2px solid #0000ff;
|
|
1708
1876
|
}
|
|
1709
1877
|
|
|
1878
|
+
.hover-container-outline-svg.is-valid .outline-path {
|
|
1879
|
+
stroke: #0000ff;
|
|
1880
|
+
}
|
|
1881
|
+
|
|
1710
1882
|
/* 不允许嵌套(后端 false) */
|
|
1711
1883
|
.hover-container-outline.is-invalid {
|
|
1712
1884
|
border: 2px solid #f1eded;
|
|
1713
1885
|
background: rgba(240, 237, 237, 0.842);
|
|
1714
1886
|
}
|
|
1715
1887
|
|
|
1888
|
+
.hover-container-outline-svg.is-invalid .outline-path {
|
|
1889
|
+
stroke: #f1eded;
|
|
1890
|
+
fill: rgba(240, 237, 237, 0.35);
|
|
1891
|
+
}
|
|
1892
|
+
|
|
1716
1893
|
/* 删除了选择框、调整大小手柄和操作按钮相关的样式,这些样式已经移到了 SelectionBox 组件中 */
|
|
1717
1894
|
|
|
1718
1895
|
.resize-ghost {
|
|
@@ -1768,11 +1945,30 @@ defineExpose({
|
|
|
1768
1945
|
border-radius: 2px;
|
|
1769
1946
|
}
|
|
1770
1947
|
|
|
1948
|
+
.highlight-overlay-svg {
|
|
1949
|
+
position: absolute;
|
|
1950
|
+
pointer-events: none;
|
|
1951
|
+
}
|
|
1952
|
+
|
|
1953
|
+
.highlight-overlay-svg .outline-path {
|
|
1954
|
+
fill: transparent;
|
|
1955
|
+
stroke-width: 3px;
|
|
1956
|
+
stroke-linejoin: round;
|
|
1957
|
+
}
|
|
1958
|
+
|
|
1771
1959
|
.highlight-overlay.blue {
|
|
1772
1960
|
border: 3px solid #1890ff;
|
|
1773
1961
|
}
|
|
1774
1962
|
|
|
1963
|
+
.highlight-overlay-svg.blue .outline-path {
|
|
1964
|
+
stroke: #1890ff;
|
|
1965
|
+
}
|
|
1966
|
+
|
|
1775
1967
|
.highlight-overlay.red {
|
|
1776
1968
|
border: 3px solid #f56c6c;
|
|
1777
1969
|
}
|
|
1970
|
+
|
|
1971
|
+
.highlight-overlay-svg.red .outline-path {
|
|
1972
|
+
stroke: #f56c6c;
|
|
1973
|
+
}
|
|
1778
1974
|
</style>
|