mirror of
https://github.com/excalidraw/excalidraw.git
synced 2025-11-15 18:25:58 +01:00
fix: restore from invalid fixedSegments & type-safer point updates (#9899)
* fix: restore from invalid fixedSegments & type-safer point updates * fix: Type updates and throw for invalid point states --------- Co-authored-by: Mark Tolmacs <mark@lazycat.hu>
This commit is contained in:
@@ -359,6 +359,12 @@ const handleSegmentRelease = (
|
|||||||
null,
|
null,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
if (!restoredPoints || restoredPoints.length < 2) {
|
||||||
|
throw new Error(
|
||||||
|
"Property 'points' is required in the update returned by normalizeArrowElementUpdate()",
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
const nextPoints: GlobalPoint[] = [];
|
const nextPoints: GlobalPoint[] = [];
|
||||||
|
|
||||||
// First part of the arrow are the old points
|
// First part of the arrow are the old points
|
||||||
@@ -706,7 +712,7 @@ const handleEndpointDrag = (
|
|||||||
endGlobalPoint: GlobalPoint,
|
endGlobalPoint: GlobalPoint,
|
||||||
hoveredStartElement: ExcalidrawBindableElement | null,
|
hoveredStartElement: ExcalidrawBindableElement | null,
|
||||||
hoveredEndElement: ExcalidrawBindableElement | null,
|
hoveredEndElement: ExcalidrawBindableElement | null,
|
||||||
) => {
|
): ElementUpdate<ExcalidrawElbowArrowElement> => {
|
||||||
let startIsSpecial = arrow.startIsSpecial ?? null;
|
let startIsSpecial = arrow.startIsSpecial ?? null;
|
||||||
let endIsSpecial = arrow.endIsSpecial ?? null;
|
let endIsSpecial = arrow.endIsSpecial ?? null;
|
||||||
const globalUpdatedPoints = updatedPoints.map((p, i) =>
|
const globalUpdatedPoints = updatedPoints.map((p, i) =>
|
||||||
@@ -741,8 +747,15 @@ const handleEndpointDrag = (
|
|||||||
|
|
||||||
// Calculate the moving second point connection and add the start point
|
// Calculate the moving second point connection and add the start point
|
||||||
{
|
{
|
||||||
const secondPoint = globalUpdatedPoints[startIsSpecial ? 2 : 1];
|
const secondPoint = globalUpdatedPoints.at(startIsSpecial ? 2 : 1);
|
||||||
const thirdPoint = globalUpdatedPoints[startIsSpecial ? 3 : 2];
|
const thirdPoint = globalUpdatedPoints.at(startIsSpecial ? 3 : 2);
|
||||||
|
|
||||||
|
if (!secondPoint || !thirdPoint) {
|
||||||
|
throw new Error(
|
||||||
|
`Second and third points must exist when handling endpoint drag (${startIsSpecial})`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
const startIsHorizontal = headingIsHorizontal(startHeading);
|
const startIsHorizontal = headingIsHorizontal(startHeading);
|
||||||
const secondIsHorizontal = headingIsHorizontal(
|
const secondIsHorizontal = headingIsHorizontal(
|
||||||
vectorToHeading(vectorFromPoint(secondPoint, thirdPoint)),
|
vectorToHeading(vectorFromPoint(secondPoint, thirdPoint)),
|
||||||
@@ -801,10 +814,19 @@ const handleEndpointDrag = (
|
|||||||
|
|
||||||
// Calculate the moving second to last point connection
|
// Calculate the moving second to last point connection
|
||||||
{
|
{
|
||||||
const secondToLastPoint =
|
const secondToLastPoint = globalUpdatedPoints.at(
|
||||||
globalUpdatedPoints[globalUpdatedPoints.length - (endIsSpecial ? 3 : 2)];
|
globalUpdatedPoints.length - (endIsSpecial ? 3 : 2),
|
||||||
const thirdToLastPoint =
|
);
|
||||||
globalUpdatedPoints[globalUpdatedPoints.length - (endIsSpecial ? 4 : 3)];
|
const thirdToLastPoint = globalUpdatedPoints.at(
|
||||||
|
globalUpdatedPoints.length - (endIsSpecial ? 4 : 3),
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!secondToLastPoint || !thirdToLastPoint) {
|
||||||
|
throw new Error(
|
||||||
|
`Second and third to last points must exist when handling endpoint drag (${endIsSpecial})`,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
const endIsHorizontal = headingIsHorizontal(endHeading);
|
const endIsHorizontal = headingIsHorizontal(endHeading);
|
||||||
const secondIsHorizontal = headingForPointIsHorizontal(
|
const secondIsHorizontal = headingForPointIsHorizontal(
|
||||||
thirdToLastPoint,
|
thirdToLastPoint,
|
||||||
@@ -2071,16 +2093,7 @@ const normalizeArrowElementUpdate = (
|
|||||||
nextFixedSegments: readonly FixedSegment[] | null,
|
nextFixedSegments: readonly FixedSegment[] | null,
|
||||||
startIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"],
|
startIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"],
|
||||||
endIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"],
|
endIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"],
|
||||||
): {
|
): ElementUpdate<ExcalidrawElbowArrowElement> => {
|
||||||
points: LocalPoint[];
|
|
||||||
x: number;
|
|
||||||
y: number;
|
|
||||||
width: number;
|
|
||||||
height: number;
|
|
||||||
fixedSegments: readonly FixedSegment[] | null;
|
|
||||||
startIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"];
|
|
||||||
endIsSpecial?: ExcalidrawElbowArrowElement["startIsSpecial"];
|
|
||||||
} => {
|
|
||||||
const offsetX = global[0][0];
|
const offsetX = global[0][0];
|
||||||
const offsetY = global[0][1];
|
const offsetY = global[0][1];
|
||||||
let points = global.map((p) =>
|
let points = global.map((p) =>
|
||||||
|
|||||||
@@ -387,7 +387,10 @@ export const restoreElement = (
|
|||||||
elbowed: true,
|
elbowed: true,
|
||||||
startBinding: repairBinding(element, element.startBinding),
|
startBinding: repairBinding(element, element.startBinding),
|
||||||
endBinding: repairBinding(element, element.endBinding),
|
endBinding: repairBinding(element, element.endBinding),
|
||||||
fixedSegments: element.fixedSegments,
|
fixedSegments:
|
||||||
|
element.fixedSegments?.length && base.points.length >= 4
|
||||||
|
? element.fixedSegments
|
||||||
|
: null,
|
||||||
startIsSpecial: element.startIsSpecial,
|
startIsSpecial: element.startIsSpecial,
|
||||||
endIsSpecial: element.endIsSpecial,
|
endIsSpecial: element.endIsSpecial,
|
||||||
})
|
})
|
||||||
|
|||||||
Reference in New Issue
Block a user