perf: improve new element drawing (#8340)

Co-authored-by: dwelle <5153846+dwelle@users.noreply.github.com>
This commit is contained in:
Ryan Di 2024-08-24 02:27:57 +08:00 committed by GitHub
parent b5d7f5b4ba
commit 5e1ff7cafe
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
34 changed files with 749 additions and 495 deletions

View file

@ -159,26 +159,42 @@ export const getDragOffsetXY = (
return [x - x1, y - y1];
};
export const dragNewElement = (
newElement: NonDeletedExcalidrawElement,
elementType: AppState["activeTool"]["type"],
originX: number,
originY: number,
x: number,
y: number,
width: number,
height: number,
shouldMaintainAspectRatio: boolean,
shouldResizeFromCenter: boolean,
zoom: NormalizedZoomValue,
export const dragNewElement = ({
newElement,
elementType,
originX,
originY,
x,
y,
width,
height,
shouldMaintainAspectRatio,
shouldResizeFromCenter,
zoom,
widthAspectRatio = null,
originOffset = null,
informMutation = true,
}: {
newElement: NonDeletedExcalidrawElement;
elementType: AppState["activeTool"]["type"];
originX: number;
originY: number;
x: number;
y: number;
width: number;
height: number;
shouldMaintainAspectRatio: boolean;
shouldResizeFromCenter: boolean;
zoom: NormalizedZoomValue;
/** whether to keep given aspect ratio when `isResizeWithSidesSameLength` is
true */
widthAspectRatio?: number | null,
originOffset: {
widthAspectRatio?: number | null;
originOffset?: {
x: number;
y: number;
} | null = null,
) => {
} | null;
informMutation?: boolean;
}) => {
if (shouldMaintainAspectRatio && newElement.type !== "selection") {
if (widthAspectRatio) {
height = width / widthAspectRatio;
@ -242,12 +258,16 @@ export const dragNewElement = (
}
if (width !== 0 && height !== 0) {
mutateElement(newElement, {
x: newX + (originOffset?.x ?? 0),
y: newY + (originOffset?.y ?? 0),
width,
height,
...textAutoResize,
});
mutateElement(
newElement,
{
x: newX + (originOffset?.x ?? 0),
y: newY + (originOffset?.y ?? 0),
width,
height,
...textAutoResize,
},
informMutation,
);
}
};

View file

@ -375,12 +375,13 @@ export const newFreeDrawElement = (
type: "freedraw";
points?: ExcalidrawFreeDrawElement["points"];
simulatePressure: boolean;
pressures?: ExcalidrawFreeDrawElement["pressures"];
} & ElementConstructorOpts,
): NonDeleted<ExcalidrawFreeDrawElement> => {
return {
..._newElementBase<ExcalidrawFreeDrawElement>(opts.type, opts),
points: opts.points || [],
pressures: [],
pressures: opts.pressures || [],
simulatePressure: opts.simulatePressure,
lastCommittedPoint: null,
};

View file

@ -9,7 +9,7 @@ export const showSelectedShapeActions = (
Boolean(
!appState.viewModeEnabled &&
((appState.activeTool.type !== "custom" &&
(appState.editingElement ||
(appState.editingTextElement ||
(appState.activeTool.type !== "selection" &&
appState.activeTool.type !== "eraser" &&
appState.activeTool.type !== "hand" &&

View file

@ -61,9 +61,9 @@ describe("textWysiwyg", () => {
Keyboard.keyPress(KEYS.ENTER);
expect(h.state.editingElement?.id).toBe(text.id);
expect(h.state.editingTextElement?.id).toBe(text.id);
expect(
(h.state.editingElement as ExcalidrawTextElement).containerId,
(h.state.editingTextElement as ExcalidrawTextElement).containerId,
).toBe(null);
});
@ -105,7 +105,7 @@ describe("textWysiwyg", () => {
Keyboard.keyPress(KEYS.ENTER);
expect(h.state.editingElement?.id).toBe(boundText2.id);
expect(h.state.editingTextElement?.id).toBe(boundText2.id);
});
it("should not create bound text on ENTER if text exists at container center", () => {
@ -133,7 +133,7 @@ describe("textWysiwyg", () => {
Keyboard.keyPress(KEYS.ENTER);
expect(h.state.editingElement?.id).toBe(text.id);
expect(h.state.editingTextElement?.id).toBe(text.id);
});
it("should edit existing bound text on ENTER even if higher z-index unbound text exists at container center", () => {
@ -174,7 +174,7 @@ describe("textWysiwyg", () => {
Keyboard.keyPress(KEYS.ENTER);
expect(h.state.editingElement?.id).toBe(boundText.id);
expect(h.state.editingTextElement?.id).toBe(boundText.id);
});
it("should edit text under cursor when clicked with text tool", async () => {
@ -195,7 +195,7 @@ describe("textWysiwyg", () => {
const editor = await getTextEditor(textEditorSelector, false);
expect(editor).not.toBe(null);
expect(h.state.editingElement?.id).toBe(text.id);
expect(h.state.editingTextElement?.id).toBe(text.id);
expect(h.elements.length).toBe(1);
});
@ -217,7 +217,7 @@ describe("textWysiwyg", () => {
const editor = await getTextEditor(textEditorSelector, false);
expect(editor).not.toBe(null);
expect(h.state.editingElement?.id).toBe(text.id);
expect(h.state.editingTextElement?.id).toBe(text.id);
expect(h.elements.length).toBe(1);
});
@ -286,7 +286,7 @@ describe("textWysiwyg", () => {
mouse.doubleClickAt(text.x + text.width / 2, text.y + text.height / 2);
const editor = await getTextEditor(textEditorSelector);
expect(editor).not.toBe(null);
expect(h.state.editingElement?.id).toBe(text.id);
expect(h.state.editingTextElement?.id).toBe(text.id);
expect(h.elements.length).toBe(1);
const nextText = `${wrappedText} is great!`;
@ -881,7 +881,7 @@ describe("textWysiwyg", () => {
expect(await getTextEditor(textEditorSelector, false)).toBe(null);
expect(h.state.editingElement).toBe(null);
expect(h.state.editingTextElement).toBe(null);
expect(text.fontFamily).toEqual(FONT_FAMILY.Excalifont);