From bc2bae2a9a9d37435d39ad51dfd7fec1d6e38433 Mon Sep 17 00:00:00 2001 From: Timur Khazamov Date: Mon, 13 Jan 2020 04:32:25 +0500 Subject: [PATCH] Shift drag to add to selection (#355) * Shift drag to add to selection * Inlined variable --- src/index.tsx | 24 +++++++++++++++++------- src/scene/index.ts | 2 +- src/scene/selection.ts | 12 ++++++------ 3 files changed, 24 insertions(+), 14 deletions(-) diff --git a/src/index.tsx b/src/index.tsx index 7f0cf643a..a018987f4 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -15,7 +15,7 @@ import { import { clearSelection, deleteSelectedElements, - setSelection, + getElementsWithinSelection, isOverScrollBars, restoreFromLocalStorage, saveToLocalStorage, @@ -510,11 +510,11 @@ export class App extends React.Component<{}, AppState> { document.documentElement.style.cursor = `${resizeHandle}-resize`; isResizingElements = true; } else { + hitElement = getElementAtPosition(elements, x, y); // clear selection if shift is not clicked - if (!e.shiftKey) { + if (!hitElement?.isSelected && !e.shiftKey) { elements = clearSelection(elements); } - hitElement = getElementAtPosition(elements, x, y); // If we click on something if (hitElement) { @@ -746,13 +746,23 @@ export class App extends React.Component<{}, AppState> { this.state.scrollY; draggingElement.width = width; // Make a perfect square or circle when shift is enabled - draggingElement.height = e.shiftKey - ? Math.abs(width) * Math.sign(height) - : height; + draggingElement.height = + e.shiftKey && this.state.elementType !== "selection" + ? Math.abs(width) * Math.sign(height) + : height; draggingElement.shape = null; if (this.state.elementType === "selection") { - elements = setSelection(elements, draggingElement); + if (!e.shiftKey) { + elements = clearSelection(elements); + } + const elementsWithinSelection = getElementsWithinSelection( + elements, + draggingElement + ); + elementsWithinSelection.forEach(element => { + element.isSelected = true; + }); } // We don't want to save history when moving an element history.skipRecording(); diff --git a/src/scene/index.ts b/src/scene/index.ts index e812a8271..21e896908 100644 --- a/src/scene/index.ts +++ b/src/scene/index.ts @@ -4,7 +4,7 @@ export { getSelectedIndices, deleteSelectedElements, someElementIsSelected, - setSelection, + getElementsWithinSelection, getSelectedAttribute } from "./selection"; export { diff --git a/src/scene/selection.ts b/src/scene/selection.ts index 6347fae8c..73b0a2db2 100644 --- a/src/scene/selection.ts +++ b/src/scene/selection.ts @@ -1,7 +1,7 @@ import { ExcalidrawElement } from "../element/types"; import { getElementAbsoluteCoords } from "../element"; -export function setSelection( +export function getElementsWithinSelection( elements: readonly ExcalidrawElement[], selection: ExcalidrawElement ) { @@ -11,22 +11,22 @@ export function setSelection( selectionX2, selectionY2 ] = getElementAbsoluteCoords(selection); - elements.forEach(element => { + return elements.filter(element => { const [ elementX1, elementY1, elementX2, elementY2 ] = getElementAbsoluteCoords(element); - element.isSelected = + + return ( element.type !== "selection" && selectionX1 <= elementX1 && selectionY1 <= elementY1 && selectionX2 >= elementX2 && - selectionY2 >= elementY2; + selectionY2 >= elementY2 + ); }); - - return elements; } export function clearSelection(elements: readonly ExcalidrawElement[]) {