@eclipse-glsp/client 2.2.0-next.328 → 2.2.0-next.330

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (400) hide show
  1. package/css/change-bounds.css +15 -0
  2. package/css/glsp-sprotty.css +17 -0
  3. package/lib/base/action-dispatcher.js.map +1 -1
  4. package/lib/base/action-handler-registry.js.map +1 -1
  5. package/lib/base/args-feature.js.map +1 -1
  6. package/lib/base/auto-complete/auto-complete-widget.js.map +1 -1
  7. package/lib/base/auto-complete/validation-decorator.js.map +1 -1
  8. package/lib/base/command-stack.js.map +1 -1
  9. package/lib/base/drag-aware-mouse-listener.d.ts +5 -2
  10. package/lib/base/drag-aware-mouse-listener.d.ts.map +1 -1
  11. package/lib/base/drag-aware-mouse-listener.js +11 -0
  12. package/lib/base/drag-aware-mouse-listener.js.map +1 -1
  13. package/lib/base/editor-context-service.js.map +1 -1
  14. package/lib/base/feedback/css-feedback.d.ts +4 -0
  15. package/lib/base/feedback/css-feedback.d.ts.map +1 -1
  16. package/lib/base/feedback/css-feedback.js +4 -0
  17. package/lib/base/feedback/css-feedback.js.map +1 -1
  18. package/lib/base/feedback/feeback-emitter.d.ts +67 -0
  19. package/lib/base/feedback/feeback-emitter.d.ts.map +1 -0
  20. package/lib/base/feedback/feeback-emitter.js +109 -0
  21. package/lib/base/feedback/feeback-emitter.js.map +1 -0
  22. package/lib/base/feedback/feedback-action-dispatcher.d.ts +17 -5
  23. package/lib/base/feedback/feedback-action-dispatcher.d.ts.map +1 -1
  24. package/lib/base/feedback/feedback-action-dispatcher.js +23 -3
  25. package/lib/base/feedback/feedback-action-dispatcher.js.map +1 -1
  26. package/lib/base/feedback/index.d.ts +1 -0
  27. package/lib/base/feedback/index.d.ts.map +1 -1
  28. package/lib/base/feedback/index.js +1 -0
  29. package/lib/base/feedback/index.js.map +1 -1
  30. package/lib/base/focus/focus-tracker.js.map +1 -1
  31. package/lib/base/model/diagram-loader.js.map +1 -1
  32. package/lib/base/model/glsp-model-source.js.map +1 -1
  33. package/lib/base/model/model-initialization-constraint.js.map +1 -1
  34. package/lib/base/model/model-registry.js.map +1 -1
  35. package/lib/base/selection-clearing-mouse-listener.js.map +1 -1
  36. package/lib/base/selection-service.d.ts +3 -2
  37. package/lib/base/selection-service.d.ts.map +1 -1
  38. package/lib/base/selection-service.js.map +1 -1
  39. package/lib/base/tool-manager/index.d.ts +2 -2
  40. package/lib/base/tool-manager/index.d.ts.map +1 -1
  41. package/lib/base/tool-manager/index.js +2 -2
  42. package/lib/base/tool-manager/index.js.map +1 -1
  43. package/lib/base/tool-manager/tool-manager.js.map +1 -1
  44. package/lib/base/view/mouse-tool.js.map +1 -1
  45. package/lib/base/view/view-registry.js.map +1 -1
  46. package/lib/default-modules.d.ts +1 -1
  47. package/lib/default-modules.js +1 -1
  48. package/lib/default-modules.js.map +1 -1
  49. package/lib/features/accessibility/edge-autocomplete/edge-autocomplete-palette.js.map +1 -1
  50. package/lib/features/accessibility/edge-autocomplete/edge-autocomplete-tool.js.map +1 -1
  51. package/lib/features/accessibility/element-navigation/diagram-navigation-tool.js.map +1 -1
  52. package/lib/features/accessibility/element-navigation/left-right-top-bottom-navigator.js.map +1 -1
  53. package/lib/features/accessibility/element-navigation/local-element-navigator.d.ts +3 -3
  54. package/lib/features/accessibility/element-navigation/local-element-navigator.d.ts.map +1 -1
  55. package/lib/features/accessibility/element-navigation/local-element-navigator.js.map +1 -1
  56. package/lib/features/accessibility/element-navigation/position-navigator.js.map +1 -1
  57. package/lib/features/accessibility/focus-tracker/focus-tracker-tool.js.map +1 -1
  58. package/lib/features/accessibility/global-keylistener-tool.js.map +1 -1
  59. package/lib/features/accessibility/key-shortcut/accessible-key-shortcut-tool.js.map +1 -1
  60. package/lib/features/accessibility/key-shortcut/accessible-key-shortcut.js.map +1 -1
  61. package/lib/features/accessibility/key-shortcut/index.d.ts +2 -2
  62. package/lib/features/accessibility/key-shortcut/index.d.ts.map +1 -1
  63. package/lib/features/accessibility/key-shortcut/index.js +2 -2
  64. package/lib/features/accessibility/key-shortcut/index.js.map +1 -1
  65. package/lib/features/accessibility/keyboard-grid/index.d.ts +2 -2
  66. package/lib/features/accessibility/keyboard-grid/index.d.ts.map +1 -1
  67. package/lib/features/accessibility/keyboard-grid/index.js +2 -2
  68. package/lib/features/accessibility/keyboard-grid/index.js.map +1 -1
  69. package/lib/features/accessibility/keyboard-grid/keyboard-grid.js.map +1 -1
  70. package/lib/features/accessibility/keyboard-grid/keyboard-node-grid.js.map +1 -1
  71. package/lib/features/accessibility/keyboard-pointer/index.d.ts +2 -2
  72. package/lib/features/accessibility/keyboard-pointer/index.d.ts.map +1 -1
  73. package/lib/features/accessibility/keyboard-pointer/index.js +2 -2
  74. package/lib/features/accessibility/keyboard-pointer/index.js.map +1 -1
  75. package/lib/features/accessibility/keyboard-pointer/keyboard-pointer-listener.d.ts +1 -1
  76. package/lib/features/accessibility/keyboard-pointer/keyboard-pointer-listener.d.ts.map +1 -1
  77. package/lib/features/accessibility/keyboard-pointer/keyboard-pointer-listener.js +1 -1
  78. package/lib/features/accessibility/keyboard-pointer/keyboard-pointer-listener.js.map +1 -1
  79. package/lib/features/accessibility/keyboard-pointer/keyboard-pointer.js.map +1 -1
  80. package/lib/features/accessibility/keyboard-tool-palette/index.d.ts +2 -2
  81. package/lib/features/accessibility/keyboard-tool-palette/index.d.ts.map +1 -1
  82. package/lib/features/accessibility/keyboard-tool-palette/index.js +2 -2
  83. package/lib/features/accessibility/keyboard-tool-palette/index.js.map +1 -1
  84. package/lib/features/accessibility/keyboard-tool-palette/keyboard-tool-palette.js.map +1 -1
  85. package/lib/features/accessibility/move-zoom/move-handler.d.ts +4 -2
  86. package/lib/features/accessibility/move-zoom/move-handler.d.ts.map +1 -1
  87. package/lib/features/accessibility/move-zoom/move-handler.js +10 -4
  88. package/lib/features/accessibility/move-zoom/move-handler.js.map +1 -1
  89. package/lib/features/accessibility/move-zoom/zoom-handler.js.map +1 -1
  90. package/lib/features/accessibility/resize-key-tool/resize-key-handler.d.ts +4 -2
  91. package/lib/features/accessibility/resize-key-tool/resize-key-handler.d.ts.map +1 -1
  92. package/lib/features/accessibility/resize-key-tool/resize-key-handler.js +11 -3
  93. package/lib/features/accessibility/resize-key-tool/resize-key-handler.js.map +1 -1
  94. package/lib/features/accessibility/resize-key-tool/resize-key-tool.js.map +1 -1
  95. package/lib/features/accessibility/search/index.d.ts +2 -2
  96. package/lib/features/accessibility/search/index.d.ts.map +1 -1
  97. package/lib/features/accessibility/search/index.js +2 -2
  98. package/lib/features/accessibility/search/index.js.map +1 -1
  99. package/lib/features/accessibility/search/search-palette.js.map +1 -1
  100. package/lib/features/accessibility/search/search-tool.js.map +1 -1
  101. package/lib/features/accessibility/toast/toast-tool.js.map +1 -1
  102. package/lib/features/accessibility/view-key-tools/deselect-key-tool.js.map +1 -1
  103. package/lib/features/accessibility/view-key-tools/movement-key-tool.js.map +1 -1
  104. package/lib/features/accessibility/view-key-tools/zoom-key-tool.js.map +1 -1
  105. package/lib/features/bounds/freeform-layout.js.map +1 -1
  106. package/lib/features/bounds/glsp-hidden-bounds-updater.js.map +1 -1
  107. package/lib/features/bounds/hbox-layout.js.map +1 -1
  108. package/lib/features/bounds/layouter.js.map +1 -1
  109. package/lib/features/bounds/local-bounds.js.map +1 -1
  110. package/lib/features/bounds/set-bounds-feedback-command.js.map +1 -1
  111. package/lib/features/bounds/vbox-layout.js.map +1 -1
  112. package/lib/features/change-bounds/model.d.ts +8 -8
  113. package/lib/features/change-bounds/model.d.ts.map +1 -1
  114. package/lib/features/change-bounds/model.js +17 -5
  115. package/lib/features/change-bounds/model.js.map +1 -1
  116. package/lib/features/change-bounds/movement-restrictor.d.ts +3 -2
  117. package/lib/features/change-bounds/movement-restrictor.d.ts.map +1 -1
  118. package/lib/features/change-bounds/movement-restrictor.js.map +1 -1
  119. package/lib/features/change-bounds/point-position-updater.js.map +1 -1
  120. package/lib/features/change-bounds/position-snapper.js.map +1 -1
  121. package/lib/features/command-palette/command-palette-module.d.ts +1 -1
  122. package/lib/features/command-palette/command-palette-module.js +1 -1
  123. package/lib/features/command-palette/command-palette.js.map +1 -1
  124. package/lib/features/command-palette/index.d.ts +1 -1
  125. package/lib/features/command-palette/index.js +1 -1
  126. package/lib/features/command-palette/server-command-palette-provider.js.map +1 -1
  127. package/lib/features/context-menu/context-menu-module.js.map +1 -1
  128. package/lib/features/context-menu/glsp-context-menu-mouse-listener.js.map +1 -1
  129. package/lib/features/context-menu/server-context-menu-provider.js.map +1 -1
  130. package/lib/features/copy-paste/copy-paste-context-menu.js.map +1 -1
  131. package/lib/features/copy-paste/copy-paste-handler.js.map +1 -1
  132. package/lib/features/copy-paste/copy-paste-standalone.js.map +1 -1
  133. package/lib/features/decoration/decoration-placer.js.map +1 -1
  134. package/lib/features/element-template/add-template-element.js.map +1 -1
  135. package/lib/features/element-template/mouse-tracking-element-position-listener.d.ts +15 -5
  136. package/lib/features/element-template/mouse-tracking-element-position-listener.d.ts.map +1 -1
  137. package/lib/features/element-template/mouse-tracking-element-position-listener.js +27 -38
  138. package/lib/features/element-template/mouse-tracking-element-position-listener.js.map +1 -1
  139. package/lib/features/element-template/remove-template-element.js.map +1 -1
  140. package/lib/features/export/glsp-svg-exporter.js.map +1 -1
  141. package/lib/features/helper-lines/helper-line-feedback.js.map +1 -1
  142. package/lib/features/helper-lines/helper-line-manager-default.d.ts +4 -2
  143. package/lib/features/helper-lines/helper-line-manager-default.d.ts.map +1 -1
  144. package/lib/features/helper-lines/helper-line-manager-default.js +8 -12
  145. package/lib/features/helper-lines/helper-line-manager-default.js.map +1 -1
  146. package/lib/features/helper-lines/index.d.ts +2 -2
  147. package/lib/features/helper-lines/index.d.ts.map +1 -1
  148. package/lib/features/helper-lines/index.js +2 -2
  149. package/lib/features/helper-lines/index.js.map +1 -1
  150. package/lib/features/helper-lines/model.js.map +1 -1
  151. package/lib/features/helper-lines/view.js.map +1 -1
  152. package/lib/features/hints/type-hint-provider.d.ts +3 -0
  153. package/lib/features/hints/type-hint-provider.d.ts.map +1 -1
  154. package/lib/features/hints/type-hint-provider.js +10 -1
  155. package/lib/features/hints/type-hint-provider.js.map +1 -1
  156. package/lib/features/hover/hover.js.map +1 -1
  157. package/lib/features/hover/index.d.ts +2 -2
  158. package/lib/features/hover/index.d.ts.map +1 -1
  159. package/lib/features/hover/index.js +2 -2
  160. package/lib/features/hover/index.js.map +1 -1
  161. package/lib/features/index.d.ts +2 -1
  162. package/lib/features/index.d.ts.map +1 -1
  163. package/lib/features/index.js +2 -1
  164. package/lib/features/index.js.map +1 -1
  165. package/lib/features/label-edit/edit-label-validator.js.map +1 -1
  166. package/lib/features/label-edit-ui/label-edit-ui.js.map +1 -1
  167. package/lib/features/layout/layout-elements-action.js.map +1 -1
  168. package/lib/features/navigation/navigation-action-handler.js.map +1 -1
  169. package/lib/features/navigation/navigation-target-resolver.js.map +1 -1
  170. package/lib/features/reconnect/model.js.map +1 -1
  171. package/lib/features/routing/glsp-manhattan-edge-router.js.map +1 -1
  172. package/lib/features/save/save-keylistener.js.map +1 -1
  173. package/lib/features/select/select-mouse-listener.d.ts +4 -3
  174. package/lib/features/select/select-mouse-listener.d.ts.map +1 -1
  175. package/lib/features/select/select-mouse-listener.js.map +1 -1
  176. package/lib/features/source-model-watcher/source-model-changed-action-handler.js.map +1 -1
  177. package/lib/features/status/status-overlay.js.map +1 -1
  178. package/lib/features/svg-metadata/metadata-placer.js.map +1 -1
  179. package/lib/features/tool-palette/index.d.ts +2 -2
  180. package/lib/features/tool-palette/index.d.ts.map +1 -1
  181. package/lib/features/tool-palette/index.js +2 -2
  182. package/lib/features/tool-palette/index.js.map +1 -1
  183. package/lib/features/tool-palette/tool-palette.js.map +1 -1
  184. package/lib/features/tools/base-tools.d.ts +23 -4
  185. package/lib/features/tools/base-tools.d.ts.map +1 -1
  186. package/lib/features/tools/base-tools.js +11 -6
  187. package/lib/features/tools/base-tools.js.map +1 -1
  188. package/lib/features/tools/change-bounds/change-bounds-tool-feedback.d.ts +1 -35
  189. package/lib/features/tools/change-bounds/change-bounds-tool-feedback.d.ts.map +1 -1
  190. package/lib/features/tools/change-bounds/change-bounds-tool-feedback.js +5 -206
  191. package/lib/features/tools/change-bounds/change-bounds-tool-feedback.js.map +1 -1
  192. package/lib/features/tools/change-bounds/change-bounds-tool-module.d.ts +1 -0
  193. package/lib/features/tools/change-bounds/change-bounds-tool-module.d.ts.map +1 -1
  194. package/lib/features/tools/change-bounds/change-bounds-tool-module.js +1 -0
  195. package/lib/features/tools/change-bounds/change-bounds-tool-module.js.map +1 -1
  196. package/lib/features/tools/change-bounds/change-bounds-tool-move-feedback.d.ts +67 -0
  197. package/lib/features/tools/change-bounds/change-bounds-tool-move-feedback.d.ts.map +1 -0
  198. package/lib/features/tools/change-bounds/change-bounds-tool-move-feedback.js +227 -0
  199. package/lib/features/tools/change-bounds/change-bounds-tool-move-feedback.js.map +1 -0
  200. package/lib/features/tools/change-bounds/change-bounds-tool.d.ts +34 -24
  201. package/lib/features/tools/change-bounds/change-bounds-tool.d.ts.map +1 -1
  202. package/lib/features/tools/change-bounds/change-bounds-tool.js +172 -180
  203. package/lib/features/tools/change-bounds/change-bounds-tool.js.map +1 -1
  204. package/lib/features/tools/change-bounds/index.d.ts +3 -2
  205. package/lib/features/tools/change-bounds/index.d.ts.map +1 -1
  206. package/lib/features/tools/change-bounds/index.js +3 -2
  207. package/lib/features/tools/change-bounds/index.js.map +1 -1
  208. package/lib/features/tools/change-bounds/view.d.ts +1 -1
  209. package/lib/features/tools/change-bounds/view.d.ts.map +1 -1
  210. package/lib/features/tools/change-bounds/view.js +3 -0
  211. package/lib/features/tools/change-bounds/view.js.map +1 -1
  212. package/lib/features/tools/deletion/delete-tool.d.ts +16 -1
  213. package/lib/features/tools/deletion/delete-tool.d.ts.map +1 -1
  214. package/lib/features/tools/deletion/delete-tool.js +5 -2
  215. package/lib/features/tools/deletion/delete-tool.js.map +1 -1
  216. package/lib/features/tools/edge-creation/dangling-edge-feedback.d.ts +17 -1
  217. package/lib/features/tools/edge-creation/dangling-edge-feedback.d.ts.map +1 -1
  218. package/lib/features/tools/edge-creation/dangling-edge-feedback.js +3 -1
  219. package/lib/features/tools/edge-creation/dangling-edge-feedback.js.map +1 -1
  220. package/lib/features/tools/edge-creation/edge-creation-tool-feedback.d.ts +4 -2
  221. package/lib/features/tools/edge-creation/edge-creation-tool-feedback.d.ts.map +1 -1
  222. package/lib/features/tools/edge-creation/edge-creation-tool-feedback.js +5 -8
  223. package/lib/features/tools/edge-creation/edge-creation-tool-feedback.js.map +1 -1
  224. package/lib/features/tools/edge-creation/edge-creation-tool.d.ts +20 -2
  225. package/lib/features/tools/edge-creation/edge-creation-tool.d.ts.map +1 -1
  226. package/lib/features/tools/edge-creation/edge-creation-tool.js +23 -18
  227. package/lib/features/tools/edge-creation/edge-creation-tool.js.map +1 -1
  228. package/lib/features/tools/edge-creation/index.d.ts +2 -2
  229. package/lib/features/tools/edge-creation/index.d.ts.map +1 -1
  230. package/lib/features/tools/edge-creation/index.js +2 -2
  231. package/lib/features/tools/edge-creation/index.js.map +1 -1
  232. package/lib/features/tools/edge-edit/edge-edit-tool-feedback.d.ts +3 -1
  233. package/lib/features/tools/edge-edit/edge-edit-tool-feedback.d.ts.map +1 -1
  234. package/lib/features/tools/edge-edit/edge-edit-tool-feedback.js +5 -8
  235. package/lib/features/tools/edge-edit/edge-edit-tool-feedback.js.map +1 -1
  236. package/lib/features/tools/edge-edit/edge-edit-tool.d.ts +4 -4
  237. package/lib/features/tools/edge-edit/edge-edit-tool.d.ts.map +1 -1
  238. package/lib/features/tools/edge-edit/edge-edit-tool.js +27 -44
  239. package/lib/features/tools/edge-edit/edge-edit-tool.js.map +1 -1
  240. package/lib/features/tools/edge-edit/index.d.ts +2 -2
  241. package/lib/features/tools/edge-edit/index.d.ts.map +1 -1
  242. package/lib/features/tools/edge-edit/index.js +2 -2
  243. package/lib/features/tools/edge-edit/index.js.map +1 -1
  244. package/lib/features/tools/marquee-selection/index.d.ts +2 -2
  245. package/lib/features/tools/marquee-selection/index.d.ts.map +1 -1
  246. package/lib/features/tools/marquee-selection/index.js +2 -2
  247. package/lib/features/tools/marquee-selection/index.js.map +1 -1
  248. package/lib/features/tools/marquee-selection/marquee-behavior.js.map +1 -1
  249. package/lib/features/tools/marquee-selection/marquee-mouse-tool.d.ts +3 -2
  250. package/lib/features/tools/marquee-selection/marquee-mouse-tool.d.ts.map +1 -1
  251. package/lib/features/tools/marquee-selection/marquee-mouse-tool.js +4 -2
  252. package/lib/features/tools/marquee-selection/marquee-mouse-tool.js.map +1 -1
  253. package/lib/features/tools/marquee-selection/marquee-tool-feedback.js.map +1 -1
  254. package/lib/features/tools/marquee-selection/marquee-tool.js.map +1 -1
  255. package/lib/features/tools/node-creation/node-creation-tool.d.ts +14 -5
  256. package/lib/features/tools/node-creation/node-creation-tool.d.ts.map +1 -1
  257. package/lib/features/tools/node-creation/node-creation-tool.js +58 -24
  258. package/lib/features/tools/node-creation/node-creation-tool.js.map +1 -1
  259. package/lib/features/tools/tool-focus-loss-module.js.map +1 -1
  260. package/lib/features/undo-redo/undo-redo-key-listener.js.map +1 -1
  261. package/lib/features/validation/issue-marker.js.map +1 -1
  262. package/lib/features/validation/marker-navigator.d.ts +7 -6
  263. package/lib/features/validation/marker-navigator.d.ts.map +1 -1
  264. package/lib/features/validation/marker-navigator.js.map +1 -1
  265. package/lib/features/validation/validate.d.ts +2 -5
  266. package/lib/features/validation/validate.d.ts.map +1 -1
  267. package/lib/features/validation/validate.js +4 -16
  268. package/lib/features/validation/validate.js.map +1 -1
  269. package/lib/features/viewport/glsp-scroll-mouse-listener.js.map +1 -1
  270. package/lib/features/viewport/reposition.js.map +1 -1
  271. package/lib/features/viewport/viewport-handler.js.map +1 -1
  272. package/lib/model.js.map +1 -1
  273. package/lib/standalone-modules.js.map +1 -1
  274. package/lib/utils/argument-utils.js.map +1 -1
  275. package/lib/utils/geometry-util.d.ts +1 -1
  276. package/lib/utils/geometry-util.d.ts.map +1 -1
  277. package/lib/utils/gmodel-util.d.ts +27 -2
  278. package/lib/utils/gmodel-util.d.ts.map +1 -1
  279. package/lib/utils/gmodel-util.js +30 -1
  280. package/lib/utils/gmodel-util.js.map +1 -1
  281. package/lib/utils/html-utils.js.map +1 -1
  282. package/lib/utils/layout-utils.d.ts +8 -7
  283. package/lib/utils/layout-utils.d.ts.map +1 -1
  284. package/lib/utils/layout-utils.js +2 -4
  285. package/lib/utils/layout-utils.js.map +1 -1
  286. package/lib/utils/marker.js.map +1 -1
  287. package/lib/utils/viewpoint-util.d.ts +4 -4
  288. package/lib/utils/viewpoint-util.d.ts.map +1 -1
  289. package/lib/utils/viewpoint-util.js.map +1 -1
  290. package/lib/views/compartments.js.map +1 -1
  291. package/lib/views/gedge-view.js.map +1 -1
  292. package/lib/views/glsp-projection-view.js.map +1 -1
  293. package/lib/views/index.d.ts +2 -2
  294. package/lib/views/index.d.ts.map +1 -1
  295. package/lib/views/index.js +2 -2
  296. package/lib/views/index.js.map +1 -1
  297. package/lib/views/issue-marker-view.js.map +1 -1
  298. package/lib/views/rounded-corner-view.js.map +1 -1
  299. package/lib/views/rounded-corner.d.ts +1 -1
  300. package/lib/views/rounded-corner.d.ts.map +1 -1
  301. package/lib/views/rounded-corner.js.map +1 -1
  302. package/package.json +3 -3
  303. package/src/base/drag-aware-mouse-listener.ts +16 -2
  304. package/src/base/feedback/css-feedback.ts +4 -0
  305. package/src/base/feedback/feeback-emitter.ts +112 -0
  306. package/src/base/feedback/feedback-action-dispatcher.ts +41 -6
  307. package/src/base/feedback/index.ts +1 -0
  308. package/src/base/selection-service.spec.ts +5 -0
  309. package/src/base/selection-service.ts +2 -3
  310. package/src/features/accessibility/element-navigation/local-element-navigator.ts +4 -4
  311. package/src/features/accessibility/move-zoom/move-handler.ts +11 -6
  312. package/src/features/accessibility/resize-key-tool/resize-key-handler.ts +11 -7
  313. package/src/features/change-bounds/model.ts +25 -13
  314. package/src/features/change-bounds/movement-restrictor.ts +6 -22
  315. package/src/features/element-template/mouse-tracking-element-position-listener.ts +55 -45
  316. package/src/features/helper-lines/helper-line-feedback.ts +50 -57
  317. package/src/features/helper-lines/helper-line-manager-default.ts +12 -21
  318. package/src/features/helper-lines/model.ts +6 -25
  319. package/src/features/hints/type-hint-provider.spec.ts +4 -1
  320. package/src/features/hints/type-hint-provider.ts +9 -2
  321. package/src/features/layout/layout-elements-action.ts +10 -7
  322. package/src/features/select/select-mouse-listener.ts +4 -3
  323. package/src/features/tools/base-tools.ts +15 -8
  324. package/src/features/tools/change-bounds/change-bounds-tool-feedback.ts +6 -232
  325. package/src/features/tools/change-bounds/change-bounds-tool-module.ts +1 -0
  326. package/src/features/tools/change-bounds/change-bounds-tool-move-feedback.ts +254 -0
  327. package/src/features/tools/change-bounds/change-bounds-tool.ts +217 -226
  328. package/src/features/tools/change-bounds/index.ts +1 -0
  329. package/src/features/tools/change-bounds/view.tsx +4 -1
  330. package/src/features/tools/deletion/delete-tool.ts +6 -6
  331. package/src/features/tools/edge-creation/dangling-edge-feedback.ts +7 -4
  332. package/src/features/tools/edge-creation/edge-creation-tool-feedback.ts +9 -9
  333. package/src/features/tools/edge-creation/edge-creation-tool.ts +33 -23
  334. package/src/features/tools/edge-edit/edge-edit-tool-feedback.ts +8 -8
  335. package/src/features/tools/edge-edit/edge-edit-tool.ts +42 -49
  336. package/src/features/tools/marquee-selection/marquee-mouse-tool.ts +7 -6
  337. package/src/features/tools/node-creation/node-creation-tool.ts +69 -25
  338. package/src/features/validation/marker-navigator.ts +6 -8
  339. package/src/features/validation/validate.ts +5 -20
  340. package/src/features/viewport/reposition.ts +11 -14
  341. package/src/utils/geometry-util.ts +45 -64
  342. package/src/utils/gmodel-util.ts +45 -2
  343. package/src/utils/layout-utils.ts +9 -20
  344. package/src/utils/viewpoint-util.ts +13 -25
  345. package/lib/base/action-dispatcher.spec.d.ts +0 -2
  346. package/lib/base/action-dispatcher.spec.d.ts.map +0 -1
  347. package/lib/base/action-dispatcher.spec.js +0 -78
  348. package/lib/base/action-dispatcher.spec.js.map +0 -1
  349. package/lib/base/model/model-initialization-constraint.spec.d.ts +0 -2
  350. package/lib/base/model/model-initialization-constraint.spec.d.ts.map +0 -1
  351. package/lib/base/model/model-initialization-constraint.spec.js +0 -97
  352. package/lib/base/model/model-initialization-constraint.spec.js.map +0 -1
  353. package/lib/base/selection-service.spec.d.ts +0 -2
  354. package/lib/base/selection-service.spec.d.ts.map +0 -1
  355. package/lib/base/selection-service.spec.js +0 -287
  356. package/lib/base/selection-service.spec.js.map +0 -1
  357. package/lib/features/bounds/freeform-layout.spec.d.ts +0 -3
  358. package/lib/features/bounds/freeform-layout.spec.d.ts.map +0 -1
  359. package/lib/features/bounds/freeform-layout.spec.js +0 -201
  360. package/lib/features/bounds/freeform-layout.spec.js.map +0 -1
  361. package/lib/features/bounds/hbox-layout.spec.d.ts +0 -3
  362. package/lib/features/bounds/hbox-layout.spec.d.ts.map +0 -1
  363. package/lib/features/bounds/hbox-layout.spec.js +0 -160
  364. package/lib/features/bounds/hbox-layout.spec.js.map +0 -1
  365. package/lib/features/bounds/layouter-test-util.spec.d.ts +0 -32
  366. package/lib/features/bounds/layouter-test-util.spec.d.ts.map +0 -1
  367. package/lib/features/bounds/layouter-test-util.spec.js +0 -96
  368. package/lib/features/bounds/layouter-test-util.spec.js.map +0 -1
  369. package/lib/features/bounds/vbox-layout.spec.d.ts +0 -3
  370. package/lib/features/bounds/vbox-layout.spec.d.ts.map +0 -1
  371. package/lib/features/bounds/vbox-layout.spec.js +0 -160
  372. package/lib/features/bounds/vbox-layout.spec.js.map +0 -1
  373. package/lib/features/change-bounds/snap.spec.d.ts +0 -17
  374. package/lib/features/change-bounds/snap.spec.d.ts.map +0 -1
  375. package/lib/features/change-bounds/snap.spec.js +0 -83
  376. package/lib/features/change-bounds/snap.spec.js.map +0 -1
  377. package/lib/features/hints/type-hint-provider.spec.d.ts +0 -2
  378. package/lib/features/hints/type-hint-provider.spec.d.ts.map +0 -1
  379. package/lib/features/hints/type-hint-provider.spec.js +0 -333
  380. package/lib/features/hints/type-hint-provider.spec.js.map +0 -1
  381. package/lib/features/layout/layout-elements-action.spec.d.ts +0 -3
  382. package/lib/features/layout/layout-elements-action.spec.d.ts.map +0 -1
  383. package/lib/features/layout/layout-elements-action.spec.js +0 -329
  384. package/lib/features/layout/layout-elements-action.spec.js.map +0 -1
  385. package/lib/features/navigation/navigation-target-resolver.spec.d.ts +0 -3
  386. package/lib/features/navigation/navigation-target-resolver.spec.d.ts.map +0 -1
  387. package/lib/features/navigation/navigation-target-resolver.spec.js +0 -53
  388. package/lib/features/navigation/navigation-target-resolver.spec.js.map +0 -1
  389. package/lib/features/tools/marquee-selection/marquee-behavior.spec.d.ts +0 -17
  390. package/lib/features/tools/marquee-selection/marquee-behavior.spec.d.ts.map +0 -1
  391. package/lib/features/tools/marquee-selection/marquee-behavior.spec.js +0 -165
  392. package/lib/features/tools/marquee-selection/marquee-behavior.spec.js.map +0 -1
  393. package/lib/features/validation/marker-navigator.spec.d.ts +0 -3
  394. package/lib/features/validation/marker-navigator.spec.d.ts.map +0 -1
  395. package/lib/features/validation/marker-navigator.spec.js +0 -166
  396. package/lib/features/validation/marker-navigator.spec.js.map +0 -1
  397. package/lib/utils/gmodel-util.spec.d.ts +0 -2
  398. package/lib/utils/gmodel-util.spec.d.ts.map +0 -1
  399. package/lib/utils/gmodel-util.spec.js +0 -186
  400. package/lib/utils/gmodel-util.spec.js.map +0 -1
