From f3997128b9fa28d2a1dfcc15e14d8cc14de4239e Mon Sep 17 00:00:00 2001 From: Nick O'Leary Date: Tue, 11 Jan 2022 19:49:40 +0000 Subject: [PATCH 1/2] Add wire-slice mode to delete wires with Ctrl-RHClick-Drag --- .../editor-client/src/js/ui/state.js | 3 +- .../@node-red/editor-client/src/js/ui/view.js | 68 +++++++++++++++---- .../editor-client/src/sass/flow.scss | 7 ++ 3 files changed, 63 insertions(+), 15 deletions(-) diff --git a/packages/node_modules/@node-red/editor-client/src/js/ui/state.js b/packages/node_modules/@node-red/editor-client/src/js/ui/state.js index bb455d235..3e907a44f 100644 --- a/packages/node_modules/@node-red/editor-client/src/js/ui/state.js +++ b/packages/node_modules/@node-red/editor-client/src/js/ui/state.js @@ -28,5 +28,6 @@ RED.state = { SELECTING_NODE: 11, GROUP_DRAGGING: 12, GROUP_RESIZE: 13, - DETACHED_DRAGGING: 14 + DETACHED_DRAGGING: 14, + SLICING: 15 } diff --git a/packages/node_modules/@node-red/editor-client/src/js/ui/view.js b/packages/node_modules/@node-red/editor-client/src/js/ui/view.js index c64e9af84..90ed7f901 100755 --- a/packages/node_modules/@node-red/editor-client/src/js/ui/view.js +++ b/packages/node_modules/@node-red/editor-client/src/js/ui/view.js @@ -74,6 +74,8 @@ RED.view = (function() { var mouse_mode = 0; var mousedown_group_handle = null; var lasso = null; + var slicePath = null; + var slicePathLast = null; var ghostNode = null; var showStatus = false; var lastClickNode = null; @@ -229,6 +231,12 @@ RED.view = (function() { } } else if (mouse_mode === RED.state.PANNING && d3.event.buttons !== 4) { resetMouseVars(); + } else if (slicePath) { + if (d3.event.buttons !== 2) { + slicePath.remove(); + slicePath = null; + resetMouseVars() + } } }) .on("touchend", function() { @@ -957,19 +965,18 @@ RED.view = (function() { lasso = null; } } - if (mouse_mode === 0 || mouse_mode === RED.state.QUICK_JOINING) { - if (d3.event.metaKey || d3.event.ctrlKey) { - d3.event.stopPropagation(); - clearSelection(); - point = d3.mouse(this); - var clickedGroup = getGroupAt(point[0],point[1]); - if (drag_lines.length > 0) { - clickedGroup = clickedGroup || RED.nodes.group(drag_lines[0].node.g) - } - showQuickAddDialog({position:point, group:clickedGroup}); + if ((mouse_mode === 0 || mouse_mode === RED.state.QUICK_JOINING) && (d3.event.touches || d3.event.button === 0) && (d3.event.metaKey || d3.event.ctrlKey)) { + // Trigger quick add dialog + d3.event.stopPropagation(); + clearSelection(); + point = d3.mouse(this); + var clickedGroup = getGroupAt(point[0],point[1]); + if (drag_lines.length > 0) { + clickedGroup = clickedGroup || RED.nodes.group(drag_lines[0].node.g) } - } - if (mouse_mode === 0 && !(d3.event.metaKey || d3.event.ctrlKey)) { + showQuickAddDialog({position:point, group:clickedGroup}); + } else if (mouse_mode === 0 && (d3.event.touches || d3.event.button === 0) && !(d3.event.metaKey || d3.event.ctrlKey)) { + // Tigger lasso if (!touchStartTime) { point = d3.mouse(this); lasso = eventLayer.append("rect") @@ -984,6 +991,13 @@ RED.view = (function() { .attr("class","nr-ui-view-lasso"); d3.event.preventDefault(); } + } else if (mouse_mode === 0 && d3.event.button === 2 && (d3.event.metaKey || d3.event.ctrlKey)) { + clearSelection(); + mouse_mode = RED.state.SLICING; + point = d3.mouse(this); + slicePath = eventLayer.append("path").attr("class","nr-ui-view-slice").attr("d",`M${point[0]} ${point[1]}`) + slicePathLast = point; + RED.view.redraw(); } } @@ -1380,6 +1394,17 @@ RED.view = (function() { .attr("height",h) ; return; + } else if (mouse_mode === RED.state.SLICING) { + if (slicePath) { + var delta = Math.max(1,Math.abs(slicePathLast[0]-mouse_position[0]))*Math.max(1,Math.abs(slicePathLast[1]-mouse_position[1])) + if (delta > 20) { + var currentPath = slicePath.attr("d") + currentPath += " L"+mouse_position[0]+" "+mouse_position[1] + slicePath.attr("d",currentPath); + slicePathLast = mouse_position + } + } + return } if (mouse_mode === RED.state.SELECTING_NODE) { @@ -1777,6 +1802,11 @@ RED.view = (function() { } else if (mouse_mode == RED.state.DEFAULT && mousedown_link == null && !d3.event.ctrlKey && !d3.event.metaKey ) { clearSelection(); updateSelection(); + } else if (slicePath) { + deleteSelection(); + slicePath.remove(); + slicePath = null; + RED.view.redraw(true); } if (mouse_mode == RED.state.MOVING_ACTIVE) { if (movingSet.length() > 0) { @@ -2571,7 +2601,7 @@ RED.view = (function() { activeHoverGroup.hovered = false; activeHoverGroup = null; } - d3.select(".red-ui-flow-link-splice").classed("red-ui-flow-link-splice",false); + d3.selectAll(".red-ui-flow-link-splice").classed("red-ui-flow-link-splice",false); if (spliceTimer) { clearTimeout(spliceTimer); spliceTimer = null; @@ -3471,6 +3501,9 @@ RED.view = (function() { d3.event.stopPropagation(); return; } + if (d3.event.button === 2) { + return + } mousedown_link = d; if (!(d3.event.metaKey || d3.event.ctrlKey)) { @@ -3491,7 +3524,7 @@ RED.view = (function() { redraw(); focusView(); d3.event.stopPropagation(); - if (!mousedown_link.link && movingSet.length() === 0 && selectedLinks.length() === 1 && selectedLinks.has(mousedown_link) && (d3.event.metaKey || d3.event.ctrlKey)) { + if (!mousedown_link.link && movingSet.length() === 0 && (d3.event.touches || d3.event.button === 0) && selectedLinks.length() === 1 && selectedLinks.has(mousedown_link) && (d3.event.metaKey || d3.event.ctrlKey)) { d3.select(this).classed("red-ui-flow-link-splice",true); var point = d3.mouse(this); var clickedGroup = getGroupAt(point[0],point[1]); @@ -4479,6 +4512,13 @@ RED.view = (function() { d3.select(pathBack) .on("mousedown",linkMouseDown) .on("touchstart",linkTouchStart) + .on("mousemove", function(d) { + if (mouse_mode === RED.state.SLICING) { + selectedLinks.add(d) + l.classed("red-ui-flow-link-splice",true) + redraw() + } + }) var pathOutline = document.createElementNS("http://www.w3.org/2000/svg","path"); pathOutline.__data__ = d; diff --git a/packages/node_modules/@node-red/editor-client/src/sass/flow.scss b/packages/node_modules/@node-red/editor-client/src/sass/flow.scss index 860ec1095..f3dd1ca44 100644 --- a/packages/node_modules/@node-red/editor-client/src/sass/flow.scss +++ b/packages/node_modules/@node-red/editor-client/src/sass/flow.scss @@ -21,6 +21,13 @@ stroke-dasharray: 10 5; } +.nr-ui-view-slice { + stroke-width: 1px; + stroke: $view-lasso-stroke; + fill: none; + stroke-dasharray: 10 5; +} + .node_label_italic, // deprecated: use red-ui-flow-node-label-italic .red-ui-flow-node-label-italic { font-style: italic; From af949c62c2bf16d875c5331f8d7cfab572cf955d Mon Sep 17 00:00:00 2001 From: Nick O'Leary Date: Wed, 12 Jan 2022 17:24:25 +0000 Subject: [PATCH 2/2] Allow 'escape' to cancel wire-slicing --- .../@node-red/editor-client/src/js/ui/view.js | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/packages/node_modules/@node-red/editor-client/src/js/ui/view.js b/packages/node_modules/@node-red/editor-client/src/js/ui/view.js index 90ed7f901..ce55c6acb 100755 --- a/packages/node_modules/@node-red/editor-client/src/js/ui/view.js +++ b/packages/node_modules/@node-red/editor-client/src/js/ui/view.js @@ -1959,6 +1959,16 @@ RED.view = (function() { clearSelection(); RED.history.pop(); mouse_mode = 0; + } else if (mouse_mode === RED.state.SLICING) { + if (slicePath) { + slicePath.remove(); + slicePath = null; + resetMouseVars() + } + clearSelection(); + } else if (lasso) { + lasso.remove(); + lasso = null; } else if (activeGroup) { exitActiveGroup() } else {