tldraw 4.1.0-canary.e653ec63c99b → 4.1.0-canary.f414ee471d7f
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist-cjs/index.d.ts +2 -0
- package/dist-cjs/index.js +1 -1
- package/dist-cjs/lib/shapes/arrow/ArrowShapeUtil.js +3 -0
- package/dist-cjs/lib/shapes/arrow/ArrowShapeUtil.js.map +2 -2
- package/dist-cjs/lib/shapes/bookmark/BookmarkShapeUtil.js +13 -1
- package/dist-cjs/lib/shapes/bookmark/BookmarkShapeUtil.js.map +2 -2
- package/dist-cjs/lib/shapes/line/LineShapeUtil.js +3 -0
- package/dist-cjs/lib/shapes/line/LineShapeUtil.js.map +2 -2
- package/dist-cjs/lib/ui/components/Minimap/MinimapManager.js +5 -0
- package/dist-cjs/lib/ui/components/Minimap/MinimapManager.js.map +2 -2
- package/dist-cjs/lib/ui/version.js +3 -3
- package/dist-cjs/lib/ui/version.js.map +1 -1
- package/dist-esm/index.d.mts +2 -0
- package/dist-esm/index.mjs +1 -1
- package/dist-esm/lib/shapes/arrow/ArrowShapeUtil.mjs +3 -0
- package/dist-esm/lib/shapes/arrow/ArrowShapeUtil.mjs.map +2 -2
- package/dist-esm/lib/shapes/bookmark/BookmarkShapeUtil.mjs +13 -1
- package/dist-esm/lib/shapes/bookmark/BookmarkShapeUtil.mjs.map +2 -2
- package/dist-esm/lib/shapes/line/LineShapeUtil.mjs +3 -0
- package/dist-esm/lib/shapes/line/LineShapeUtil.mjs.map +2 -2
- package/dist-esm/lib/ui/components/Minimap/MinimapManager.mjs +5 -0
- package/dist-esm/lib/ui/components/Minimap/MinimapManager.mjs.map +2 -2
- package/dist-esm/lib/ui/version.mjs +3 -3
- package/dist-esm/lib/ui/version.mjs.map +1 -1
- package/package.json +3 -3
- package/src/lib/shapes/arrow/ArrowShapeUtil.tsx +3 -0
- package/src/lib/shapes/bookmark/BookmarkShapeUtil.tsx +13 -3
- package/src/lib/shapes/line/LineShapeUtil.tsx +3 -0
- package/src/lib/ui/components/Minimap/MinimapManager.ts +6 -0
- package/src/lib/ui/version.ts +3 -3
- package/tldraw.css +7 -2
package/dist-cjs/index.d.ts
CHANGED
|
@@ -312,6 +312,7 @@ export declare class ArrowShapeUtil extends ShapeUtil<TLArrowShape> {
|
|
|
312
312
|
hideRotateHandle(): boolean;
|
|
313
313
|
hideSelectionBoundsBg(): boolean;
|
|
314
314
|
hideSelectionBoundsFg(): boolean;
|
|
315
|
+
hideInMinimap(): boolean;
|
|
315
316
|
canBeLaidOut(shape: TLArrowShape, info: TLShapeUtilCanBeLaidOutOpts): boolean;
|
|
316
317
|
getFontFaces(shape: TLArrowShape): TLFontFace[];
|
|
317
318
|
getDefaultProps(): TLArrowShape['props'];
|
|
@@ -1988,6 +1989,7 @@ export declare class LineShapeUtil extends ShapeUtil<TLLineShape> {
|
|
|
1988
1989
|
hideRotateHandle(): boolean;
|
|
1989
1990
|
hideSelectionBoundsFg(): boolean;
|
|
1990
1991
|
hideSelectionBoundsBg(): boolean;
|
|
1992
|
+
hideInMinimap(): boolean;
|
|
1991
1993
|
getDefaultProps(): TLLineShape['props'];
|
|
1992
1994
|
getGeometry(shape: TLLineShape): PathBuilderGeometry2d;
|
|
1993
1995
|
getHandles(shape: TLLineShape): TLHandle[];
|
package/dist-cjs/index.js
CHANGED
|
@@ -579,7 +579,7 @@ var import_buildFromV1Document = require("./lib/utils/tldr/buildFromV1Document")
|
|
|
579
579
|
var import_file = require("./lib/utils/tldr/file");
|
|
580
580
|
(0, import_editor.registerTldrawLibraryVersion)(
|
|
581
581
|
"tldraw",
|
|
582
|
-
"4.1.0-canary.
|
|
582
|
+
"4.1.0-canary.f414ee471d7f",
|
|
583
583
|
"cjs"
|
|
584
584
|
);
|
|
585
585
|
//# sourceMappingURL=index.js.map
|
|
@@ -99,6 +99,9 @@ class ArrowShapeUtil extends import_editor.ShapeUtil {
|
|
|
99
99
|
hideSelectionBoundsFg() {
|
|
100
100
|
return true;
|
|
101
101
|
}
|
|
102
|
+
hideInMinimap() {
|
|
103
|
+
return true;
|
|
104
|
+
}
|
|
102
105
|
canBeLaidOut(shape, info) {
|
|
103
106
|
if (info.type === "flip") {
|
|
104
107
|
const bindings = (0, import_shared.getArrowBindings)(this.editor, shape);
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../src/lib/shapes/arrow/ArrowShapeUtil.tsx"],
|
|
4
|
-
"sourcesContent": ["import {\n\tArc2d,\n\tBox,\n\tEMPTY_ARRAY,\n\tEdge2d,\n\tEditor,\n\tGeometry2d,\n\tGroup2d,\n\tIndexKey,\n\tPI2,\n\tPolyline2d,\n\tRectangle2d,\n\tSVGContainer,\n\tShapeUtil,\n\tSvgExportContext,\n\tTLArrowBinding,\n\tTLArrowBindingProps,\n\tTLArrowShape,\n\tTLArrowShapeProps,\n\tTLHandle,\n\tTLHandleDragInfo,\n\tTLResizeInfo,\n\tTLShapePartial,\n\tTLShapeUtilCanBeLaidOutOpts,\n\tTLShapeUtilCanBindOpts,\n\tTLShapeUtilCanvasSvgDef,\n\tVec,\n\tWeakCache,\n\tarrowShapeMigrations,\n\tarrowShapeProps,\n\tclamp,\n\tdebugFlags,\n\texhaustiveSwitchError,\n\tgetColorValue,\n\tgetDefaultColorTheme,\n\tgetFontsFromRichText,\n\tinvLerp,\n\tlerp,\n\tmapObjectMapValues,\n\tmaybeSnapToGrid,\n\tstructuredClone,\n\ttoDomPrecision,\n\ttoRichText,\n\ttrack,\n\tuseEditor,\n\tuseIsEditing,\n\tuseSharedSafeId,\n\tuseValue,\n} from '@tldraw/editor'\nimport React, { useMemo } from 'react'\nimport { updateArrowTerminal } from '../../bindings/arrow/ArrowBindingUtil'\nimport { isEmptyRichText, renderPlaintextFromRichText } from '../../utils/text/richText'\nimport { PathBuilder } from '../shared/PathBuilder'\nimport { RichTextLabel, RichTextSVG } from '../shared/RichTextLabel'\nimport { ShapeFill } from '../shared/ShapeFill'\nimport { ARROW_LABEL_PADDING, STROKE_SIZES, TEXT_PROPS } from '../shared/default-shape-constants'\nimport { getFillDefForCanvas, getFillDefForExport } from '../shared/defaultStyleDefs'\nimport { useDefaultColorTheme } from '../shared/useDefaultColorTheme'\nimport { getArrowBodyPath, getArrowHandlePath } from './ArrowPath'\nimport { ArrowShapeOptions } from './arrow-types'\nimport {\n\tgetArrowLabelDefaultPosition,\n\tgetArrowLabelFontSize,\n\tgetArrowLabelPosition,\n} from './arrowLabel'\nimport { updateArrowTargetState } from './arrowTargetState'\nimport { getArrowheadPathForType } from './arrowheads'\nimport { ElbowArrowDebug } from './elbow/ElbowArrowDebug'\nimport { ElbowArrowAxes } from './elbow/definitions'\nimport { getElbowArrowSnapLines, perpDistanceToLineAngle } from './elbow/elbowArrowSnapLines'\nimport {\n\tTLArrowBindings,\n\tcreateOrUpdateArrowBinding,\n\tgetArrowBindings,\n\tgetArrowInfo,\n\tgetArrowTerminalsInArrowSpace,\n\tremoveArrowBinding,\n} from './shared'\n\nenum ArrowHandles {\n\tStart = 'start',\n\tMiddle = 'middle',\n\tEnd = 'end',\n}\n\n/** @public */\nexport class ArrowShapeUtil extends ShapeUtil<TLArrowShape> {\n\tstatic override type = 'arrow' as const\n\tstatic override props = arrowShapeProps\n\tstatic override migrations = arrowShapeMigrations\n\n\toverride options: ArrowShapeOptions = {\n\t\texpandElbowLegLength: {\n\t\t\ts: 28,\n\t\t\tm: 36,\n\t\t\tl: 44,\n\t\t\txl: 66,\n\t\t},\n\t\tminElbowLegLength: {\n\t\t\ts: STROKE_SIZES.s * 3,\n\t\t\tm: STROKE_SIZES.m * 3,\n\t\t\tl: STROKE_SIZES.l * 3,\n\t\t\txl: STROKE_SIZES.xl * 3,\n\t\t},\n\t\tminElbowHandleDistance: 16,\n\n\t\tarcArrowCenterSnapDistance: 16,\n\t\telbowArrowCenterSnapDistance: 24,\n\t\telbowArrowEdgeSnapDistance: 20,\n\t\telbowArrowPointSnapDistance: 24,\n\t\telbowArrowAxisSnapDistance: 16,\n\n\t\tlabelCenterSnapDistance: 10,\n\n\t\telbowMidpointSnapDistance: 10,\n\t\telbowMinSegmentLengthToShowMidpointHandle: 20,\n\n\t\thoverPreciseTimeout: 600,\n\t\tpointingPreciseTimeout: 320,\n\n\t\tshouldBeExact: (editor: Editor) => editor.inputs.altKey,\n\t\tshouldIgnoreTargets: (editor: Editor) => editor.inputs.ctrlKey,\n\t}\n\n\toverride canEdit() {\n\t\treturn true\n\t}\n\toverride canBind({ toShapeType }: TLShapeUtilCanBindOpts<TLArrowShape>): boolean {\n\t\t// bindings can go from arrows to shapes, but not from shapes to arrows\n\t\treturn toShapeType !== 'arrow'\n\t}\n\toverride canSnap() {\n\t\treturn false\n\t}\n\toverride hideResizeHandles() {\n\t\treturn true\n\t}\n\toverride hideRotateHandle() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsBg() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\n\toverride canBeLaidOut(shape: TLArrowShape, info: TLShapeUtilCanBeLaidOutOpts) {\n\t\tif (info.type === 'flip') {\n\t\t\t// If we don't have this then the flip will be non-idempotent; that is, the flip will be multipotent, varipotent, or perhaps even omni-potent... and we can't have that\n\t\t\tconst bindings = getArrowBindings(this.editor, shape)\n\t\t\tconst { start, end } = bindings\n\t\t\tconst { shapes = [] } = info\n\t\t\tif (start && !shapes.find((s) => s.id === start.toId)) return false\n\t\t\tif (end && !shapes.find((s) => s.id === end.toId)) return false\n\t\t}\n\t\treturn true\n\t}\n\n\toverride getFontFaces(shape: TLArrowShape) {\n\t\tif (isEmptyRichText(shape.props.richText)) return EMPTY_ARRAY\n\n\t\treturn getFontsFromRichText(this.editor, shape.props.richText, {\n\t\t\tfamily: `tldraw_${shape.props.font}`,\n\t\t\tweight: 'normal',\n\t\t\tstyle: 'normal',\n\t\t})\n\t}\n\n\toverride getDefaultProps(): TLArrowShape['props'] {\n\t\treturn {\n\t\t\tkind: 'arc',\n\t\t\telbowMidPoint: 0.5,\n\t\t\tdash: 'draw',\n\t\t\tsize: 'm',\n\t\t\tfill: 'none',\n\t\t\tcolor: 'black',\n\t\t\tlabelColor: 'black',\n\t\t\tbend: 0,\n\t\t\tstart: { x: 0, y: 0 },\n\t\t\tend: { x: 2, y: 0 },\n\t\t\tarrowheadStart: 'none',\n\t\t\tarrowheadEnd: 'arrow',\n\t\t\trichText: toRichText(''),\n\t\t\tlabelPosition: 0.5,\n\t\t\tfont: 'draw',\n\t\t\tscale: 1,\n\t\t}\n\t}\n\n\tgetGeometry(shape: TLArrowShape) {\n\t\tconst isEditing = this.editor.getEditingShapeId() === shape.id\n\t\tconst info = getArrowInfo(this.editor, shape)!\n\n\t\tconst debugGeom: Geometry2d[] = []\n\n\t\tconst bodyGeom =\n\t\t\tinfo.type === 'straight'\n\t\t\t\t? new Edge2d({\n\t\t\t\t\t\tstart: Vec.From(info.start.point),\n\t\t\t\t\t\tend: Vec.From(info.end.point),\n\t\t\t\t\t})\n\t\t\t\t: info.type === 'arc'\n\t\t\t\t\t? new Arc2d({\n\t\t\t\t\t\t\tcenter: Vec.Cast(info.handleArc.center),\n\t\t\t\t\t\t\tstart: Vec.Cast(info.start.point),\n\t\t\t\t\t\t\tend: Vec.Cast(info.end.point),\n\t\t\t\t\t\t\tsweepFlag: info.bodyArc.sweepFlag,\n\t\t\t\t\t\t\tlargeArcFlag: info.bodyArc.largeArcFlag,\n\t\t\t\t\t\t})\n\t\t\t\t\t: new Polyline2d({ points: info.route.points })\n\n\t\tlet labelGeom\n\t\tif (isEditing || !isEmptyRichText(shape.props.richText)) {\n\t\t\tconst labelPosition = getArrowLabelPosition(this.editor, shape)\n\t\t\tif (debugFlags.debugGeometry.get()) {\n\t\t\t\tdebugGeom.push(...labelPosition.debugGeom)\n\t\t\t}\n\t\t\tlabelGeom = new Rectangle2d({\n\t\t\t\tx: labelPosition.box.x,\n\t\t\t\ty: labelPosition.box.y,\n\t\t\t\twidth: labelPosition.box.w,\n\t\t\t\theight: labelPosition.box.h,\n\t\t\t\tisFilled: true,\n\t\t\t\tisLabel: true,\n\t\t\t})\n\t\t}\n\n\t\treturn new Group2d({\n\t\t\tchildren: [...(labelGeom ? [bodyGeom, labelGeom] : [bodyGeom]), ...debugGeom],\n\t\t})\n\t}\n\n\toverride getHandles(shape: TLArrowShape): TLHandle[] {\n\t\tconst info = getArrowInfo(this.editor, shape)!\n\n\t\tconst handles: TLHandle[] = [\n\t\t\t{\n\t\t\t\tid: ArrowHandles.Start,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tindex: 'a1' as IndexKey,\n\t\t\t\tx: info.start.handle.x,\n\t\t\t\ty: info.start.handle.y,\n\t\t\t},\n\t\t\t{\n\t\t\t\tid: ArrowHandles.End,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tindex: 'a3' as IndexKey,\n\t\t\t\tx: info.end.handle.x,\n\t\t\t\ty: info.end.handle.y,\n\t\t\t},\n\t\t]\n\n\t\tif (shape.props.kind === 'arc' && (info.type === 'straight' || info.type === 'arc')) {\n\t\t\thandles.push({\n\t\t\t\tid: ArrowHandles.Middle,\n\t\t\t\ttype: 'virtual',\n\t\t\t\tindex: 'a2' as IndexKey,\n\t\t\t\tx: info.middle.x,\n\t\t\t\ty: info.middle.y,\n\t\t\t})\n\t\t}\n\n\t\tif (shape.props.kind === 'elbow' && info.type === 'elbow' && info.route.midpointHandle) {\n\t\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\n\t\t\tconst segmentStart = shapePageTransform.applyToPoint(info.route.midpointHandle.segmentStart)\n\t\t\tconst segmentEnd = shapePageTransform.applyToPoint(info.route.midpointHandle.segmentEnd)\n\t\t\tconst segmentLength = Vec.Dist(segmentStart, segmentEnd) * this.editor.getZoomLevel()\n\n\t\t\tif (segmentLength > this.options.elbowMinSegmentLengthToShowMidpointHandle) {\n\t\t\t\thandles.push({\n\t\t\t\t\tid: ArrowHandles.Middle,\n\t\t\t\t\ttype: 'vertex',\n\t\t\t\t\tindex: 'a2' as IndexKey,\n\t\t\t\t\tx: info.route.midpointHandle.point.x,\n\t\t\t\t\ty: info.route.midpointHandle.point.y,\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\n\t\treturn handles\n\t}\n\n\toverride getText(shape: TLArrowShape) {\n\t\treturn renderPlaintextFromRichText(this.editor, shape.props.richText)\n\t}\n\n\toverride onHandleDrag(shape: TLArrowShape, info: TLHandleDragInfo<TLArrowShape>) {\n\t\tconst handleId = info.handle.id as ArrowHandles\n\t\tswitch (handleId) {\n\t\t\tcase ArrowHandles.Middle:\n\t\t\t\tswitch (shape.props.kind) {\n\t\t\t\t\tcase 'arc':\n\t\t\t\t\t\treturn this.onArcMidpointHandleDrag(shape, info)\n\t\t\t\t\tcase 'elbow':\n\t\t\t\t\t\treturn this.onElbowMidpointHandleDrag(shape, info)\n\t\t\t\t\tdefault:\n\t\t\t\t\t\texhaustiveSwitchError(shape.props.kind)\n\t\t\t\t}\n\t\t\tcase ArrowHandles.Start:\n\t\t\tcase ArrowHandles.End:\n\t\t\t\treturn this.onTerminalHandleDrag(shape, info, handleId)\n\t\t\tdefault:\n\t\t\t\texhaustiveSwitchError(handleId)\n\t\t}\n\t}\n\n\tprivate onArcMidpointHandleDrag(shape: TLArrowShape, { handle }: TLHandleDragInfo<TLArrowShape>) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\t// Bending the arrow...\n\t\tconst { start, end } = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\n\t\tconst delta = Vec.Sub(end, start)\n\t\tconst v = Vec.Per(delta)\n\n\t\tconst med = Vec.Med(end, start)\n\t\tconst A = Vec.Sub(med, v)\n\t\tconst B = Vec.Add(med, v)\n\n\t\tconst point = Vec.NearestPointOnLineSegment(A, B, handle, false)\n\t\tlet bend = Vec.Dist(point, med)\n\t\tif (Vec.Clockwise(point, end, med)) bend *= -1\n\t\treturn { id: shape.id, type: shape.type, props: { bend } }\n\t}\n\n\tprivate onElbowMidpointHandleDrag(\n\t\tshape: TLArrowShape,\n\t\t{ handle }: TLHandleDragInfo<TLArrowShape>\n\t) {\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (info?.type !== 'elbow') return\n\n\t\tconst shapeToPageTransform = this.editor.getShapePageTransform(shape.id)!\n\t\tconst handlePagePoint = shapeToPageTransform.applyToPoint(handle)\n\t\tconst axisName = info.route.midpointHandle?.axis\n\t\tif (!axisName) return\n\t\tconst axis = ElbowArrowAxes[axisName]\n\n\t\tconst midRange = info.elbow[axis.midRange]\n\t\tif (!midRange) return\n\n\t\t// We're snapping against a list of parallel lines. The way we do this is to calculate the\n\t\t// angle of the line we're snapping to...\n\t\tlet angle = Vec.Angle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(0, 0)),\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(0, 1))\n\t\t)\n\t\tif (angle < 0) angle += Math.PI\n\n\t\t// ...then calculate the perpendicular distance from the origin to the (infinite) line in\n\t\t// question. This returns a signed distance - lines \"behind\" the origin are negative.\n\t\tconst handlePoint = perpDistanceToLineAngle(handlePagePoint, angle)\n\n\t\t// As we're only ever moving along one dimension, we can use this perpendicular distance for\n\t\t// all of our snapping calculations.\n\t\tconst loPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(midRange.lo, 0)),\n\t\t\tangle\n\t\t)\n\t\tconst hiPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(midRange.hi, 0)),\n\t\t\tangle\n\t\t)\n\n\t\t// we want to snap to certain points. the maximum distance at which a snap will occur is\n\t\t// relative to the zoom level:\n\t\tconst maxSnapDistance = this.options.elbowMidpointSnapDistance / this.editor.getZoomLevel()\n\n\t\t// we snap to the midpoint of the range by default\n\t\tconst midPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(lerp(midRange.lo, midRange.hi, 0.5), 0)),\n\t\t\tangle\n\t\t)\n\n\t\tlet snapPoint = midPoint\n\t\tlet snapDistance = Math.abs(midPoint - handlePoint)\n\n\t\t// then we check all the other arrows that are on-screen.\n\t\tfor (const [snapAngle, snapLines] of getElbowArrowSnapLines(this.editor)) {\n\t\t\tconst { isParallel, isFlippedParallel } = anglesAreApproximatelyParallel(angle, snapAngle)\n\t\t\tif (isParallel || isFlippedParallel) {\n\t\t\t\tfor (const snapLine of snapLines) {\n\t\t\t\t\tconst doesShareStartIntersection =\n\t\t\t\t\t\tsnapLine.startBoundShapeId &&\n\t\t\t\t\t\t(snapLine.startBoundShapeId === info.bindings.start?.toId ||\n\t\t\t\t\t\t\tsnapLine.startBoundShapeId === info.bindings.end?.toId)\n\n\t\t\t\t\tconst doesShareEndIntersection =\n\t\t\t\t\t\tsnapLine.endBoundShapeId &&\n\t\t\t\t\t\t(snapLine.endBoundShapeId === info.bindings.start?.toId ||\n\t\t\t\t\t\t\tsnapLine.endBoundShapeId === info.bindings.end?.toId)\n\n\t\t\t\t\tif (!doesShareStartIntersection && !doesShareEndIntersection) continue\n\n\t\t\t\t\tconst point = isFlippedParallel ? -snapLine.perpDistance : snapLine.perpDistance\n\t\t\t\t\tconst distance = Math.abs(point - handlePoint)\n\t\t\t\t\tif (distance < snapDistance) {\n\t\t\t\t\t\tsnapPoint = point\n\t\t\t\t\t\tsnapDistance = distance\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (snapDistance > maxSnapDistance) {\n\t\t\tsnapPoint = handlePoint\n\t\t}\n\n\t\tconst newMid = clamp(invLerp(loPoint, hiPoint, snapPoint), 0, 1)\n\n\t\treturn {\n\t\t\tid: shape.id,\n\t\t\ttype: shape.type,\n\t\t\tprops: {\n\t\t\t\telbowMidPoint: newMid,\n\t\t\t},\n\t\t}\n\t}\n\n\tprivate onTerminalHandleDrag(\n\t\tshape: TLArrowShape,\n\t\t{ handle, isPrecise }: TLHandleDragInfo<TLArrowShape>,\n\t\thandleId: ArrowHandles.Start | ArrowHandles.End\n\t) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\tconst update: TLShapePartial<TLArrowShape> = { id: shape.id, type: 'arrow', props: {} }\n\n\t\tconst currentBinding = bindings[handleId]\n\n\t\tconst oppositeHandleId = handleId === ArrowHandles.Start ? ArrowHandles.End : ArrowHandles.Start\n\t\tconst oppositeBinding = bindings[oppositeHandleId]\n\n\t\tconst targetInfo = updateArrowTargetState({\n\t\t\teditor: this.editor,\n\t\t\tpointInPageSpace: this.editor.getShapePageTransform(shape.id)!.applyToPoint(handle),\n\t\t\tarrow: shape,\n\t\t\tisPrecise: isPrecise,\n\t\t\tcurrentBinding,\n\t\t\toppositeBinding,\n\t\t})\n\n\t\tif (!targetInfo) {\n\t\t\t// todo: maybe double check that this isn't equal to the other handle too?\n\t\t\tremoveArrowBinding(this.editor, shape, handleId)\n\t\t\tconst newPoint = maybeSnapToGrid(new Vec(handle.x, handle.y), this.editor)\n\t\t\tupdate.props![handleId] = {\n\t\t\t\tx: newPoint.x,\n\t\t\t\ty: newPoint.y,\n\t\t\t}\n\t\t\treturn update\n\t\t}\n\n\t\t// we've got a target! the handle is being dragged over a shape, bind to it\n\t\tconst bindingProps: TLArrowBindingProps = {\n\t\t\tterminal: handleId,\n\t\t\tnormalizedAnchor: targetInfo.normalizedAnchor,\n\t\t\tisPrecise: targetInfo.isPrecise,\n\t\t\tisExact: targetInfo.isExact,\n\t\t\tsnap: targetInfo.snap,\n\t\t}\n\n\t\tcreateOrUpdateArrowBinding(this.editor, shape, targetInfo.target.id, bindingProps)\n\n\t\tconst newBindings = getArrowBindings(this.editor, shape)\n\t\tif (newBindings.start && newBindings.end && newBindings.start.toId === newBindings.end.toId) {\n\t\t\tif (\n\t\t\t\tVec.Equals(newBindings.start.props.normalizedAnchor, newBindings.end.props.normalizedAnchor)\n\t\t\t) {\n\t\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, newBindings.end.toId, {\n\t\t\t\t\t...newBindings.end.props,\n\t\t\t\t\tnormalizedAnchor: {\n\t\t\t\t\t\tx: newBindings.end.props.normalizedAnchor.x + 0.05,\n\t\t\t\t\t\ty: newBindings.end.props.normalizedAnchor.y,\n\t\t\t\t\t},\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\n\t\treturn update\n\t}\n\n\toverride onTranslateStart(shape: TLArrowShape) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\t// ...if the user is dragging ONLY this arrow, for elbow shapes, we can't maintain the bindings well just yet so we remove them entirely\n\t\tif (shape.props.kind === 'elbow' && this.editor.getOnlySelectedShapeId() === shape.id) {\n\t\t\tconst info = getArrowInfo(this.editor, shape)\n\t\t\tif (!info) return\n\t\t\tconst update: TLShapePartial<TLArrowShape> = { id: shape.id, type: 'arrow', props: {} }\n\t\t\tif (bindings.start) {\n\t\t\t\tupdate.props!.start = { x: info.start.point.x, y: info.start.point.y }\n\t\t\t\tremoveArrowBinding(this.editor, shape, 'start')\n\t\t\t}\n\t\t\tif (bindings.end) {\n\t\t\t\tupdate.props!.end = { x: info.end.point.x, y: info.end.point.y }\n\t\t\t\tremoveArrowBinding(this.editor, shape, 'end')\n\t\t\t}\n\t\t\treturn update\n\t\t}\n\n\t\tconst terminalsInArrowSpace = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\n\t\t// If at least one bound shape is in the selection, do nothing;\n\t\t// If no bound shapes are in the selection, unbind any bound shapes\n\n\t\tconst selectedShapeIds = this.editor.getSelectedShapeIds()\n\n\t\tif (\n\t\t\t(bindings.start &&\n\t\t\t\t(selectedShapeIds.includes(bindings.start.toId) ||\n\t\t\t\t\tthis.editor.isAncestorSelected(bindings.start.toId))) ||\n\t\t\t(bindings.end &&\n\t\t\t\t(selectedShapeIds.includes(bindings.end.toId) ||\n\t\t\t\t\tthis.editor.isAncestorSelected(bindings.end.toId)))\n\t\t) {\n\t\t\treturn\n\t\t}\n\n\t\t// When we start translating shapes, record where their bindings were in page space so we\n\t\t// can maintain them as we translate the arrow\n\t\tshapeAtTranslationStart.set(shape, {\n\t\t\tpagePosition: shapePageTransform.applyToPoint(shape),\n\t\t\tterminalBindings: mapObjectMapValues(terminalsInArrowSpace, (terminalName, point) => {\n\t\t\t\tconst binding = bindings[terminalName]\n\t\t\t\tif (!binding) return null\n\t\t\t\treturn {\n\t\t\t\t\tbinding,\n\t\t\t\t\tshapePosition: point,\n\t\t\t\t\tpagePosition: shapePageTransform.applyToPoint(point),\n\t\t\t\t}\n\t\t\t}),\n\t\t})\n\n\t\t// update arrow terminal bindings eagerly to make sure the arrows unbind nicely when translating\n\t\tif (bindings.start) {\n\t\t\tupdateArrowTerminal({\n\t\t\t\teditor: this.editor,\n\t\t\t\tarrow: shape,\n\t\t\t\tterminal: 'start',\n\t\t\t\tuseHandle: true,\n\t\t\t})\n\t\t\tshape = this.editor.getShape(shape.id) as TLArrowShape\n\t\t}\n\t\tif (bindings.end) {\n\t\t\tupdateArrowTerminal({\n\t\t\t\teditor: this.editor,\n\t\t\t\tarrow: shape,\n\t\t\t\tterminal: 'end',\n\t\t\t\tuseHandle: true,\n\t\t\t})\n\t\t}\n\n\t\tfor (const handleName of [ArrowHandles.Start, ArrowHandles.End] as const) {\n\t\t\tconst binding = bindings[handleName]\n\t\t\tif (!binding) continue\n\n\t\t\tthis.editor.updateBinding({\n\t\t\t\t...binding,\n\t\t\t\tprops: { ...binding.props, isPrecise: true },\n\t\t\t})\n\t\t}\n\n\t\treturn\n\t}\n\n\toverride onTranslate(initialShape: TLArrowShape, shape: TLArrowShape) {\n\t\tconst atTranslationStart = shapeAtTranslationStart.get(initialShape)\n\t\tif (!atTranslationStart) return\n\n\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\t\tconst pageDelta = Vec.Sub(\n\t\t\tshapePageTransform.applyToPoint(shape),\n\t\t\tatTranslationStart.pagePosition\n\t\t)\n\n\t\tfor (const terminalBinding of Object.values(atTranslationStart.terminalBindings)) {\n\t\t\tif (!terminalBinding) continue\n\n\t\t\tconst newPagePoint = Vec.Add(terminalBinding.pagePosition, Vec.Mul(pageDelta, 0.5))\n\t\t\tconst newTarget = this.editor.getShapeAtPoint(newPagePoint, {\n\t\t\t\thitInside: true,\n\t\t\t\thitFrameInside: true,\n\t\t\t\tmargin: 0,\n\t\t\t\tfilter: (targetShape) => {\n\t\t\t\t\treturn (\n\t\t\t\t\t\t!targetShape.isLocked &&\n\t\t\t\t\t\tthis.editor.canBindShapes({ fromShape: shape, toShape: targetShape, binding: 'arrow' })\n\t\t\t\t\t)\n\t\t\t\t},\n\t\t\t})\n\n\t\t\tif (newTarget?.id === terminalBinding.binding.toId) {\n\t\t\t\tconst targetBounds = Box.ZeroFix(this.editor.getShapeGeometry(newTarget).bounds)\n\t\t\t\tconst pointInTargetSpace = this.editor.getPointInShapeSpace(newTarget, newPagePoint)\n\t\t\t\tconst normalizedAnchor = {\n\t\t\t\t\tx: (pointInTargetSpace.x - targetBounds.minX) / targetBounds.width,\n\t\t\t\t\ty: (pointInTargetSpace.y - targetBounds.minY) / targetBounds.height,\n\t\t\t\t}\n\t\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, newTarget.id, {\n\t\t\t\t\t...terminalBinding.binding.props,\n\t\t\t\t\tnormalizedAnchor,\n\t\t\t\t\tisPrecise: true,\n\t\t\t\t})\n\t\t\t} else {\n\t\t\t\tremoveArrowBinding(this.editor, shape, terminalBinding.binding.props.terminal)\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate readonly _resizeInitialBindings = new WeakCache<TLArrowShape, TLArrowBindings>()\n\n\toverride onResize(shape: TLArrowShape, info: TLResizeInfo<TLArrowShape>) {\n\t\tconst { scaleX, scaleY } = info\n\n\t\tconst bindings = this._resizeInitialBindings.get(shape, () =>\n\t\t\tgetArrowBindings(this.editor, shape)\n\t\t)\n\t\tconst terminals = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\n\t\tconst { start, end } = structuredClone<TLArrowShape['props']>(shape.props)\n\t\tlet { bend } = shape.props\n\n\t\t// Rescale start handle if it's not bound to a shape\n\t\tif (!bindings.start) {\n\t\t\tstart.x = terminals.start.x * scaleX\n\t\t\tstart.y = terminals.start.y * scaleY\n\t\t}\n\n\t\t// Rescale end handle if it's not bound to a shape\n\t\tif (!bindings.end) {\n\t\t\tend.x = terminals.end.x * scaleX\n\t\t\tend.y = terminals.end.y * scaleY\n\t\t}\n\n\t\t// todo: we should only change the normalized anchor positions\n\t\t// of the shape's handles if the bound shape is also being resized\n\n\t\tconst mx = Math.abs(scaleX)\n\t\tconst my = Math.abs(scaleY)\n\n\t\tconst startNormalizedAnchor = bindings?.start\n\t\t\t? Vec.From(bindings.start.props.normalizedAnchor)\n\t\t\t: null\n\t\tconst endNormalizedAnchor = bindings?.end ? Vec.From(bindings.end.props.normalizedAnchor) : null\n\n\t\tif (scaleX < 0 && scaleY >= 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= -1\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.x = 1 - startNormalizedAnchor.x\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.x = 1 - endNormalizedAnchor.x\n\t\t\t}\n\t\t} else if (scaleX >= 0 && scaleY < 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= -1\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.y = 1 - startNormalizedAnchor.y\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.y = 1 - endNormalizedAnchor.y\n\t\t\t}\n\t\t} else if (scaleX >= 0 && scaleY >= 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\t\t} else if (scaleX < 0 && scaleY < 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.x = 1 - startNormalizedAnchor.x\n\t\t\t\tstartNormalizedAnchor.y = 1 - startNormalizedAnchor.y\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.x = 1 - endNormalizedAnchor.x\n\t\t\t\tendNormalizedAnchor.y = 1 - endNormalizedAnchor.y\n\t\t\t}\n\t\t}\n\n\t\tif (bindings.start && startNormalizedAnchor) {\n\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, bindings.start.toId, {\n\t\t\t\t...bindings.start.props,\n\t\t\t\tnormalizedAnchor: startNormalizedAnchor.toJson(),\n\t\t\t})\n\t\t}\n\t\tif (bindings.end && endNormalizedAnchor) {\n\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, bindings.end.toId, {\n\t\t\t\t...bindings.end.props,\n\t\t\t\tnormalizedAnchor: endNormalizedAnchor.toJson(),\n\t\t\t})\n\t\t}\n\n\t\tconst next = {\n\t\t\tprops: {\n\t\t\t\tstart,\n\t\t\t\tend,\n\t\t\t\tbend,\n\t\t\t},\n\t\t}\n\n\t\treturn next\n\t}\n\n\toverride onDoubleClickHandle(\n\t\tshape: TLArrowShape,\n\t\thandle: TLHandle\n\t): TLShapePartial<TLArrowShape> | void {\n\t\tswitch (handle.id) {\n\t\t\tcase ArrowHandles.Start: {\n\t\t\t\treturn {\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: {\n\t\t\t\t\t\t...shape.props,\n\t\t\t\t\t\tarrowheadStart: shape.props.arrowheadStart === 'none' ? 'arrow' : 'none',\n\t\t\t\t\t},\n\t\t\t\t}\n\t\t\t}\n\t\t\tcase ArrowHandles.End: {\n\t\t\t\treturn {\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: {\n\t\t\t\t\t\t...shape.props,\n\t\t\t\t\t\tarrowheadEnd: shape.props.arrowheadEnd === 'none' ? 'arrow' : 'none',\n\t\t\t\t\t},\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tcomponent(shape: TLArrowShape) {\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst theme = useDefaultColorTheme()\n\t\tconst onlySelectedShape = this.editor.getOnlySelectedShape()\n\t\tconst shouldDisplayHandles =\n\t\t\tthis.editor.isInAny(\n\t\t\t\t'select.idle',\n\t\t\t\t'select.pointing_handle',\n\t\t\t\t'select.dragging_handle',\n\t\t\t\t'select.translating',\n\t\t\t\t'arrow.dragging'\n\t\t\t) && !this.editor.getIsReadonly()\n\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (!info?.isValid) return null\n\n\t\tconst labelPosition = getArrowLabelPosition(this.editor, shape)\n\t\tconst isSelected = shape.id === this.editor.getOnlySelectedShapeId()\n\t\tconst isEditing = this.editor.getEditingShapeId() === shape.id\n\t\tconst showArrowLabel = isEditing || !isEmptyRichText(shape.props.richText)\n\n\t\treturn (\n\t\t\t<>\n\t\t\t\t<SVGContainer style={{ minWidth: 50, minHeight: 50 }}>\n\t\t\t\t\t<ArrowSvg\n\t\t\t\t\t\tshape={shape}\n\t\t\t\t\t\tshouldDisplayHandles={shouldDisplayHandles && onlySelectedShape?.id === shape.id}\n\t\t\t\t\t/>\n\t\t\t\t\t{shape.props.kind === 'elbow' && debugFlags.debugElbowArrows.get() && (\n\t\t\t\t\t\t<ElbowArrowDebug arrow={shape} />\n\t\t\t\t\t)}\n\t\t\t\t</SVGContainer>\n\t\t\t\t{showArrowLabel && (\n\t\t\t\t\t<RichTextLabel\n\t\t\t\t\t\tshapeId={shape.id}\n\t\t\t\t\t\ttype=\"arrow\"\n\t\t\t\t\t\tfont={shape.props.font}\n\t\t\t\t\t\tfontSize={getArrowLabelFontSize(shape)}\n\t\t\t\t\t\tlineHeight={TEXT_PROPS.lineHeight}\n\t\t\t\t\t\talign=\"middle\"\n\t\t\t\t\t\tverticalAlign=\"middle\"\n\t\t\t\t\t\tlabelColor={getColorValue(theme, shape.props.labelColor, 'solid')}\n\t\t\t\t\t\trichText={shape.props.richText}\n\t\t\t\t\t\ttextWidth={labelPosition.box.w - ARROW_LABEL_PADDING * 2 * shape.props.scale}\n\t\t\t\t\t\tisSelected={isSelected}\n\t\t\t\t\t\tpadding={0}\n\t\t\t\t\t\tstyle={{\n\t\t\t\t\t\t\ttransform: `translate(${labelPosition.box.center.x}px, ${labelPosition.box.center.y}px)`,\n\t\t\t\t\t\t}}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t</>\n\t\t)\n\t}\n\n\tindicator(shape: TLArrowShape) {\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst isEditing = useIsEditing(shape.id)\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst clipPathId = useSharedSafeId(shape.id + '_clip')\n\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (!info) return null\n\n\t\tconst { start, end } = getArrowTerminalsInArrowSpace(this.editor, shape, info?.bindings)\n\t\tconst geometry = this.editor.getShapeGeometry<Group2d>(shape)\n\t\tconst bounds = geometry.bounds\n\t\tconst isEmpty = isEmptyRichText(shape.props.richText)\n\n\t\tconst labelGeometry = isEditing || !isEmpty ? (geometry.children[1] as Rectangle2d) : null\n\n\t\tif (Vec.Equals(start, end)) return null\n\n\t\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\n\t\tconst as = info.start.arrowhead && getArrowheadPathForType(info, 'start', strokeWidth)\n\t\tconst ae = info.end.arrowhead && getArrowheadPathForType(info, 'end', strokeWidth)\n\n\t\tconst includeClipPath =\n\t\t\t(as && info.start.arrowhead !== 'arrow') ||\n\t\t\t(ae && info.end.arrowhead !== 'arrow') ||\n\t\t\t!!labelGeometry\n\n\t\tconst labelBounds = labelGeometry ? labelGeometry.getBounds() : new Box(0, 0, 0, 0)\n\n\t\tif (isEditing && labelGeometry) {\n\t\t\treturn (\n\t\t\t\t<rect\n\t\t\t\t\tx={toDomPrecision(labelBounds.x)}\n\t\t\t\t\ty={toDomPrecision(labelBounds.y)}\n\t\t\t\t\twidth={labelBounds.w}\n\t\t\t\t\theight={labelBounds.h}\n\t\t\t\t\trx={3.5 * shape.props.scale}\n\t\t\t\t\try={3.5 * shape.props.scale}\n\t\t\t\t/>\n\t\t\t)\n\t\t}\n\t\tconst clipStartArrowhead = !(\n\t\t\tinfo.start.arrowhead === 'none' || info.start.arrowhead === 'arrow'\n\t\t)\n\t\tconst clipEndArrowhead = !(info.end.arrowhead === 'none' || info.end.arrowhead === 'arrow')\n\n\t\treturn (\n\t\t\t<g>\n\t\t\t\t{includeClipPath && (\n\t\t\t\t\t<defs>\n\t\t\t\t\t\t<ArrowClipPath\n\t\t\t\t\t\t\tradius={3.5 * shape.props.scale}\n\t\t\t\t\t\t\thasText={!isEmpty}\n\t\t\t\t\t\t\tbounds={bounds}\n\t\t\t\t\t\t\tlabelBounds={labelBounds}\n\t\t\t\t\t\t\tas={clipStartArrowhead && as ? as : ''}\n\t\t\t\t\t\t\tae={clipEndArrowhead && ae ? ae : ''}\n\t\t\t\t\t\t/>\n\t\t\t\t\t</defs>\n\t\t\t\t)}\n\t\t\t\t<g\n\t\t\t\t\tstyle={{\n\t\t\t\t\t\tclipPath: includeClipPath ? `url(#${clipPathId})` : undefined,\n\t\t\t\t\t\tWebkitClipPath: includeClipPath ? `url(#${clipPathId})` : undefined,\n\t\t\t\t\t}}\n\t\t\t\t>\n\t\t\t\t\t{/* This rect needs to be here if we're creating a mask due to an svg quirk on Chrome */}\n\t\t\t\t\t{includeClipPath && (\n\t\t\t\t\t\t<rect\n\t\t\t\t\t\t\tx={bounds.minX - 100}\n\t\t\t\t\t\t\ty={bounds.minY - 100}\n\t\t\t\t\t\t\twidth={bounds.width + 200}\n\t\t\t\t\t\t\theight={bounds.height + 200}\n\t\t\t\t\t\t\topacity={0}\n\t\t\t\t\t\t/>\n\t\t\t\t\t)}\n\n\t\t\t\t\t{getArrowBodyPath(\n\t\t\t\t\t\tshape,\n\t\t\t\t\t\tinfo,\n\t\t\t\t\t\tshape.props.dash === 'draw'\n\t\t\t\t\t\t\t? {\n\t\t\t\t\t\t\t\t\tstyle: 'draw',\n\t\t\t\t\t\t\t\t\trandomSeed: shape.id,\n\t\t\t\t\t\t\t\t\tstrokeWidth: 1,\n\t\t\t\t\t\t\t\t\tpasses: 1,\n\t\t\t\t\t\t\t\t\toffset: 0,\n\t\t\t\t\t\t\t\t\troundness: strokeWidth * 2,\n\t\t\t\t\t\t\t\t\tprops: { strokeWidth: undefined },\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t: { style: 'solid', strokeWidth: 1, props: { strokeWidth: undefined } }\n\t\t\t\t\t)}\n\t\t\t\t</g>\n\t\t\t\t{as && <path d={as} />}\n\t\t\t\t{ae && <path d={ae} />}\n\t\t\t\t{labelGeometry && (\n\t\t\t\t\t<rect\n\t\t\t\t\t\tx={toDomPrecision(labelBounds.x)}\n\t\t\t\t\t\ty={toDomPrecision(labelBounds.y)}\n\t\t\t\t\t\twidth={labelBounds.w}\n\t\t\t\t\t\theight={labelBounds.h}\n\t\t\t\t\t\trx={3.5}\n\t\t\t\t\t\try={3.5}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t</g>\n\t\t)\n\t}\n\n\toverride onEditStart(shape: TLArrowShape) {\n\t\tif (isEmptyRichText(shape.props.richText)) {\n\t\t\t// editing text for the first time, so set the position to the default:\n\t\t\tconst labelPosition = getArrowLabelDefaultPosition(this.editor, shape)\n\t\t\tthis.editor.updateShape<TLArrowShape>({\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { labelPosition },\n\t\t\t})\n\t\t}\n\t}\n\n\toverride toSvg(shape: TLArrowShape, ctx: SvgExportContext) {\n\t\tctx.addExportDef(getFillDefForExport(shape.props.fill))\n\t\tconst theme = getDefaultColorTheme(ctx)\n\t\tconst scaleFactor = 1 / shape.props.scale\n\n\t\treturn (\n\t\t\t<g transform={`scale(${scaleFactor})`}>\n\t\t\t\t<ArrowSvg shape={shape} shouldDisplayHandles={false} />\n\t\t\t\t<RichTextSVG\n\t\t\t\t\tfontSize={getArrowLabelFontSize(shape)}\n\t\t\t\t\tfont={shape.props.font}\n\t\t\t\t\talign=\"middle\"\n\t\t\t\t\tverticalAlign=\"middle\"\n\t\t\t\t\tlabelColor={getColorValue(theme, shape.props.labelColor, 'solid')}\n\t\t\t\t\trichText={shape.props.richText}\n\t\t\t\t\tbounds={getArrowLabelPosition(this.editor, shape)\n\t\t\t\t\t\t.box.clone()\n\t\t\t\t\t\t.expandBy(-ARROW_LABEL_PADDING * shape.props.scale)}\n\t\t\t\t\tpadding={0}\n\t\t\t\t\tshowTextOutline={true}\n\t\t\t\t/>\n\t\t\t</g>\n\t\t)\n\t}\n\n\toverride getCanvasSvgDefs(): TLShapeUtilCanvasSvgDef[] {\n\t\treturn [\n\t\t\tgetFillDefForCanvas(),\n\t\t\t{\n\t\t\t\tkey: `arrow:dot`,\n\t\t\t\tcomponent: ArrowheadDotDef,\n\t\t\t},\n\t\t\t{\n\t\t\t\tkey: `arrow:cross`,\n\t\t\t\tcomponent: ArrowheadCrossDef,\n\t\t\t},\n\t\t]\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLArrowShape,\n\t\tendShape: TLArrowShape,\n\t\tprogress: number\n\t): TLArrowShapeProps {\n\t\treturn {\n\t\t\t...(progress > 0.5 ? endShape.props : startShape.props),\n\t\t\tscale: lerp(startShape.props.scale, endShape.props.scale, progress),\n\t\t\tstart: {\n\t\t\t\tx: lerp(startShape.props.start.x, endShape.props.start.x, progress),\n\t\t\t\ty: lerp(startShape.props.start.y, endShape.props.start.y, progress),\n\t\t\t},\n\t\t\tend: {\n\t\t\t\tx: lerp(startShape.props.end.x, endShape.props.end.x, progress),\n\t\t\t\ty: lerp(startShape.props.end.y, endShape.props.end.y, progress),\n\t\t\t},\n\t\t\tbend: lerp(startShape.props.bend, endShape.props.bend, progress),\n\t\t\tlabelPosition: lerp(startShape.props.labelPosition, endShape.props.labelPosition, progress),\n\t\t}\n\t}\n}\n\nexport function getArrowLength(editor: Editor, shape: TLArrowShape): number {\n\tconst info = getArrowInfo(editor, shape)!\n\n\treturn info.type === 'straight'\n\t\t? Vec.Dist(info.start.handle, info.end.handle)\n\t\t: info.type === 'arc'\n\t\t\t? Math.abs(info.handleArc.length)\n\t\t\t: info.route.distance\n}\n\nconst ArrowSvg = track(function ArrowSvg({\n\tshape,\n\tshouldDisplayHandles,\n}: {\n\tshape: TLArrowShape\n\tshouldDisplayHandles: boolean\n}) {\n\tconst editor = useEditor()\n\tconst theme = useDefaultColorTheme()\n\tconst info = getArrowInfo(editor, shape)\n\tconst isForceSolid = useValue(\n\t\t'force solid',\n\t\t() => {\n\t\t\treturn editor.getZoomLevel() < 0.2\n\t\t},\n\t\t[editor]\n\t)\n\tconst clipPathId = useSharedSafeId(shape.id + '_clip')\n\tconst arrowheadDotId = useSharedSafeId('arrowhead-dot')\n\tconst arrowheadCrossId = useSharedSafeId('arrowhead-cross')\n\tconst isEditing = useIsEditing(shape.id)\n\tconst geometry = editor.getShapeGeometry(shape)\n\tif (!geometry) return null\n\tconst bounds = Box.ZeroFix(geometry.bounds)\n\tconst bindings = getArrowBindings(editor, shape)\n\tconst isEmpty = isEmptyRichText(shape.props.richText)\n\n\tif (!info?.isValid) return null\n\n\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\n\tconst as = info.start.arrowhead && getArrowheadPathForType(info, 'start', strokeWidth)\n\tconst ae = info.end.arrowhead && getArrowheadPathForType(info, 'end', strokeWidth)\n\n\tlet handlePath: null | React.JSX.Element = null\n\n\tif (shouldDisplayHandles && (bindings.start || bindings.end)) {\n\t\thandlePath = getArrowHandlePath(info, {\n\t\t\tstyle: 'dashed',\n\t\t\tstart: 'skip',\n\t\t\tend: 'skip',\n\t\t\tlengthRatio: 2.5,\n\t\t\tstrokeWidth: 2 / editor.getZoomLevel(),\n\t\t\tprops: {\n\t\t\t\tclassName: 'tl-arrow-hint',\n\t\t\t\tmarkerStart: bindings.start\n\t\t\t\t\t? bindings.start.props.isExact\n\t\t\t\t\t\t? ''\n\t\t\t\t\t\t: bindings.start.props.isPrecise\n\t\t\t\t\t\t\t? `url(#${arrowheadCrossId})`\n\t\t\t\t\t\t\t: `url(#${arrowheadDotId})`\n\t\t\t\t\t: '',\n\t\t\t\tmarkerEnd: bindings.end\n\t\t\t\t\t? bindings.end.props.isExact\n\t\t\t\t\t\t? ''\n\t\t\t\t\t\t: bindings.end.props.isPrecise\n\t\t\t\t\t\t\t? `url(#${arrowheadCrossId})`\n\t\t\t\t\t\t\t: `url(#${arrowheadDotId})`\n\t\t\t\t\t: '',\n\t\t\t\topacity: 0.16,\n\t\t\t},\n\t\t})\n\t}\n\n\tconst labelPosition = getArrowLabelPosition(editor, shape)\n\n\tconst clipStartArrowhead = !(info.start.arrowhead === 'none' || info.start.arrowhead === 'arrow')\n\tconst clipEndArrowhead = !(info.end.arrowhead === 'none' || info.end.arrowhead === 'arrow')\n\n\treturn (\n\t\t<>\n\t\t\t{/* Yep */}\n\t\t\t<defs>\n\t\t\t\t<clipPath id={clipPathId}>\n\t\t\t\t\t<ArrowClipPath\n\t\t\t\t\t\tradius={3.5 * shape.props.scale}\n\t\t\t\t\t\thasText={isEditing || !isEmpty}\n\t\t\t\t\t\tbounds={bounds}\n\t\t\t\t\t\tlabelBounds={labelPosition.box}\n\t\t\t\t\t\tas={clipStartArrowhead && as ? as : ''}\n\t\t\t\t\t\tae={clipEndArrowhead && ae ? ae : ''}\n\t\t\t\t\t/>\n\t\t\t\t</clipPath>\n\t\t\t</defs>\n\t\t\t<g\n\t\t\t\tfill=\"none\"\n\t\t\t\tstroke={getColorValue(theme, shape.props.color, 'solid')}\n\t\t\t\tstrokeWidth={strokeWidth}\n\t\t\t\tstrokeLinejoin=\"round\"\n\t\t\t\tstrokeLinecap=\"round\"\n\t\t\t\tpointerEvents=\"none\"\n\t\t\t>\n\t\t\t\t{handlePath}\n\t\t\t\t<g\n\t\t\t\t\tstyle={{\n\t\t\t\t\t\tclipPath: `url(#${clipPathId})`,\n\t\t\t\t\t\tWebkitClipPath: `url(#${clipPathId})`,\n\t\t\t\t\t}}\n\t\t\t\t>\n\t\t\t\t\t<rect\n\t\t\t\t\t\tx={toDomPrecision(bounds.minX - 100)}\n\t\t\t\t\t\ty={toDomPrecision(bounds.minY - 100)}\n\t\t\t\t\t\twidth={toDomPrecision(bounds.width + 200)}\n\t\t\t\t\t\theight={toDomPrecision(bounds.height + 200)}\n\t\t\t\t\t\topacity={0}\n\t\t\t\t\t/>\n\t\t\t\t\t{getArrowBodyPath(shape, info, {\n\t\t\t\t\t\tstyle: shape.props.dash,\n\t\t\t\t\t\tstrokeWidth,\n\t\t\t\t\t\tforceSolid: isForceSolid,\n\t\t\t\t\t\trandomSeed: shape.id,\n\t\t\t\t\t})}\n\t\t\t\t</g>\n\t\t\t\t{as && clipStartArrowhead && shape.props.fill !== 'none' && (\n\t\t\t\t\t<ShapeFill\n\t\t\t\t\t\ttheme={theme}\n\t\t\t\t\t\td={as}\n\t\t\t\t\t\tcolor={shape.props.color}\n\t\t\t\t\t\tfill={shape.props.fill}\n\t\t\t\t\t\tscale={shape.props.scale}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t\t{ae && clipEndArrowhead && shape.props.fill !== 'none' && (\n\t\t\t\t\t<ShapeFill\n\t\t\t\t\t\ttheme={theme}\n\t\t\t\t\t\td={ae}\n\t\t\t\t\t\tcolor={shape.props.color}\n\t\t\t\t\t\tfill={shape.props.fill}\n\t\t\t\t\t\tscale={shape.props.scale}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t\t{as && <path d={as} />}\n\t\t\t\t{ae && <path d={ae} />}\n\t\t\t</g>\n\t\t</>\n\t)\n})\n\nfunction ArrowClipPath({\n\tradius,\n\thasText,\n\tbounds,\n\tlabelBounds,\n\tas,\n\tae,\n}: {\n\tradius: number\n\thasText: boolean\n\tbounds: Box\n\tlabelBounds: Box\n\tas: string\n\tae: string\n}) {\n\tconst path = useMemo(() => {\n\t\t// The direction in which we create the different path parts is important, as it determines what gets clipped.\n\t\t// See the description on the directions in the non-zero fill rule example:\n\t\t// https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/fill-rule#nonzero\n\t\tconst path = new PathBuilder()\n\n\t\t// We create this one in the clockwise direction\n\t\tpath\n\t\t\t.moveTo(bounds.left - 100, bounds.top - 100)\n\t\t\t.lineTo(bounds.right + 100, bounds.top - 100)\n\t\t\t.lineTo(bounds.right + 100, bounds.bottom + 100)\n\t\t\t.lineTo(bounds.left - 100, bounds.bottom + 100)\n\t\t\t.close()\n\n\t\tif (hasText) {\n\t\t\t// We create this one in the counter-clockwise direction, which cuts out the label box\n\t\t\tpath\n\t\t\t\t.moveTo(labelBounds.left, labelBounds.top + radius)\n\t\t\t\t.lineTo(labelBounds.left, labelBounds.bottom - radius)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.left + radius, labelBounds.bottom)\n\t\t\t\t.lineTo(labelBounds.right - radius, labelBounds.bottom)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.right, labelBounds.bottom - radius)\n\t\t\t\t.lineTo(labelBounds.right, labelBounds.top + radius)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.right - radius, labelBounds.top)\n\t\t\t\t.lineTo(labelBounds.left + radius, labelBounds.top)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.left, labelBounds.top + radius)\n\t\t\t\t.close()\n\t\t}\n\n\t\treturn path.toD()\n\t}, [\n\t\tradius,\n\t\thasText,\n\t\tbounds.bottom,\n\t\tbounds.left,\n\t\tbounds.right,\n\t\tbounds.top,\n\t\tlabelBounds.bottom,\n\t\tlabelBounds.left,\n\t\tlabelBounds.right,\n\t\tlabelBounds.top,\n\t])\n\n\t// We also append the arrowhead paths to the clip path, so that we also clip the arrowheads\n\treturn <path d={`${path}${as}${ae}`} />\n}\n\nconst shapeAtTranslationStart = new WeakMap<\n\tTLArrowShape,\n\t{\n\t\tpagePosition: Vec\n\t\tterminalBindings: Record<\n\t\t\t'start' | 'end',\n\t\t\t{\n\t\t\t\tpagePosition: Vec\n\t\t\t\tshapePosition: Vec\n\t\t\t\tbinding: TLArrowBinding\n\t\t\t} | null\n\t\t>\n\t}\n>()\n\nfunction ArrowheadDotDef() {\n\tconst id = useSharedSafeId('arrowhead-dot')\n\treturn (\n\t\t<marker id={id} className=\"tl-arrow-hint\" refX=\"3.0\" refY=\"3.0\" orient=\"0\">\n\t\t\t<circle cx=\"3\" cy=\"3\" r=\"2\" strokeDasharray=\"100%\" />\n\t\t</marker>\n\t)\n}\n\nfunction ArrowheadCrossDef() {\n\tconst id = useSharedSafeId('arrowhead-cross')\n\treturn (\n\t\t<marker id={id} className=\"tl-arrow-hint\" refX=\"3.0\" refY=\"3.0\" orient=\"auto\">\n\t\t\t<line x1=\"1.5\" y1=\"1.5\" x2=\"4.5\" y2=\"4.5\" strokeDasharray=\"100%\" />\n\t\t\t<line x1=\"1.5\" y1=\"4.5\" x2=\"4.5\" y2=\"1.5\" strokeDasharray=\"100%\" />\n\t\t</marker>\n\t)\n}\n\n/**\n * Take 2 angles and return true if they are approximately parallel. Angle that point in the same\n * (or opposite) directions are considered parallel. This also handles wrap around - e.g. 0, \u03C0, and\n * 2\u03C0 are all considered parallel.\n */\nfunction anglesAreApproximatelyParallel(a: number, b: number, tolerance = 0.0001) {\n\tconst diff = Math.abs(a - b)\n\n\tconst isParallel = diff < tolerance\n\tconst isFlippedParallel = Math.abs(diff - Math.PI) < tolerance\n\tconst is360Parallel = Math.abs(diff - PI2) < tolerance\n\n\treturn { isParallel: isParallel || is360Parallel, isFlippedParallel }\n}\n"],
|
|
5
|
-
"mappings": "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",
|
|
4
|
+
"sourcesContent": ["import {\n\tArc2d,\n\tBox,\n\tEMPTY_ARRAY,\n\tEdge2d,\n\tEditor,\n\tGeometry2d,\n\tGroup2d,\n\tIndexKey,\n\tPI2,\n\tPolyline2d,\n\tRectangle2d,\n\tSVGContainer,\n\tShapeUtil,\n\tSvgExportContext,\n\tTLArrowBinding,\n\tTLArrowBindingProps,\n\tTLArrowShape,\n\tTLArrowShapeProps,\n\tTLHandle,\n\tTLHandleDragInfo,\n\tTLResizeInfo,\n\tTLShapePartial,\n\tTLShapeUtilCanBeLaidOutOpts,\n\tTLShapeUtilCanBindOpts,\n\tTLShapeUtilCanvasSvgDef,\n\tVec,\n\tWeakCache,\n\tarrowShapeMigrations,\n\tarrowShapeProps,\n\tclamp,\n\tdebugFlags,\n\texhaustiveSwitchError,\n\tgetColorValue,\n\tgetDefaultColorTheme,\n\tgetFontsFromRichText,\n\tinvLerp,\n\tlerp,\n\tmapObjectMapValues,\n\tmaybeSnapToGrid,\n\tstructuredClone,\n\ttoDomPrecision,\n\ttoRichText,\n\ttrack,\n\tuseEditor,\n\tuseIsEditing,\n\tuseSharedSafeId,\n\tuseValue,\n} from '@tldraw/editor'\nimport React, { useMemo } from 'react'\nimport { updateArrowTerminal } from '../../bindings/arrow/ArrowBindingUtil'\nimport { isEmptyRichText, renderPlaintextFromRichText } from '../../utils/text/richText'\nimport { PathBuilder } from '../shared/PathBuilder'\nimport { RichTextLabel, RichTextSVG } from '../shared/RichTextLabel'\nimport { ShapeFill } from '../shared/ShapeFill'\nimport { ARROW_LABEL_PADDING, STROKE_SIZES, TEXT_PROPS } from '../shared/default-shape-constants'\nimport { getFillDefForCanvas, getFillDefForExport } from '../shared/defaultStyleDefs'\nimport { useDefaultColorTheme } from '../shared/useDefaultColorTheme'\nimport { getArrowBodyPath, getArrowHandlePath } from './ArrowPath'\nimport { ArrowShapeOptions } from './arrow-types'\nimport {\n\tgetArrowLabelDefaultPosition,\n\tgetArrowLabelFontSize,\n\tgetArrowLabelPosition,\n} from './arrowLabel'\nimport { updateArrowTargetState } from './arrowTargetState'\nimport { getArrowheadPathForType } from './arrowheads'\nimport { ElbowArrowDebug } from './elbow/ElbowArrowDebug'\nimport { ElbowArrowAxes } from './elbow/definitions'\nimport { getElbowArrowSnapLines, perpDistanceToLineAngle } from './elbow/elbowArrowSnapLines'\nimport {\n\tTLArrowBindings,\n\tcreateOrUpdateArrowBinding,\n\tgetArrowBindings,\n\tgetArrowInfo,\n\tgetArrowTerminalsInArrowSpace,\n\tremoveArrowBinding,\n} from './shared'\n\nenum ArrowHandles {\n\tStart = 'start',\n\tMiddle = 'middle',\n\tEnd = 'end',\n}\n\n/** @public */\nexport class ArrowShapeUtil extends ShapeUtil<TLArrowShape> {\n\tstatic override type = 'arrow' as const\n\tstatic override props = arrowShapeProps\n\tstatic override migrations = arrowShapeMigrations\n\n\toverride options: ArrowShapeOptions = {\n\t\texpandElbowLegLength: {\n\t\t\ts: 28,\n\t\t\tm: 36,\n\t\t\tl: 44,\n\t\t\txl: 66,\n\t\t},\n\t\tminElbowLegLength: {\n\t\t\ts: STROKE_SIZES.s * 3,\n\t\t\tm: STROKE_SIZES.m * 3,\n\t\t\tl: STROKE_SIZES.l * 3,\n\t\t\txl: STROKE_SIZES.xl * 3,\n\t\t},\n\t\tminElbowHandleDistance: 16,\n\n\t\tarcArrowCenterSnapDistance: 16,\n\t\telbowArrowCenterSnapDistance: 24,\n\t\telbowArrowEdgeSnapDistance: 20,\n\t\telbowArrowPointSnapDistance: 24,\n\t\telbowArrowAxisSnapDistance: 16,\n\n\t\tlabelCenterSnapDistance: 10,\n\n\t\telbowMidpointSnapDistance: 10,\n\t\telbowMinSegmentLengthToShowMidpointHandle: 20,\n\n\t\thoverPreciseTimeout: 600,\n\t\tpointingPreciseTimeout: 320,\n\n\t\tshouldBeExact: (editor: Editor) => editor.inputs.altKey,\n\t\tshouldIgnoreTargets: (editor: Editor) => editor.inputs.ctrlKey,\n\t}\n\n\toverride canEdit() {\n\t\treturn true\n\t}\n\toverride canBind({ toShapeType }: TLShapeUtilCanBindOpts<TLArrowShape>): boolean {\n\t\t// bindings can go from arrows to shapes, but not from shapes to arrows\n\t\treturn toShapeType !== 'arrow'\n\t}\n\toverride canSnap() {\n\t\treturn false\n\t}\n\toverride hideResizeHandles() {\n\t\treturn true\n\t}\n\toverride hideRotateHandle() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsBg() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\toverride hideInMinimap() {\n\t\treturn true\n\t}\n\n\toverride canBeLaidOut(shape: TLArrowShape, info: TLShapeUtilCanBeLaidOutOpts) {\n\t\tif (info.type === 'flip') {\n\t\t\t// If we don't have this then the flip will be non-idempotent; that is, the flip will be multipotent, varipotent, or perhaps even omni-potent... and we can't have that\n\t\t\tconst bindings = getArrowBindings(this.editor, shape)\n\t\t\tconst { start, end } = bindings\n\t\t\tconst { shapes = [] } = info\n\t\t\tif (start && !shapes.find((s) => s.id === start.toId)) return false\n\t\t\tif (end && !shapes.find((s) => s.id === end.toId)) return false\n\t\t}\n\t\treturn true\n\t}\n\n\toverride getFontFaces(shape: TLArrowShape) {\n\t\tif (isEmptyRichText(shape.props.richText)) return EMPTY_ARRAY\n\n\t\treturn getFontsFromRichText(this.editor, shape.props.richText, {\n\t\t\tfamily: `tldraw_${shape.props.font}`,\n\t\t\tweight: 'normal',\n\t\t\tstyle: 'normal',\n\t\t})\n\t}\n\n\toverride getDefaultProps(): TLArrowShape['props'] {\n\t\treturn {\n\t\t\tkind: 'arc',\n\t\t\telbowMidPoint: 0.5,\n\t\t\tdash: 'draw',\n\t\t\tsize: 'm',\n\t\t\tfill: 'none',\n\t\t\tcolor: 'black',\n\t\t\tlabelColor: 'black',\n\t\t\tbend: 0,\n\t\t\tstart: { x: 0, y: 0 },\n\t\t\tend: { x: 2, y: 0 },\n\t\t\tarrowheadStart: 'none',\n\t\t\tarrowheadEnd: 'arrow',\n\t\t\trichText: toRichText(''),\n\t\t\tlabelPosition: 0.5,\n\t\t\tfont: 'draw',\n\t\t\tscale: 1,\n\t\t}\n\t}\n\n\tgetGeometry(shape: TLArrowShape) {\n\t\tconst isEditing = this.editor.getEditingShapeId() === shape.id\n\t\tconst info = getArrowInfo(this.editor, shape)!\n\n\t\tconst debugGeom: Geometry2d[] = []\n\n\t\tconst bodyGeom =\n\t\t\tinfo.type === 'straight'\n\t\t\t\t? new Edge2d({\n\t\t\t\t\t\tstart: Vec.From(info.start.point),\n\t\t\t\t\t\tend: Vec.From(info.end.point),\n\t\t\t\t\t})\n\t\t\t\t: info.type === 'arc'\n\t\t\t\t\t? new Arc2d({\n\t\t\t\t\t\t\tcenter: Vec.Cast(info.handleArc.center),\n\t\t\t\t\t\t\tstart: Vec.Cast(info.start.point),\n\t\t\t\t\t\t\tend: Vec.Cast(info.end.point),\n\t\t\t\t\t\t\tsweepFlag: info.bodyArc.sweepFlag,\n\t\t\t\t\t\t\tlargeArcFlag: info.bodyArc.largeArcFlag,\n\t\t\t\t\t\t})\n\t\t\t\t\t: new Polyline2d({ points: info.route.points })\n\n\t\tlet labelGeom\n\t\tif (isEditing || !isEmptyRichText(shape.props.richText)) {\n\t\t\tconst labelPosition = getArrowLabelPosition(this.editor, shape)\n\t\t\tif (debugFlags.debugGeometry.get()) {\n\t\t\t\tdebugGeom.push(...labelPosition.debugGeom)\n\t\t\t}\n\t\t\tlabelGeom = new Rectangle2d({\n\t\t\t\tx: labelPosition.box.x,\n\t\t\t\ty: labelPosition.box.y,\n\t\t\t\twidth: labelPosition.box.w,\n\t\t\t\theight: labelPosition.box.h,\n\t\t\t\tisFilled: true,\n\t\t\t\tisLabel: true,\n\t\t\t})\n\t\t}\n\n\t\treturn new Group2d({\n\t\t\tchildren: [...(labelGeom ? [bodyGeom, labelGeom] : [bodyGeom]), ...debugGeom],\n\t\t})\n\t}\n\n\toverride getHandles(shape: TLArrowShape): TLHandle[] {\n\t\tconst info = getArrowInfo(this.editor, shape)!\n\n\t\tconst handles: TLHandle[] = [\n\t\t\t{\n\t\t\t\tid: ArrowHandles.Start,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tindex: 'a1' as IndexKey,\n\t\t\t\tx: info.start.handle.x,\n\t\t\t\ty: info.start.handle.y,\n\t\t\t},\n\t\t\t{\n\t\t\t\tid: ArrowHandles.End,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tindex: 'a3' as IndexKey,\n\t\t\t\tx: info.end.handle.x,\n\t\t\t\ty: info.end.handle.y,\n\t\t\t},\n\t\t]\n\n\t\tif (shape.props.kind === 'arc' && (info.type === 'straight' || info.type === 'arc')) {\n\t\t\thandles.push({\n\t\t\t\tid: ArrowHandles.Middle,\n\t\t\t\ttype: 'virtual',\n\t\t\t\tindex: 'a2' as IndexKey,\n\t\t\t\tx: info.middle.x,\n\t\t\t\ty: info.middle.y,\n\t\t\t})\n\t\t}\n\n\t\tif (shape.props.kind === 'elbow' && info.type === 'elbow' && info.route.midpointHandle) {\n\t\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\n\t\t\tconst segmentStart = shapePageTransform.applyToPoint(info.route.midpointHandle.segmentStart)\n\t\t\tconst segmentEnd = shapePageTransform.applyToPoint(info.route.midpointHandle.segmentEnd)\n\t\t\tconst segmentLength = Vec.Dist(segmentStart, segmentEnd) * this.editor.getZoomLevel()\n\n\t\t\tif (segmentLength > this.options.elbowMinSegmentLengthToShowMidpointHandle) {\n\t\t\t\thandles.push({\n\t\t\t\t\tid: ArrowHandles.Middle,\n\t\t\t\t\ttype: 'vertex',\n\t\t\t\t\tindex: 'a2' as IndexKey,\n\t\t\t\t\tx: info.route.midpointHandle.point.x,\n\t\t\t\t\ty: info.route.midpointHandle.point.y,\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\n\t\treturn handles\n\t}\n\n\toverride getText(shape: TLArrowShape) {\n\t\treturn renderPlaintextFromRichText(this.editor, shape.props.richText)\n\t}\n\n\toverride onHandleDrag(shape: TLArrowShape, info: TLHandleDragInfo<TLArrowShape>) {\n\t\tconst handleId = info.handle.id as ArrowHandles\n\t\tswitch (handleId) {\n\t\t\tcase ArrowHandles.Middle:\n\t\t\t\tswitch (shape.props.kind) {\n\t\t\t\t\tcase 'arc':\n\t\t\t\t\t\treturn this.onArcMidpointHandleDrag(shape, info)\n\t\t\t\t\tcase 'elbow':\n\t\t\t\t\t\treturn this.onElbowMidpointHandleDrag(shape, info)\n\t\t\t\t\tdefault:\n\t\t\t\t\t\texhaustiveSwitchError(shape.props.kind)\n\t\t\t\t}\n\t\t\tcase ArrowHandles.Start:\n\t\t\tcase ArrowHandles.End:\n\t\t\t\treturn this.onTerminalHandleDrag(shape, info, handleId)\n\t\t\tdefault:\n\t\t\t\texhaustiveSwitchError(handleId)\n\t\t}\n\t}\n\n\tprivate onArcMidpointHandleDrag(shape: TLArrowShape, { handle }: TLHandleDragInfo<TLArrowShape>) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\t// Bending the arrow...\n\t\tconst { start, end } = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\n\t\tconst delta = Vec.Sub(end, start)\n\t\tconst v = Vec.Per(delta)\n\n\t\tconst med = Vec.Med(end, start)\n\t\tconst A = Vec.Sub(med, v)\n\t\tconst B = Vec.Add(med, v)\n\n\t\tconst point = Vec.NearestPointOnLineSegment(A, B, handle, false)\n\t\tlet bend = Vec.Dist(point, med)\n\t\tif (Vec.Clockwise(point, end, med)) bend *= -1\n\t\treturn { id: shape.id, type: shape.type, props: { bend } }\n\t}\n\n\tprivate onElbowMidpointHandleDrag(\n\t\tshape: TLArrowShape,\n\t\t{ handle }: TLHandleDragInfo<TLArrowShape>\n\t) {\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (info?.type !== 'elbow') return\n\n\t\tconst shapeToPageTransform = this.editor.getShapePageTransform(shape.id)!\n\t\tconst handlePagePoint = shapeToPageTransform.applyToPoint(handle)\n\t\tconst axisName = info.route.midpointHandle?.axis\n\t\tif (!axisName) return\n\t\tconst axis = ElbowArrowAxes[axisName]\n\n\t\tconst midRange = info.elbow[axis.midRange]\n\t\tif (!midRange) return\n\n\t\t// We're snapping against a list of parallel lines. The way we do this is to calculate the\n\t\t// angle of the line we're snapping to...\n\t\tlet angle = Vec.Angle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(0, 0)),\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(0, 1))\n\t\t)\n\t\tif (angle < 0) angle += Math.PI\n\n\t\t// ...then calculate the perpendicular distance from the origin to the (infinite) line in\n\t\t// question. This returns a signed distance - lines \"behind\" the origin are negative.\n\t\tconst handlePoint = perpDistanceToLineAngle(handlePagePoint, angle)\n\n\t\t// As we're only ever moving along one dimension, we can use this perpendicular distance for\n\t\t// all of our snapping calculations.\n\t\tconst loPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(midRange.lo, 0)),\n\t\t\tangle\n\t\t)\n\t\tconst hiPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(midRange.hi, 0)),\n\t\t\tangle\n\t\t)\n\n\t\t// we want to snap to certain points. the maximum distance at which a snap will occur is\n\t\t// relative to the zoom level:\n\t\tconst maxSnapDistance = this.options.elbowMidpointSnapDistance / this.editor.getZoomLevel()\n\n\t\t// we snap to the midpoint of the range by default\n\t\tconst midPoint = perpDistanceToLineAngle(\n\t\t\tshapeToPageTransform.applyToPoint(axis.v(lerp(midRange.lo, midRange.hi, 0.5), 0)),\n\t\t\tangle\n\t\t)\n\n\t\tlet snapPoint = midPoint\n\t\tlet snapDistance = Math.abs(midPoint - handlePoint)\n\n\t\t// then we check all the other arrows that are on-screen.\n\t\tfor (const [snapAngle, snapLines] of getElbowArrowSnapLines(this.editor)) {\n\t\t\tconst { isParallel, isFlippedParallel } = anglesAreApproximatelyParallel(angle, snapAngle)\n\t\t\tif (isParallel || isFlippedParallel) {\n\t\t\t\tfor (const snapLine of snapLines) {\n\t\t\t\t\tconst doesShareStartIntersection =\n\t\t\t\t\t\tsnapLine.startBoundShapeId &&\n\t\t\t\t\t\t(snapLine.startBoundShapeId === info.bindings.start?.toId ||\n\t\t\t\t\t\t\tsnapLine.startBoundShapeId === info.bindings.end?.toId)\n\n\t\t\t\t\tconst doesShareEndIntersection =\n\t\t\t\t\t\tsnapLine.endBoundShapeId &&\n\t\t\t\t\t\t(snapLine.endBoundShapeId === info.bindings.start?.toId ||\n\t\t\t\t\t\t\tsnapLine.endBoundShapeId === info.bindings.end?.toId)\n\n\t\t\t\t\tif (!doesShareStartIntersection && !doesShareEndIntersection) continue\n\n\t\t\t\t\tconst point = isFlippedParallel ? -snapLine.perpDistance : snapLine.perpDistance\n\t\t\t\t\tconst distance = Math.abs(point - handlePoint)\n\t\t\t\t\tif (distance < snapDistance) {\n\t\t\t\t\t\tsnapPoint = point\n\t\t\t\t\t\tsnapDistance = distance\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (snapDistance > maxSnapDistance) {\n\t\t\tsnapPoint = handlePoint\n\t\t}\n\n\t\tconst newMid = clamp(invLerp(loPoint, hiPoint, snapPoint), 0, 1)\n\n\t\treturn {\n\t\t\tid: shape.id,\n\t\t\ttype: shape.type,\n\t\t\tprops: {\n\t\t\t\telbowMidPoint: newMid,\n\t\t\t},\n\t\t}\n\t}\n\n\tprivate onTerminalHandleDrag(\n\t\tshape: TLArrowShape,\n\t\t{ handle, isPrecise }: TLHandleDragInfo<TLArrowShape>,\n\t\thandleId: ArrowHandles.Start | ArrowHandles.End\n\t) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\tconst update: TLShapePartial<TLArrowShape> = { id: shape.id, type: 'arrow', props: {} }\n\n\t\tconst currentBinding = bindings[handleId]\n\n\t\tconst oppositeHandleId = handleId === ArrowHandles.Start ? ArrowHandles.End : ArrowHandles.Start\n\t\tconst oppositeBinding = bindings[oppositeHandleId]\n\n\t\tconst targetInfo = updateArrowTargetState({\n\t\t\teditor: this.editor,\n\t\t\tpointInPageSpace: this.editor.getShapePageTransform(shape.id)!.applyToPoint(handle),\n\t\t\tarrow: shape,\n\t\t\tisPrecise: isPrecise,\n\t\t\tcurrentBinding,\n\t\t\toppositeBinding,\n\t\t})\n\n\t\tif (!targetInfo) {\n\t\t\t// todo: maybe double check that this isn't equal to the other handle too?\n\t\t\tremoveArrowBinding(this.editor, shape, handleId)\n\t\t\tconst newPoint = maybeSnapToGrid(new Vec(handle.x, handle.y), this.editor)\n\t\t\tupdate.props![handleId] = {\n\t\t\t\tx: newPoint.x,\n\t\t\t\ty: newPoint.y,\n\t\t\t}\n\t\t\treturn update\n\t\t}\n\n\t\t// we've got a target! the handle is being dragged over a shape, bind to it\n\t\tconst bindingProps: TLArrowBindingProps = {\n\t\t\tterminal: handleId,\n\t\t\tnormalizedAnchor: targetInfo.normalizedAnchor,\n\t\t\tisPrecise: targetInfo.isPrecise,\n\t\t\tisExact: targetInfo.isExact,\n\t\t\tsnap: targetInfo.snap,\n\t\t}\n\n\t\tcreateOrUpdateArrowBinding(this.editor, shape, targetInfo.target.id, bindingProps)\n\n\t\tconst newBindings = getArrowBindings(this.editor, shape)\n\t\tif (newBindings.start && newBindings.end && newBindings.start.toId === newBindings.end.toId) {\n\t\t\tif (\n\t\t\t\tVec.Equals(newBindings.start.props.normalizedAnchor, newBindings.end.props.normalizedAnchor)\n\t\t\t) {\n\t\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, newBindings.end.toId, {\n\t\t\t\t\t...newBindings.end.props,\n\t\t\t\t\tnormalizedAnchor: {\n\t\t\t\t\t\tx: newBindings.end.props.normalizedAnchor.x + 0.05,\n\t\t\t\t\t\ty: newBindings.end.props.normalizedAnchor.y,\n\t\t\t\t\t},\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\n\t\treturn update\n\t}\n\n\toverride onTranslateStart(shape: TLArrowShape) {\n\t\tconst bindings = getArrowBindings(this.editor, shape)\n\n\t\t// ...if the user is dragging ONLY this arrow, for elbow shapes, we can't maintain the bindings well just yet so we remove them entirely\n\t\tif (shape.props.kind === 'elbow' && this.editor.getOnlySelectedShapeId() === shape.id) {\n\t\t\tconst info = getArrowInfo(this.editor, shape)\n\t\t\tif (!info) return\n\t\t\tconst update: TLShapePartial<TLArrowShape> = { id: shape.id, type: 'arrow', props: {} }\n\t\t\tif (bindings.start) {\n\t\t\t\tupdate.props!.start = { x: info.start.point.x, y: info.start.point.y }\n\t\t\t\tremoveArrowBinding(this.editor, shape, 'start')\n\t\t\t}\n\t\t\tif (bindings.end) {\n\t\t\t\tupdate.props!.end = { x: info.end.point.x, y: info.end.point.y }\n\t\t\t\tremoveArrowBinding(this.editor, shape, 'end')\n\t\t\t}\n\t\t\treturn update\n\t\t}\n\n\t\tconst terminalsInArrowSpace = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\n\t\t// If at least one bound shape is in the selection, do nothing;\n\t\t// If no bound shapes are in the selection, unbind any bound shapes\n\n\t\tconst selectedShapeIds = this.editor.getSelectedShapeIds()\n\n\t\tif (\n\t\t\t(bindings.start &&\n\t\t\t\t(selectedShapeIds.includes(bindings.start.toId) ||\n\t\t\t\t\tthis.editor.isAncestorSelected(bindings.start.toId))) ||\n\t\t\t(bindings.end &&\n\t\t\t\t(selectedShapeIds.includes(bindings.end.toId) ||\n\t\t\t\t\tthis.editor.isAncestorSelected(bindings.end.toId)))\n\t\t) {\n\t\t\treturn\n\t\t}\n\n\t\t// When we start translating shapes, record where their bindings were in page space so we\n\t\t// can maintain them as we translate the arrow\n\t\tshapeAtTranslationStart.set(shape, {\n\t\t\tpagePosition: shapePageTransform.applyToPoint(shape),\n\t\t\tterminalBindings: mapObjectMapValues(terminalsInArrowSpace, (terminalName, point) => {\n\t\t\t\tconst binding = bindings[terminalName]\n\t\t\t\tif (!binding) return null\n\t\t\t\treturn {\n\t\t\t\t\tbinding,\n\t\t\t\t\tshapePosition: point,\n\t\t\t\t\tpagePosition: shapePageTransform.applyToPoint(point),\n\t\t\t\t}\n\t\t\t}),\n\t\t})\n\n\t\t// update arrow terminal bindings eagerly to make sure the arrows unbind nicely when translating\n\t\tif (bindings.start) {\n\t\t\tupdateArrowTerminal({\n\t\t\t\teditor: this.editor,\n\t\t\t\tarrow: shape,\n\t\t\t\tterminal: 'start',\n\t\t\t\tuseHandle: true,\n\t\t\t})\n\t\t\tshape = this.editor.getShape(shape.id) as TLArrowShape\n\t\t}\n\t\tif (bindings.end) {\n\t\t\tupdateArrowTerminal({\n\t\t\t\teditor: this.editor,\n\t\t\t\tarrow: shape,\n\t\t\t\tterminal: 'end',\n\t\t\t\tuseHandle: true,\n\t\t\t})\n\t\t}\n\n\t\tfor (const handleName of [ArrowHandles.Start, ArrowHandles.End] as const) {\n\t\t\tconst binding = bindings[handleName]\n\t\t\tif (!binding) continue\n\n\t\t\tthis.editor.updateBinding({\n\t\t\t\t...binding,\n\t\t\t\tprops: { ...binding.props, isPrecise: true },\n\t\t\t})\n\t\t}\n\n\t\treturn\n\t}\n\n\toverride onTranslate(initialShape: TLArrowShape, shape: TLArrowShape) {\n\t\tconst atTranslationStart = shapeAtTranslationStart.get(initialShape)\n\t\tif (!atTranslationStart) return\n\n\t\tconst shapePageTransform = this.editor.getShapePageTransform(shape.id)!\n\t\tconst pageDelta = Vec.Sub(\n\t\t\tshapePageTransform.applyToPoint(shape),\n\t\t\tatTranslationStart.pagePosition\n\t\t)\n\n\t\tfor (const terminalBinding of Object.values(atTranslationStart.terminalBindings)) {\n\t\t\tif (!terminalBinding) continue\n\n\t\t\tconst newPagePoint = Vec.Add(terminalBinding.pagePosition, Vec.Mul(pageDelta, 0.5))\n\t\t\tconst newTarget = this.editor.getShapeAtPoint(newPagePoint, {\n\t\t\t\thitInside: true,\n\t\t\t\thitFrameInside: true,\n\t\t\t\tmargin: 0,\n\t\t\t\tfilter: (targetShape) => {\n\t\t\t\t\treturn (\n\t\t\t\t\t\t!targetShape.isLocked &&\n\t\t\t\t\t\tthis.editor.canBindShapes({ fromShape: shape, toShape: targetShape, binding: 'arrow' })\n\t\t\t\t\t)\n\t\t\t\t},\n\t\t\t})\n\n\t\t\tif (newTarget?.id === terminalBinding.binding.toId) {\n\t\t\t\tconst targetBounds = Box.ZeroFix(this.editor.getShapeGeometry(newTarget).bounds)\n\t\t\t\tconst pointInTargetSpace = this.editor.getPointInShapeSpace(newTarget, newPagePoint)\n\t\t\t\tconst normalizedAnchor = {\n\t\t\t\t\tx: (pointInTargetSpace.x - targetBounds.minX) / targetBounds.width,\n\t\t\t\t\ty: (pointInTargetSpace.y - targetBounds.minY) / targetBounds.height,\n\t\t\t\t}\n\t\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, newTarget.id, {\n\t\t\t\t\t...terminalBinding.binding.props,\n\t\t\t\t\tnormalizedAnchor,\n\t\t\t\t\tisPrecise: true,\n\t\t\t\t})\n\t\t\t} else {\n\t\t\t\tremoveArrowBinding(this.editor, shape, terminalBinding.binding.props.terminal)\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate readonly _resizeInitialBindings = new WeakCache<TLArrowShape, TLArrowBindings>()\n\n\toverride onResize(shape: TLArrowShape, info: TLResizeInfo<TLArrowShape>) {\n\t\tconst { scaleX, scaleY } = info\n\n\t\tconst bindings = this._resizeInitialBindings.get(shape, () =>\n\t\t\tgetArrowBindings(this.editor, shape)\n\t\t)\n\t\tconst terminals = getArrowTerminalsInArrowSpace(this.editor, shape, bindings)\n\n\t\tconst { start, end } = structuredClone<TLArrowShape['props']>(shape.props)\n\t\tlet { bend } = shape.props\n\n\t\t// Rescale start handle if it's not bound to a shape\n\t\tif (!bindings.start) {\n\t\t\tstart.x = terminals.start.x * scaleX\n\t\t\tstart.y = terminals.start.y * scaleY\n\t\t}\n\n\t\t// Rescale end handle if it's not bound to a shape\n\t\tif (!bindings.end) {\n\t\t\tend.x = terminals.end.x * scaleX\n\t\t\tend.y = terminals.end.y * scaleY\n\t\t}\n\n\t\t// todo: we should only change the normalized anchor positions\n\t\t// of the shape's handles if the bound shape is also being resized\n\n\t\tconst mx = Math.abs(scaleX)\n\t\tconst my = Math.abs(scaleY)\n\n\t\tconst startNormalizedAnchor = bindings?.start\n\t\t\t? Vec.From(bindings.start.props.normalizedAnchor)\n\t\t\t: null\n\t\tconst endNormalizedAnchor = bindings?.end ? Vec.From(bindings.end.props.normalizedAnchor) : null\n\n\t\tif (scaleX < 0 && scaleY >= 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= -1\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.x = 1 - startNormalizedAnchor.x\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.x = 1 - endNormalizedAnchor.x\n\t\t\t}\n\t\t} else if (scaleX >= 0 && scaleY < 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= -1\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.y = 1 - startNormalizedAnchor.y\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.y = 1 - endNormalizedAnchor.y\n\t\t\t}\n\t\t} else if (scaleX >= 0 && scaleY >= 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\t\t} else if (scaleX < 0 && scaleY < 0) {\n\t\t\tif (bend !== 0) {\n\t\t\t\tbend *= Math.max(mx, my)\n\t\t\t}\n\n\t\t\tif (startNormalizedAnchor) {\n\t\t\t\tstartNormalizedAnchor.x = 1 - startNormalizedAnchor.x\n\t\t\t\tstartNormalizedAnchor.y = 1 - startNormalizedAnchor.y\n\t\t\t}\n\n\t\t\tif (endNormalizedAnchor) {\n\t\t\t\tendNormalizedAnchor.x = 1 - endNormalizedAnchor.x\n\t\t\t\tendNormalizedAnchor.y = 1 - endNormalizedAnchor.y\n\t\t\t}\n\t\t}\n\n\t\tif (bindings.start && startNormalizedAnchor) {\n\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, bindings.start.toId, {\n\t\t\t\t...bindings.start.props,\n\t\t\t\tnormalizedAnchor: startNormalizedAnchor.toJson(),\n\t\t\t})\n\t\t}\n\t\tif (bindings.end && endNormalizedAnchor) {\n\t\t\tcreateOrUpdateArrowBinding(this.editor, shape, bindings.end.toId, {\n\t\t\t\t...bindings.end.props,\n\t\t\t\tnormalizedAnchor: endNormalizedAnchor.toJson(),\n\t\t\t})\n\t\t}\n\n\t\tconst next = {\n\t\t\tprops: {\n\t\t\t\tstart,\n\t\t\t\tend,\n\t\t\t\tbend,\n\t\t\t},\n\t\t}\n\n\t\treturn next\n\t}\n\n\toverride onDoubleClickHandle(\n\t\tshape: TLArrowShape,\n\t\thandle: TLHandle\n\t): TLShapePartial<TLArrowShape> | void {\n\t\tswitch (handle.id) {\n\t\t\tcase ArrowHandles.Start: {\n\t\t\t\treturn {\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: {\n\t\t\t\t\t\t...shape.props,\n\t\t\t\t\t\tarrowheadStart: shape.props.arrowheadStart === 'none' ? 'arrow' : 'none',\n\t\t\t\t\t},\n\t\t\t\t}\n\t\t\t}\n\t\t\tcase ArrowHandles.End: {\n\t\t\t\treturn {\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: {\n\t\t\t\t\t\t...shape.props,\n\t\t\t\t\t\tarrowheadEnd: shape.props.arrowheadEnd === 'none' ? 'arrow' : 'none',\n\t\t\t\t\t},\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tcomponent(shape: TLArrowShape) {\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst theme = useDefaultColorTheme()\n\t\tconst onlySelectedShape = this.editor.getOnlySelectedShape()\n\t\tconst shouldDisplayHandles =\n\t\t\tthis.editor.isInAny(\n\t\t\t\t'select.idle',\n\t\t\t\t'select.pointing_handle',\n\t\t\t\t'select.dragging_handle',\n\t\t\t\t'select.translating',\n\t\t\t\t'arrow.dragging'\n\t\t\t) && !this.editor.getIsReadonly()\n\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (!info?.isValid) return null\n\n\t\tconst labelPosition = getArrowLabelPosition(this.editor, shape)\n\t\tconst isSelected = shape.id === this.editor.getOnlySelectedShapeId()\n\t\tconst isEditing = this.editor.getEditingShapeId() === shape.id\n\t\tconst showArrowLabel = isEditing || !isEmptyRichText(shape.props.richText)\n\n\t\treturn (\n\t\t\t<>\n\t\t\t\t<SVGContainer style={{ minWidth: 50, minHeight: 50 }}>\n\t\t\t\t\t<ArrowSvg\n\t\t\t\t\t\tshape={shape}\n\t\t\t\t\t\tshouldDisplayHandles={shouldDisplayHandles && onlySelectedShape?.id === shape.id}\n\t\t\t\t\t/>\n\t\t\t\t\t{shape.props.kind === 'elbow' && debugFlags.debugElbowArrows.get() && (\n\t\t\t\t\t\t<ElbowArrowDebug arrow={shape} />\n\t\t\t\t\t)}\n\t\t\t\t</SVGContainer>\n\t\t\t\t{showArrowLabel && (\n\t\t\t\t\t<RichTextLabel\n\t\t\t\t\t\tshapeId={shape.id}\n\t\t\t\t\t\ttype=\"arrow\"\n\t\t\t\t\t\tfont={shape.props.font}\n\t\t\t\t\t\tfontSize={getArrowLabelFontSize(shape)}\n\t\t\t\t\t\tlineHeight={TEXT_PROPS.lineHeight}\n\t\t\t\t\t\talign=\"middle\"\n\t\t\t\t\t\tverticalAlign=\"middle\"\n\t\t\t\t\t\tlabelColor={getColorValue(theme, shape.props.labelColor, 'solid')}\n\t\t\t\t\t\trichText={shape.props.richText}\n\t\t\t\t\t\ttextWidth={labelPosition.box.w - ARROW_LABEL_PADDING * 2 * shape.props.scale}\n\t\t\t\t\t\tisSelected={isSelected}\n\t\t\t\t\t\tpadding={0}\n\t\t\t\t\t\tstyle={{\n\t\t\t\t\t\t\ttransform: `translate(${labelPosition.box.center.x}px, ${labelPosition.box.center.y}px)`,\n\t\t\t\t\t\t}}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t</>\n\t\t)\n\t}\n\n\tindicator(shape: TLArrowShape) {\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst isEditing = useIsEditing(shape.id)\n\t\t// eslint-disable-next-line react-hooks/rules-of-hooks\n\t\tconst clipPathId = useSharedSafeId(shape.id + '_clip')\n\n\t\tconst info = getArrowInfo(this.editor, shape)\n\t\tif (!info) return null\n\n\t\tconst { start, end } = getArrowTerminalsInArrowSpace(this.editor, shape, info?.bindings)\n\t\tconst geometry = this.editor.getShapeGeometry<Group2d>(shape)\n\t\tconst bounds = geometry.bounds\n\t\tconst isEmpty = isEmptyRichText(shape.props.richText)\n\n\t\tconst labelGeometry = isEditing || !isEmpty ? (geometry.children[1] as Rectangle2d) : null\n\n\t\tif (Vec.Equals(start, end)) return null\n\n\t\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\n\t\tconst as = info.start.arrowhead && getArrowheadPathForType(info, 'start', strokeWidth)\n\t\tconst ae = info.end.arrowhead && getArrowheadPathForType(info, 'end', strokeWidth)\n\n\t\tconst includeClipPath =\n\t\t\t(as && info.start.arrowhead !== 'arrow') ||\n\t\t\t(ae && info.end.arrowhead !== 'arrow') ||\n\t\t\t!!labelGeometry\n\n\t\tconst labelBounds = labelGeometry ? labelGeometry.getBounds() : new Box(0, 0, 0, 0)\n\n\t\tif (isEditing && labelGeometry) {\n\t\t\treturn (\n\t\t\t\t<rect\n\t\t\t\t\tx={toDomPrecision(labelBounds.x)}\n\t\t\t\t\ty={toDomPrecision(labelBounds.y)}\n\t\t\t\t\twidth={labelBounds.w}\n\t\t\t\t\theight={labelBounds.h}\n\t\t\t\t\trx={3.5 * shape.props.scale}\n\t\t\t\t\try={3.5 * shape.props.scale}\n\t\t\t\t/>\n\t\t\t)\n\t\t}\n\t\tconst clipStartArrowhead = !(\n\t\t\tinfo.start.arrowhead === 'none' || info.start.arrowhead === 'arrow'\n\t\t)\n\t\tconst clipEndArrowhead = !(info.end.arrowhead === 'none' || info.end.arrowhead === 'arrow')\n\n\t\treturn (\n\t\t\t<g>\n\t\t\t\t{includeClipPath && (\n\t\t\t\t\t<defs>\n\t\t\t\t\t\t<ArrowClipPath\n\t\t\t\t\t\t\tradius={3.5 * shape.props.scale}\n\t\t\t\t\t\t\thasText={!isEmpty}\n\t\t\t\t\t\t\tbounds={bounds}\n\t\t\t\t\t\t\tlabelBounds={labelBounds}\n\t\t\t\t\t\t\tas={clipStartArrowhead && as ? as : ''}\n\t\t\t\t\t\t\tae={clipEndArrowhead && ae ? ae : ''}\n\t\t\t\t\t\t/>\n\t\t\t\t\t</defs>\n\t\t\t\t)}\n\t\t\t\t<g\n\t\t\t\t\tstyle={{\n\t\t\t\t\t\tclipPath: includeClipPath ? `url(#${clipPathId})` : undefined,\n\t\t\t\t\t\tWebkitClipPath: includeClipPath ? `url(#${clipPathId})` : undefined,\n\t\t\t\t\t}}\n\t\t\t\t>\n\t\t\t\t\t{/* This rect needs to be here if we're creating a mask due to an svg quirk on Chrome */}\n\t\t\t\t\t{includeClipPath && (\n\t\t\t\t\t\t<rect\n\t\t\t\t\t\t\tx={bounds.minX - 100}\n\t\t\t\t\t\t\ty={bounds.minY - 100}\n\t\t\t\t\t\t\twidth={bounds.width + 200}\n\t\t\t\t\t\t\theight={bounds.height + 200}\n\t\t\t\t\t\t\topacity={0}\n\t\t\t\t\t\t/>\n\t\t\t\t\t)}\n\n\t\t\t\t\t{getArrowBodyPath(\n\t\t\t\t\t\tshape,\n\t\t\t\t\t\tinfo,\n\t\t\t\t\t\tshape.props.dash === 'draw'\n\t\t\t\t\t\t\t? {\n\t\t\t\t\t\t\t\t\tstyle: 'draw',\n\t\t\t\t\t\t\t\t\trandomSeed: shape.id,\n\t\t\t\t\t\t\t\t\tstrokeWidth: 1,\n\t\t\t\t\t\t\t\t\tpasses: 1,\n\t\t\t\t\t\t\t\t\toffset: 0,\n\t\t\t\t\t\t\t\t\troundness: strokeWidth * 2,\n\t\t\t\t\t\t\t\t\tprops: { strokeWidth: undefined },\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t: { style: 'solid', strokeWidth: 1, props: { strokeWidth: undefined } }\n\t\t\t\t\t)}\n\t\t\t\t</g>\n\t\t\t\t{as && <path d={as} />}\n\t\t\t\t{ae && <path d={ae} />}\n\t\t\t\t{labelGeometry && (\n\t\t\t\t\t<rect\n\t\t\t\t\t\tx={toDomPrecision(labelBounds.x)}\n\t\t\t\t\t\ty={toDomPrecision(labelBounds.y)}\n\t\t\t\t\t\twidth={labelBounds.w}\n\t\t\t\t\t\theight={labelBounds.h}\n\t\t\t\t\t\trx={3.5}\n\t\t\t\t\t\try={3.5}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t</g>\n\t\t)\n\t}\n\n\toverride onEditStart(shape: TLArrowShape) {\n\t\tif (isEmptyRichText(shape.props.richText)) {\n\t\t\t// editing text for the first time, so set the position to the default:\n\t\t\tconst labelPosition = getArrowLabelDefaultPosition(this.editor, shape)\n\t\t\tthis.editor.updateShape<TLArrowShape>({\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { labelPosition },\n\t\t\t})\n\t\t}\n\t}\n\n\toverride toSvg(shape: TLArrowShape, ctx: SvgExportContext) {\n\t\tctx.addExportDef(getFillDefForExport(shape.props.fill))\n\t\tconst theme = getDefaultColorTheme(ctx)\n\t\tconst scaleFactor = 1 / shape.props.scale\n\n\t\treturn (\n\t\t\t<g transform={`scale(${scaleFactor})`}>\n\t\t\t\t<ArrowSvg shape={shape} shouldDisplayHandles={false} />\n\t\t\t\t<RichTextSVG\n\t\t\t\t\tfontSize={getArrowLabelFontSize(shape)}\n\t\t\t\t\tfont={shape.props.font}\n\t\t\t\t\talign=\"middle\"\n\t\t\t\t\tverticalAlign=\"middle\"\n\t\t\t\t\tlabelColor={getColorValue(theme, shape.props.labelColor, 'solid')}\n\t\t\t\t\trichText={shape.props.richText}\n\t\t\t\t\tbounds={getArrowLabelPosition(this.editor, shape)\n\t\t\t\t\t\t.box.clone()\n\t\t\t\t\t\t.expandBy(-ARROW_LABEL_PADDING * shape.props.scale)}\n\t\t\t\t\tpadding={0}\n\t\t\t\t\tshowTextOutline={true}\n\t\t\t\t/>\n\t\t\t</g>\n\t\t)\n\t}\n\n\toverride getCanvasSvgDefs(): TLShapeUtilCanvasSvgDef[] {\n\t\treturn [\n\t\t\tgetFillDefForCanvas(),\n\t\t\t{\n\t\t\t\tkey: `arrow:dot`,\n\t\t\t\tcomponent: ArrowheadDotDef,\n\t\t\t},\n\t\t\t{\n\t\t\t\tkey: `arrow:cross`,\n\t\t\t\tcomponent: ArrowheadCrossDef,\n\t\t\t},\n\t\t]\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLArrowShape,\n\t\tendShape: TLArrowShape,\n\t\tprogress: number\n\t): TLArrowShapeProps {\n\t\treturn {\n\t\t\t...(progress > 0.5 ? endShape.props : startShape.props),\n\t\t\tscale: lerp(startShape.props.scale, endShape.props.scale, progress),\n\t\t\tstart: {\n\t\t\t\tx: lerp(startShape.props.start.x, endShape.props.start.x, progress),\n\t\t\t\ty: lerp(startShape.props.start.y, endShape.props.start.y, progress),\n\t\t\t},\n\t\t\tend: {\n\t\t\t\tx: lerp(startShape.props.end.x, endShape.props.end.x, progress),\n\t\t\t\ty: lerp(startShape.props.end.y, endShape.props.end.y, progress),\n\t\t\t},\n\t\t\tbend: lerp(startShape.props.bend, endShape.props.bend, progress),\n\t\t\tlabelPosition: lerp(startShape.props.labelPosition, endShape.props.labelPosition, progress),\n\t\t}\n\t}\n}\n\nexport function getArrowLength(editor: Editor, shape: TLArrowShape): number {\n\tconst info = getArrowInfo(editor, shape)!\n\n\treturn info.type === 'straight'\n\t\t? Vec.Dist(info.start.handle, info.end.handle)\n\t\t: info.type === 'arc'\n\t\t\t? Math.abs(info.handleArc.length)\n\t\t\t: info.route.distance\n}\n\nconst ArrowSvg = track(function ArrowSvg({\n\tshape,\n\tshouldDisplayHandles,\n}: {\n\tshape: TLArrowShape\n\tshouldDisplayHandles: boolean\n}) {\n\tconst editor = useEditor()\n\tconst theme = useDefaultColorTheme()\n\tconst info = getArrowInfo(editor, shape)\n\tconst isForceSolid = useValue(\n\t\t'force solid',\n\t\t() => {\n\t\t\treturn editor.getZoomLevel() < 0.2\n\t\t},\n\t\t[editor]\n\t)\n\tconst clipPathId = useSharedSafeId(shape.id + '_clip')\n\tconst arrowheadDotId = useSharedSafeId('arrowhead-dot')\n\tconst arrowheadCrossId = useSharedSafeId('arrowhead-cross')\n\tconst isEditing = useIsEditing(shape.id)\n\tconst geometry = editor.getShapeGeometry(shape)\n\tif (!geometry) return null\n\tconst bounds = Box.ZeroFix(geometry.bounds)\n\tconst bindings = getArrowBindings(editor, shape)\n\tconst isEmpty = isEmptyRichText(shape.props.richText)\n\n\tif (!info?.isValid) return null\n\n\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\n\tconst as = info.start.arrowhead && getArrowheadPathForType(info, 'start', strokeWidth)\n\tconst ae = info.end.arrowhead && getArrowheadPathForType(info, 'end', strokeWidth)\n\n\tlet handlePath: null | React.JSX.Element = null\n\n\tif (shouldDisplayHandles && (bindings.start || bindings.end)) {\n\t\thandlePath = getArrowHandlePath(info, {\n\t\t\tstyle: 'dashed',\n\t\t\tstart: 'skip',\n\t\t\tend: 'skip',\n\t\t\tlengthRatio: 2.5,\n\t\t\tstrokeWidth: 2 / editor.getZoomLevel(),\n\t\t\tprops: {\n\t\t\t\tclassName: 'tl-arrow-hint',\n\t\t\t\tmarkerStart: bindings.start\n\t\t\t\t\t? bindings.start.props.isExact\n\t\t\t\t\t\t? ''\n\t\t\t\t\t\t: bindings.start.props.isPrecise\n\t\t\t\t\t\t\t? `url(#${arrowheadCrossId})`\n\t\t\t\t\t\t\t: `url(#${arrowheadDotId})`\n\t\t\t\t\t: '',\n\t\t\t\tmarkerEnd: bindings.end\n\t\t\t\t\t? bindings.end.props.isExact\n\t\t\t\t\t\t? ''\n\t\t\t\t\t\t: bindings.end.props.isPrecise\n\t\t\t\t\t\t\t? `url(#${arrowheadCrossId})`\n\t\t\t\t\t\t\t: `url(#${arrowheadDotId})`\n\t\t\t\t\t: '',\n\t\t\t\topacity: 0.16,\n\t\t\t},\n\t\t})\n\t}\n\n\tconst labelPosition = getArrowLabelPosition(editor, shape)\n\n\tconst clipStartArrowhead = !(info.start.arrowhead === 'none' || info.start.arrowhead === 'arrow')\n\tconst clipEndArrowhead = !(info.end.arrowhead === 'none' || info.end.arrowhead === 'arrow')\n\n\treturn (\n\t\t<>\n\t\t\t{/* Yep */}\n\t\t\t<defs>\n\t\t\t\t<clipPath id={clipPathId}>\n\t\t\t\t\t<ArrowClipPath\n\t\t\t\t\t\tradius={3.5 * shape.props.scale}\n\t\t\t\t\t\thasText={isEditing || !isEmpty}\n\t\t\t\t\t\tbounds={bounds}\n\t\t\t\t\t\tlabelBounds={labelPosition.box}\n\t\t\t\t\t\tas={clipStartArrowhead && as ? as : ''}\n\t\t\t\t\t\tae={clipEndArrowhead && ae ? ae : ''}\n\t\t\t\t\t/>\n\t\t\t\t</clipPath>\n\t\t\t</defs>\n\t\t\t<g\n\t\t\t\tfill=\"none\"\n\t\t\t\tstroke={getColorValue(theme, shape.props.color, 'solid')}\n\t\t\t\tstrokeWidth={strokeWidth}\n\t\t\t\tstrokeLinejoin=\"round\"\n\t\t\t\tstrokeLinecap=\"round\"\n\t\t\t\tpointerEvents=\"none\"\n\t\t\t>\n\t\t\t\t{handlePath}\n\t\t\t\t<g\n\t\t\t\t\tstyle={{\n\t\t\t\t\t\tclipPath: `url(#${clipPathId})`,\n\t\t\t\t\t\tWebkitClipPath: `url(#${clipPathId})`,\n\t\t\t\t\t}}\n\t\t\t\t>\n\t\t\t\t\t<rect\n\t\t\t\t\t\tx={toDomPrecision(bounds.minX - 100)}\n\t\t\t\t\t\ty={toDomPrecision(bounds.minY - 100)}\n\t\t\t\t\t\twidth={toDomPrecision(bounds.width + 200)}\n\t\t\t\t\t\theight={toDomPrecision(bounds.height + 200)}\n\t\t\t\t\t\topacity={0}\n\t\t\t\t\t/>\n\t\t\t\t\t{getArrowBodyPath(shape, info, {\n\t\t\t\t\t\tstyle: shape.props.dash,\n\t\t\t\t\t\tstrokeWidth,\n\t\t\t\t\t\tforceSolid: isForceSolid,\n\t\t\t\t\t\trandomSeed: shape.id,\n\t\t\t\t\t})}\n\t\t\t\t</g>\n\t\t\t\t{as && clipStartArrowhead && shape.props.fill !== 'none' && (\n\t\t\t\t\t<ShapeFill\n\t\t\t\t\t\ttheme={theme}\n\t\t\t\t\t\td={as}\n\t\t\t\t\t\tcolor={shape.props.color}\n\t\t\t\t\t\tfill={shape.props.fill}\n\t\t\t\t\t\tscale={shape.props.scale}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t\t{ae && clipEndArrowhead && shape.props.fill !== 'none' && (\n\t\t\t\t\t<ShapeFill\n\t\t\t\t\t\ttheme={theme}\n\t\t\t\t\t\td={ae}\n\t\t\t\t\t\tcolor={shape.props.color}\n\t\t\t\t\t\tfill={shape.props.fill}\n\t\t\t\t\t\tscale={shape.props.scale}\n\t\t\t\t\t/>\n\t\t\t\t)}\n\t\t\t\t{as && <path d={as} />}\n\t\t\t\t{ae && <path d={ae} />}\n\t\t\t</g>\n\t\t</>\n\t)\n})\n\nfunction ArrowClipPath({\n\tradius,\n\thasText,\n\tbounds,\n\tlabelBounds,\n\tas,\n\tae,\n}: {\n\tradius: number\n\thasText: boolean\n\tbounds: Box\n\tlabelBounds: Box\n\tas: string\n\tae: string\n}) {\n\tconst path = useMemo(() => {\n\t\t// The direction in which we create the different path parts is important, as it determines what gets clipped.\n\t\t// See the description on the directions in the non-zero fill rule example:\n\t\t// https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute/fill-rule#nonzero\n\t\tconst path = new PathBuilder()\n\n\t\t// We create this one in the clockwise direction\n\t\tpath\n\t\t\t.moveTo(bounds.left - 100, bounds.top - 100)\n\t\t\t.lineTo(bounds.right + 100, bounds.top - 100)\n\t\t\t.lineTo(bounds.right + 100, bounds.bottom + 100)\n\t\t\t.lineTo(bounds.left - 100, bounds.bottom + 100)\n\t\t\t.close()\n\n\t\tif (hasText) {\n\t\t\t// We create this one in the counter-clockwise direction, which cuts out the label box\n\t\t\tpath\n\t\t\t\t.moveTo(labelBounds.left, labelBounds.top + radius)\n\t\t\t\t.lineTo(labelBounds.left, labelBounds.bottom - radius)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.left + radius, labelBounds.bottom)\n\t\t\t\t.lineTo(labelBounds.right - radius, labelBounds.bottom)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.right, labelBounds.bottom - radius)\n\t\t\t\t.lineTo(labelBounds.right, labelBounds.top + radius)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.right - radius, labelBounds.top)\n\t\t\t\t.lineTo(labelBounds.left + radius, labelBounds.top)\n\t\t\t\t.circularArcTo(radius, false, false, labelBounds.left, labelBounds.top + radius)\n\t\t\t\t.close()\n\t\t}\n\n\t\treturn path.toD()\n\t}, [\n\t\tradius,\n\t\thasText,\n\t\tbounds.bottom,\n\t\tbounds.left,\n\t\tbounds.right,\n\t\tbounds.top,\n\t\tlabelBounds.bottom,\n\t\tlabelBounds.left,\n\t\tlabelBounds.right,\n\t\tlabelBounds.top,\n\t])\n\n\t// We also append the arrowhead paths to the clip path, so that we also clip the arrowheads\n\treturn <path d={`${path}${as}${ae}`} />\n}\n\nconst shapeAtTranslationStart = new WeakMap<\n\tTLArrowShape,\n\t{\n\t\tpagePosition: Vec\n\t\tterminalBindings: Record<\n\t\t\t'start' | 'end',\n\t\t\t{\n\t\t\t\tpagePosition: Vec\n\t\t\t\tshapePosition: Vec\n\t\t\t\tbinding: TLArrowBinding\n\t\t\t} | null\n\t\t>\n\t}\n>()\n\nfunction ArrowheadDotDef() {\n\tconst id = useSharedSafeId('arrowhead-dot')\n\treturn (\n\t\t<marker id={id} className=\"tl-arrow-hint\" refX=\"3.0\" refY=\"3.0\" orient=\"0\">\n\t\t\t<circle cx=\"3\" cy=\"3\" r=\"2\" strokeDasharray=\"100%\" />\n\t\t</marker>\n\t)\n}\n\nfunction ArrowheadCrossDef() {\n\tconst id = useSharedSafeId('arrowhead-cross')\n\treturn (\n\t\t<marker id={id} className=\"tl-arrow-hint\" refX=\"3.0\" refY=\"3.0\" orient=\"auto\">\n\t\t\t<line x1=\"1.5\" y1=\"1.5\" x2=\"4.5\" y2=\"4.5\" strokeDasharray=\"100%\" />\n\t\t\t<line x1=\"1.5\" y1=\"4.5\" x2=\"4.5\" y2=\"1.5\" strokeDasharray=\"100%\" />\n\t\t</marker>\n\t)\n}\n\n/**\n * Take 2 angles and return true if they are approximately parallel. Angle that point in the same\n * (or opposite) directions are considered parallel. This also handles wrap around - e.g. 0, \u03C0, and\n * 2\u03C0 are all considered parallel.\n */\nfunction anglesAreApproximatelyParallel(a: number, b: number, tolerance = 0.0001) {\n\tconst diff = Math.abs(a - b)\n\n\tconst isParallel = diff < tolerance\n\tconst isFlippedParallel = Math.abs(diff - Math.PI) < tolerance\n\tconst is360Parallel = Math.abs(diff - PI2) < tolerance\n\n\treturn { isParallel: isParallel || is360Parallel, isFlippedParallel }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": ["ArrowHandles", "ArrowSvg", "path"]
|
|
7
7
|
}
|
|
@@ -147,7 +147,19 @@ function BookmarkShapeComponent({ shape }) {
|
|
|
147
147
|
asset?.props.image && /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_HyperlinkButton.HyperlinkButton, { url: shape.props.url })
|
|
148
148
|
] }),
|
|
149
149
|
/* @__PURE__ */ (0, import_jsx_runtime.jsxs)("div", { className: "tl-bookmark__copy_container", children: [
|
|
150
|
-
asset?.props.title ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
150
|
+
asset?.props.title ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
151
|
+
"a",
|
|
152
|
+
{
|
|
153
|
+
className: "tl-bookmark__link",
|
|
154
|
+
href: shape.props.url || "",
|
|
155
|
+
target: "_blank",
|
|
156
|
+
rel: "noopener noreferrer",
|
|
157
|
+
draggable: false,
|
|
158
|
+
onPointerDown: markAsHandledOnShiftKey,
|
|
159
|
+
onPointerUp: markAsHandledOnShiftKey,
|
|
160
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)("h2", { className: "tl-bookmark__heading", children: (0, import_text.convertCommonTitleHTMLEntities)(asset.props.title) })
|
|
161
|
+
}
|
|
162
|
+
) : null,
|
|
151
163
|
asset?.props.description && asset?.props.image ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)("p", { className: "tl-bookmark__description", children: asset.props.description }) : null,
|
|
152
164
|
/* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
|
|
153
165
|
"a",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../src/lib/shapes/bookmark/BookmarkShapeUtil.tsx"],
|
|
4
|
-
"sourcesContent": ["import {\n\tAssetRecordType,\n\tBaseBoxShapeUtil,\n\tEditor,\n\tHTMLContainer,\n\tT,\n\tTLAssetId,\n\tTLBookmarkAsset,\n\tTLBookmarkShape,\n\tTLBookmarkShapeProps,\n\tbookmarkShapeMigrations,\n\tbookmarkShapeProps,\n\tdebounce,\n\tgetHashForString,\n\tlerp,\n\ttlenv,\n\ttoDomPrecision,\n\tuseEditor,\n\tuseSvgExportContext,\n} from '@tldraw/editor'\nimport classNames from 'classnames'\nimport { PointerEventHandler, useCallback, useState } from 'react'\nimport { convertCommonTitleHTMLEntities } from '../../utils/text/text'\nimport { HyperlinkButton } from '../shared/HyperlinkButton'\nimport { LINK_ICON } from '../shared/icons-editor'\nimport { getRotatedBoxShadow } from '../shared/rotated-box-shadow'\n\nconst BOOKMARK_WIDTH = 300\nconst BOOKMARK_HEIGHT = 320\nconst BOOKMARK_JUST_URL_HEIGHT = 46\nconst SHORT_BOOKMARK_HEIGHT = 101\n\n/** @public */\nexport class BookmarkShapeUtil extends BaseBoxShapeUtil<TLBookmarkShape> {\n\tstatic override type = 'bookmark' as const\n\tstatic override props = bookmarkShapeProps\n\tstatic override migrations = bookmarkShapeMigrations\n\n\toverride canResize() {\n\t\treturn false\n\t}\n\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\n\toverride getText(shape: TLBookmarkShape) {\n\t\treturn shape.props.url\n\t}\n\n\toverride getAriaDescriptor(shape: TLBookmarkShape) {\n\t\tconst asset = (\n\t\t\tshape.props.assetId ? this.editor.getAsset(shape.props.assetId) : null\n\t\t) as TLBookmarkAsset | null\n\n\t\tif (!asset?.props.title) return undefined\n\n\t\treturn (\n\t\t\tconvertCommonTitleHTMLEntities(asset.props.title) +\n\t\t\t(asset.props.description ? ', ' + asset.props.description : '')\n\t\t)\n\t}\n\n\toverride getDefaultProps(): TLBookmarkShape['props'] {\n\t\treturn {\n\t\t\turl: '',\n\t\t\tw: BOOKMARK_WIDTH,\n\t\t\th: BOOKMARK_HEIGHT,\n\t\t\tassetId: null,\n\t\t}\n\t}\n\n\toverride component(shape: TLBookmarkShape) {\n\t\treturn <BookmarkShapeComponent shape={shape} />\n\t}\n\n\toverride indicator(shape: TLBookmarkShape) {\n\t\treturn (\n\t\t\t<rect\n\t\t\t\twidth={toDomPrecision(shape.props.w)}\n\t\t\t\theight={toDomPrecision(shape.props.h)}\n\t\t\t\trx=\"6\"\n\t\t\t\try=\"6\"\n\t\t\t/>\n\t\t)\n\t}\n\n\toverride onBeforeCreate(next: TLBookmarkShape) {\n\t\treturn getBookmarkSize(this.editor, next)\n\t}\n\n\toverride onBeforeUpdate(prev: TLBookmarkShape, shape: TLBookmarkShape) {\n\t\tif (prev.props.url !== shape.props.url) {\n\t\t\tif (!T.linkUrl.isValid(shape.props.url)) {\n\t\t\t\treturn { ...shape, props: { ...shape.props, url: prev.props.url } }\n\t\t\t} else {\n\t\t\t\tupdateBookmarkAssetOnUrlChange(this.editor, shape)\n\t\t\t}\n\t\t}\n\n\t\tif (prev.props.assetId !== shape.props.assetId) {\n\t\t\treturn getBookmarkSize(this.editor, shape)\n\t\t}\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLBookmarkShape,\n\t\tendShape: TLBookmarkShape,\n\t\tt: number\n\t): TLBookmarkShapeProps {\n\t\treturn {\n\t\t\t...(t > 0.5 ? endShape.props : startShape.props),\n\t\t\tw: lerp(startShape.props.w, endShape.props.w, t),\n\t\t\th: lerp(startShape.props.h, endShape.props.h, t),\n\t\t}\n\t}\n}\n\nfunction BookmarkShapeComponent({ shape }: { shape: TLBookmarkShape }) {\n\tconst editor = useEditor()\n\n\tconst asset = (\n\t\tshape.props.assetId ? editor.getAsset(shape.props.assetId) : null\n\t) as TLBookmarkAsset\n\n\tconst isSafariExport = !!useSvgExportContext() && tlenv.isSafari\n\n\tconst pageRotation = editor.getShapePageTransform(shape)!.rotation()\n\n\tconst address = getHumanReadableAddress(shape)\n\n\tconst [isFaviconValid, setIsFaviconValid] = useState(true)\n\tconst onFaviconError = () => setIsFaviconValid(false)\n\n\tconst markAsHandledOnShiftKey = useCallback<PointerEventHandler>(\n\t\t(e) => {\n\t\t\tif (!editor.inputs.shiftKey) editor.markEventAsHandled(e)\n\t\t},\n\t\t[editor]\n\t)\n\n\treturn (\n\t\t<HTMLContainer>\n\t\t\t<div\n\t\t\t\tclassName={classNames(\n\t\t\t\t\t'tl-bookmark__container',\n\t\t\t\t\tisSafariExport && 'tl-bookmark__container--safariExport'\n\t\t\t\t)}\n\t\t\t\tstyle={{\n\t\t\t\t\tboxShadow: isSafariExport ? undefined : getRotatedBoxShadow(pageRotation),\n\t\t\t\t\tmaxHeight: shape.props.h,\n\t\t\t\t}}\n\t\t\t>\n\t\t\t\t{(!asset || asset.props.image) && (\n\t\t\t\t\t<div className=\"tl-bookmark__image_container\">\n\t\t\t\t\t\t{asset ? (\n\t\t\t\t\t\t\t<img\n\t\t\t\t\t\t\t\tclassName=\"tl-bookmark__image\"\n\t\t\t\t\t\t\t\tdraggable={false}\n\t\t\t\t\t\t\t\treferrerPolicy=\"strict-origin-when-cross-origin\"\n\t\t\t\t\t\t\t\tsrc={asset?.props.image}\n\t\t\t\t\t\t\t\talt={asset?.props.title || ''}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t) : (\n\t\t\t\t\t\t\t<div className=\"tl-bookmark__placeholder\" />\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{asset?.props.image && <HyperlinkButton url={shape.props.url} />}\n\t\t\t\t\t</div>\n\t\t\t\t)}\n\t\t\t\t<div className=\"tl-bookmark__copy_container\">\n\t\t\t\t\t{asset?.props.title ? (\n\t\t\t\t\t\t<h2 className=\"tl-bookmark__heading\">\n\t\t\t\t\t\t\t{convertCommonTitleHTMLEntities(asset.props.title)}\n\t\t\t\t\t\t</h2>\n\t\t\t\t\t) : null}\n\t\t\t\t\t{asset?.props.description && asset?.props.image ? (\n\t\t\t\t\t\t<p className=\"tl-bookmark__description\">{asset.props.description}</p>\n\t\t\t\t\t) : null}\n\t\t\t\t\t<a\n\t\t\t\t\t\tclassName=\"tl-bookmark__link\"\n\t\t\t\t\t\thref={shape.props.url || ''}\n\t\t\t\t\t\ttarget=\"_blank\"\n\t\t\t\t\t\trel=\"noopener noreferrer\"\n\t\t\t\t\t\tdraggable={false}\n\t\t\t\t\t\tonPointerDown={markAsHandledOnShiftKey}\n\t\t\t\t\t\tonPointerUp={markAsHandledOnShiftKey}\n\t\t\t\t\t>\n\t\t\t\t\t\t{isFaviconValid && asset?.props.favicon ? (\n\t\t\t\t\t\t\t<img\n\t\t\t\t\t\t\t\tclassName=\"tl-bookmark__favicon\"\n\t\t\t\t\t\t\t\tsrc={asset?.props.favicon}\n\t\t\t\t\t\t\t\treferrerPolicy=\"strict-origin-when-cross-origin\"\n\t\t\t\t\t\t\t\tonError={onFaviconError}\n\t\t\t\t\t\t\t\talt={`favicon of ${address}`}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t) : (\n\t\t\t\t\t\t\t<div\n\t\t\t\t\t\t\t\tclassName=\"tl-hyperlink__icon\"\n\t\t\t\t\t\t\t\tstyle={{\n\t\t\t\t\t\t\t\t\tmask: `url(\"${LINK_ICON}\") center 100% / 100% no-repeat`,\n\t\t\t\t\t\t\t\t\tWebkitMask: `url(\"${LINK_ICON}\") center 100% / 100% no-repeat`,\n\t\t\t\t\t\t\t\t}}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t<span>{address}</span>\n\t\t\t\t\t</a>\n\t\t\t\t</div>\n\t\t\t</div>\n\t\t</HTMLContainer>\n\t)\n}\n\nfunction getBookmarkSize(editor: Editor, shape: TLBookmarkShape) {\n\tconst asset = (\n\t\tshape.props.assetId ? editor.getAsset(shape.props.assetId) : null\n\t) as TLBookmarkAsset\n\n\tlet h = BOOKMARK_HEIGHT\n\n\tif (asset) {\n\t\tif (!asset.props.image) {\n\t\t\tif (!asset.props.title) {\n\t\t\t\th = BOOKMARK_JUST_URL_HEIGHT\n\t\t\t} else {\n\t\t\t\th = SHORT_BOOKMARK_HEIGHT\n\t\t\t}\n\t\t}\n\t}\n\n\treturn {\n\t\t...shape,\n\t\tprops: {\n\t\t\t...shape.props,\n\t\t\th,\n\t\t},\n\t}\n}\n\n/** @internal */\nexport const getHumanReadableAddress = (shape: TLBookmarkShape) => {\n\ttry {\n\t\tconst url = new URL(shape.props.url)\n\t\t// we want the hostname without any www\n\t\treturn url.hostname.replace(/^www\\./, '')\n\t} catch {\n\t\treturn shape.props.url\n\t}\n}\n\nfunction updateBookmarkAssetOnUrlChange(editor: Editor, shape: TLBookmarkShape) {\n\tconst { url } = shape.props\n\n\t// Derive the asset id from the URL\n\tconst assetId: TLAssetId = AssetRecordType.createId(getHashForString(url))\n\n\tif (editor.getAsset(assetId)) {\n\t\t// Existing asset for this URL?\n\t\tif (shape.props.assetId !== assetId) {\n\t\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t\t{\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: { assetId },\n\t\t\t\t},\n\t\t\t])\n\t\t}\n\t} else {\n\t\t// No asset for this URL?\n\n\t\t// First, clear out the existing asset reference\n\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t{\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { assetId: null },\n\t\t\t},\n\t\t])\n\n\t\t// Then try to asyncronously create a new one\n\t\tcreateBookmarkAssetOnUrlChange(editor, shape)\n\t}\n}\n\nconst createBookmarkAssetOnUrlChange = debounce(async (editor: Editor, shape: TLBookmarkShape) => {\n\tif (editor.isDisposed) return\n\n\tconst { url } = shape.props\n\n\t// Create the asset using the external content manager's createAssetFromUrl method.\n\t// This may be overwritten by the user (for example, we overwrite it on tldraw.com)\n\tconst asset = await editor.getAssetForExternalContent({ type: 'url', url })\n\n\tif (!asset) {\n\t\t// No asset? Just leave the bookmark as a null assetId.\n\t\treturn\n\t}\n\n\teditor.run(() => {\n\t\t// Create the new asset\n\t\teditor.createAssets([asset])\n\n\t\t// And update the shape\n\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t{\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { assetId: asset.id },\n\t\t\t},\n\t\t])\n\t})\n}, 500)\n"],
|
|
5
|
-
"mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAyES;AAzET,oBAmBO;AACP,wBAAuB;AACvB,mBAA2D;AAC3D,kBAA+C;AAC/C,6BAAgC;AAChC,0BAA0B;AAC1B,gCAAoC;AAEpC,MAAM,iBAAiB;AACvB,MAAM,kBAAkB;AACxB,MAAM,2BAA2B;AACjC,MAAM,wBAAwB;AAGvB,MAAM,0BAA0B,+BAAkC;AAAA,EACxE,OAAgB,OAAO;AAAA,EACvB,OAAgB,QAAQ;AAAA,EACxB,OAAgB,aAAa;AAAA,EAEpB,YAAY;AACpB,WAAO;AAAA,EACR;AAAA,EAES,wBAAwB;AAChC,WAAO;AAAA,EACR;AAAA,EAES,QAAQ,OAAwB;AACxC,WAAO,MAAM,MAAM;AAAA,EACpB;AAAA,EAES,kBAAkB,OAAwB;AAClD,UAAM,QACL,MAAM,MAAM,UAAU,KAAK,OAAO,SAAS,MAAM,MAAM,OAAO,IAAI;AAGnE,QAAI,CAAC,OAAO,MAAM,MAAO,QAAO;AAEhC,eACC,4CAA+B,MAAM,MAAM,KAAK,KAC/C,MAAM,MAAM,cAAc,OAAO,MAAM,MAAM,cAAc;AAAA,EAE9D;AAAA,EAES,kBAA4C;AACpD,WAAO;AAAA,MACN,KAAK;AAAA,MACL,GAAG;AAAA,MACH,GAAG;AAAA,MACH,SAAS;AAAA,IACV;AAAA,EACD;AAAA,EAES,UAAU,OAAwB;AAC1C,WAAO,4CAAC,0BAAuB,OAAc;AAAA,EAC9C;AAAA,EAES,UAAU,OAAwB;AAC1C,WACC;AAAA,MAAC;AAAA;AAAA,QACA,WAAO,8BAAe,MAAM,MAAM,CAAC;AAAA,QACnC,YAAQ,8BAAe,MAAM,MAAM,CAAC;AAAA,QACpC,IAAG;AAAA,QACH,IAAG;AAAA;AAAA,IACJ;AAAA,EAEF;AAAA,EAES,eAAe,MAAuB;AAC9C,WAAO,gBAAgB,KAAK,QAAQ,IAAI;AAAA,EACzC;AAAA,EAES,eAAe,MAAuB,OAAwB;AACtE,QAAI,KAAK,MAAM,QAAQ,MAAM,MAAM,KAAK;AACvC,UAAI,CAAC,gBAAE,QAAQ,QAAQ,MAAM,MAAM,GAAG,GAAG;AACxC,eAAO,EAAE,GAAG,OAAO,OAAO,EAAE,GAAG,MAAM,OAAO,KAAK,KAAK,MAAM,IAAI,EAAE;AAAA,MACnE,OAAO;AACN,uCAA+B,KAAK,QAAQ,KAAK;AAAA,MAClD;AAAA,IACD;AAEA,QAAI,KAAK,MAAM,YAAY,MAAM,MAAM,SAAS;AAC/C,aAAO,gBAAgB,KAAK,QAAQ,KAAK;AAAA,IAC1C;AAAA,EACD;AAAA,EACS,qBACR,YACA,UACA,GACuB;AACvB,WAAO;AAAA,MACN,GAAI,IAAI,MAAM,SAAS,QAAQ,WAAW;AAAA,MAC1C,OAAG,oBAAK,WAAW,MAAM,GAAG,SAAS,MAAM,GAAG,CAAC;AAAA,MAC/C,OAAG,oBAAK,WAAW,MAAM,GAAG,SAAS,MAAM,GAAG,CAAC;AAAA,IAChD;AAAA,EACD;AACD;AAEA,SAAS,uBAAuB,EAAE,MAAM,GAA+B;AACtE,QAAM,aAAS,yBAAU;AAEzB,QAAM,QACL,MAAM,MAAM,UAAU,OAAO,SAAS,MAAM,MAAM,OAAO,IAAI;AAG9D,QAAM,iBAAiB,CAAC,KAAC,mCAAoB,KAAK,oBAAM;AAExD,QAAM,eAAe,OAAO,sBAAsB,KAAK,EAAG,SAAS;AAEnE,QAAM,UAAU,wBAAwB,KAAK;AAE7C,QAAM,CAAC,gBAAgB,iBAAiB,QAAI,uBAAS,IAAI;AACzD,QAAM,iBAAiB,MAAM,kBAAkB,KAAK;AAEpD,QAAM,8BAA0B;AAAA,IAC/B,CAAC,MAAM;AACN,UAAI,CAAC,OAAO,OAAO,SAAU,QAAO,mBAAmB,CAAC;AAAA,IACzD;AAAA,IACA,CAAC,MAAM;AAAA,EACR;AAEA,SACC,4CAAC,+BACA;AAAA,IAAC;AAAA;AAAA,MACA,eAAW,kBAAAA;AAAA,QACV;AAAA,QACA,kBAAkB;AAAA,MACnB;AAAA,MACA,OAAO;AAAA,QACN,WAAW,iBAAiB,aAAY,+CAAoB,YAAY;AAAA,QACxE,WAAW,MAAM,MAAM;AAAA,MACxB;AAAA,MAEE;AAAA,UAAC,SAAS,MAAM,MAAM,UACvB,6CAAC,SAAI,WAAU,gCACb;AAAA,kBACA;AAAA,YAAC;AAAA;AAAA,cACA,WAAU;AAAA,cACV,WAAW;AAAA,cACX,gBAAe;AAAA,cACf,KAAK,OAAO,MAAM;AAAA,cAClB,KAAK,OAAO,MAAM,SAAS;AAAA;AAAA,UAC5B,IAEA,4CAAC,SAAI,WAAU,4BAA2B;AAAA,UAE1C,OAAO,MAAM,SAAS,4CAAC,0CAAgB,KAAK,MAAM,MAAM,KAAK;AAAA,WAC/D;AAAA,QAED,6CAAC,SAAI,WAAU,+BACb;AAAA,iBAAO,MAAM,QACb,
|
|
4
|
+
"sourcesContent": ["import {\n\tAssetRecordType,\n\tBaseBoxShapeUtil,\n\tEditor,\n\tHTMLContainer,\n\tT,\n\tTLAssetId,\n\tTLBookmarkAsset,\n\tTLBookmarkShape,\n\tTLBookmarkShapeProps,\n\tbookmarkShapeMigrations,\n\tbookmarkShapeProps,\n\tdebounce,\n\tgetHashForString,\n\tlerp,\n\ttlenv,\n\ttoDomPrecision,\n\tuseEditor,\n\tuseSvgExportContext,\n} from '@tldraw/editor'\nimport classNames from 'classnames'\nimport { PointerEventHandler, useCallback, useState } from 'react'\nimport { convertCommonTitleHTMLEntities } from '../../utils/text/text'\nimport { HyperlinkButton } from '../shared/HyperlinkButton'\nimport { LINK_ICON } from '../shared/icons-editor'\nimport { getRotatedBoxShadow } from '../shared/rotated-box-shadow'\n\nconst BOOKMARK_WIDTH = 300\nconst BOOKMARK_HEIGHT = 320\nconst BOOKMARK_JUST_URL_HEIGHT = 46\nconst SHORT_BOOKMARK_HEIGHT = 101\n\n/** @public */\nexport class BookmarkShapeUtil extends BaseBoxShapeUtil<TLBookmarkShape> {\n\tstatic override type = 'bookmark' as const\n\tstatic override props = bookmarkShapeProps\n\tstatic override migrations = bookmarkShapeMigrations\n\n\toverride canResize() {\n\t\treturn false\n\t}\n\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\n\toverride getText(shape: TLBookmarkShape) {\n\t\treturn shape.props.url\n\t}\n\n\toverride getAriaDescriptor(shape: TLBookmarkShape) {\n\t\tconst asset = (\n\t\t\tshape.props.assetId ? this.editor.getAsset(shape.props.assetId) : null\n\t\t) as TLBookmarkAsset | null\n\n\t\tif (!asset?.props.title) return undefined\n\n\t\treturn (\n\t\t\tconvertCommonTitleHTMLEntities(asset.props.title) +\n\t\t\t(asset.props.description ? ', ' + asset.props.description : '')\n\t\t)\n\t}\n\n\toverride getDefaultProps(): TLBookmarkShape['props'] {\n\t\treturn {\n\t\t\turl: '',\n\t\t\tw: BOOKMARK_WIDTH,\n\t\t\th: BOOKMARK_HEIGHT,\n\t\t\tassetId: null,\n\t\t}\n\t}\n\n\toverride component(shape: TLBookmarkShape) {\n\t\treturn <BookmarkShapeComponent shape={shape} />\n\t}\n\n\toverride indicator(shape: TLBookmarkShape) {\n\t\treturn (\n\t\t\t<rect\n\t\t\t\twidth={toDomPrecision(shape.props.w)}\n\t\t\t\theight={toDomPrecision(shape.props.h)}\n\t\t\t\trx=\"6\"\n\t\t\t\try=\"6\"\n\t\t\t/>\n\t\t)\n\t}\n\n\toverride onBeforeCreate(next: TLBookmarkShape) {\n\t\treturn getBookmarkSize(this.editor, next)\n\t}\n\n\toverride onBeforeUpdate(prev: TLBookmarkShape, shape: TLBookmarkShape) {\n\t\tif (prev.props.url !== shape.props.url) {\n\t\t\tif (!T.linkUrl.isValid(shape.props.url)) {\n\t\t\t\treturn { ...shape, props: { ...shape.props, url: prev.props.url } }\n\t\t\t} else {\n\t\t\t\tupdateBookmarkAssetOnUrlChange(this.editor, shape)\n\t\t\t}\n\t\t}\n\n\t\tif (prev.props.assetId !== shape.props.assetId) {\n\t\t\treturn getBookmarkSize(this.editor, shape)\n\t\t}\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLBookmarkShape,\n\t\tendShape: TLBookmarkShape,\n\t\tt: number\n\t): TLBookmarkShapeProps {\n\t\treturn {\n\t\t\t...(t > 0.5 ? endShape.props : startShape.props),\n\t\t\tw: lerp(startShape.props.w, endShape.props.w, t),\n\t\t\th: lerp(startShape.props.h, endShape.props.h, t),\n\t\t}\n\t}\n}\n\nfunction BookmarkShapeComponent({ shape }: { shape: TLBookmarkShape }) {\n\tconst editor = useEditor()\n\n\tconst asset = (\n\t\tshape.props.assetId ? editor.getAsset(shape.props.assetId) : null\n\t) as TLBookmarkAsset\n\n\tconst isSafariExport = !!useSvgExportContext() && tlenv.isSafari\n\n\tconst pageRotation = editor.getShapePageTransform(shape)!.rotation()\n\n\tconst address = getHumanReadableAddress(shape)\n\n\tconst [isFaviconValid, setIsFaviconValid] = useState(true)\n\tconst onFaviconError = () => setIsFaviconValid(false)\n\n\tconst markAsHandledOnShiftKey = useCallback<PointerEventHandler>(\n\t\t(e) => {\n\t\t\tif (!editor.inputs.shiftKey) editor.markEventAsHandled(e)\n\t\t},\n\t\t[editor]\n\t)\n\n\treturn (\n\t\t<HTMLContainer>\n\t\t\t<div\n\t\t\t\tclassName={classNames(\n\t\t\t\t\t'tl-bookmark__container',\n\t\t\t\t\tisSafariExport && 'tl-bookmark__container--safariExport'\n\t\t\t\t)}\n\t\t\t\tstyle={{\n\t\t\t\t\tboxShadow: isSafariExport ? undefined : getRotatedBoxShadow(pageRotation),\n\t\t\t\t\tmaxHeight: shape.props.h,\n\t\t\t\t}}\n\t\t\t>\n\t\t\t\t{(!asset || asset.props.image) && (\n\t\t\t\t\t<div className=\"tl-bookmark__image_container\">\n\t\t\t\t\t\t{asset ? (\n\t\t\t\t\t\t\t<img\n\t\t\t\t\t\t\t\tclassName=\"tl-bookmark__image\"\n\t\t\t\t\t\t\t\tdraggable={false}\n\t\t\t\t\t\t\t\treferrerPolicy=\"strict-origin-when-cross-origin\"\n\t\t\t\t\t\t\t\tsrc={asset?.props.image}\n\t\t\t\t\t\t\t\talt={asset?.props.title || ''}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t) : (\n\t\t\t\t\t\t\t<div className=\"tl-bookmark__placeholder\" />\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t{asset?.props.image && <HyperlinkButton url={shape.props.url} />}\n\t\t\t\t\t</div>\n\t\t\t\t)}\n\t\t\t\t<div className=\"tl-bookmark__copy_container\">\n\t\t\t\t\t{asset?.props.title ? (\n\t\t\t\t\t\t<a\n\t\t\t\t\t\t\tclassName=\"tl-bookmark__link\"\n\t\t\t\t\t\t\thref={shape.props.url || ''}\n\t\t\t\t\t\t\ttarget=\"_blank\"\n\t\t\t\t\t\t\trel=\"noopener noreferrer\"\n\t\t\t\t\t\t\tdraggable={false}\n\t\t\t\t\t\t\tonPointerDown={markAsHandledOnShiftKey}\n\t\t\t\t\t\t\tonPointerUp={markAsHandledOnShiftKey}\n\t\t\t\t\t\t>\n\t\t\t\t\t\t\t<h2 className=\"tl-bookmark__heading\">\n\t\t\t\t\t\t\t\t{convertCommonTitleHTMLEntities(asset.props.title)}\n\t\t\t\t\t\t\t</h2>\n\t\t\t\t\t\t</a>\n\t\t\t\t\t) : null}\n\t\t\t\t\t{asset?.props.description && asset?.props.image ? (\n\t\t\t\t\t\t<p className=\"tl-bookmark__description\">{asset.props.description}</p>\n\t\t\t\t\t) : null}\n\t\t\t\t\t<a\n\t\t\t\t\t\tclassName=\"tl-bookmark__link\"\n\t\t\t\t\t\thref={shape.props.url || ''}\n\t\t\t\t\t\ttarget=\"_blank\"\n\t\t\t\t\t\trel=\"noopener noreferrer\"\n\t\t\t\t\t\tdraggable={false}\n\t\t\t\t\t\tonPointerDown={markAsHandledOnShiftKey}\n\t\t\t\t\t\tonPointerUp={markAsHandledOnShiftKey}\n\t\t\t\t\t>\n\t\t\t\t\t\t{isFaviconValid && asset?.props.favicon ? (\n\t\t\t\t\t\t\t<img\n\t\t\t\t\t\t\t\tclassName=\"tl-bookmark__favicon\"\n\t\t\t\t\t\t\t\tsrc={asset?.props.favicon}\n\t\t\t\t\t\t\t\treferrerPolicy=\"strict-origin-when-cross-origin\"\n\t\t\t\t\t\t\t\tonError={onFaviconError}\n\t\t\t\t\t\t\t\talt={`favicon of ${address}`}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t) : (\n\t\t\t\t\t\t\t<div\n\t\t\t\t\t\t\t\tclassName=\"tl-hyperlink__icon\"\n\t\t\t\t\t\t\t\tstyle={{\n\t\t\t\t\t\t\t\t\tmask: `url(\"${LINK_ICON}\") center 100% / 100% no-repeat`,\n\t\t\t\t\t\t\t\t\tWebkitMask: `url(\"${LINK_ICON}\") center 100% / 100% no-repeat`,\n\t\t\t\t\t\t\t\t}}\n\t\t\t\t\t\t\t/>\n\t\t\t\t\t\t)}\n\t\t\t\t\t\t<span>{address}</span>\n\t\t\t\t\t</a>\n\t\t\t\t</div>\n\t\t\t</div>\n\t\t</HTMLContainer>\n\t)\n}\n\nfunction getBookmarkSize(editor: Editor, shape: TLBookmarkShape) {\n\tconst asset = (\n\t\tshape.props.assetId ? editor.getAsset(shape.props.assetId) : null\n\t) as TLBookmarkAsset\n\n\tlet h = BOOKMARK_HEIGHT\n\n\tif (asset) {\n\t\tif (!asset.props.image) {\n\t\t\tif (!asset.props.title) {\n\t\t\t\th = BOOKMARK_JUST_URL_HEIGHT\n\t\t\t} else {\n\t\t\t\th = SHORT_BOOKMARK_HEIGHT\n\t\t\t}\n\t\t}\n\t}\n\n\treturn {\n\t\t...shape,\n\t\tprops: {\n\t\t\t...shape.props,\n\t\t\th,\n\t\t},\n\t}\n}\n\n/** @internal */\nexport const getHumanReadableAddress = (shape: TLBookmarkShape) => {\n\ttry {\n\t\tconst url = new URL(shape.props.url)\n\t\t// we want the hostname without any www\n\t\treturn url.hostname.replace(/^www\\./, '')\n\t} catch {\n\t\treturn shape.props.url\n\t}\n}\n\nfunction updateBookmarkAssetOnUrlChange(editor: Editor, shape: TLBookmarkShape) {\n\tconst { url } = shape.props\n\n\t// Derive the asset id from the URL\n\tconst assetId: TLAssetId = AssetRecordType.createId(getHashForString(url))\n\n\tif (editor.getAsset(assetId)) {\n\t\t// Existing asset for this URL?\n\t\tif (shape.props.assetId !== assetId) {\n\t\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t\t{\n\t\t\t\t\tid: shape.id,\n\t\t\t\t\ttype: shape.type,\n\t\t\t\t\tprops: { assetId },\n\t\t\t\t},\n\t\t\t])\n\t\t}\n\t} else {\n\t\t// No asset for this URL?\n\n\t\t// First, clear out the existing asset reference\n\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t{\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { assetId: null },\n\t\t\t},\n\t\t])\n\n\t\t// Then try to asyncronously create a new one\n\t\tcreateBookmarkAssetOnUrlChange(editor, shape)\n\t}\n}\n\nconst createBookmarkAssetOnUrlChange = debounce(async (editor: Editor, shape: TLBookmarkShape) => {\n\tif (editor.isDisposed) return\n\n\tconst { url } = shape.props\n\n\t// Create the asset using the external content manager's createAssetFromUrl method.\n\t// This may be overwritten by the user (for example, we overwrite it on tldraw.com)\n\tconst asset = await editor.getAssetForExternalContent({ type: 'url', url })\n\n\tif (!asset) {\n\t\t// No asset? Just leave the bookmark as a null assetId.\n\t\treturn\n\t}\n\n\teditor.run(() => {\n\t\t// Create the new asset\n\t\teditor.createAssets([asset])\n\n\t\t// And update the shape\n\t\teditor.updateShapes<TLBookmarkShape>([\n\t\t\t{\n\t\t\t\tid: shape.id,\n\t\t\t\ttype: shape.type,\n\t\t\t\tprops: { assetId: asset.id },\n\t\t\t},\n\t\t])\n\t})\n}, 500)\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": ["classNames"]
|
|
7
7
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../src/lib/shapes/line/LineShapeUtil.tsx"],
|
|
4
|
-
"sourcesContent": ["import {\n\tGroup2d,\n\tHandleSnapGeometry,\n\tSVGContainer,\n\tShapeUtil,\n\tTLHandle,\n\tTLHandleDragInfo,\n\tTLLineShape,\n\tTLLineShapePoint,\n\tTLResizeInfo,\n\tVec,\n\tWeakCache,\n\tZERO_INDEX_KEY,\n\tassert,\n\tgetColorValue,\n\tgetIndexAbove,\n\tgetIndexBetween,\n\tgetIndices,\n\tlerp,\n\tlineShapeMigrations,\n\tlineShapeProps,\n\tmapObjectMapValues,\n\tmaybeSnapToGrid,\n\tsortByIndex,\n} from '@tldraw/editor'\n\nimport { STROKE_SIZES } from '../arrow/shared'\nimport { PathBuilder, PathBuilderGeometry2d } from '../shared/PathBuilder'\nimport { useDefaultColorTheme } from '../shared/useDefaultColorTheme'\n\nconst handlesCache = new WeakCache<TLLineShape['props'], TLHandle[]>()\n\n/** @public */\nexport class LineShapeUtil extends ShapeUtil<TLLineShape> {\n\tstatic override type = 'line' as const\n\tstatic override props = lineShapeProps\n\tstatic override migrations = lineShapeMigrations\n\n\toverride hideResizeHandles() {\n\t\treturn true\n\t}\n\toverride hideRotateHandle() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsBg() {\n\t\treturn true\n\t}\n\n\toverride getDefaultProps(): TLLineShape['props'] {\n\t\tconst [start, end] = getIndices(2)\n\t\treturn {\n\t\t\tdash: 'draw',\n\t\t\tsize: 'm',\n\t\t\tcolor: 'black',\n\t\t\tspline: 'line',\n\t\t\tpoints: {\n\t\t\t\t[start]: { id: start, index: start, x: 0, y: 0 },\n\t\t\t\t[end]: { id: end, index: end, x: 0.1, y: 0.1 },\n\t\t\t},\n\t\t\tscale: 1,\n\t\t}\n\t}\n\n\tgetGeometry(shape: TLLineShape) {\n\t\t// todo: should we have min size?\n\t\tconst geometry = getPathForLineShape(shape).toGeometry()\n\t\tassert(geometry instanceof PathBuilderGeometry2d)\n\t\treturn geometry\n\t}\n\n\toverride getHandles(shape: TLLineShape) {\n\t\treturn handlesCache.get(shape.props, () => {\n\t\t\tconst spline = this.getGeometry(shape)\n\n\t\t\tconst points = linePointsToArray(shape)\n\t\t\tconst results: TLHandle[] = points.map((point) => ({\n\t\t\t\t...point,\n\t\t\t\tid: point.index,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tcanSnap: true,\n\t\t\t}))\n\n\t\t\tfor (let i = 0; i < points.length - 1; i++) {\n\t\t\t\tconst index = getIndexBetween(points[i].index, points[i + 1].index)\n\t\t\t\tconst segment = spline.getSegments()[i]\n\t\t\t\tconst point = segment.interpolateAlongEdge(0.5)\n\t\t\t\tresults.push({\n\t\t\t\t\tid: index,\n\t\t\t\t\ttype: 'create',\n\t\t\t\t\tindex,\n\t\t\t\t\tx: point.x,\n\t\t\t\t\ty: point.y,\n\t\t\t\t\tcanSnap: true,\n\t\t\t\t})\n\t\t\t}\n\n\t\t\treturn results.sort(sortByIndex)\n\t\t})\n\t}\n\n\t// Events\n\n\toverride onResize(shape: TLLineShape, info: TLResizeInfo<TLLineShape>) {\n\t\tconst { scaleX, scaleY } = info\n\n\t\treturn {\n\t\t\tprops: {\n\t\t\t\tpoints: mapObjectMapValues(shape.props.points, (_, { id, index, x, y }) => ({\n\t\t\t\t\tid,\n\t\t\t\t\tindex,\n\t\t\t\t\tx: x * scaleX,\n\t\t\t\t\ty: y * scaleY,\n\t\t\t\t})),\n\t\t\t},\n\t\t}\n\t}\n\n\toverride onBeforeCreate(next: TLLineShape): void | TLLineShape {\n\t\tconst {\n\t\t\tprops: { points },\n\t\t} = next\n\t\tconst pointKeys = Object.keys(points)\n\n\t\tif (pointKeys.length < 2) {\n\t\t\treturn\n\t\t}\n\n\t\tconst firstPoint = points[pointKeys[0]]\n\t\tconst allSame = pointKeys.every((key) => {\n\t\t\tconst point = points[key]\n\t\t\treturn point.x === firstPoint.x && point.y === firstPoint.y\n\t\t})\n\t\tif (allSame) {\n\t\t\tconst lastKey = pointKeys[pointKeys.length - 1]\n\t\t\tpoints[lastKey] = {\n\t\t\t\t...points[lastKey],\n\t\t\t\tx: points[lastKey].x + 0.1,\n\t\t\t\ty: points[lastKey].y + 0.1,\n\t\t\t}\n\t\t\treturn next\n\t\t}\n\t\treturn\n\t}\n\n\toverride onHandleDrag(shape: TLLineShape, { handle }: TLHandleDragInfo<TLLineShape>) {\n\t\tconst newPoint = maybeSnapToGrid(new Vec(handle.x, handle.y), this.editor)\n\t\treturn {\n\t\t\t...shape,\n\t\t\tprops: {\n\t\t\t\t...shape.props,\n\t\t\t\tpoints: {\n\t\t\t\t\t...shape.props.points,\n\t\t\t\t\t[handle.id]: { id: handle.id, index: handle.index, x: newPoint.x, y: newPoint.y },\n\t\t\t\t},\n\t\t\t},\n\t\t}\n\t}\n\n\toverride onHandleDragStart(shape: TLLineShape, { handle }: TLHandleDragInfo<TLLineShape>) {\n\t\t// For line shapes, if we're dragging a \"create\" handle, then\n\t\t// create a new vertex handle at that point; and make this handle\n\t\t// the handle that we're dragging.\n\t\tif (handle.type === 'create') {\n\t\t\treturn {\n\t\t\t\t...shape,\n\t\t\t\tprops: {\n\t\t\t\t\t...shape.props,\n\t\t\t\t\tpoints: {\n\t\t\t\t\t\t...shape.props.points,\n\t\t\t\t\t\t[handle.index]: { id: handle.index, index: handle.index, x: handle.x, y: handle.y },\n\t\t\t\t\t},\n\t\t\t\t},\n\t\t\t}\n\t\t}\n\t\treturn\n\t}\n\n\tcomponent(shape: TLLineShape) {\n\t\treturn (\n\t\t\t<SVGContainer style={{ minWidth: 50, minHeight: 50 }}>\n\t\t\t\t<LineShapeSvg shape={shape} />\n\t\t\t</SVGContainer>\n\t\t)\n\t}\n\n\tindicator(shape: TLLineShape) {\n\t\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\t\tconst path = getPathForLineShape(shape)\n\t\tconst { dash } = shape.props\n\n\t\treturn path.toSvg({\n\t\t\tstyle: dash === 'draw' ? 'draw' : 'solid',\n\t\t\tstrokeWidth: 1,\n\t\t\tpasses: 1,\n\t\t\trandomSeed: shape.id,\n\t\t\toffset: 0,\n\t\t\troundness: strokeWidth * 2,\n\t\t\tprops: { strokeWidth: undefined },\n\t\t})\n\t}\n\n\toverride toSvg(shape: TLLineShape) {\n\t\treturn <LineShapeSvg shouldScale shape={shape} />\n\t}\n\n\toverride getHandleSnapGeometry(shape: TLLineShape): HandleSnapGeometry {\n\t\tconst points = linePointsToArray(shape)\n\t\treturn {\n\t\t\tpoints,\n\t\t\tgetSelfSnapPoints: (handle) => {\n\t\t\t\tconst index = this.getHandles(shape)\n\t\t\t\t\t.filter((h) => h.type === 'vertex')\n\t\t\t\t\t.findIndex((h) => h.id === handle.id)!\n\n\t\t\t\t// We want to skip the current and adjacent handles\n\t\t\t\treturn points.filter((_, i) => Math.abs(i - index) > 1).map(Vec.From)\n\t\t\t},\n\t\t\tgetSelfSnapOutline: (handle) => {\n\t\t\t\t// We want to skip the segments that include the handle, so\n\t\t\t\t// find the index of the handle that shares the same index property\n\t\t\t\t// as the initial dragging handle; this catches a quirk of create handles\n\t\t\t\tconst index = this.getHandles(shape)\n\t\t\t\t\t.filter((h) => h.type === 'vertex')\n\t\t\t\t\t.findIndex((h) => h.id === handle.id)!\n\n\t\t\t\t// Get all the outline segments from the shape that don't include the handle\n\t\t\t\tconst segments = this.getGeometry(shape)\n\t\t\t\t\t.getSegments()\n\t\t\t\t\t.filter((_, i) => i !== index - 1 && i !== index)\n\n\t\t\t\tif (!segments.length) return null\n\t\t\t\treturn new Group2d({ children: segments })\n\t\t\t},\n\t\t}\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLLineShape,\n\t\tendShape: TLLineShape,\n\t\tt: number\n\t): TLLineShape['props'] {\n\t\tconst startPoints = linePointsToArray(startShape)\n\t\tconst endPoints = linePointsToArray(endShape)\n\n\t\tconst pointsToUseStart: TLLineShapePoint[] = []\n\t\tconst pointsToUseEnd: TLLineShapePoint[] = []\n\n\t\tlet index = ZERO_INDEX_KEY\n\n\t\tif (startPoints.length > endPoints.length) {\n\t\t\t// we'll need to expand points\n\t\t\tfor (let i = 0; i < startPoints.length; i++) {\n\t\t\t\tpointsToUseStart[i] = { ...startPoints[i] }\n\t\t\t\tif (endPoints[i] === undefined) {\n\t\t\t\t\tpointsToUseEnd[i] = { ...endPoints[endPoints.length - 1], id: index }\n\t\t\t\t} else {\n\t\t\t\t\tpointsToUseEnd[i] = { ...endPoints[i], id: index }\n\t\t\t\t}\n\t\t\t\tindex = getIndexAbove(index)\n\t\t\t}\n\t\t} else if (endPoints.length > startPoints.length) {\n\t\t\t// we'll need to converge points\n\t\t\tfor (let i = 0; i < endPoints.length; i++) {\n\t\t\t\tpointsToUseEnd[i] = { ...endPoints[i] }\n\t\t\t\tif (startPoints[i] === undefined) {\n\t\t\t\t\tpointsToUseStart[i] = {\n\t\t\t\t\t\t...startPoints[startPoints.length - 1],\n\t\t\t\t\t\tid: index,\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tpointsToUseStart[i] = { ...startPoints[i], id: index }\n\t\t\t\t}\n\t\t\t\tindex = getIndexAbove(index)\n\t\t\t}\n\t\t} else {\n\t\t\t// noop, easy\n\t\t\tfor (let i = 0; i < endPoints.length; i++) {\n\t\t\t\tpointsToUseStart[i] = startPoints[i]\n\t\t\t\tpointsToUseEnd[i] = endPoints[i]\n\t\t\t}\n\t\t}\n\n\t\treturn {\n\t\t\t...(t > 0.5 ? endShape.props : startShape.props),\n\t\t\tpoints: Object.fromEntries(\n\t\t\t\tpointsToUseStart.map((point, i) => {\n\t\t\t\t\tconst endPoint = pointsToUseEnd[i]\n\t\t\t\t\treturn [\n\t\t\t\t\t\tpoint.id,\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\t...point,\n\t\t\t\t\t\t\tx: lerp(point.x, endPoint.x, t),\n\t\t\t\t\t\t\ty: lerp(point.y, endPoint.y, t),\n\t\t\t\t\t\t},\n\t\t\t\t\t]\n\t\t\t\t})\n\t\t\t),\n\t\t\tscale: lerp(startShape.props.scale, endShape.props.scale, t),\n\t\t}\n\t}\n}\n\nfunction linePointsToArray(shape: TLLineShape) {\n\treturn Object.values(shape.props.points).sort(sortByIndex)\n}\n\nconst pathCache = new WeakCache<TLLineShape, PathBuilder>()\nfunction getPathForLineShape(shape: TLLineShape): PathBuilder {\n\treturn pathCache.get(shape, () => {\n\t\tconst points = linePointsToArray(shape).map(Vec.From)\n\n\t\tswitch (shape.props.spline) {\n\t\t\tcase 'cubic': {\n\t\t\t\treturn PathBuilder.cubicSplineThroughPoints(points, { endOffsets: 0 })\n\t\t\t}\n\t\t\tcase 'line': {\n\t\t\t\treturn PathBuilder.lineThroughPoints(points, { endOffsets: 0 })\n\t\t\t}\n\t\t}\n\t})\n}\n\nfunction LineShapeSvg({\n\tshape,\n\tshouldScale = false,\n\tforceSolid = false,\n}: {\n\tshape: TLLineShape\n\tshouldScale?: boolean\n\tforceSolid?: boolean\n}) {\n\tconst theme = useDefaultColorTheme()\n\n\tconst path = getPathForLineShape(shape)\n\tconst { dash, color, size } = shape.props\n\n\tconst scaleFactor = 1 / shape.props.scale\n\n\tconst scale = shouldScale ? scaleFactor : 1\n\n\tconst strokeWidth = STROKE_SIZES[size] * shape.props.scale\n\n\treturn path.toSvg({\n\t\tstyle: dash,\n\t\tstrokeWidth,\n\t\tforceSolid,\n\t\trandomSeed: shape.id,\n\t\tprops: {\n\t\t\ttransform: `scale(${scale})`,\n\t\t\tstroke: getColorValue(theme, color, 'solid'),\n\t\t\tfill: 'none',\n\t\t},\n\t})\n}\n"],
|
|
5
|
-
"mappings": ";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;
|
|
4
|
+
"sourcesContent": ["import {\n\tGroup2d,\n\tHandleSnapGeometry,\n\tSVGContainer,\n\tShapeUtil,\n\tTLHandle,\n\tTLHandleDragInfo,\n\tTLLineShape,\n\tTLLineShapePoint,\n\tTLResizeInfo,\n\tVec,\n\tWeakCache,\n\tZERO_INDEX_KEY,\n\tassert,\n\tgetColorValue,\n\tgetIndexAbove,\n\tgetIndexBetween,\n\tgetIndices,\n\tlerp,\n\tlineShapeMigrations,\n\tlineShapeProps,\n\tmapObjectMapValues,\n\tmaybeSnapToGrid,\n\tsortByIndex,\n} from '@tldraw/editor'\n\nimport { STROKE_SIZES } from '../arrow/shared'\nimport { PathBuilder, PathBuilderGeometry2d } from '../shared/PathBuilder'\nimport { useDefaultColorTheme } from '../shared/useDefaultColorTheme'\n\nconst handlesCache = new WeakCache<TLLineShape['props'], TLHandle[]>()\n\n/** @public */\nexport class LineShapeUtil extends ShapeUtil<TLLineShape> {\n\tstatic override type = 'line' as const\n\tstatic override props = lineShapeProps\n\tstatic override migrations = lineShapeMigrations\n\n\toverride hideResizeHandles() {\n\t\treturn true\n\t}\n\toverride hideRotateHandle() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsFg() {\n\t\treturn true\n\t}\n\toverride hideSelectionBoundsBg() {\n\t\treturn true\n\t}\n\toverride hideInMinimap() {\n\t\treturn true\n\t}\n\n\toverride getDefaultProps(): TLLineShape['props'] {\n\t\tconst [start, end] = getIndices(2)\n\t\treturn {\n\t\t\tdash: 'draw',\n\t\t\tsize: 'm',\n\t\t\tcolor: 'black',\n\t\t\tspline: 'line',\n\t\t\tpoints: {\n\t\t\t\t[start]: { id: start, index: start, x: 0, y: 0 },\n\t\t\t\t[end]: { id: end, index: end, x: 0.1, y: 0.1 },\n\t\t\t},\n\t\t\tscale: 1,\n\t\t}\n\t}\n\n\tgetGeometry(shape: TLLineShape) {\n\t\t// todo: should we have min size?\n\t\tconst geometry = getPathForLineShape(shape).toGeometry()\n\t\tassert(geometry instanceof PathBuilderGeometry2d)\n\t\treturn geometry\n\t}\n\n\toverride getHandles(shape: TLLineShape) {\n\t\treturn handlesCache.get(shape.props, () => {\n\t\t\tconst spline = this.getGeometry(shape)\n\n\t\t\tconst points = linePointsToArray(shape)\n\t\t\tconst results: TLHandle[] = points.map((point) => ({\n\t\t\t\t...point,\n\t\t\t\tid: point.index,\n\t\t\t\ttype: 'vertex',\n\t\t\t\tcanSnap: true,\n\t\t\t}))\n\n\t\t\tfor (let i = 0; i < points.length - 1; i++) {\n\t\t\t\tconst index = getIndexBetween(points[i].index, points[i + 1].index)\n\t\t\t\tconst segment = spline.getSegments()[i]\n\t\t\t\tconst point = segment.interpolateAlongEdge(0.5)\n\t\t\t\tresults.push({\n\t\t\t\t\tid: index,\n\t\t\t\t\ttype: 'create',\n\t\t\t\t\tindex,\n\t\t\t\t\tx: point.x,\n\t\t\t\t\ty: point.y,\n\t\t\t\t\tcanSnap: true,\n\t\t\t\t})\n\t\t\t}\n\n\t\t\treturn results.sort(sortByIndex)\n\t\t})\n\t}\n\n\t// Events\n\n\toverride onResize(shape: TLLineShape, info: TLResizeInfo<TLLineShape>) {\n\t\tconst { scaleX, scaleY } = info\n\n\t\treturn {\n\t\t\tprops: {\n\t\t\t\tpoints: mapObjectMapValues(shape.props.points, (_, { id, index, x, y }) => ({\n\t\t\t\t\tid,\n\t\t\t\t\tindex,\n\t\t\t\t\tx: x * scaleX,\n\t\t\t\t\ty: y * scaleY,\n\t\t\t\t})),\n\t\t\t},\n\t\t}\n\t}\n\n\toverride onBeforeCreate(next: TLLineShape): void | TLLineShape {\n\t\tconst {\n\t\t\tprops: { points },\n\t\t} = next\n\t\tconst pointKeys = Object.keys(points)\n\n\t\tif (pointKeys.length < 2) {\n\t\t\treturn\n\t\t}\n\n\t\tconst firstPoint = points[pointKeys[0]]\n\t\tconst allSame = pointKeys.every((key) => {\n\t\t\tconst point = points[key]\n\t\t\treturn point.x === firstPoint.x && point.y === firstPoint.y\n\t\t})\n\t\tif (allSame) {\n\t\t\tconst lastKey = pointKeys[pointKeys.length - 1]\n\t\t\tpoints[lastKey] = {\n\t\t\t\t...points[lastKey],\n\t\t\t\tx: points[lastKey].x + 0.1,\n\t\t\t\ty: points[lastKey].y + 0.1,\n\t\t\t}\n\t\t\treturn next\n\t\t}\n\t\treturn\n\t}\n\n\toverride onHandleDrag(shape: TLLineShape, { handle }: TLHandleDragInfo<TLLineShape>) {\n\t\tconst newPoint = maybeSnapToGrid(new Vec(handle.x, handle.y), this.editor)\n\t\treturn {\n\t\t\t...shape,\n\t\t\tprops: {\n\t\t\t\t...shape.props,\n\t\t\t\tpoints: {\n\t\t\t\t\t...shape.props.points,\n\t\t\t\t\t[handle.id]: { id: handle.id, index: handle.index, x: newPoint.x, y: newPoint.y },\n\t\t\t\t},\n\t\t\t},\n\t\t}\n\t}\n\n\toverride onHandleDragStart(shape: TLLineShape, { handle }: TLHandleDragInfo<TLLineShape>) {\n\t\t// For line shapes, if we're dragging a \"create\" handle, then\n\t\t// create a new vertex handle at that point; and make this handle\n\t\t// the handle that we're dragging.\n\t\tif (handle.type === 'create') {\n\t\t\treturn {\n\t\t\t\t...shape,\n\t\t\t\tprops: {\n\t\t\t\t\t...shape.props,\n\t\t\t\t\tpoints: {\n\t\t\t\t\t\t...shape.props.points,\n\t\t\t\t\t\t[handle.index]: { id: handle.index, index: handle.index, x: handle.x, y: handle.y },\n\t\t\t\t\t},\n\t\t\t\t},\n\t\t\t}\n\t\t}\n\t\treturn\n\t}\n\n\tcomponent(shape: TLLineShape) {\n\t\treturn (\n\t\t\t<SVGContainer style={{ minWidth: 50, minHeight: 50 }}>\n\t\t\t\t<LineShapeSvg shape={shape} />\n\t\t\t</SVGContainer>\n\t\t)\n\t}\n\n\tindicator(shape: TLLineShape) {\n\t\tconst strokeWidth = STROKE_SIZES[shape.props.size] * shape.props.scale\n\t\tconst path = getPathForLineShape(shape)\n\t\tconst { dash } = shape.props\n\n\t\treturn path.toSvg({\n\t\t\tstyle: dash === 'draw' ? 'draw' : 'solid',\n\t\t\tstrokeWidth: 1,\n\t\t\tpasses: 1,\n\t\t\trandomSeed: shape.id,\n\t\t\toffset: 0,\n\t\t\troundness: strokeWidth * 2,\n\t\t\tprops: { strokeWidth: undefined },\n\t\t})\n\t}\n\n\toverride toSvg(shape: TLLineShape) {\n\t\treturn <LineShapeSvg shouldScale shape={shape} />\n\t}\n\n\toverride getHandleSnapGeometry(shape: TLLineShape): HandleSnapGeometry {\n\t\tconst points = linePointsToArray(shape)\n\t\treturn {\n\t\t\tpoints,\n\t\t\tgetSelfSnapPoints: (handle) => {\n\t\t\t\tconst index = this.getHandles(shape)\n\t\t\t\t\t.filter((h) => h.type === 'vertex')\n\t\t\t\t\t.findIndex((h) => h.id === handle.id)!\n\n\t\t\t\t// We want to skip the current and adjacent handles\n\t\t\t\treturn points.filter((_, i) => Math.abs(i - index) > 1).map(Vec.From)\n\t\t\t},\n\t\t\tgetSelfSnapOutline: (handle) => {\n\t\t\t\t// We want to skip the segments that include the handle, so\n\t\t\t\t// find the index of the handle that shares the same index property\n\t\t\t\t// as the initial dragging handle; this catches a quirk of create handles\n\t\t\t\tconst index = this.getHandles(shape)\n\t\t\t\t\t.filter((h) => h.type === 'vertex')\n\t\t\t\t\t.findIndex((h) => h.id === handle.id)!\n\n\t\t\t\t// Get all the outline segments from the shape that don't include the handle\n\t\t\t\tconst segments = this.getGeometry(shape)\n\t\t\t\t\t.getSegments()\n\t\t\t\t\t.filter((_, i) => i !== index - 1 && i !== index)\n\n\t\t\t\tif (!segments.length) return null\n\t\t\t\treturn new Group2d({ children: segments })\n\t\t\t},\n\t\t}\n\t}\n\toverride getInterpolatedProps(\n\t\tstartShape: TLLineShape,\n\t\tendShape: TLLineShape,\n\t\tt: number\n\t): TLLineShape['props'] {\n\t\tconst startPoints = linePointsToArray(startShape)\n\t\tconst endPoints = linePointsToArray(endShape)\n\n\t\tconst pointsToUseStart: TLLineShapePoint[] = []\n\t\tconst pointsToUseEnd: TLLineShapePoint[] = []\n\n\t\tlet index = ZERO_INDEX_KEY\n\n\t\tif (startPoints.length > endPoints.length) {\n\t\t\t// we'll need to expand points\n\t\t\tfor (let i = 0; i < startPoints.length; i++) {\n\t\t\t\tpointsToUseStart[i] = { ...startPoints[i] }\n\t\t\t\tif (endPoints[i] === undefined) {\n\t\t\t\t\tpointsToUseEnd[i] = { ...endPoints[endPoints.length - 1], id: index }\n\t\t\t\t} else {\n\t\t\t\t\tpointsToUseEnd[i] = { ...endPoints[i], id: index }\n\t\t\t\t}\n\t\t\t\tindex = getIndexAbove(index)\n\t\t\t}\n\t\t} else if (endPoints.length > startPoints.length) {\n\t\t\t// we'll need to converge points\n\t\t\tfor (let i = 0; i < endPoints.length; i++) {\n\t\t\t\tpointsToUseEnd[i] = { ...endPoints[i] }\n\t\t\t\tif (startPoints[i] === undefined) {\n\t\t\t\t\tpointsToUseStart[i] = {\n\t\t\t\t\t\t...startPoints[startPoints.length - 1],\n\t\t\t\t\t\tid: index,\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tpointsToUseStart[i] = { ...startPoints[i], id: index }\n\t\t\t\t}\n\t\t\t\tindex = getIndexAbove(index)\n\t\t\t}\n\t\t} else {\n\t\t\t// noop, easy\n\t\t\tfor (let i = 0; i < endPoints.length; i++) {\n\t\t\t\tpointsToUseStart[i] = startPoints[i]\n\t\t\t\tpointsToUseEnd[i] = endPoints[i]\n\t\t\t}\n\t\t}\n\n\t\treturn {\n\t\t\t...(t > 0.5 ? endShape.props : startShape.props),\n\t\t\tpoints: Object.fromEntries(\n\t\t\t\tpointsToUseStart.map((point, i) => {\n\t\t\t\t\tconst endPoint = pointsToUseEnd[i]\n\t\t\t\t\treturn [\n\t\t\t\t\t\tpoint.id,\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\t...point,\n\t\t\t\t\t\t\tx: lerp(point.x, endPoint.x, t),\n\t\t\t\t\t\t\ty: lerp(point.y, endPoint.y, t),\n\t\t\t\t\t\t},\n\t\t\t\t\t]\n\t\t\t\t})\n\t\t\t),\n\t\t\tscale: lerp(startShape.props.scale, endShape.props.scale, t),\n\t\t}\n\t}\n}\n\nfunction linePointsToArray(shape: TLLineShape) {\n\treturn Object.values(shape.props.points).sort(sortByIndex)\n}\n\nconst pathCache = new WeakCache<TLLineShape, PathBuilder>()\nfunction getPathForLineShape(shape: TLLineShape): PathBuilder {\n\treturn pathCache.get(shape, () => {\n\t\tconst points = linePointsToArray(shape).map(Vec.From)\n\n\t\tswitch (shape.props.spline) {\n\t\t\tcase 'cubic': {\n\t\t\t\treturn PathBuilder.cubicSplineThroughPoints(points, { endOffsets: 0 })\n\t\t\t}\n\t\t\tcase 'line': {\n\t\t\t\treturn PathBuilder.lineThroughPoints(points, { endOffsets: 0 })\n\t\t\t}\n\t\t}\n\t})\n}\n\nfunction LineShapeSvg({\n\tshape,\n\tshouldScale = false,\n\tforceSolid = false,\n}: {\n\tshape: TLLineShape\n\tshouldScale?: boolean\n\tforceSolid?: boolean\n}) {\n\tconst theme = useDefaultColorTheme()\n\n\tconst path = getPathForLineShape(shape)\n\tconst { dash, color, size } = shape.props\n\n\tconst scaleFactor = 1 / shape.props.scale\n\n\tconst scale = shouldScale ? scaleFactor : 1\n\n\tconst strokeWidth = STROKE_SIZES[size] * shape.props.scale\n\n\treturn path.toSvg({\n\t\tstyle: dash,\n\t\tstrokeWidth,\n\t\tforceSolid,\n\t\trandomSeed: shape.id,\n\t\tprops: {\n\t\t\ttransform: `scale(${scale})`,\n\t\t\tstroke: getColorValue(theme, color, 'solid'),\n\t\t\tfill: 'none',\n\t\t},\n\t})\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|
|
@@ -242,6 +242,11 @@ class MinimapManager {
|
|
|
242
242
|
const geometry = this.shapeGeometryCache.get(shapeId);
|
|
243
243
|
if (!geometry) continue;
|
|
244
244
|
const len2 = geometry.length;
|
|
245
|
+
const shape = this.editor.getShape(shapeId);
|
|
246
|
+
if (shape) {
|
|
247
|
+
const shapeUtil = this.editor.getShapeUtil(shape.type);
|
|
248
|
+
if (shapeUtil.hideInMinimap?.(shape)) continue;
|
|
249
|
+
}
|
|
245
250
|
if (selectedShapes.has(shapeId)) {
|
|
246
251
|
(0, import_minimap_webgl_setup.appendVertices)(this.gl.selectedShapes, selectedShapeOffset, geometry);
|
|
247
252
|
selectedShapeOffset += len2;
|