@@ -20,17 +20,34 @@ import {
20
20
  CommandActionHandler,
21
21
  CommandExecutionContext,
22
22
  Disposable,
23
+ GModelElement,
23
24
  IActionDispatcher,
24
25
  ICommand,
25
26
  ILogger,
27
+ MaybeFunction,
26
28
  TYPES,
29
+ call,
30
+ asArray as toArray,
27
31
  toTypeGuard
28
32
  } from '@eclipse-glsp/sprotty';
29
33
  import { inject, injectable } from 'inversify';
30
34
  import { getFeedbackRank } from './feedback-command';
35
+ import { FeedbackEmitter } from './feeback-emitter';
31
36
 
32
37
  export interface IFeedbackEmitter {}
33
38
 
39
+ export const feedbackFeature = Symbol('feedbackFeature');
40
+
41
+ export type MaybeActions = MaybeFunction<Action[] | Action | undefined>;
42
+
43
+ export namespace MaybeActions {
44
+ // eslint-disable-next-line @typescript-eslint/no-shadow
45
+ export function asArray(actions?: MaybeActions): Action[] {
46
+ const cleanup = actions ? call(actions) : [];
47
+ return cleanup ? toArray(cleanup) : [];
48
+ }
49
+ }
50
+
34
51
  /**
35
52
  * Dispatcher for actions that are meant to show visual feedback on
36
53
  * the diagram that is not part of the diagram sent from the server
@@ -52,7 +69,7 @@ export interface IFeedbackActionDispatcher {
52
69
  * @param cleanupActions the actions to be sent out when the feedback is de-registered through the returned Disposable.
53
70
  * @returns A 'Disposable' that de-registers the feedback and cleans up any pending feedback with the given `cleanupActions`.
54
71
  */
