mirror of
https://github.com/excalidraw/excalidraw.git
synced 2025-05-03 10:00:07 -04:00
refactor: point()
-> pointFrom()
to fix compiler issue (#8578)
This commit is contained in:
parent
a977dd1bf5
commit
47ee8a0094
51 changed files with 845 additions and 703 deletions
|
@ -66,7 +66,7 @@ import {
|
|||
import type { LocalPoint, Radians } from "../../math";
|
||||
import {
|
||||
lineSegment,
|
||||
point,
|
||||
pointFrom,
|
||||
pointRotateRads,
|
||||
type GlobalPoint,
|
||||
vectorFromPoint,
|
||||
|
@ -720,7 +720,7 @@ export const getHeadingForElbowArrowSnap = (
|
|||
return vectorToHeading(
|
||||
vectorFromPoint(
|
||||
p,
|
||||
point<GlobalPoint>(
|
||||
pointFrom<GlobalPoint>(
|
||||
bindableElement.x + bindableElement.width / 2,
|
||||
bindableElement.y + bindableElement.height / 2,
|
||||
),
|
||||
|
@ -766,15 +766,15 @@ export const bindPointToSnapToElementOutline = (
|
|||
const intersections = [
|
||||
...(intersectElementWithLine(
|
||||
bindableElement,
|
||||
point(p[0], p[1] - 2 * bindableElement.height),
|
||||
point(p[0], p[1] + 2 * bindableElement.height),
|
||||
pointFrom(p[0], p[1] - 2 * bindableElement.height),
|
||||
pointFrom(p[0], p[1] + 2 * bindableElement.height),
|
||||
FIXED_BINDING_DISTANCE,
|
||||
elementsMap,
|
||||
) ?? []),
|
||||
...(intersectElementWithLine(
|
||||
bindableElement,
|
||||
point(p[0] - 2 * bindableElement.width, p[1]),
|
||||
point(p[0] + 2 * bindableElement.width, p[1]),
|
||||
pointFrom(p[0] - 2 * bindableElement.width, p[1]),
|
||||
pointFrom(p[0] + 2 * bindableElement.width, p[1]),
|
||||
FIXED_BINDING_DISTANCE,
|
||||
elementsMap,
|
||||
) ?? []),
|
||||
|
@ -815,25 +815,25 @@ const headingToMidBindPoint = (
|
|||
switch (true) {
|
||||
case compareHeading(heading, HEADING_UP):
|
||||
return pointRotateRads(
|
||||
point((aabb[0] + aabb[2]) / 2 + 0.1, aabb[1]),
|
||||
pointFrom((aabb[0] + aabb[2]) / 2 + 0.1, aabb[1]),
|
||||
center,
|
||||
bindableElement.angle,
|
||||
);
|
||||
case compareHeading(heading, HEADING_RIGHT):
|
||||
return pointRotateRads(
|
||||
point(aabb[2], (aabb[1] + aabb[3]) / 2 + 0.1),
|
||||
pointFrom(aabb[2], (aabb[1] + aabb[3]) / 2 + 0.1),
|
||||
center,
|
||||
bindableElement.angle,
|
||||
);
|
||||
case compareHeading(heading, HEADING_DOWN):
|
||||
return pointRotateRads(
|
||||
point((aabb[0] + aabb[2]) / 2 - 0.1, aabb[3]),
|
||||
pointFrom((aabb[0] + aabb[2]) / 2 - 0.1, aabb[3]),
|
||||
center,
|
||||
bindableElement.angle,
|
||||
);
|
||||
default:
|
||||
return pointRotateRads(
|
||||
point(aabb[0], (aabb[1] + aabb[3]) / 2 - 0.1),
|
||||
pointFrom(aabb[0], (aabb[1] + aabb[3]) / 2 - 0.1),
|
||||
center,
|
||||
bindableElement.angle,
|
||||
);
|
||||
|
@ -844,7 +844,7 @@ export const avoidRectangularCorner = (
|
|||
element: ExcalidrawBindableElement,
|
||||
p: GlobalPoint,
|
||||
): GlobalPoint => {
|
||||
const center = point<GlobalPoint>(
|
||||
const center = pointFrom<GlobalPoint>(
|
||||
element.x + element.width / 2,
|
||||
element.y + element.height / 2,
|
||||
);
|
||||
|
@ -854,13 +854,13 @@ export const avoidRectangularCorner = (
|
|||
// Top left
|
||||
if (nonRotatedPoint[1] - element.y > -FIXED_BINDING_DISTANCE) {
|
||||
return pointRotateRads<GlobalPoint>(
|
||||
point(element.x - FIXED_BINDING_DISTANCE, element.y),
|
||||
pointFrom(element.x - FIXED_BINDING_DISTANCE, element.y),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
}
|
||||
return pointRotateRads(
|
||||
point(element.x, element.y - FIXED_BINDING_DISTANCE),
|
||||
pointFrom(element.x, element.y - FIXED_BINDING_DISTANCE),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
|
@ -871,13 +871,16 @@ export const avoidRectangularCorner = (
|
|||
// Bottom left
|
||||
if (nonRotatedPoint[0] - element.x > -FIXED_BINDING_DISTANCE) {
|
||||
return pointRotateRads(
|
||||
point(element.x, element.y + element.height + FIXED_BINDING_DISTANCE),
|
||||
pointFrom(
|
||||
element.x,
|
||||
element.y + element.height + FIXED_BINDING_DISTANCE,
|
||||
),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
}
|
||||
return pointRotateRads(
|
||||
point(element.x - FIXED_BINDING_DISTANCE, element.y + element.height),
|
||||
pointFrom(element.x - FIXED_BINDING_DISTANCE, element.y + element.height),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
|
@ -891,7 +894,7 @@ export const avoidRectangularCorner = (
|
|||
element.width + FIXED_BINDING_DISTANCE
|
||||
) {
|
||||
return pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.x + element.width,
|
||||
element.y + element.height + FIXED_BINDING_DISTANCE,
|
||||
),
|
||||
|
@ -900,7 +903,7 @@ export const avoidRectangularCorner = (
|
|||
);
|
||||
}
|
||||
return pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.x + element.width + FIXED_BINDING_DISTANCE,
|
||||
element.y + element.height,
|
||||
),
|
||||
|
@ -917,13 +920,16 @@ export const avoidRectangularCorner = (
|
|||
element.width + FIXED_BINDING_DISTANCE
|
||||
) {
|
||||
return pointRotateRads(
|
||||
point(element.x + element.width, element.y - FIXED_BINDING_DISTANCE),
|
||||
pointFrom(
|
||||
element.x + element.width,
|
||||
element.y - FIXED_BINDING_DISTANCE,
|
||||
),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
}
|
||||
return pointRotateRads(
|
||||
point(element.x + element.width + FIXED_BINDING_DISTANCE, element.y),
|
||||
pointFrom(element.x + element.width + FIXED_BINDING_DISTANCE, element.y),
|
||||
center,
|
||||
element.angle,
|
||||
);
|
||||
|
@ -938,7 +944,10 @@ export const snapToMid = (
|
|||
tolerance: number = 0.05,
|
||||
): GlobalPoint => {
|
||||
const { x, y, width, height, angle } = element;
|
||||
const center = point<GlobalPoint>(x + width / 2 - 0.1, y + height / 2 - 0.1);
|
||||
const center = pointFrom<GlobalPoint>(
|
||||
x + width / 2 - 0.1,
|
||||
y + height / 2 - 0.1,
|
||||
);
|
||||
const nonRotated = pointRotateRads(p, center, -angle as Radians);
|
||||
|
||||
// snap-to-center point is adaptive to element size, but we don't want to go
|
||||
|
@ -953,7 +962,7 @@ export const snapToMid = (
|
|||
) {
|
||||
// LEFT
|
||||
return pointRotateRads(
|
||||
point(x - FIXED_BINDING_DISTANCE, center[1]),
|
||||
pointFrom(x - FIXED_BINDING_DISTANCE, center[1]),
|
||||
center,
|
||||
angle,
|
||||
);
|
||||
|
@ -964,7 +973,7 @@ export const snapToMid = (
|
|||
) {
|
||||
// TOP
|
||||
return pointRotateRads(
|
||||
point(center[0], y - FIXED_BINDING_DISTANCE),
|
||||
pointFrom(center[0], y - FIXED_BINDING_DISTANCE),
|
||||
center,
|
||||
angle,
|
||||
);
|
||||
|
@ -975,7 +984,7 @@ export const snapToMid = (
|
|||
) {
|
||||
// RIGHT
|
||||
return pointRotateRads(
|
||||
point(x + width + FIXED_BINDING_DISTANCE, center[1]),
|
||||
pointFrom(x + width + FIXED_BINDING_DISTANCE, center[1]),
|
||||
center,
|
||||
angle,
|
||||
);
|
||||
|
@ -986,7 +995,7 @@ export const snapToMid = (
|
|||
) {
|
||||
// DOWN
|
||||
return pointRotateRads(
|
||||
point(center[0], y + height + FIXED_BINDING_DISTANCE),
|
||||
pointFrom(center[0], y + height + FIXED_BINDING_DISTANCE),
|
||||
center,
|
||||
angle,
|
||||
);
|
||||
|
@ -1023,11 +1032,11 @@ const updateBoundPoint = (
|
|||
startOrEnd === "startBinding" ? "start" : "end",
|
||||
elementsMap,
|
||||
).fixedPoint;
|
||||
const globalMidPoint = point<GlobalPoint>(
|
||||
const globalMidPoint = pointFrom<GlobalPoint>(
|
||||
bindableElement.x + bindableElement.width / 2,
|
||||
bindableElement.y + bindableElement.height / 2,
|
||||
);
|
||||
const global = point<GlobalPoint>(
|
||||
const global = pointFrom<GlobalPoint>(
|
||||
bindableElement.x + fixedPoint[0] * bindableElement.width,
|
||||
bindableElement.y + fixedPoint[1] * bindableElement.height,
|
||||
);
|
||||
|
@ -1118,7 +1127,7 @@ export const calculateFixedPointForElbowArrowBinding = (
|
|||
hoveredElement,
|
||||
elementsMap,
|
||||
);
|
||||
const globalMidPoint = point(
|
||||
const globalMidPoint = pointFrom(
|
||||
bounds[0] + (bounds[2] - bounds[0]) / 2,
|
||||
bounds[1] + (bounds[3] - bounds[1]) / 2,
|
||||
);
|
||||
|
@ -1337,9 +1346,9 @@ export const bindingBorderTest = (
|
|||
const threshold = maxBindingGap(element, element.width, element.height);
|
||||
const shape = getElementShape(element, elementsMap);
|
||||
return (
|
||||
isPointOnShape(point(x, y), shape, threshold) ||
|
||||
isPointOnShape(pointFrom(x, y), shape, threshold) ||
|
||||
(fullShape === true &&
|
||||
pointInsideBounds(point(x, y), aabbForElement(element)))
|
||||
pointInsideBounds(pointFrom(x, y), aabbForElement(element)))
|
||||
);
|
||||
};
|
||||
|
||||
|
@ -2197,11 +2206,11 @@ export const getGlobalFixedPointForBindableElement = (
|
|||
const [fixedX, fixedY] = normalizeFixedPoint(fixedPointRatio);
|
||||
|
||||
return pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.x + element.width * fixedX,
|
||||
element.y + element.height * fixedY,
|
||||
),
|
||||
point<GlobalPoint>(
|
||||
pointFrom<GlobalPoint>(
|
||||
element.x + element.width / 2,
|
||||
element.y + element.height / 2,
|
||||
),
|
||||
|
@ -2229,7 +2238,7 @@ const getGlobalFixedPoints = (
|
|||
arrow.startBinding.fixedPoint,
|
||||
startElement as ExcalidrawBindableElement,
|
||||
)
|
||||
: point<GlobalPoint>(
|
||||
: pointFrom<GlobalPoint>(
|
||||
arrow.x + arrow.points[0][0],
|
||||
arrow.y + arrow.points[0][1],
|
||||
);
|
||||
|
@ -2239,7 +2248,7 @@ const getGlobalFixedPoints = (
|
|||
arrow.endBinding.fixedPoint,
|
||||
endElement as ExcalidrawBindableElement,
|
||||
)
|
||||
: point<GlobalPoint>(
|
||||
: pointFrom<GlobalPoint>(
|
||||
arrow.x + arrow.points[arrow.points.length - 1][0],
|
||||
arrow.y + arrow.points[arrow.points.length - 1][1],
|
||||
);
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
import type { LocalPoint } from "../../math";
|
||||
import { point } from "../../math";
|
||||
import { pointFrom } from "../../math";
|
||||
import { ROUNDNESS } from "../constants";
|
||||
import { arrayToMap } from "../utils";
|
||||
import { getElementAbsoluteCoords, getElementBounds } from "./bounds";
|
||||
|
@ -125,9 +125,9 @@ describe("getElementBounds", () => {
|
|||
a: 0.6447741904932416,
|
||||
}),
|
||||
points: [
|
||||
point<LocalPoint>(0, 0),
|
||||
point<LocalPoint>(67.33984375, 92.48828125),
|
||||
point<LocalPoint>(-102.7890625, 52.15625),
|
||||
pointFrom<LocalPoint>(0, 0),
|
||||
pointFrom<LocalPoint>(67.33984375, 92.48828125),
|
||||
pointFrom<LocalPoint>(-102.7890625, 52.15625),
|
||||
],
|
||||
} as ExcalidrawLinearElement;
|
||||
|
||||
|
|
|
@ -34,7 +34,7 @@ import type {
|
|||
import {
|
||||
degreesToRadians,
|
||||
lineSegment,
|
||||
point,
|
||||
pointFrom,
|
||||
pointDistance,
|
||||
pointFromArray,
|
||||
pointRotateRads,
|
||||
|
@ -113,8 +113,8 @@ export class ElementBounds {
|
|||
const [minX, minY, maxX, maxY] = getBoundsFromPoints(
|
||||
element.points.map(([x, y]) =>
|
||||
pointRotateRads(
|
||||
point(x, y),
|
||||
point(cx - element.x, cy - element.y),
|
||||
pointFrom(x, y),
|
||||
pointFrom(cx - element.x, cy - element.y),
|
||||
element.angle,
|
||||
),
|
||||
),
|
||||
|
@ -130,23 +130,23 @@ export class ElementBounds {
|
|||
bounds = getLinearElementRotatedBounds(element, cx, cy, elementsMap);
|
||||
} else if (element.type === "diamond") {
|
||||
const [x11, y11] = pointRotateRads(
|
||||
point(cx, y1),
|
||||
point(cx, cy),
|
||||
pointFrom(cx, y1),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x12, y12] = pointRotateRads(
|
||||
point(cx, y2),
|
||||
point(cx, cy),
|
||||
pointFrom(cx, y2),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x22, y22] = pointRotateRads(
|
||||
point(x1, cy),
|
||||
point(cx, cy),
|
||||
pointFrom(x1, cy),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x21, y21] = pointRotateRads(
|
||||
point(x2, cy),
|
||||
point(cx, cy),
|
||||
pointFrom(x2, cy),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const minX = Math.min(x11, x12, x22, x21);
|
||||
|
@ -164,23 +164,23 @@ export class ElementBounds {
|
|||
bounds = [cx - ww, cy - hh, cx + ww, cy + hh];
|
||||
} else {
|
||||
const [x11, y11] = pointRotateRads(
|
||||
point(x1, y1),
|
||||
point(cx, cy),
|
||||
pointFrom(x1, y1),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x12, y12] = pointRotateRads(
|
||||
point(x1, y2),
|
||||
point(cx, cy),
|
||||
pointFrom(x1, y2),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x22, y22] = pointRotateRads(
|
||||
point(x2, y2),
|
||||
point(cx, cy),
|
||||
pointFrom(x2, y2),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const [x21, y21] = pointRotateRads(
|
||||
point(x2, y1),
|
||||
point(cx, cy),
|
||||
pointFrom(x2, y1),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const minX = Math.min(x11, x12, x22, x21);
|
||||
|
@ -255,7 +255,7 @@ export const getElementLineSegments = (
|
|||
elementsMap,
|
||||
);
|
||||
|
||||
const center: GlobalPoint = point(cx, cy);
|
||||
const center: GlobalPoint = pointFrom(cx, cy);
|
||||
|
||||
if (isLinearElement(element) || isFreeDrawElement(element)) {
|
||||
const segments: LineSegment<GlobalPoint>[] = [];
|
||||
|
@ -266,7 +266,7 @@ export const getElementLineSegments = (
|
|||
segments.push(
|
||||
lineSegment(
|
||||
pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.points[i][0] + element.x,
|
||||
element.points[i][1] + element.y,
|
||||
),
|
||||
|
@ -274,7 +274,7 @@ export const getElementLineSegments = (
|
|||
element.angle,
|
||||
),
|
||||
pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.points[i + 1][0] + element.x,
|
||||
element.points[i + 1][1] + element.y,
|
||||
),
|
||||
|
@ -470,7 +470,7 @@ export const getMinMaxXYFromCurvePathOps = (
|
|||
ops: Op[],
|
||||
transformXY?: (p: GlobalPoint) => GlobalPoint,
|
||||
): Bounds => {
|
||||
let currentP: GlobalPoint = point(0, 0);
|
||||
let currentP: GlobalPoint = pointFrom(0, 0);
|
||||
|
||||
const { minX, minY, maxX, maxY } = ops.reduce(
|
||||
(limits, { op, data }) => {
|
||||
|
@ -484,9 +484,9 @@ export const getMinMaxXYFromCurvePathOps = (
|
|||
// move operation does not draw anything; so, it always
|
||||
// returns false
|
||||
} else if (op === "bcurveTo") {
|
||||
const _p1 = point<GlobalPoint>(data[0], data[1]);
|
||||
const _p2 = point<GlobalPoint>(data[2], data[3]);
|
||||
const _p3 = point<GlobalPoint>(data[4], data[5]);
|
||||
const _p1 = pointFrom<GlobalPoint>(data[0], data[1]);
|
||||
const _p2 = pointFrom<GlobalPoint>(data[2], data[3]);
|
||||
const _p3 = pointFrom<GlobalPoint>(data[4], data[5]);
|
||||
|
||||
const p1 = transformXY ? transformXY(_p1) : _p1;
|
||||
const p2 = transformXY ? transformXY(_p2) : _p2;
|
||||
|
@ -591,21 +591,21 @@ export const getArrowheadPoints = (
|
|||
|
||||
invariant(data.length === 6, "Op data length is not 6");
|
||||
|
||||
const p3 = point(data[4], data[5]);
|
||||
const p2 = point(data[2], data[3]);
|
||||
const p1 = point(data[0], data[1]);
|
||||
const p3 = pointFrom(data[4], data[5]);
|
||||
const p2 = pointFrom(data[2], data[3]);
|
||||
const p1 = pointFrom(data[0], data[1]);
|
||||
|
||||
// We need to find p0 of the bezier curve.
|
||||
// It is typically the last point of the previous
|
||||
// curve; it can also be the position of moveTo operation.
|
||||
const prevOp = ops[index - 1];
|
||||
let p0 = point(0, 0);
|
||||
let p0 = pointFrom(0, 0);
|
||||
if (prevOp.op === "move") {
|
||||
const p = pointFromArray(prevOp.data);
|
||||
invariant(p != null, "Op data is not a point");
|
||||
p0 = p;
|
||||
} else if (prevOp.op === "bcurveTo") {
|
||||
p0 = point(prevOp.data[4], prevOp.data[5]);
|
||||
p0 = pointFrom(prevOp.data[4], prevOp.data[5]);
|
||||
}
|
||||
|
||||
// B(t) = p0 * (1-t)^3 + 3p1 * t * (1-t)^2 + 3p2 * t^2 * (1-t) + p3 * t^3
|
||||
|
@ -671,13 +671,13 @@ export const getArrowheadPoints = (
|
|||
|
||||
// Return points
|
||||
const [x3, y3] = pointRotateRads(
|
||||
point(xs, ys),
|
||||
point(x2, y2),
|
||||
pointFrom(xs, ys),
|
||||
pointFrom(x2, y2),
|
||||
((-angle * Math.PI) / 180) as Radians,
|
||||
);
|
||||
const [x4, y4] = pointRotateRads(
|
||||
point(xs, ys),
|
||||
point(x2, y2),
|
||||
pointFrom(xs, ys),
|
||||
pointFrom(x2, y2),
|
||||
degreesToRadians(angle),
|
||||
);
|
||||
|
||||
|
@ -690,8 +690,8 @@ export const getArrowheadPoints = (
|
|||
const [px, py] = element.points.length > 1 ? element.points[1] : [0, 0];
|
||||
|
||||
[ox, oy] = pointRotateRads(
|
||||
point(x2 + minSize * 2, y2),
|
||||
point(x2, y2),
|
||||
pointFrom(x2 + minSize * 2, y2),
|
||||
pointFrom(x2, y2),
|
||||
Math.atan2(py - y2, px - x2) as Radians,
|
||||
);
|
||||
} else {
|
||||
|
@ -701,8 +701,8 @@ export const getArrowheadPoints = (
|
|||
: [0, 0];
|
||||
|
||||
[ox, oy] = pointRotateRads(
|
||||
point(x2 - minSize * 2, y2),
|
||||
point(x2, y2),
|
||||
pointFrom(x2 - minSize * 2, y2),
|
||||
pointFrom(x2, y2),
|
||||
Math.atan2(y2 - py, x2 - px) as Radians,
|
||||
);
|
||||
}
|
||||
|
@ -746,8 +746,8 @@ const getLinearElementRotatedBounds = (
|
|||
if (element.points.length < 2) {
|
||||
const [pointX, pointY] = element.points[0];
|
||||
const [x, y] = pointRotateRads(
|
||||
point(element.x + pointX, element.y + pointY),
|
||||
point(cx, cy),
|
||||
pointFrom(element.x + pointX, element.y + pointY),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
|
||||
|
@ -775,8 +775,8 @@ const getLinearElementRotatedBounds = (
|
|||
const ops = getCurvePathOps(shape);
|
||||
const transformXY = ([x, y]: GlobalPoint) =>
|
||||
pointRotateRads<GlobalPoint>(
|
||||
point(element.x + x, element.y + y),
|
||||
point(cx, cy),
|
||||
pointFrom(element.x + x, element.y + y),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
const res = getMinMaxXYFromCurvePathOps(ops, transformXY);
|
||||
|
@ -931,8 +931,8 @@ export const getClosestElementBounds = (
|
|||
elements.forEach((element) => {
|
||||
const [x1, y1, x2, y2] = getElementBounds(element, elementsMap);
|
||||
const distance = pointDistance(
|
||||
point((x1 + x2) / 2, (y1 + y2) / 2),
|
||||
point(from.x, from.y),
|
||||
pointFrom((x1 + x2) / 2, (y1 + y2) / 2),
|
||||
pointFrom(from.x, from.y),
|
||||
);
|
||||
|
||||
if (distance < minDistance) {
|
||||
|
@ -990,7 +990,7 @@ export const getVisibleSceneBounds = ({
|
|||
};
|
||||
|
||||
export const getCenterForBounds = (bounds: Bounds): GlobalPoint =>
|
||||
point(
|
||||
pointFrom(
|
||||
bounds[0] + (bounds[2] - bounds[0]) / 2,
|
||||
bounds[1] + (bounds[3] - bounds[1]) / 2,
|
||||
);
|
||||
|
|
|
@ -17,7 +17,7 @@ import {
|
|||
} from "./typeChecks";
|
||||
import { getBoundTextShape, isPathALoop } from "../shapes";
|
||||
import type { GlobalPoint, LocalPoint, Polygon } from "../../math";
|
||||
import { isPointWithinBounds, point } from "../../math";
|
||||
import { isPointWithinBounds, pointFrom } from "../../math";
|
||||
|
||||
export const shouldTestInside = (element: ExcalidrawElement) => {
|
||||
if (element.type === "arrow") {
|
||||
|
@ -61,13 +61,13 @@ export const hitElementItself = <Point extends GlobalPoint | LocalPoint>({
|
|||
let hit = shouldTestInside(element)
|
||||
? // Since `inShape` tests STRICTLY againt the insides of a shape
|
||||
// we would need `onShape` as well to include the "borders"
|
||||
isPointInShape(point(x, y), shape) ||
|
||||
isPointOnShape(point(x, y), shape, threshold)
|
||||
: isPointOnShape(point(x, y), shape, threshold);
|
||||
isPointInShape(pointFrom(x, y), shape) ||
|
||||
isPointOnShape(pointFrom(x, y), shape, threshold)
|
||||
: isPointOnShape(pointFrom(x, y), shape, threshold);
|
||||
|
||||
// hit test against a frame's name
|
||||
if (!hit && frameNameBound) {
|
||||
hit = isPointInShape(point(x, y), {
|
||||
hit = isPointInShape(pointFrom(x, y), {
|
||||
type: "polygon",
|
||||
data: getPolygonShape(frameNameBound as ExcalidrawRectangleElement)
|
||||
.data as Polygon<Point>,
|
||||
|
@ -89,7 +89,11 @@ export const hitElementBoundingBox = (
|
|||
y1 -= tolerance;
|
||||
x2 += tolerance;
|
||||
y2 += tolerance;
|
||||
return isPointWithinBounds(point(x1, y1), point(x, y), point(x2, y2));
|
||||
return isPointWithinBounds(
|
||||
pointFrom(x1, y1),
|
||||
pointFrom(x, y),
|
||||
pointFrom(x2, y2),
|
||||
);
|
||||
};
|
||||
|
||||
export const hitElementBoundingBoxOnly = <
|
||||
|
@ -115,5 +119,5 @@ export const hitElementBoundText = <Point extends GlobalPoint | LocalPoint>(
|
|||
y: number,
|
||||
textShape: GeometricShape<Point> | null,
|
||||
): boolean => {
|
||||
return !!textShape && isPointInShape(point(x, y), textShape);
|
||||
return !!textShape && isPointInShape(pointFrom(x, y), textShape);
|
||||
};
|
||||
|
|
|
@ -29,7 +29,7 @@ import {
|
|||
isFlowchartNodeElement,
|
||||
} from "./typeChecks";
|
||||
import { invariant } from "../utils";
|
||||
import { point, type LocalPoint } from "../../math";
|
||||
import { pointFrom, type LocalPoint } from "../../math";
|
||||
import { aabbForElement } from "../shapes";
|
||||
|
||||
type LinkDirection = "up" | "right" | "down" | "left";
|
||||
|
@ -421,7 +421,7 @@ const createBindingArrow = (
|
|||
strokeColor: appState.currentItemStrokeColor,
|
||||
strokeStyle: appState.currentItemStrokeStyle,
|
||||
strokeWidth: appState.currentItemStrokeWidth,
|
||||
points: [point(0, 0), point(endX, endY)],
|
||||
points: [pointFrom(0, 0), pointFrom(endX, endY)],
|
||||
elbowed: true,
|
||||
});
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ import type {
|
|||
Radians,
|
||||
} from "../../math";
|
||||
import {
|
||||
point,
|
||||
pointFrom,
|
||||
pointRotateRads,
|
||||
pointScaleFromOrigin,
|
||||
radiansToDegrees,
|
||||
|
@ -82,7 +82,7 @@ export const headingForPointFromElement = <
|
|||
|
||||
const top = pointRotateRads(
|
||||
pointScaleFromOrigin(
|
||||
point(element.x + element.width / 2, element.y),
|
||||
pointFrom(element.x + element.width / 2, element.y),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
),
|
||||
|
@ -91,7 +91,7 @@ export const headingForPointFromElement = <
|
|||
);
|
||||
const right = pointRotateRads(
|
||||
pointScaleFromOrigin(
|
||||
point(element.x + element.width, element.y + element.height / 2),
|
||||
pointFrom(element.x + element.width, element.y + element.height / 2),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
),
|
||||
|
@ -100,7 +100,7 @@ export const headingForPointFromElement = <
|
|||
);
|
||||
const bottom = pointRotateRads(
|
||||
pointScaleFromOrigin(
|
||||
point(element.x + element.width / 2, element.y + element.height),
|
||||
pointFrom(element.x + element.width / 2, element.y + element.height),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
),
|
||||
|
@ -109,7 +109,7 @@ export const headingForPointFromElement = <
|
|||
);
|
||||
const left = pointRotateRads(
|
||||
pointScaleFromOrigin(
|
||||
point(element.x, element.y + element.height / 2),
|
||||
pointFrom(element.x, element.y + element.height / 2),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
),
|
||||
|
@ -133,22 +133,22 @@ export const headingForPointFromElement = <
|
|||
}
|
||||
|
||||
const topLeft = pointScaleFromOrigin(
|
||||
point(aabb[0], aabb[1]),
|
||||
pointFrom(aabb[0], aabb[1]),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
) as Point;
|
||||
const topRight = pointScaleFromOrigin(
|
||||
point(aabb[2], aabb[1]),
|
||||
pointFrom(aabb[2], aabb[1]),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
) as Point;
|
||||
const bottomLeft = pointScaleFromOrigin(
|
||||
point(aabb[0], aabb[3]),
|
||||
pointFrom(aabb[0], aabb[3]),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
) as Point;
|
||||
const bottomRight = pointScaleFromOrigin(
|
||||
point(aabb[2], aabb[3]),
|
||||
pointFrom(aabb[2], aabb[3]),
|
||||
midPoint,
|
||||
SEARCH_CONE_MULTIPLIER,
|
||||
) as Point;
|
||||
|
|
|
@ -49,7 +49,7 @@ import type Scene from "../scene/Scene";
|
|||
import type { Radians } from "../../math";
|
||||
import {
|
||||
pointCenter,
|
||||
point,
|
||||
pointFrom,
|
||||
pointRotateRads,
|
||||
pointsEqual,
|
||||
vector,
|
||||
|
@ -108,7 +108,7 @@ export class LinearElementEditor {
|
|||
this.elementId = element.id as string & {
|
||||
_brand: "excalidrawLinearElementId";
|
||||
};
|
||||
if (!pointsEqual(element.points[0], point(0, 0))) {
|
||||
if (!pointsEqual(element.points[0], pointFrom(0, 0))) {
|
||||
console.error("Linear element is not normalized", Error().stack);
|
||||
}
|
||||
|
||||
|
@ -287,7 +287,7 @@ export class LinearElementEditor {
|
|||
element,
|
||||
elementsMap,
|
||||
referencePoint,
|
||||
point(scenePointerX, scenePointerY),
|
||||
pointFrom(scenePointerX, scenePointerY),
|
||||
event[KEYS.CTRL_OR_CMD] ? null : app.getEffectiveGridSize(),
|
||||
);
|
||||
|
||||
|
@ -296,7 +296,7 @@ export class LinearElementEditor {
|
|||
[
|
||||
{
|
||||
index: selectedIndex,
|
||||
point: point(
|
||||
point: pointFrom(
|
||||
width + referencePoint[0],
|
||||
height + referencePoint[1],
|
||||
),
|
||||
|
@ -329,7 +329,7 @@ export class LinearElementEditor {
|
|||
scenePointerY - linearElementEditor.pointerOffset.y,
|
||||
event[KEYS.CTRL_OR_CMD] ? null : app.getEffectiveGridSize(),
|
||||
)
|
||||
: point(
|
||||
: pointFrom(
|
||||
element.points[pointIndex][0] + deltaX,
|
||||
element.points[pointIndex][1] + deltaY,
|
||||
);
|
||||
|
@ -590,11 +590,11 @@ export class LinearElementEditor {
|
|||
linearElementEditor.segmentMidPointHoveredCoords;
|
||||
if (existingSegmentMidpointHitCoords) {
|
||||
const distance = pointDistance(
|
||||
point(
|
||||
pointFrom(
|
||||
existingSegmentMidpointHitCoords[0],
|
||||
existingSegmentMidpointHitCoords[1],
|
||||
),
|
||||
point(scenePointer.x, scenePointer.y),
|
||||
pointFrom(scenePointer.x, scenePointer.y),
|
||||
);
|
||||
if (distance <= threshold) {
|
||||
return existingSegmentMidpointHitCoords;
|
||||
|
@ -606,8 +606,8 @@ export class LinearElementEditor {
|
|||
while (index < midPoints.length) {
|
||||
if (midPoints[index] !== null) {
|
||||
const distance = pointDistance(
|
||||
point(midPoints[index]![0], midPoints[index]![1]),
|
||||
point(scenePointer.x, scenePointer.y),
|
||||
pointFrom(midPoints[index]![0], midPoints[index]![1]),
|
||||
pointFrom(scenePointer.x, scenePointer.y),
|
||||
);
|
||||
if (distance <= threshold) {
|
||||
return midPoints[index];
|
||||
|
@ -626,8 +626,8 @@ export class LinearElementEditor {
|
|||
zoom: AppState["zoom"],
|
||||
) {
|
||||
let distance = pointDistance(
|
||||
point(startPoint[0], startPoint[1]),
|
||||
point(endPoint[0], endPoint[1]),
|
||||
pointFrom(startPoint[0], startPoint[1]),
|
||||
pointFrom(endPoint[0], endPoint[1]),
|
||||
);
|
||||
if (element.points.length > 2 && element.roundness) {
|
||||
distance = getBezierCurveLength(element, endPoint);
|
||||
|
@ -829,11 +829,11 @@ export class LinearElementEditor {
|
|||
const targetPoint =
|
||||
clickedPointIndex > -1 &&
|
||||
pointRotateRads(
|
||||
point(
|
||||
pointFrom(
|
||||
element.x + element.points[clickedPointIndex][0],
|
||||
element.y + element.points[clickedPointIndex][1],
|
||||
),
|
||||
point(cx, cy),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
|
||||
|
@ -928,11 +928,11 @@ export class LinearElementEditor {
|
|||
element,
|
||||
elementsMap,
|
||||
lastCommittedPoint,
|
||||
point(scenePointerX, scenePointerY),
|
||||
pointFrom(scenePointerX, scenePointerY),
|
||||
event[KEYS.CTRL_OR_CMD] ? null : app.getEffectiveGridSize(),
|
||||
);
|
||||
|
||||
newPoint = point(
|
||||
newPoint = pointFrom(
|
||||
width + lastCommittedPoint[0],
|
||||
height + lastCommittedPoint[1],
|
||||
);
|
||||
|
@ -984,8 +984,8 @@ export class LinearElementEditor {
|
|||
|
||||
const { x, y } = element;
|
||||
return pointRotateRads(
|
||||
point(x + p[0], y + p[1]),
|
||||
point(cx, cy),
|
||||
pointFrom(x + p[0], y + p[1]),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
}
|
||||
|
@ -1001,8 +1001,8 @@ export class LinearElementEditor {
|
|||
return element.points.map((p) => {
|
||||
const { x, y } = element;
|
||||
return pointRotateRads(
|
||||
point(x + p[0], y + p[1]),
|
||||
point(cx, cy),
|
||||
pointFrom(x + p[0], y + p[1]),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
});
|
||||
|
@ -1025,8 +1025,12 @@ export class LinearElementEditor {
|
|||
const { x, y } = element;
|
||||
|
||||
return p
|
||||
? pointRotateRads(point(x + p[0], y + p[1]), point(cx, cy), element.angle)
|
||||
: pointRotateRads(point(x, y), point(cx, cy), element.angle);
|
||||
? pointRotateRads(
|
||||
pointFrom(x + p[0], y + p[1]),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
)
|
||||
: pointRotateRads(pointFrom(x, y), pointFrom(cx, cy), element.angle);
|
||||
}
|
||||
|
||||
static pointFromAbsoluteCoords(
|
||||
|
@ -1036,7 +1040,7 @@ export class LinearElementEditor {
|
|||
): LocalPoint {
|
||||
if (isElbowArrow(element)) {
|
||||
// No rotation for elbow arrows
|
||||
return point(
|
||||
return pointFrom(
|
||||
absoluteCoords[0] - element.x,
|
||||
absoluteCoords[1] - element.y,
|
||||
);
|
||||
|
@ -1046,11 +1050,11 @@ export class LinearElementEditor {
|
|||
const cx = (x1 + x2) / 2;
|
||||
const cy = (y1 + y2) / 2;
|
||||
const [x, y] = pointRotateRads(
|
||||
point(absoluteCoords[0], absoluteCoords[1]),
|
||||
point(cx, cy),
|
||||
pointFrom(absoluteCoords[0], absoluteCoords[1]),
|
||||
pointFrom(cx, cy),
|
||||
-element.angle as Radians,
|
||||
);
|
||||
return point(x - element.x, y - element.y);
|
||||
return pointFrom(x - element.x, y - element.y);
|
||||
}
|
||||
|
||||
static getPointIndexUnderCursor(
|
||||
|
@ -1071,7 +1075,7 @@ export class LinearElementEditor {
|
|||
while (--idx > -1) {
|
||||
const p = pointHandles[idx];
|
||||
if (
|
||||
pointDistance(point(x, y), point(p[0], p[1])) * zoom.value <
|
||||
pointDistance(pointFrom(x, y), pointFrom(p[0], p[1])) * zoom.value <
|
||||
// +1px to account for outline stroke
|
||||
LinearElementEditor.POINT_HANDLE_SIZE + 1
|
||||
) {
|
||||
|
@ -1093,12 +1097,12 @@ export class LinearElementEditor {
|
|||
const cx = (x1 + x2) / 2;
|
||||
const cy = (y1 + y2) / 2;
|
||||
const [rotatedX, rotatedY] = pointRotateRads(
|
||||
point(pointerOnGrid[0], pointerOnGrid[1]),
|
||||
point(cx, cy),
|
||||
pointFrom(pointerOnGrid[0], pointerOnGrid[1]),
|
||||
pointFrom(cx, cy),
|
||||
-element.angle as Radians,
|
||||
);
|
||||
|
||||
return point(rotatedX - element.x, rotatedY - element.y);
|
||||
return pointFrom(rotatedX - element.x, rotatedY - element.y);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1118,7 +1122,7 @@ export class LinearElementEditor {
|
|||
|
||||
return {
|
||||
points: points.map((p) => {
|
||||
return point(p[0] - offsetX, p[1] - offsetY);
|
||||
return pointFrom(p[0] - offsetX, p[1] - offsetY);
|
||||
}),
|
||||
x: element.x + offsetX,
|
||||
y: element.y + offsetY,
|
||||
|
@ -1172,8 +1176,8 @@ export class LinearElementEditor {
|
|||
}
|
||||
acc.push(
|
||||
nextPoint
|
||||
? point((p[0] + nextPoint[0]) / 2, (p[1] + nextPoint[1]) / 2)
|
||||
: point(p[0], p[1]),
|
||||
? pointFrom((p[0] + nextPoint[0]) / 2, (p[1] + nextPoint[1]) / 2)
|
||||
: pointFrom(p[0], p[1]),
|
||||
);
|
||||
|
||||
nextSelectedIndices.push(indexCursor + 1);
|
||||
|
@ -1194,7 +1198,7 @@ export class LinearElementEditor {
|
|||
[
|
||||
{
|
||||
index: element.points.length - 1,
|
||||
point: point(lastPoint[0] + 30, lastPoint[1] + 30),
|
||||
point: pointFrom(lastPoint[0] + 30, lastPoint[1] + 30),
|
||||
},
|
||||
],
|
||||
elementsMap,
|
||||
|
@ -1235,7 +1239,9 @@ export class LinearElementEditor {
|
|||
const nextPoints = element.points.reduce((acc: LocalPoint[], p, idx) => {
|
||||
if (!pointIndices.includes(idx)) {
|
||||
acc.push(
|
||||
!acc.length ? point(0, 0) : point(p[0] - offsetX, p[1] - offsetY),
|
||||
!acc.length
|
||||
? pointFrom(0, 0)
|
||||
: pointFrom(p[0] - offsetX, p[1] - offsetY),
|
||||
);
|
||||
}
|
||||
return acc;
|
||||
|
@ -1312,9 +1318,9 @@ export class LinearElementEditor {
|
|||
const deltaY =
|
||||
selectedPointData.point[1] - points[selectedPointData.index][1];
|
||||
|
||||
return point(p[0] + deltaX - offsetX, p[1] + deltaY - offsetY);
|
||||
return pointFrom(p[0] + deltaX - offsetX, p[1] + deltaY - offsetY);
|
||||
}
|
||||
return offsetX || offsetY ? point(p[0] - offsetX, p[1] - offsetY) : p;
|
||||
return offsetX || offsetY ? pointFrom(p[0] - offsetX, p[1] - offsetY) : p;
|
||||
});
|
||||
|
||||
LinearElementEditor._updatePoints(
|
||||
|
@ -1368,8 +1374,8 @@ export class LinearElementEditor {
|
|||
|
||||
const origin = linearElementEditor.pointerDownState.origin!;
|
||||
const dist = pointDistance(
|
||||
point(origin.x, origin.y),
|
||||
point(pointerCoords.x, pointerCoords.y),
|
||||
pointFrom(origin.x, origin.y),
|
||||
pointFrom(pointerCoords.x, pointerCoords.y),
|
||||
);
|
||||
if (
|
||||
!appState.editingLinearElement &&
|
||||
|
@ -1493,8 +1499,8 @@ export class LinearElementEditor {
|
|||
const dX = prevCenterX - nextCenterX;
|
||||
const dY = prevCenterY - nextCenterY;
|
||||
const rotated = pointRotateRads(
|
||||
point(offsetX, offsetY),
|
||||
point(dX, dY),
|
||||
pointFrom(offsetX, offsetY),
|
||||
pointFrom(dX, dY),
|
||||
element.angle,
|
||||
);
|
||||
mutateElement(element, {
|
||||
|
@ -1540,8 +1546,8 @@ export class LinearElementEditor {
|
|||
);
|
||||
|
||||
return pointRotateRads(
|
||||
point(width, height),
|
||||
point(0, 0),
|
||||
pointFrom(width, height),
|
||||
pointFrom(0, 0),
|
||||
-element.angle as Radians,
|
||||
);
|
||||
}
|
||||
|
@ -1611,36 +1617,36 @@ export class LinearElementEditor {
|
|||
);
|
||||
const boundTextX2 = boundTextX1 + boundTextElement.width;
|
||||
const boundTextY2 = boundTextY1 + boundTextElement.height;
|
||||
const centerPoint = point(cx, cy);
|
||||
const centerPoint = pointFrom(cx, cy);
|
||||
|
||||
const topLeftRotatedPoint = pointRotateRads(
|
||||
point(x1, y1),
|
||||
pointFrom(x1, y1),
|
||||
centerPoint,
|
||||
element.angle,
|
||||
);
|
||||
const topRightRotatedPoint = pointRotateRads(
|
||||
point(x2, y1),
|
||||
pointFrom(x2, y1),
|
||||
centerPoint,
|
||||
element.angle,
|
||||
);
|
||||
|
||||
const counterRotateBoundTextTopLeft = pointRotateRads(
|
||||
point(boundTextX1, boundTextY1),
|
||||
pointFrom(boundTextX1, boundTextY1),
|
||||
centerPoint,
|
||||
-element.angle as Radians,
|
||||
);
|
||||
const counterRotateBoundTextTopRight = pointRotateRads(
|
||||
point(boundTextX2, boundTextY1),
|
||||
pointFrom(boundTextX2, boundTextY1),
|
||||
centerPoint,
|
||||
-element.angle as Radians,
|
||||
);
|
||||
const counterRotateBoundTextBottomLeft = pointRotateRads(
|
||||
point(boundTextX1, boundTextY2),
|
||||
pointFrom(boundTextX1, boundTextY2),
|
||||
centerPoint,
|
||||
-element.angle as Radians,
|
||||
);
|
||||
const counterRotateBoundTextBottomRight = pointRotateRads(
|
||||
point(boundTextX2, boundTextY2),
|
||||
pointFrom(boundTextX2, boundTextY2),
|
||||
centerPoint,
|
||||
-element.angle as Radians,
|
||||
);
|
||||
|
|
|
@ -5,7 +5,7 @@ import { FONT_FAMILY, ROUNDNESS } from "../constants";
|
|||
import { isPrimitive } from "../utils";
|
||||
import type { ExcalidrawLinearElement } from "./types";
|
||||
import type { LocalPoint } from "../../math";
|
||||
import { point } from "../../math";
|
||||
import { pointFrom } from "../../math";
|
||||
|
||||
const assertCloneObjects = (source: any, clone: any) => {
|
||||
for (const key in clone) {
|
||||
|
@ -38,7 +38,7 @@ describe("duplicating single elements", () => {
|
|||
element.__proto__ = { hello: "world" };
|
||||
|
||||
mutateElement(element, {
|
||||
points: [point<LocalPoint>(1, 2), point<LocalPoint>(3, 4)],
|
||||
points: [pointFrom<LocalPoint>(1, 2), pointFrom<LocalPoint>(3, 4)],
|
||||
});
|
||||
|
||||
const copy = duplicateElement(null, new Map(), element);
|
||||
|
|
|
@ -58,7 +58,7 @@ import type { GlobalPoint } from "../../math";
|
|||
import {
|
||||
pointCenter,
|
||||
normalizeRadians,
|
||||
point,
|
||||
pointFrom,
|
||||
pointFromPair,
|
||||
pointRotateRads,
|
||||
type Radians,
|
||||
|
@ -240,8 +240,8 @@ const resizeSingleTextElement = (
|
|||
);
|
||||
// rotation pointer with reverse angle
|
||||
const [rotatedX, rotatedY] = pointRotateRads(
|
||||
point(pointerX, pointerY),
|
||||
point(cx, cy),
|
||||
pointFrom(pointerX, pointerY),
|
||||
pointFrom(cx, cy),
|
||||
-element.angle as Radians,
|
||||
);
|
||||
let scaleX = 0;
|
||||
|
@ -276,23 +276,23 @@ const resizeSingleTextElement = (
|
|||
const startBottomRight = [x2, y2];
|
||||
const startCenter = [cx, cy];
|
||||
|
||||
let newTopLeft = point<GlobalPoint>(x1, y1);
|
||||
let newTopLeft = pointFrom<GlobalPoint>(x1, y1);
|
||||
if (["n", "w", "nw"].includes(transformHandleType)) {
|
||||
newTopLeft = point<GlobalPoint>(
|
||||
newTopLeft = pointFrom<GlobalPoint>(
|
||||
startBottomRight[0] - Math.abs(nextWidth),
|
||||
startBottomRight[1] - Math.abs(nextHeight),
|
||||
);
|
||||
}
|
||||
if (transformHandleType === "ne") {
|
||||
const bottomLeft = [startTopLeft[0], startBottomRight[1]];
|
||||
newTopLeft = point<GlobalPoint>(
|
||||
newTopLeft = pointFrom<GlobalPoint>(
|
||||
bottomLeft[0],
|
||||
bottomLeft[1] - Math.abs(nextHeight),
|
||||
);
|
||||
}
|
||||
if (transformHandleType === "sw") {
|
||||
const topRight = [startBottomRight[0], startTopLeft[1]];
|
||||
newTopLeft = point<GlobalPoint>(
|
||||
newTopLeft = pointFrom<GlobalPoint>(
|
||||
topRight[0] - Math.abs(nextWidth),
|
||||
topRight[1],
|
||||
);
|
||||
|
@ -311,12 +311,20 @@ const resizeSingleTextElement = (
|
|||
}
|
||||
|
||||
const angle = element.angle;
|
||||
const rotatedTopLeft = pointRotateRads(newTopLeft, point(cx, cy), angle);
|
||||
const newCenter = point<GlobalPoint>(
|
||||
const rotatedTopLeft = pointRotateRads(
|
||||
newTopLeft,
|
||||
pointFrom(cx, cy),
|
||||
angle,
|
||||
);
|
||||
const newCenter = pointFrom<GlobalPoint>(
|
||||
newTopLeft[0] + Math.abs(nextWidth) / 2,
|
||||
newTopLeft[1] + Math.abs(nextHeight) / 2,
|
||||
);
|
||||
const rotatedNewCenter = pointRotateRads(newCenter, point(cx, cy), angle);
|
||||
const rotatedNewCenter = pointRotateRads(
|
||||
newCenter,
|
||||
pointFrom(cx, cy),
|
||||
angle,
|
||||
);
|
||||
newTopLeft = pointRotateRads(
|
||||
rotatedTopLeft,
|
||||
rotatedNewCenter,
|
||||
|
@ -341,12 +349,12 @@ const resizeSingleTextElement = (
|
|||
stateAtResizeStart.height,
|
||||
true,
|
||||
);
|
||||
const startTopLeft = point<GlobalPoint>(x1, y1);
|
||||
const startBottomRight = point<GlobalPoint>(x2, y2);
|
||||
const startTopLeft = pointFrom<GlobalPoint>(x1, y1);
|
||||
const startBottomRight = pointFrom<GlobalPoint>(x2, y2);
|
||||
const startCenter = pointCenter(startTopLeft, startBottomRight);
|
||||
|
||||
const rotatedPointer = pointRotateRads(
|
||||
point(pointerX, pointerY),
|
||||
pointFrom(pointerX, pointerY),
|
||||
startCenter,
|
||||
-stateAtResizeStart.angle as Radians,
|
||||
);
|
||||
|
@ -419,7 +427,7 @@ const resizeSingleTextElement = (
|
|||
startCenter,
|
||||
angle,
|
||||
);
|
||||
const newCenter = point(
|
||||
const newCenter = pointFrom(
|
||||
newTopLeft[0] + Math.abs(newBoundsWidth) / 2,
|
||||
newTopLeft[1] + Math.abs(newBoundsHeight) / 2,
|
||||
);
|
||||
|
@ -461,13 +469,13 @@ export const resizeSingleElement = (
|
|||
stateAtResizeStart.height,
|
||||
true,
|
||||
);
|
||||
const startTopLeft = point(x1, y1);
|
||||
const startBottomRight = point(x2, y2);
|
||||
const startTopLeft = pointFrom(x1, y1);
|
||||
const startBottomRight = pointFrom(x2, y2);
|
||||
const startCenter = pointCenter(startTopLeft, startBottomRight);
|
||||
|
||||
// Calculate new dimensions based on cursor position
|
||||
const rotatedPointer = pointRotateRads(
|
||||
point(pointerX, pointerY),
|
||||
pointFrom(pointerX, pointerY),
|
||||
startCenter,
|
||||
-stateAtResizeStart.angle as Radians,
|
||||
);
|
||||
|
@ -648,7 +656,7 @@ export const resizeSingleElement = (
|
|||
startCenter,
|
||||
angle,
|
||||
);
|
||||
const newCenter = point(
|
||||
const newCenter = pointFrom(
|
||||
newTopLeft[0] + Math.abs(newBoundsWidth) / 2,
|
||||
newTopLeft[1] + Math.abs(newBoundsHeight) / 2,
|
||||
);
|
||||
|
@ -817,20 +825,20 @@ export const resizeMultipleElements = (
|
|||
const direction = transformHandleType;
|
||||
|
||||
const anchorsMap: Record<TransformHandleDirection, GlobalPoint> = {
|
||||
ne: point(minX, maxY),
|
||||
se: point(minX, minY),
|
||||
sw: point(maxX, minY),
|
||||
nw: point(maxX, maxY),
|
||||
e: point(minX, minY + height / 2),
|
||||
w: point(maxX, minY + height / 2),
|
||||
n: point(minX + width / 2, maxY),
|
||||
s: point(minX + width / 2, minY),
|
||||
ne: pointFrom(minX, maxY),
|
||||
se: pointFrom(minX, minY),
|
||||
sw: pointFrom(maxX, minY),
|
||||
nw: pointFrom(maxX, maxY),
|
||||
e: pointFrom(minX, minY + height / 2),
|
||||
w: pointFrom(maxX, minY + height / 2),
|
||||
n: pointFrom(minX + width / 2, maxY),
|
||||
s: pointFrom(minX + width / 2, minY),
|
||||
};
|
||||
|
||||
// anchor point must be on the opposite side of the dragged selection handle
|
||||
// or be the center of the selection if shouldResizeFromCenter
|
||||
const [anchorX, anchorY] = shouldResizeFromCenter
|
||||
? point(midX, midY)
|
||||
? pointFrom(midX, midY)
|
||||
: anchorsMap[direction];
|
||||
|
||||
const resizeFromCenterScale = shouldResizeFromCenter ? 2 : 1;
|
||||
|
@ -1044,8 +1052,8 @@ const rotateMultipleElements = (
|
|||
const origAngle =
|
||||
originalElements.get(element.id)?.angle ?? element.angle;
|
||||
const [rotatedCX, rotatedCY] = pointRotateRads(
|
||||
point(cx, cy),
|
||||
point(centerX, centerY),
|
||||
pointFrom(cx, cy),
|
||||
pointFrom(centerX, centerY),
|
||||
(centerAngle + origAngle - element.angle) as Radians,
|
||||
);
|
||||
|
||||
|
@ -1101,40 +1109,44 @@ export const getResizeOffsetXY = (
|
|||
const angle = (
|
||||
selectedElements.length === 1 ? selectedElements[0].angle : 0
|
||||
) as Radians;
|
||||
[x, y] = pointRotateRads(point(x, y), point(cx, cy), -angle as Radians);
|
||||
[x, y] = pointRotateRads(
|
||||
pointFrom(x, y),
|
||||
pointFrom(cx, cy),
|
||||
-angle as Radians,
|
||||
);
|
||||
switch (transformHandleType) {
|
||||
case "n":
|
||||
return pointRotateRads(
|
||||
point(x - (x1 + x2) / 2, y - y1),
|
||||
point(0, 0),
|
||||
pointFrom(x - (x1 + x2) / 2, y - y1),
|
||||
pointFrom(0, 0),
|
||||
angle,
|
||||
);
|
||||
case "s":
|
||||
return pointRotateRads(
|
||||
point(x - (x1 + x2) / 2, y - y2),
|
||||
point(0, 0),
|
||||
pointFrom(x - (x1 + x2) / 2, y - y2),
|
||||
pointFrom(0, 0),
|
||||
angle,
|
||||
);
|
||||
case "w":
|
||||
return pointRotateRads(
|
||||
point(x - x1, y - (y1 + y2) / 2),
|
||||
point(0, 0),
|
||||
pointFrom(x - x1, y - (y1 + y2) / 2),
|
||||
pointFrom(0, 0),
|
||||
angle,
|
||||
);
|
||||
case "e":
|
||||
return pointRotateRads(
|
||||
point(x - x2, y - (y1 + y2) / 2),
|
||||
point(0, 0),
|
||||
pointFrom(x - x2, y - (y1 + y2) / 2),
|
||||
pointFrom(0, 0),
|
||||
angle,
|
||||
);
|
||||
case "nw":
|
||||
return pointRotateRads(point(x - x1, y - y1), point(0, 0), angle);
|
||||
return pointRotateRads(pointFrom(x - x1, y - y1), pointFrom(0, 0), angle);
|
||||
case "ne":
|
||||
return pointRotateRads(point(x - x2, y - y1), point(0, 0), angle);
|
||||
return pointRotateRads(pointFrom(x - x2, y - y1), pointFrom(0, 0), angle);
|
||||
case "sw":
|
||||
return pointRotateRads(point(x - x1, y - y2), point(0, 0), angle);
|
||||
return pointRotateRads(pointFrom(x - x1, y - y2), pointFrom(0, 0), angle);
|
||||
case "se":
|
||||
return pointRotateRads(point(x - x2, y - y2), point(0, 0), angle);
|
||||
return pointRotateRads(pointFrom(x - x2, y - y2), pointFrom(0, 0), angle);
|
||||
default:
|
||||
return [0, 0];
|
||||
}
|
||||
|
|
|
@ -23,7 +23,7 @@ import { SIDE_RESIZING_THRESHOLD } from "../constants";
|
|||
import { isLinearElement } from "./typeChecks";
|
||||
import type { GlobalPoint, LineSegment, LocalPoint } from "../../math";
|
||||
import {
|
||||
point,
|
||||
pointFrom,
|
||||
pointOnLineSegment,
|
||||
pointRotateRads,
|
||||
type Radians,
|
||||
|
@ -92,16 +92,20 @@ export const resizeTest = <Point extends GlobalPoint | LocalPoint>(
|
|||
if (!(isLinearElement(element) && element.points.length <= 2)) {
|
||||
const SPACING = SIDE_RESIZING_THRESHOLD / zoom.value;
|
||||
const sides = getSelectionBorders(
|
||||
point(x1 - SPACING, y1 - SPACING),
|
||||
point(x2 + SPACING, y2 + SPACING),
|
||||
point(cx, cy),
|
||||
pointFrom(x1 - SPACING, y1 - SPACING),
|
||||
pointFrom(x2 + SPACING, y2 + SPACING),
|
||||
pointFrom(cx, cy),
|
||||
element.angle,
|
||||
);
|
||||
|
||||
for (const [dir, side] of Object.entries(sides)) {
|
||||
// test to see if x, y are on the line segment
|
||||
if (
|
||||
pointOnLineSegment(point(x, y), side as LineSegment<Point>, SPACING)
|
||||
pointOnLineSegment(
|
||||
pointFrom(x, y),
|
||||
side as LineSegment<Point>,
|
||||
SPACING,
|
||||
)
|
||||
) {
|
||||
return dir as TransformHandleType;
|
||||
}
|
||||
|
@ -178,9 +182,9 @@ export const getTransformHandleTypeFromCoords = <
|
|||
const SPACING = SIDE_RESIZING_THRESHOLD / zoom.value;
|
||||
|
||||
const sides = getSelectionBorders(
|
||||
point(x1 - SPACING, y1 - SPACING),
|
||||
point(x2 + SPACING, y2 + SPACING),
|
||||
point(cx, cy),
|
||||
pointFrom(x1 - SPACING, y1 - SPACING),
|
||||
pointFrom(x2 + SPACING, y2 + SPACING),
|
||||
pointFrom(cx, cy),
|
||||
0 as Radians,
|
||||
);
|
||||
|
||||
|
@ -188,7 +192,7 @@ export const getTransformHandleTypeFromCoords = <
|
|||
// test to see if x, y are on the line segment
|
||||
if (
|
||||
pointOnLineSegment(
|
||||
point(scenePointerX, scenePointerY),
|
||||
pointFrom(scenePointerX, scenePointerY),
|
||||
side as LineSegment<Point>,
|
||||
SPACING,
|
||||
)
|
||||
|
@ -265,10 +269,10 @@ const getSelectionBorders = <Point extends LocalPoint | GlobalPoint>(
|
|||
center: Point,
|
||||
angle: Radians,
|
||||
) => {
|
||||
const topLeft = pointRotateRads(point(x1, y1), center, angle);
|
||||
const topRight = pointRotateRads(point(x2, y1), center, angle);
|
||||
const bottomLeft = pointRotateRads(point(x1, y2), center, angle);
|
||||
const bottomRight = pointRotateRads(point(x2, y2), center, angle);
|
||||
const topLeft = pointRotateRads(pointFrom(x1, y1), center, angle);
|
||||
const topRight = pointRotateRads(pointFrom(x2, y1), center, angle);
|
||||
const bottomLeft = pointRotateRads(pointFrom(x1, y2), center, angle);
|
||||
const bottomRight = pointRotateRads(pointFrom(x2, y2), center, angle);
|
||||
|
||||
return {
|
||||
n: [topLeft, topRight],
|
||||
|
|
|
@ -17,7 +17,7 @@ import type {
|
|||
ExcalidrawElbowArrowElement,
|
||||
} from "./types";
|
||||
import { ARROW_TYPE } from "../constants";
|
||||
import { point } from "../../math";
|
||||
import { pointFrom } from "../../math";
|
||||
|
||||
const { h } = window;
|
||||
|
||||
|
@ -32,8 +32,8 @@ describe("elbow arrow routing", () => {
|
|||
}) as ExcalidrawElbowArrowElement;
|
||||
scene.insertElement(arrow);
|
||||
mutateElbowArrow(arrow, scene.getNonDeletedElementsMap(), [
|
||||
point(-45 - arrow.x, -100.1 - arrow.y),
|
||||
point(45 - arrow.x, 99.9 - arrow.y),
|
||||
pointFrom(-45 - arrow.x, -100.1 - arrow.y),
|
||||
pointFrom(45 - arrow.x, 99.9 - arrow.y),
|
||||
]);
|
||||
expect(arrow.points).toEqual([
|
||||
[0, 0],
|
||||
|
@ -69,7 +69,7 @@ describe("elbow arrow routing", () => {
|
|||
y: -100.1,
|
||||
width: 90,
|
||||
height: 200,
|
||||
points: [point(0, 0), point(90, 200)],
|
||||
points: [pointFrom(0, 0), pointFrom(90, 200)],
|
||||
}) as ExcalidrawElbowArrowElement;
|
||||
scene.insertElement(rectangle1);
|
||||
scene.insertElement(rectangle2);
|
||||
|
@ -81,7 +81,7 @@ describe("elbow arrow routing", () => {
|
|||
expect(arrow.startBinding).not.toBe(null);
|
||||
expect(arrow.endBinding).not.toBe(null);
|
||||
|
||||
mutateElbowArrow(arrow, elementsMap, [point(0, 0), point(90, 200)]);
|
||||
mutateElbowArrow(arrow, elementsMap, [pointFrom(0, 0), pointFrom(90, 200)]);
|
||||
|
||||
expect(arrow.points).toEqual([
|
||||
[0, 0],
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import type { Radians } from "../../math";
|
||||
import {
|
||||
point,
|
||||
pointFrom,
|
||||
pointScaleFromOrigin,
|
||||
pointTranslate,
|
||||
vector,
|
||||
|
@ -743,13 +743,13 @@ const getDonglePosition = (
|
|||
): GlobalPoint => {
|
||||
switch (heading) {
|
||||
case HEADING_UP:
|
||||
return point(p[0], bounds[1]);
|
||||
return pointFrom(p[0], bounds[1]);
|
||||
case HEADING_RIGHT:
|
||||
return point(bounds[2], p[1]);
|
||||
return pointFrom(bounds[2], p[1]);
|
||||
case HEADING_DOWN:
|
||||
return point(p[0], bounds[3]);
|
||||
return pointFrom(p[0], bounds[3]);
|
||||
}
|
||||
return point(bounds[0], p[1]);
|
||||
return pointFrom(bounds[0], p[1]);
|
||||
};
|
||||
|
||||
const estimateSegmentCount = (
|
||||
|
|
|
@ -19,7 +19,7 @@ import type {
|
|||
import { API } from "../tests/helpers/api";
|
||||
import { getOriginalContainerHeightFromCache } from "./containerCache";
|
||||
import { getTextEditor, updateTextEditor } from "../tests/queries/dom";
|
||||
import { point } from "../../math";
|
||||
import { pointFrom } from "../../math";
|
||||
|
||||
// Unmount ReactDOM from root
|
||||
ReactDOM.unmountComponentAtNode(document.getElementById("root")!);
|
||||
|
@ -42,7 +42,7 @@ describe("textWysiwyg", () => {
|
|||
type: "line",
|
||||
width: 100,
|
||||
height: 0,
|
||||
points: [point(0, 0), point(100, 0)],
|
||||
points: [pointFrom(0, 0), pointFrom(100, 0)],
|
||||
});
|
||||
const textSize = 20;
|
||||
const text = API.createElement({
|
||||
|
|
|
@ -19,7 +19,7 @@ import {
|
|||
isIOS,
|
||||
} from "../constants";
|
||||
import type { Radians } from "../../math";
|
||||
import { point, pointRotateRads } from "../../math";
|
||||
import { pointFrom, pointRotateRads } from "../../math";
|
||||
|
||||
export type TransformHandleDirection =
|
||||
| "n"
|
||||
|
@ -95,8 +95,8 @@ const generateTransformHandle = (
|
|||
angle: Radians,
|
||||
): TransformHandle => {
|
||||
const [xx, yy] = pointRotateRads(
|
||||
point(x + width / 2, y + height / 2),
|
||||
point(cx, cy),
|
||||
pointFrom(x + width / 2, y + height / 2),
|
||||
pointFrom(cx, cy),
|
||||
angle,
|
||||
);
|
||||
return [xx - width / 2, yy - height / 2, width, height];
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue