feat: grid mode for line editing (#1984)
This commit is contained in:
parent
c171fb4c7f
commit
818821c293
@ -1883,6 +1883,7 @@ class App extends React.Component<ExcalidrawProps, AppState> {
|
||||
scenePointerX,
|
||||
scenePointerY,
|
||||
this.state.editingLinearElement,
|
||||
this.state.gridSize,
|
||||
);
|
||||
if (editingLinearElement !== this.state.editingLinearElement) {
|
||||
this.setState({ editingLinearElement });
|
||||
@ -2778,8 +2779,6 @@ class App extends React.Component<ExcalidrawProps, AppState> {
|
||||
(appState) => this.setState(appState),
|
||||
x,
|
||||
y,
|
||||
pointerDownState.lastCoords.x,
|
||||
pointerDownState.lastCoords.y,
|
||||
);
|
||||
|
||||
if (didDrag) {
|
||||
|
@ -3,7 +3,7 @@ import {
|
||||
ExcalidrawLinearElement,
|
||||
ExcalidrawElement,
|
||||
} from "./types";
|
||||
import { distance2d, rotate, isPathALoop } from "../math";
|
||||
import { distance2d, rotate, isPathALoop, getGridPoint } from "../math";
|
||||
import { getElementAbsoluteCoords } from ".";
|
||||
import { getElementPointsCoords } from "./bounds";
|
||||
import { Point, AppState } from "../types";
|
||||
@ -20,6 +20,7 @@ export class LinearElementEditor {
|
||||
/** whether you're dragging a point */
|
||||
public isDragging: boolean;
|
||||
public lastUncommittedPoint: Point | null;
|
||||
public pointerOffset: { x: number; y: number };
|
||||
|
||||
constructor(element: NonDeleted<ExcalidrawLinearElement>, scene: Scene) {
|
||||
this.elementId = element.id as string & {
|
||||
@ -31,6 +32,7 @@ export class LinearElementEditor {
|
||||
this.activePointIndex = null;
|
||||
this.lastUncommittedPoint = null;
|
||||
this.isDragging = false;
|
||||
this.pointerOffset = { x: 0, y: 0 };
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
@ -57,8 +59,6 @@ export class LinearElementEditor {
|
||||
setState: React.Component<any, AppState>["setState"],
|
||||
scenePointerX: number,
|
||||
scenePointerY: number,
|
||||
lastX: number,
|
||||
lastY: number,
|
||||
): boolean {
|
||||
if (!appState.editingLinearElement) {
|
||||
return false;
|
||||
@ -80,18 +80,14 @@ export class LinearElementEditor {
|
||||
},
|
||||
});
|
||||
}
|
||||
const [deltaX, deltaY] = rotate(
|
||||
scenePointerX - lastX,
|
||||
scenePointerY - lastY,
|
||||
0,
|
||||
0,
|
||||
-element.angle,
|
||||
|
||||
const newPoint = LinearElementEditor.createPointAt(
|
||||
element,
|
||||
scenePointerX - editingLinearElement.pointerOffset.x,
|
||||
scenePointerY - editingLinearElement.pointerOffset.y,
|
||||
appState.gridSize,
|
||||
);
|
||||
const targetPoint = element.points[activePointIndex];
|
||||
LinearElementEditor.movePoint(element, activePointIndex, [
|
||||
targetPoint[0] + deltaX,
|
||||
targetPoint[1] + deltaY,
|
||||
]);
|
||||
LinearElementEditor.movePoint(element, activePointIndex, newPoint);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@ -120,13 +116,11 @@ export class LinearElementEditor {
|
||||
: element.points[0],
|
||||
);
|
||||
}
|
||||
if (isDragging) {
|
||||
return {
|
||||
...editingLinearElement,
|
||||
isDragging: false,
|
||||
};
|
||||
}
|
||||
return editingLinearElement;
|
||||
return {
|
||||
...editingLinearElement,
|
||||
isDragging: false,
|
||||
pointerOffset: { x: 0, y: 0 },
|
||||
};
|
||||
}
|
||||
|
||||
static handlePointerDown(
|
||||
@ -165,6 +159,7 @@ export class LinearElementEditor {
|
||||
element,
|
||||
scenePointerX,
|
||||
scenePointerY,
|
||||
appState.gridSize,
|
||||
),
|
||||
],
|
||||
});
|
||||
@ -194,10 +189,29 @@ export class LinearElementEditor {
|
||||
ret.hitElement = element;
|
||||
}
|
||||
|
||||
const [x1, y1, x2, y2] = getElementAbsoluteCoords(element);
|
||||
const cx = (x1 + x2) / 2;
|
||||
const cy = (y1 + y2) / 2;
|
||||
const targetPoint =
|
||||
clickedPointIndex > -1 &&
|
||||
rotate(
|
||||
element.x + element.points[clickedPointIndex][0],
|
||||
element.y + element.points[clickedPointIndex][1],
|
||||
cx,
|
||||
cy,
|
||||
element.angle,
|
||||
);
|
||||
|
||||
setState({
|
||||
editingLinearElement: {
|
||||
...appState.editingLinearElement,
|
||||
activePointIndex: clickedPointIndex > -1 ? clickedPointIndex : null,
|
||||
pointerOffset: targetPoint
|
||||
? {
|
||||
x: scenePointerX - targetPoint[0],
|
||||
y: scenePointerY - targetPoint[1],
|
||||
}
|
||||
: { x: 0, y: 0 },
|
||||
},
|
||||
});
|
||||
return ret;
|
||||
@ -208,6 +222,7 @@ export class LinearElementEditor {
|
||||
scenePointerX: number,
|
||||
scenePointerY: number,
|
||||
editingLinearElement: LinearElementEditor,
|
||||
gridSize: number | null,
|
||||
): LinearElementEditor {
|
||||
const { elementId, lastUncommittedPoint } = editingLinearElement;
|
||||
const element = LinearElementEditor.getElement(elementId);
|
||||
@ -227,8 +242,9 @@ export class LinearElementEditor {
|
||||
|
||||
const newPoint = LinearElementEditor.createPointAt(
|
||||
element,
|
||||
scenePointerX,
|
||||
scenePointerY,
|
||||
scenePointerX - editingLinearElement.pointerOffset.x,
|
||||
scenePointerY - editingLinearElement.pointerOffset.y,
|
||||
gridSize,
|
||||
);
|
||||
|
||||
if (lastPoint === lastUncommittedPoint) {
|
||||
@ -288,13 +304,15 @@ export class LinearElementEditor {
|
||||
element: NonDeleted<ExcalidrawLinearElement>,
|
||||
scenePointerX: number,
|
||||
scenePointerY: number,
|
||||
gridSize: number | null,
|
||||
): Point {
|
||||
const pointerOnGrid = getGridPoint(scenePointerX, scenePointerY, gridSize);
|
||||
const [x1, y1, x2, y2] = getElementAbsoluteCoords(element);
|
||||
const cx = (x1 + x2) / 2;
|
||||
const cy = (y1 + y2) / 2;
|
||||
const [rotatedX, rotatedY] = rotate(
|
||||
scenePointerX,
|
||||
scenePointerY,
|
||||
pointerOnGrid[0],
|
||||
pointerOnGrid[1],
|
||||
cx,
|
||||
cy,
|
||||
-element.angle,
|
||||
|
Loading…
x
Reference in New Issue
Block a user