55
- registerFeedback(feedbackEmitter: IFeedbackEmitter, feedbackActions: Action[], cleanupActions?: Action[]): Disposable;
72
+ registerFeedback(feedbackEmitter: IFeedbackEmitter, feedbackActions: Action[], cleanupActions?: MaybeActions): Disposable;
56
73
 
57
74
  /**
58
75
  * Deregisters a `feedbackEmitter` from this dispatcher and thereafter
@@ -64,7 +81,7 @@ export interface IFeedbackActionDispatcher {
64
81
  * to reset the normal state of the diagram without the feedback (e.g., reset a
65
82
  * CSS class that was set by a feedbackEmitter).
66
83
  */
67
- deregisterFeedback(feedbackEmitter: IFeedbackEmitter, cleanupActions?: Action[]): void;
84
+ deregisterFeedback(feedbackEmitter: IFeedbackEmitter, cleanupActions?: MaybeActions): void;
68
85
 
69
86
  /**
70
87
  * Retrieve all `actions` sent out by currently registered `feedbackEmitter`.
@@ -80,6 +97,12 @@ export interface IFeedbackActionDispatcher {
80
97
  * Applies all current feedback commands to the given command execution context.
81
98
  */
82
99
  applyFeedbackCommands(context: CommandExecutionContext): Promise<void>;
