feat: cycle through selected elements on cmd/ctrl-click

cycle_selection
dwelle 4 years ago
parent c819b653bf
commit 0e3a5b2042

@ -1862,6 +1862,7 @@ class App extends React.Component<AppProps, AppState> {
/** if true, returns the first selected element (with highest z-index)
of all hit elements */
preferSelected?: boolean;
cycleElementsUnderCursor?: boolean;
},
): NonDeleted<ExcalidrawElement> | null {
const allHitElements = this.getElementsAtPosition(x, y);
@ -1872,6 +1873,13 @@ class App extends React.Component<AppProps, AppState> {
return allHitElements[index];
}
}
} else if (opts?.cycleElementsUnderCursor) {
const selectedIdx = allHitElements.findIndex(
(element) => this.state.selectedElementIds[element.id],
);
return selectedIdx > 0
? allHitElements[selectedIdx - 1]
: allHitElements[allHitElements.length - 1];
}
const elementWithHighestZIndex =
allHitElements[allHitElements.length - 1];
@ -2746,10 +2754,13 @@ class App extends React.Component<AppProps, AppState> {
// hitElement may already be set above, so check first
pointerDownState.hit.element =
pointerDownState.hit.element ??
(!event[KEYS.CTRL_OR_CMD] ? pointerDownState.hit.element : null) ??
this.getElementAtPosition(
pointerDownState.origin.x,
pointerDownState.origin.y,
{
cycleElementsUnderCursor: event[KEYS.CTRL_OR_CMD],
},
);
// For overlapped elements one position may hit

@ -144,6 +144,52 @@ describe("inner box-selection", () => {
});
});
describe("selecting with cmd/ctrl modifier", () => {
beforeEach(async () => {
await render(<ExcalidrawApp />);
});
it("cycling through elements under cursor", async () => {
const rect1 = API.createElement({
type: "rectangle",
x: 0,
y: 0,
width: 200,
height: 200,
backgroundColor: "red",
fillStyle: "solid",
});
const rect2 = API.createElement({
type: "rectangle",
x: 0,
y: 0,
width: 200,
height: 200,
backgroundColor: "red",
fillStyle: "solid",
});
const rect3 = API.createElement({
type: "rectangle",
x: 0,
y: 0,
width: 200,
height: 200,
backgroundColor: "red",
fillStyle: "solid",
});
h.elements = [rect1, rect2, rect3];
Keyboard.withModifierKeys({ ctrl: true }, () => {
mouse.clickAt(100, 100);
assertSelectedElements(rect3);
mouse.clickAt(100, 100);
assertSelectedElements(rect2);
mouse.clickAt(100, 100);
assertSelectedElements(rect1);
mouse.clickAt(100, 100);
assertSelectedElements(rect3);
});
});
});
describe("selection element", () => {
it("create selection element on pointer down", async () => {
const { getByToolName, container } = await render(<ExcalidrawApp />);

Loading…
Cancel
Save