100
+
101
+ /**
102
+ * Creates a new feedback emitter helper object. While anything can serve as a feedback emitter,
103
+ * this method ensures that the emitter is stable and does not change between model updates.
104
+ */
105
+ createEmitter(): FeedbackEmitter;
83
106
  }
84
107
 
85
108
  @injectable()
@@ -91,7 +114,14 @@ export class FeedbackActionDispatcher implements IFeedbackActionDispatcher {
91
114
 
92
115
  @inject(ActionHandlerRegistry) protected actionHandlerRegistry: ActionHandlerRegistry;
93
116
 
94
- registerFeedback(feedbackEmitter: IFeedbackEmitter, feedbackActions: Action[], cleanupActions?: Action[] | undefined): Disposable {
117
+ registerFeedback(feedbackEmitter: IFeedbackEmitter, feedbackActions: Action[], cleanupActions?: MaybeActions): Disposable {
118
+ if (feedbackEmitter instanceof GModelElement) {
119
+ this.logger.log(
120
+ this,
121
+ // eslint-disable-next-line max-len
122
+ 'GModelElements as feedback emitters are discouraged, as they usually change between model updates and are considered unstable.'
123
+ );
124
+ }
95
125
  if (feedbackActions.length > 0) {
96
126
  this.registeredFeedback.set(feedbackEmitter, feedbackActions);
97
127
  this.dispatchFeedback(feedbackActions, feedbackEmitter);
@@ -99,10 +129,11 @@ export class FeedbackActionDispatcher implements IFeedbackActionDispatcher {
99
129
  return Disposable.create(() => this.deregisterFeedback(feedbackEmitter, cleanupActions));
100
130
  }
101
131
 
102
- deregisterFeedback(feedbackEmitter: IFeedbackEmitter, cleanupActions?: Action[] | undefined): void {
132
+ deregisterFeedback(feedbackEmitter: IFeedbackEmitter, cleanupActions?: MaybeActions): void {
103
133
  this.registeredFeedback.delete(feedbackEmitter);
104
- if (cleanupActions && cleanupActions.length > 0) {
105
- this.dispatchFeedback(cleanupActions, feedbackEmitter);
134
+ const actions = MaybeActions.asArray(cleanupActions);
135
+ if (actions.length > 0) {
136
+ this.dispatchFeedback(actions, feedbackEmitter);
106
137
  }
107
138
  }
108
139
 
@@ -145,6 +176,10 @@ export class FeedbackActionDispatcher implements IFeedbackActionDispatcher {
145
176
  );
146
177
  }
147
178
 
179
+ createEmitter(): FeedbackEmitter {
180
+ return new FeedbackEmitter(this);
181
+ }
182
+
148
183
  protected async dispatchFeedback(actions: Action[], feedbackEmitter: IFeedbackEmitter): Promise<void> {
149
184
  try {
150
185
  const actionDispatcher = await this.actionDispatcher();
@@ -14,6 +14,7 @@
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
16
  export * from './css-feedback';
17
+ export * from './feeback-emitter';
17
18
  export * from './feedback-action-dispatcher';
18
19
  export * from './feedback-command';
19
20
  export * from './set-model-command';
@@ -18,6 +18,7 @@ import { AssertionError, expect } from 'chai';
18
18
  import { Container, injectable } from 'inversify';
19
19
  import * as sinon from 'sinon';
20
20
  import { defaultModule } from './default.module';
21
+ import { FeedbackEmitter } from './feedback/feeback-emitter';
21
22
  import { IFeedbackActionDispatcher, IFeedbackEmitter } from './feedback/feedback-action-dispatcher';
22
23
  import { ISelectionListener, SelectFeedbackAction, SelectionService } from './selection-service';
23
24
 
@@ -49,6 +50,10 @@ class MockFeedbackActionDispatcher implements IFeedbackActionDispatcher {
49
50
  return [];
50
51
  }
51
52
 
53
+ createEmitter(): FeedbackEmitter {
54
+ return new FeedbackEmitter(this);
55
+ }
56
+
52
57
  async applyFeedbackCommands(context: CommandExecutionContext): Promise<void> {}
53
58
  }
54
59
 
@@ -28,7 +28,6 @@ import {
28
28
  LazyInjector,
29
29
  SelectAction,
30
30
  SelectAllAction,
31
- Selectable,
32
31
  SprottySelectAllCommand,
33
32
  SprottySelectCommand,
34
33
  TYPES,
@@ -37,7 +36,7 @@ import {
37
36
  pluck
38
37
  } from '@eclipse-glsp/sprotty';
39
38
  import { inject, injectable, postConstruct, preDestroy } from 'inversify';
40
- import { getElements, getMatchingElements } from '../utils/gmodel-util';
39
+ import { SelectableElement, getElements, getMatchingElements } from '../utils/gmodel-util';
41
40
  import { IGModelRootListener } from './editor-context-service';
42
41
  import { IFeedbackActionDispatcher } from './feedback/feedback-action-dispatcher';
43
42
  import { IDiagramStartup } from './model';
@@ -164,7 +163,7 @@ export class SelectionService implements IGModelRootListener, Disposable, IDiagr
164
163
  return this.root;
165
164
  }
166
165
 
167
- getSelectedElements(): Readonly<GModelElement & Selectable>[] {
166
+ getSelectedElements(): Readonly<SelectableElement>[] {
168
167
  return !this.root ? [] : getElements(this.root.index, Array.from(this.selectedElementIDs), isSelectable);
169
168
  }
170
169
 
@@ -13,13 +13,13 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
- import { BoundsAware, EdgeRouterRegistry, GConnectableElement, GModelElement, GModelRoot, TYPES } from '@eclipse-glsp/sprotty';
16
+ import { EdgeRouterRegistry, GConnectableElement, GModelElement, GModelRoot, TYPES } from '@eclipse-glsp/sprotty';
17
17
  import { inject, injectable, optional } from 'inversify';
18
18
  import { GLSPActionDispatcher } from '../../../base/action-dispatcher';
19
19
  import { applyCssClasses, deleteCssClasses } from '../../../base/feedback/css-feedback';
20
- import { SelectableBoundsAware } from '../../../utils/gmodel-util';
21
- import { ElementNavigator } from './element-navigator';
22
20
  import { GEdge } from '../../../model';
21
+ import { BoundsAwareModelElement, SelectableBoundsAware } from '../../../utils/gmodel-util';
22
+ import { ElementNavigator } from './element-navigator';
23
23
 
24
24
  @injectable()
25
25
  export class LocalElementNavigator implements ElementNavigator {
@@ -91,7 +91,7 @@ export class LocalElementNavigator implements ElementNavigator {
91
91
 
92
92
  protected getIterables(
93
93
  current: SelectableBoundsAware,
94
- previousCurrent?: GModelElement & BoundsAware,
94
+ previousCurrent?: BoundsAwareModelElement,
95
95
  predicate: (element: GModelElement) => boolean = () => true
96
96
  ): GModelElement[] {
97
97
  const elements: GModelElement[] = [];
@@ -17,7 +17,6 @@
17
17
  import {
18
18
  Action,
19
19
  ChangeBoundsOperation,
20
- DisposableCollection,
21
20
  ElementAndBounds,
22
21
  ElementMove,
23
22
  GModelRoot,
@@ -34,8 +33,9 @@ import {
34
33
  isBoundsAware,
35
34
  isViewport
36
35
  } from '@eclipse-glsp/sprotty';
37
- import { inject, injectable, optional } from 'inversify';
36
+ import { inject, injectable, optional, postConstruct } from 'inversify';
38
37
  import { DebouncedFunc, debounce } from 'lodash';
38
+ import { FeedbackEmitter } from '../../../base';
39
39
  import { EditorContextService } from '../../../base/editor-context-service';
40
40
  import { IFeedbackActionDispatcher } from '../../../base/feedback/feedback-action-dispatcher';
41
41
  import { SelectableBoundsAware, getElements, isSelectableAndBoundsAware } from '../../../utils/gmodel-util';
@@ -164,7 +164,12 @@ export class MoveElementHandler implements IActionHandler {
164
164
  readonly movementRestrictor?: IMovementRestrictor;
165
165
 
166
166
  protected debouncedChangeBounds?: DebouncedFunc<() => void>;
167
- protected disposableFeedback = new DisposableCollection();
167
+ protected moveFeedback: FeedbackEmitter;
168
+
169
+ @postConstruct()
170
+ protected init(): void {
171
+ this.moveFeedback = this.feedbackDispatcher.createEmitter();
172
+ }
168
173
 
169
174
  handle(action: Action): void | Action | ICommand {
170
175
  if (MoveElementAction.is(action)) {
@@ -199,13 +204,13 @@ export class MoveElementHandler implements IActionHandler {
199
204
 
200
205
  this.dispatcher.dispatchAll(viewportActions);
201
206
  const moveAction = MoveAction.create(elementMoves, { animate: false });
202
- this.disposableFeedback.push(this.feedbackDispatcher.registerFeedback(this, [moveAction]));
207
+ this.moveFeedback.add(moveAction).submit();
203
208
 
204
209
  this.scheduleChangeBounds(this.toElementAndBounds(elementMoves));
205
210
  }
206
211
 
207
212
  protected getTargetBounds(element: SelectableBoundsAware, action: MoveElementAction): Point {
208
- let position = { x: element.bounds.x + action.moveX, y: element.bounds.y + action.moveY };
213
+ let position = Point.add(element.bounds, { x: action.moveX, y: action.moveY });
209
214
  if (this.snapper && action.snap) {
210
215
  position = this.snapper.snap(position, element);
211
216
  }
@@ -219,7 +224,7 @@ export class MoveElementHandler implements IActionHandler {
219
224
  protected scheduleChangeBounds(elementAndBounds: ElementAndBounds[]): void {
220
225
  this.debouncedChangeBounds?.cancel();
221
226
  this.debouncedChangeBounds = debounce(() => {
222
- this.disposableFeedback.dispose();
227
+ this.moveFeedback.dispose();
223
228
  this.dispatcher.dispatchAll([ChangeBoundsOperation.create(elementAndBounds)]);
224
229
  this.debouncedChangeBounds = undefined;
225
230
  }, 300);
@@ -18,7 +18,6 @@ import {
18
18
  Action,
19
19
  ChangeBoundsOperation,
20
20
  Dimension,
21
- DisposableCollection,
22
21
  ElementAndBounds,
23
22
  GModelElement,
24
23
  GParentElement,
@@ -30,13 +29,13 @@ import {
30
29
  SetBoundsAction,
31
30
  TYPES
32
31
  } from '@eclipse-glsp/sprotty';
33
- import { inject, injectable, optional } from 'inversify';
32
+ import { inject, injectable, optional, postConstruct } from 'inversify';
34
33
  import { DebouncedFunc, debounce } from 'lodash';
34
+ import { FeedbackEmitter } from '../../../base';
35
35
  import { EditorContextService } from '../../../base/editor-context-service';
36
36
  import { IFeedbackActionDispatcher } from '../../../base/feedback/feedback-action-dispatcher';
37
- import { SelectableBoundsAware, getElements, isSelectableAndBoundsAware, toElementAndBounds } from '../../../utils/gmodel-util';
37
+ import { Resizable, SelectableBoundsAware, getElements, isSelectableAndBoundsAware, toElementAndBounds } from '../../../utils/gmodel-util';
38
38
  import { isValidMove, isValidSize, minHeight, minWidth } from '../../../utils/layout-utils';
39
- import { Resizable } from '../../change-bounds/model';
40
39
  import { GridSnapper } from '../../change-bounds/snap';
41
40
 
42
41
  export enum ResizeType {
@@ -79,7 +78,7 @@ export class ResizeElementHandler implements IActionHandler {
79
78
  protected feedbackDispatcher: IFeedbackActionDispatcher;
80
79
 
81
80
  protected debouncedChangeBounds?: DebouncedFunc<() => void>;
82
- protected disposableFeedback = new DisposableCollection();
81
+ protected resizeFeedback: FeedbackEmitter;
83
82
 
84
83
  // Default x resize used if GridSnapper is not provided
85
84
  static readonly defaultResizeX = 20;
@@ -96,6 +95,11 @@ export class ResizeElementHandler implements IActionHandler {
96
95
  }
97
96
  }
98
97
 
98
+ @postConstruct()
99
+ protected init(): void {
100
+ this.resizeFeedback = this.feedbackDispatcher.createEmitter();
101
+ }
102
+
99
103
  handle(action: Action): void | Action | ICommand {
100
104
  if (ResizeElementAction.is(action)) {
101
105
  this.handleResizeElement(action);
@@ -106,11 +110,11 @@ export class ResizeElementHandler implements IActionHandler {
106
110
  const elements = getElements(this.editorContextService.modelRoot.index, action.elementIds, isSelectableAndBoundsAware);
107
111
  const elementAndBounds = this.computeElementAndBounds(elements, action);
108
112
 
109
- this.disposableFeedback.push(this.feedbackDispatcher.registerFeedback(this, [SetBoundsAction.create(elementAndBounds)]));
113
+ this.resizeFeedback.add(SetBoundsAction.create(elementAndBounds)).submit();
110
114
 
111
115
  this.debouncedChangeBounds?.cancel();
112
116
  this.debouncedChangeBounds = debounce(() => {
113
- this.disposableFeedback.dispose();
117
+ this.resizeFeedback.dispose();
114
118
  this.dispatcher.dispatchAll([ChangeBoundsOperation.create(elementAndBounds)]);
115
119
  this.debouncedChangeBounds = undefined;
116
120
  }, 300);
@@ -14,24 +14,20 @@
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
16
  import {
17
- BoundsAware,
18
17
  GChildElement,
19
18
  GModelElement,
20
19
  GParentElement,
21
20
  Hoverable,
22
- Locateable,
23
- Selectable,
24
21
  hoverFeedbackFeature,
25
22
  isBoundsAware,
26
23
  isMoveable,
27
24
  isSelectable
28
25
  } from '@eclipse-glsp/sprotty';
26
+ import { BoundsAwareModelElement, MoveableElement, ResizableModelElement } from '../../utils';
29
27
 
30
28
  export const resizeFeature = Symbol('resizeFeature');
31
29
 
32
- export interface Resizable extends BoundsAware, Selectable {}
33
-
34
- export function isResizable(element: GModelElement): element is GParentElement & Resizable {
30
+ export function isResizable(element: GModelElement): element is ResizableModelElement {
35
31
  return isBoundsAware(element) && isSelectable(element) && element instanceof GParentElement && element.hasFeature(resizeFeature);
36
32
  }
37
33
 
@@ -43,15 +39,17 @@ export enum ResizeHandleLocation {
43
39
  BottomRight = 'bottom-right'
44
40
  }
45
41
 
46
- export function isBoundsAwareMoveable(element: GModelElement): element is GModelElement & Locateable & BoundsAware {
42
+ export function isBoundsAwareMoveable(element: GModelElement): element is BoundsAwareModelElement & MoveableElement {
47
43
  return isMoveable(element) && isBoundsAware(element);
48
44
  }
49
45
 
50
46
  export class SResizeHandle extends GChildElement implements Hoverable {
51
47
  static readonly TYPE = 'resize-handle';
52
48
 
49
+ override readonly parent: ResizableModelElement;
50
+
53
51
  constructor(
54
- readonly location?: ResizeHandleLocation,
52
+ readonly location: ResizeHandleLocation,
55
53
  override readonly type: string = SResizeHandle.TYPE,
56
54
  readonly hoverFeedback: boolean = false
57
55
  ) {
@@ -87,11 +85,25 @@ export class SResizeHandle extends GChildElement implements Hoverable {
87
85
  }
88
86
  }
89
87
 
90
- export function addResizeHandles(element: GParentElement): void {
91
- element.add(new SResizeHandle(ResizeHandleLocation.TopLeft));
92
- element.add(new SResizeHandle(ResizeHandleLocation.TopRight));
93
- element.add(new SResizeHandle(ResizeHandleLocation.BottomLeft));
94
- element.add(new SResizeHandle(ResizeHandleLocation.BottomRight));
88
+ export function addResizeHandles(
89
+ element: ResizableModelElement,
90
+ locations: ResizeHandleLocation[] = [
91
+ ResizeHandleLocation.TopLeft,
92
+ ResizeHandleLocation.TopRight,
93
+ ResizeHandleLocation.BottomLeft,
94
+ ResizeHandleLocation.BottomRight
95
+ ]
96
+ ): void {
97
+ for (const location of Object.values(ResizeHandleLocation)) {
98
+ const existing = element.children.find(child => child instanceof SResizeHandle && child.location === location);
99
+ if (locations.includes(location) && !existing) {
100
+ // add missing handle
101
+ element.add(new SResizeHandle(location));
102
+ } else if (!locations.includes(location) && existing) {
103
+ // remove existing handle
104
+ element.remove(existing);
105
+ }
106
+ }
95
107
  }
96
108
 
97
109
  export function removeResizeHandles(element: GParentElement): void {
@@ -13,9 +13,10 @@
13
13
  *
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
+ import { Bounds, GModelElement, GNode, GParentElement, Point } from '@eclipse-glsp/sprotty';
16
17
  import { injectable } from 'inversify';
17
- import { BoundsAware, Point, GModelElement, GNode, GParentElement } from '@eclipse-glsp/sprotty';
18
18
  import { ModifyCSSFeedbackAction } from '../../base/feedback/css-feedback';
19
+ import { BoundsAwareModelElement } from '../../utils';
19
20
  import { toAbsoluteBounds } from '../../utils/viewpoint-util';
20
21
  import { SResizeHandle, isBoundsAwareMoveable } from './model';
21
22
 
@@ -51,7 +52,7 @@ export class NoOverlapMovementRestrictor implements IMovementRestrictor {
51
52
  return false;
52
53
  }
53
54
  // Create ghost element at the newLocation
54
- const ghostElement = Object.create(element) as GModelElement & BoundsAware;
55
+ const ghostElement = Object.create(element) as BoundsAwareModelElement;
55
56
  ghostElement.bounds = {
56
57
  x: newLocation.x,
57
58
  y: newLocation.y,
@@ -64,29 +65,12 @@ export class NoOverlapMovementRestrictor implements IMovementRestrictor {
64
65
  element.root.index
65
66
  .all()
66
67
  .filter(e => e.id !== ghostElement.id && e !== ghostElement.root && e instanceof GNode)
67
- .map(e => e as GModelElement & BoundsAware)
68
+ .map(e => e as BoundsAwareModelElement)
68
69
  ).some(e => this.areOverlapping(e, ghostElement));
69
70
  }
70
71
 
71
- protected areOverlapping(element1: GModelElement & BoundsAware, element2: GModelElement & BoundsAware): boolean {
72
- const b1 = toAbsoluteBounds(element1);
73
- const b2 = toAbsoluteBounds(element2);
74
- const r1TopLeft: Point = b1;
75
- const r1BottomRight = { x: b1.x + b1.width, y: b1.y + b1.height };
76
- const r2TopLeft: Point = b2;
77
- const r2BottomRight = { x: b2.x + b2.width, y: b2.y + b2.height };
78
-
79
- // If one rectangle is on left side of other
80
- if (r1TopLeft.x > r2BottomRight.x || r2TopLeft.x > r1BottomRight.x) {
81
- return false;
82
- }
83
-
84
- // If one rectangle is above other
85
- if (r1BottomRight.y < r2TopLeft.y || r2BottomRight.y < r1TopLeft.y) {
86
- return false;
87
- }
88
-
89
- return true;
72
+ protected areOverlapping(element1: BoundsAwareModelElement, element2: BoundsAwareModelElement): boolean {
73
+ return Bounds.overlap(toAbsoluteBounds(element1), toAbsoluteBounds(element2));
90
74
  }
91
75
  }
92
76
 
@@ -14,35 +14,55 @@
14
14
  * SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
15
15
  ********************************************************************************/
16
16
 
17
- import { Action, Disposable, GModelElement, Locateable, MoveAction, Point, isBoundsAware, isMoveable } from '@eclipse-glsp/sprotty';
17
+ import {
18
+ Action,
19
+ Dimension,
20
+ Disposable,
21
+ ElementMove,
22
+ GModelElement,
23
+ MoveAction,
24
+ Point,
25
+ isBoundsAware,
26
+ isMoveable
27
+ } from '@eclipse-glsp/sprotty';
18
28
  import { injectable } from 'inversify';
19
29
  import { DragAwareMouseListener } from '../../base/drag-aware-mouse-listener';
20
30
  import { CSS_HIDDEN, ModifyCSSFeedbackAction } from '../../base/feedback/css-feedback';
31
+ import { FeedbackEmitter } from '../../base/feedback/feeback-emitter';
21
32
  import { IFeedbackEmitter } from '../../base/feedback/feedback-action-dispatcher';
22
33
  import { Tool } from '../../base/tool-manager/tool';
34
+ import { MoveableElement } from '../../utils';
23
35
  import { getAbsolutePosition } from '../../utils/viewpoint-util';
24
36
  import {
25
37
  IMovementRestrictor,
26
38
  createMovementRestrictionFeedback,
27
39
  removeMovementRestrictionFeedback
28
40
  } from '../change-bounds/movement-restrictor';
29
- import { PositionSnapper } from '../change-bounds/position-snapper';
30
41
  import { PointPositionUpdater } from '../change-bounds/point-position-updater';
42
+ import { PositionSnapper } from '../change-bounds/position-snapper';
31
43
  import { useSnap } from '../change-bounds/snap';
44
+ import { MoveFinishedEventAction } from '../tools';
32
45
 
33
46
  export interface PositioningTool extends Tool {
34
47
  readonly positionSnapper: PositionSnapper;
35
48
  readonly movementRestrictor?: IMovementRestrictor;
36
49
 
50
+ createFeedbackEmitter(): FeedbackEmitter;
51
+ /**
52
+ * @deprecated It is recommended to create a {@link createFeedbackEmitter dedicated emitter} per feedback instead of using the tool.
53
+ */
37
54
  registerFeedback(feedbackActions: Action[], feedbackEmitter?: IFeedbackEmitter, cleanupActions?: Action[]): Disposable;
55
+ /**
56
+ * @deprecated It is recommended to create a {@link createFeedbackEmitter dedicated emitter} per feedback and dispose it like that.
57
+ */
38
58
  deregisterFeedback(feedbackEmitter?: IFeedbackEmitter, cleanupActions?: Action[]): void;
39
59
  }
40
60
 
41
61
  @injectable()
42
62
  export class MouseTrackingElementPositionListener extends DragAwareMouseListener {
43
- currentPosition?: Point;
44
-
45
63
  protected positionUpdater: PointPositionUpdater;
64
+ protected moveGhostFeedback: FeedbackEmitter;
65
+ protected currentPosition?: Point;
46
66
 
47
67
  constructor(
48
68
  protected elementId: string,
@@ -51,6 +71,7 @@ export class MouseTrackingElementPositionListener extends DragAwareMouseListener
51
71
  ) {
52
72
  super();
53
73
  this.positionUpdater = new PointPositionUpdater(this.tool.positionSnapper);
74
+ this.moveGhostFeedback = this.tool.createFeedbackEmitter();
54
75
  }
55
76
 
56
77
  override mouseMove(target: GModelElement, event: MouseEvent): Action[] {
@@ -59,59 +80,48 @@ export class MouseTrackingElementPositionListener extends DragAwareMouseListener
59
80
  if (!element || !isMoveable(element)) {
60
81
  return [];
61
82
  }
62
- let targetPosition = this.getTargetPosition(target, event, element);
63
83
  if (this.positionUpdater.isLastDragPositionUndefined()) {
64
- this.positionUpdater.updateLastDragPosition(targetPosition);
84
+ this.positionUpdater.updateLastDragPosition(element.position);
65
85
  }
66
- const delta = this.positionUpdater.updatePosition(element, targetPosition, useSnap(event));
86
+ const mousePosition = getAbsolutePosition(target, event);
87
+ const delta = this.positionUpdater.updatePosition(element, mousePosition, useSnap(event));
67
88
  if (!delta) {
68
89
  return [];
69
90
  }
70
- targetPosition = this.validateMove(this.currentPosition ?? targetPosition, targetPosition, element, false);
71
- const moveGhostElement = MoveAction.create(
72
- [
73
- {
74
- elementId: element.id,
75
- fromPosition: this.currentPosition,
76
- toPosition: targetPosition
77
- }
78
- ],
79
- { animate: false, finished: false }
80
- );
81
- this.currentPosition = targetPosition;
82
- this.tool.registerFeedback([moveGhostElement], this);
83
- return element.cssClasses?.includes(CSS_HIDDEN)
84
- ? [ModifyCSSFeedbackAction.create({ elements: [element.id], remove: [CSS_HIDDEN] })]
85
- : [];
91
+ const toPosition = this.getElementTargetPosition(mousePosition, element, event);
92
+ const elementMove = { elementId: element.id, toPosition: toPosition };
93
+ this.addMoveFeeback(element, elementMove);
94
+ this.currentPosition = toPosition;
95
+ // since we are moving a ghost element that is feedback-only and will be removed anyway,
96
+ // we just send a MoveFinishedEventAction instead of reseting the position with a MoveAction and the finished flag set to true.
97
+ this.moveGhostFeedback.add(MoveAction.create([elementMove], { animate: false }), MoveFinishedEventAction.create()).submit();
98
+ return [];
86
99
  }
87
100
 
88
- protected getTargetPosition(target: GModelElement, event: MouseEvent, element: GModelElement & Locateable): Point {
89
- let targetPosition = getAbsolutePosition(target, event);
90
- if (this.cursorPosition === 'middle' && isBoundsAware(element)) {
91
- targetPosition = Point.subtract(targetPosition, { x: element.bounds.width / 2, y: element.bounds.height / 2 });
92
- }
93
- return targetPosition;
101
+ protected getElementTargetPosition(mousePosition: Point, element: MoveableElement, event: MouseEvent): Point {
102
+ const unsnappedPosition =
103
+ this.cursorPosition === 'middle' && isBoundsAware(element)
104
+ ? Point.subtract(mousePosition, Dimension.center(element.bounds))
105
+ : mousePosition;
106
+ return this.tool.positionSnapper.snapPosition(unsnappedPosition, element, useSnap(event));
94
107
  }
95
108
 
96
- protected snap(position: Point, element: GModelElement, isSnap = true): Point {
97
- return this.tool.positionSnapper.snapPosition(position, element, isSnap);
98
- }
99
-
100
- protected validateMove(startPosition: Point, toPosition: Point, element: GModelElement, isFinished: boolean): Point {
101
- let newPosition = toPosition;
109
+ protected addMoveFeeback(element: MoveableElement, elementMove: ElementMove): void {
102
110
  if (this.tool.movementRestrictor) {
103
- const valid = this.tool.movementRestrictor.validate(element, toPosition);
104
- let action;
105
- if (!valid) {
106
- action = createMovementRestrictionFeedback(element, this.tool.movementRestrictor);
107
- if (isFinished) {
108
- newPosition = startPosition;
109
- }
111
+ if (!this.tool.movementRestrictor.validate(element, elementMove.toPosition)) {
112
+ this.moveGhostFeedback.add(
113
+ createMovementRestrictionFeedback(element, this.tool.movementRestrictor),
114
+ removeMovementRestrictionFeedback(element, this.tool.movementRestrictor)
115
+ );
110
116
  } else {
111
- action = removeMovementRestrictionFeedback(element, this.tool.movementRestrictor);
117
+ this.moveGhostFeedback.add(removeMovementRestrictionFeedback(element, this.tool.movementRestrictor));
112
118
  }
113
- this.tool.registerFeedback([action], this, [removeMovementRestrictionFeedback(element, this.tool.movementRestrictor)]);
114
119
  }
115
- return newPosition;
120
+ this.moveGhostFeedback.add(ModifyCSSFeedbackAction.create({ elements: [element.id], remove: [CSS_HIDDEN] }));
121
+ }
122
+
123
+ override dispose(): void {
124
+ this.moveGhostFeedback.dispose();
125
+ super.dispose();
116
126
  }
117
127
  }