@pixerate/editor 0.40.0 → 0.41.0

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.
@@ -1,7 +1,8 @@
1
- import { C as CanvasGradientDef, A as AffineMatrix, B as BezierPathInput, a as BezierPath, S as SvgGradientDef, b as StrokeJoin, c as StrokeCap, d as BezierSegment, P as PlanarMap, e as PathfinderOperation, f as PathfinderShape } from '../pathfinder-DKRcXiLS.cjs';
1
+ import { C as CanvasGradientDef, A as AffineMatrix, B as BezierPathInput, a as BezierPath, S as SvgGradientDef, b as StrokeJoin, c as StrokeCap, d as BezierSegment, P as PlanarMap, e as PathfinderOperation, f as PathfinderShape, G as GradientStop } from '../pathfinder-BSW2ZTO6.cjs';
2
2
  import { P as Point } from '../types-BFkYA4eF.cjs';
3
3
  import { H as HistoryManager } from '../HistoryManager-DeQQMBCj.cjs';
4
4
  import { C as CommandSpec } from '../registry-D0GADKc7.cjs';
5
+ import { A as AnimationEasing } from '../easing-DTmX99QG.cjs';
5
6
  import '../types-DsiXGmjo.cjs';
6
7
  import '../schema-DYDGdYL9.cjs';
7
8
 
@@ -132,16 +133,56 @@ interface VectorNodeBase {
132
133
  * them into the geometry, so stroke widths and the rotated selection box stay exact.
133
134
  */
134
135
  transform?: VectorMatrix;
136
+ /**
137
+ * An in-between a blend group generated from its keys. Steps are rebuilt whenever a key or
138
+ * the blend options change, and are locked (clicks select the blend group).
139
+ */
140
+ blendStep?: boolean;
135
141
  }
136
142
  /** A shape made of one or more subpaths (holes and compound shapes included). */
137
143
  interface VectorPathNode extends VectorNodeBase, VectorStyle {
138
144
  type: 'path';
139
145
  subpaths: VectorSubpath[];
140
146
  }
147
+ /**
148
+ * How a blend spaces its in-betweens: a number of `steps` between each pair of keys, a fixed
149
+ * `distance` between steps along the spine, or `smoothColor` (as many steps as the colours
150
+ * need for a smooth ramp; by distance when the colours match).
151
+ */
152
+ type VectorBlendSpacing = 'steps' | 'distance' | 'smoothColor';
153
+ declare const VECTOR_BLEND_SPACINGS: readonly VectorBlendSpacing[];
154
+ /** Settings of a blend. */
155
+ interface VectorBlendOptions {
156
+ /** Default `steps`. */
157
+ spacing?: VectorBlendSpacing;
158
+ /** Steps between each pair of keys with `steps` spacing (default 5). */
159
+ steps?: number;
160
+ /** Distance between steps along the spine with `distance` spacing (default 20). */
161
+ distance?: number;
162
+ /** Turn the steps with the spine's direction (default `false`: they keep the keys' orientation). */
163
+ orientToSpine?: boolean;
164
+ /** Move anchors in straight lines instead of the rotation-aware morph (default `false`). */
165
+ linear?: boolean;
166
+ }
167
+ /** A live blend: the group's keys plus how the in-betweens are made and laid out. */
168
+ interface VectorBlend extends VectorBlendOptions {
169
+ /**
170
+ * A replaced spine in the group's space: the steps follow it instead of the straight lines
171
+ * between the keys' centres (the keys sit along it, spread evenly by arc length).
172
+ */
173
+ spine?: VectorSubpath | null;
174
+ /** The anchor of each key's first subpath its blend starts from, by key id (the Blend tool's clicks). */
175
+ starts?: Record<string, number>;
176
+ }
141
177
  /** A group of nodes that select and transform together. */
142
178
  interface VectorGroupNode extends VectorNodeBase {
143
179
  type: 'group';
144
180
  children: VectorNode[];
181
+ /**
182
+ * Makes the group a live blend: its children that are not `blendStep`s are the keys, in
183
+ * stacking order, and the steps between them are regenerated whenever a key changes.
184
+ */
185
+ blend?: VectorBlend | null;
145
186
  }
146
187
  type VectorNode = VectorPathNode | VectorGroupNode;
147
188
  /** A vector drawing: an artboard and its nodes, bottom to top. */
@@ -174,9 +215,11 @@ interface VectorHandleRef extends VectorAnchorRef {
174
215
  * shape; `scissors` cuts a path at a point, `knife` cuts filled shapes along a freehand stroke,
175
216
  * `eraser` rubs out the area under one and `width` drags a stroke's width at a point.
176
217
  * `shapeBuilder` merges (Alt: deletes) the faces the selected shapes make, and `paintBucket`
177
- * fills the region the visible outlines enclose around a click with a new shape.
218
+ * fills the region the visible outlines enclose around a click with a new shape. `blend`
219
+ * blends the shape clicked first into the one clicked next (clicking an anchor of a closed path
220
+ * starts the blend there).
178
221
  */
179
- type VectorTool = 'select' | 'direct' | 'pen' | 'pencil' | 'rect' | 'ellipse' | 'polygon' | 'star' | 'line' | 'scissors' | 'knife' | 'eraser' | 'width' | 'shapeBuilder' | 'paintBucket';
222
+ type VectorTool = 'select' | 'direct' | 'pen' | 'pencil' | 'rect' | 'ellipse' | 'polygon' | 'star' | 'line' | 'scissors' | 'knife' | 'eraser' | 'width' | 'shapeBuilder' | 'paintBucket' | 'blend';
180
223
  declare const VECTOR_TOOLS: readonly VectorTool[];
181
224
  /** Keyboard modifiers held during a pointer event. */
182
225
  interface VectorModifiers {
@@ -1089,6 +1132,10 @@ interface VectorEditorState {
1089
1132
  pointer: Vec2 | null;
1090
1133
  /** Shape Builder and paint bucket highlight: faces, line pieces and the gesture's trail. */
1091
1134
  builder: VectorBuilderPreview | null;
1135
+ /** The Blend tool's first click: the shape (and anchor of its first subpath) the next click blends from. */
1136
+ blendStart: VectorBlendStart | null;
1137
+ /** Options new blends get. */
1138
+ blendDefaults: VectorBlendOptions;
1092
1139
  canUndo: boolean;
1093
1140
  canRedo: boolean;
1094
1141
  undoLabel: string;
@@ -1102,6 +1149,22 @@ type VectorActionResult = {
1102
1149
  ok: false;
1103
1150
  message: string;
1104
1151
  };
1152
+ /** The shape the Blend tool blends from (its first click). */
1153
+ interface VectorBlendStart {
1154
+ nodeId: string;
1155
+ /** The clicked anchor of its first subpath, or null for the shape as a whole. */
1156
+ anchor: number | null;
1157
+ }
1158
+ /** Blend settings and options of `VectorEditorController.blend`. */
1159
+ interface VectorBlendInput extends VectorBlendOptions {
1160
+ /** Nodes to blend (default: the selection), in stacking order unless `keepOrder`. */
1161
+ ids?: readonly string[];
1162
+ /** Blend in the order given instead of stacking order. */
1163
+ keepOrder?: boolean;
1164
+ /** Start anchor of each key's first subpath, by key id. */
1165
+ starts?: Record<string, number>;
1166
+ name?: string;
1167
+ }
1105
1168
  /**
1106
1169
  * What the Shape Builder or paint bucket highlights, in document units: the faces (filled paths
1107
1170
  * as SVG path data) under the pointer or touched by the drag, the line pieces an erase would
@@ -1325,6 +1388,9 @@ declare class VectorEditorController {
1325
1388
  /** Paint bucket map of the visible outlines. */
1326
1389
  private fillCache;
1327
1390
  private builderPreview;
1391
+ private blendStart;
1392
+ /** Options new blends get (the toolbars edit them along with the selected blend's). */
1393
+ private blendDefaults;
1328
1394
  /** What the highlight shows, to skip notifying when the pointer stays over the same face. */
1329
1395
  private builderHoverKey;
1330
1396
  private readonly createId;
@@ -1346,6 +1412,8 @@ declare class VectorEditorController {
1346
1412
  getDocument(): VectorDocument;
1347
1413
  getNode(id: string): VectorNode | undefined;
1348
1414
  private computeState;
1415
+ /** `doc` with its blends' steps brought up to date (the same object when they already are). */
1416
+ private refreshed;
1349
1417
  private notify;
1350
1418
  private boundsOf;
1351
1419
  private frameOf;
@@ -1634,6 +1702,44 @@ declare class VectorEditorController {
1634
1702
  ids?: readonly string[];
1635
1703
  }): string[];
1636
1704
  /** The Shape Builder map of the selected (or given) paths, cached per document and selection. */
1705
+ /** Selected (or given) blend groups; a selected key or step counts as its blend. */
1706
+ private blendTargets;
1707
+ /**
1708
+ * Blends two or more selected (or given) paths or groups: they become the keys of a live
1709
+ * blend group (bottom to top, or in the order given with `keepOrder`) whose in-betweens are
1710
+ * regenerated whenever a key or the options change. The keys must share a parent. Returns
1711
+ * the blend group's id, or null.
1712
+ */
1713
+ blend(input?: VectorBlendInput): string | null;
1714
+ /** Sets the options new blends get (spacing, steps, distance, orientation, morph). */
1715
+ setBlendDefaults(patch: Partial<VectorBlendOptions>): void;
1716
+ /**
1717
+ * Adds a node as the last key of a blend (it must share the blend's parent); `start` is the
1718
+ * anchor of its first subpath the blend starts from. One undo step.
1719
+ */
1720
+ addBlendKey(blendId: string, nodeId: string, options?: {
1721
+ start?: number | null;
1722
+ }): VectorActionResult;
1723
+ /** Changes the spacing, steps, distance, orientation or morph of the selected (or given) blends. */
1724
+ setBlendOptions(patch: Partial<VectorBlendOptions>, options?: {
1725
+ ids?: readonly string[];
1726
+ }): VectorActionResult;
1727
+ /** Expand: turns the selected (or given) blends into plain groups of their keys and steps. Returns their ids. */
1728
+ expandBlend(options?: {
1729
+ ids?: readonly string[];
1730
+ }): string[];
1731
+ /** Release: replaces the selected (or given) blends with their keys (and a replaced spine as a path). */
1732
+ releaseBlend(options?: {
1733
+ ids?: readonly string[];
1734
+ }): string[];
1735
+ /**
1736
+ * Replace Spine: the selected blend's steps follow the selected path instead of the straight
1737
+ * lines between its keys. The path's first subpath becomes the spine (the path is removed)
1738
+ * and the keys move onto it, spread evenly by arc length.
1739
+ */
1740
+ replaceBlendSpine(options?: {
1741
+ ids?: readonly string[];
1742
+ }): VectorActionResult;
1637
1743
  private shapeBuilderMap;
1638
1744
  /** The faces the Shape Builder offers for the selected (or given) paths (document units). */
1639
1745
  getShapeBuilderFaces(options?: {
@@ -1838,6 +1944,10 @@ declare class VectorEditorController {
1838
1944
  private sameHover;
1839
1945
  /** Primary button down on the canvas at `screen` (pixels relative to the canvas). */
1840
1946
  pointerDown(screen: Vec2, input?: VectorPointerInput): void;
1947
+ /** The shape under the pointer for the Blend tool, and the anchor of its first subpath under it. */
1948
+ private blendHit;
1949
+ /** Blend tool: the first click picks the shape to blend from, the next one blends it into the shape clicked. */
1950
+ private downBlend;
1841
1951
  private downSelect;
1842
1952
  private downDirect;
1843
1953
  private downPen;
@@ -2062,6 +2172,29 @@ interface VectorOverlayRenderData {
2062
2172
  lines: string[];
2063
2173
  trail: string | null;
2064
2174
  } | null;
2175
+ /**
2176
+ * Blends (screen space): the spine of each selected blend (`d`, draw it dashed; `keys` are
2177
+ * where its keys sit on it; `replaced` when it is a replaced spine) and, with the Blend tool,
2178
+ * the outline of the shape it blends from (`start`, with the clicked anchor) and the anchors
2179
+ * of the first subpath under the pointer (click one to start the blend there).
2180
+ */
2181
+ blend: {
2182
+ spines: {
2183
+ id: string;
2184
+ d: string;
2185
+ keys: Vec2[];
2186
+ replaced: boolean;
2187
+ }[];
2188
+ start: {
2189
+ d: string;
2190
+ anchor: Vec2 | null;
2191
+ } | null;
2192
+ anchors: {
2193
+ x: number;
2194
+ y: number;
2195
+ hovered: boolean;
2196
+ }[];
2197
+ };
2065
2198
  /** A short status, e.g. "W 120 × H 80" or "45°". */
2066
2199
  status: string | null;
2067
2200
  }
@@ -2076,6 +2209,28 @@ declare function getVectorSceneRenderData(state: Pick<VectorEditorState, 'docume
2076
2209
  }): VectorSceneRenderData;
2077
2210
  /** The editing overlay in screen pixels. Render it on top of the scene, untransformed. */
2078
2211
  declare function getVectorOverlayRenderData(state: VectorEditorState): VectorOverlayRenderData;
2212
+ /** What the Blend controls of a toolbar or style panel show. */
2213
+ interface VectorBlendControls {
2214
+ /** Ids of the selected blends (a selected key counts as its blend). */
2215
+ ids: string[];
2216
+ /** The first selected blend's options, or the options new blends get. */
2217
+ options: Required<VectorBlendOptions>;
2218
+ /** Two or more shapes that share a parent are selected: Blend can run. */
2219
+ canBlend: boolean;
2220
+ /** One blend and one path are selected: Replace Spine can run. */
2221
+ canReplaceSpine: boolean;
2222
+ /** The first selected blend follows a replaced spine. */
2223
+ hasSpine: boolean;
2224
+ }
2225
+ /** State of the Blend controls for the current selection. */
2226
+ declare function getVectorBlendControls(state: Pick<VectorEditorState, 'document' | 'selection' | 'blendDefaults'>): VectorBlendControls;
2227
+ /**
2228
+ * Applies blend options from a toolbar: to the selected blends (one undo step) and to the
2229
+ * options new blends get, so the controls keep showing what was picked.
2230
+ */
2231
+ declare function applyVectorBlendOptions(controller: VectorEditorController, patch: Partial<VectorBlendOptions>): void;
2232
+ /** Labels of the blend spacing modes, for toolbars. */
2233
+ declare const VECTOR_BLEND_SPACING_LABELS: Readonly<Record<VectorBlendSpacing, string>>;
2079
2234
  /** Colours and sizes (screen pixels) the bundled canvases draw the overlay with. */
2080
2235
  declare const VECTOR_OVERLAY_THEME: {
2081
2236
  readonly accent: "#0ea5e9";
@@ -2252,6 +2407,18 @@ interface VectorNodeListing {
2252
2407
  /** SVG path data (paths only). */
2253
2408
  d?: string;
2254
2409
  children?: number;
2410
+ /** A blend group's options (its steps are listed as children with `blendStep`). */
2411
+ blend?: {
2412
+ spacing: string;
2413
+ steps: number;
2414
+ distance: number;
2415
+ orientToSpine: boolean;
2416
+ linear: boolean;
2417
+ spine: boolean;
2418
+ keys: string[];
2419
+ };
2420
+ /** An in-between generated by a blend (locked; changes come from its keys). */
2421
+ blendStep?: boolean;
2255
2422
  }
2256
2423
  /**
2257
2424
  * Palette and agent commands for a vector editor: list, select, add shapes and paths, style,
@@ -2712,4 +2879,240 @@ declare function planShapeBuilder(m: VectorShapeBuilderMap, touched: VectorBuild
2712
2879
  */
2713
2880
  declare function vectorFillMap(doc: VectorDocument, gap?: number): PlanarMap | null;
2714
2881
 
2715
- export { type AddVectorNodeOptions, AffineMatrix, DEFAULT_VECTOR_PATH_EDIT, DEFAULT_VECTOR_SNAP, IDENTITY_MATRIX, KAPPA, LazyMouse, type NearestSegment, type RecognizeInkOptions, SvgGradientDef, VECTOR_ARROWHEADS, VECTOR_ARROWHEAD_LABELS, VECTOR_BUILDER_HATCH_GAP, VECTOR_CLIPBOARD_TYPE, VECTOR_CONSTRUCTION_ANGLES, VECTOR_CORNER_KINDS, VECTOR_CORNER_KIND_LABELS, VECTOR_CORNER_WIDGET_INSET, VECTOR_EDIT_TOGGLES, VECTOR_FILL_GAP, VECTOR_INK_MAX_CORNERS, VECTOR_OVERLAY_THEME, VECTOR_PATHFINDER_ACTIONS, VECTOR_PATHFINDER_LABELS, VECTOR_PATHFINDER_OPERATIONS, VECTOR_PATH_ACTIONS, VECTOR_PENCIL_STRING_PX, VECTOR_PRESSURE_NOMINAL, VECTOR_ROTATE_HANDLE_OFFSET, VECTOR_STROKE_ALIGN_LABELS, VECTOR_STYLE_KEYS, VECTOR_TOOLS, VECTOR_TOOL_GLYPHS, VECTOR_TOOL_SHORTCUTS, VECTOR_TRANSFORM_HANDLES, VECTOR_WIDTH_PRESETS, VECTOR_WIDTH_PRESET_IDS, VECTOR_WIDTH_PROFILE_MAX_POINTS, VECTOR_WIDTH_PROFILE_MAX_SCALE, VECTOR_WIDTH_SAME_T, type VariableStrokeOptions, type Vec2, type VectorActionResult, type VectorAlign, type VectorAnchor, type VectorAnchorRef, type VectorAnchorType, type VectorArrange, type VectorArrowAlign, type VectorArrowhead, type VectorArrowheadShape, type VectorAverageAxis, type VectorBooleanOperation, type VectorBounds, type VectorBuilderHit, type VectorBuilderLinePiece, type VectorBuilderPreview, type VectorBuilderReplacement, type VectorBuilderTouched, type VectorCommandOptions, type VectorCorner, type VectorCornerInfo, type VectorCornerKind, type VectorCornerWidget, type VectorDefaults, type VectorDistribute, type VectorDocument, VectorEditorController, type VectorEditorOptions, type VectorEditorState, type VectorFillRule, type VectorGroupNode, type VectorGuideKind, type VectorGuideLabel, type VectorGuideLine, type VectorHandleRef, type VectorHover, type VectorInkShape, type VectorInteraction, type VectorKeyInput, type VectorLineCap, type VectorLineJoin, type VectorMatrix, type VectorModifiers, type VectorNode, type VectorNodeListing, type VectorOverlayRenderData, type VectorPaint, type VectorPathAction, type VectorPathEditOptions, type VectorPathEntry, type VectorPathNode, type VectorPathfinderAction, type VectorPathfinderOperation, type VectorPathfinderPaint, type VectorPointSnap, type VectorPointerInput, type VectorRectSnap, type VectorRenderAnchor, type VectorRenderCornerWidget, type VectorRenderGroup, type VectorRenderGuideLabel, type VectorRenderGuideLine, type VectorRenderHandle, type VectorRenderNode, type VectorRenderPath, type VectorRenderStrokeParts, type VectorRenderWidthPoint, type VectorScaleSnap, type VectorSceneRenderData, type VectorSegmentRef, type VectorSelectionBoxGeometry, type VectorSelectionFrame, type VectorSelectionStyle, type VectorShapeBuilderFace, type VectorShapeBuilderMap, type VectorShapeBuilderPlan, type VectorShapeBuilderResult, type VectorShapeInput, type VectorSnapGuides, type VectorSnapKind, type VectorSnapLeave, type VectorSnapOptions, VectorSnapTargets, type VectorStrokeAlign, type VectorStrokeParts, type VectorStrokeSpot, type VectorStyle, type VectorSubpath, type VectorSvgExportOptions, type VectorSvgImportOptions, type VectorTaperOptions, type VectorTool, type VectorTransformHandle, type VectorViewport, type VectorWaveOptions, type VectorWidthHandle, type VectorWidthPoint, type VectorWidthPointEdit, type VectorWidthPointRef, type VectorWidthPreset, type VectorWidthPresetInfo, addBuilderHit, applyMatrix, applyMatrixLinear, applyVectorCornersAttribute, arrowheadInset, arrowheadPath, arrowheadWeight, bendSegment, bezierToSubpaths, boundsFromPoints, boundsIntersect, cloneAnchor, cloneSubpath, cloneVectorDocument, cloneVectorNode, collectPathNodes, constrainToLeave, convertAnchor, cornerBisectorPoint, cornerRadiusChange, cornerSetback, createVectorCommands, curvatureMoveAnchor, cutSubpathAt, dashIntervals, decomposeRigid, effectiveStrokeAlign, ellipseSubpath, eraseFromFill, eraseFromOutline, eraserRegion, expandVectorCorners, expandVectorCornersOf, findVectorNode, fitCornerRadius, generateWidthProfile, getAnchor, getAnchorWorld, getEditablePathIds, getTransformHandlePositions, getVectorCornerWidgets, getVectorOverlayRenderData, getVectorSceneRenderData, getVectorSelectionBoxGeometry, getVectorSelectionFrame, getVectorSelectionStyle, getVectorWidthHandles, getVisibleAnchors, getVisibleHandles, hasPaint, hasStrokeExtras, hasVectorCorners, hitTestVectorNode, hitTestVectorNodes, hitTestVectorStroke, inferAnchorType, insertAnchor, insertWidthPoint, invertMatrix, isClosedBezierShape, isIdentityMatrix, isUniformWidthProfile, isVectorTextTarget, joinSubpaths, knifePath, lineSubpath, locateVectorNode, matrixRotation, mirrorWidthProfile, moveAnchorHandle, multiplyMatrices, nearestSegment, nearestStrokePosition, nextVectorCornerKind, nodeMatrix, parseSvgTransform, parseVectorSvg, planShapeBuilder, polygonSubpath, polylineBounds, pressureWidthProfile, recognizeInkShape, rectSubpath, removeAnchorKeepingShape, removeAnchors, removeAnchorsKeepingShape, removeRedundantPoints, removeWidthPoints, reverseSubpath, reverseWidthProfile, rotateMatrix, roundSubpaths, samplePolyline, sanitizeWidthProfile, scaleFor, scaleMatrix, setAnchorCorner, setSubpathCorners, setWidthPoint, simplifyPolyline, smoothSubpath, splitIntoFaces, splitSubpathAt, starSubpath, strokePositionPoint, strokeWidthProfileOf, subpathEnclosesArea, subpathPointAt, subpathSegment, subpathSegmentCount, subpathsToBezier, taperWaveFactor, toVectorKeyInput, toVectorModifiers, toVectorPointerInput, transformVectorNode, translateAnchor, translateMatrix, unionBounds, variableStrokeOutline, variableStrokeRings, vectorBuilderErasedEdges, vectorCornerAt, vectorCorners, vectorCornersAttribute, vectorDiamondPath, vectorDocumentToSvg, vectorFillMap, vectorInkShapeName, vectorNodeBounds, vectorNodeRotation, vectorNodeToBezier, vectorPaintToHex, vectorPaintToSvg, vectorParentMatrix, vectorPathData, vectorPathEntries, vectorPathWorldBezier, vectorPathfinderShape, vectorResizeCursor, vectorResultStyle, vectorShapeBuilderHit, vectorShapeBuilderMap, vectorStrokeLineArea, vectorStrokeOutline, vectorStrokeOutlinePath, vectorStrokeParts, vectorStrokeReach, vectorStrokeSvgParts, vectorStrokeWidthGeometry, vectorToolLabel, vectorWorldMatrix, walkVectorNodes, widthProfileAt, widthProfileFromAttribute, widthProfileMaxScale, widthProfilePreset, widthProfilePresetId, widthProfileToAttribute };
2882
+ /**
2883
+ * Morphing between vector paths: bring two shapes to matching anchors, then compute in-betweens.
2884
+ *
2885
+ * - **Contours** pair up in order. A contour without a partner grows out of (or shrinks into) a
2886
+ * point at the same place relative to the other shape's box. Straight segments become cubics
2887
+ * with handles at a third of the way, so a line bends smoothly into a curve.
2888
+ * - **Anchors** are inserted by arc length with de Casteljau splits, so both contours of a pair
2889
+ * keep their exact outline and get the same number of segments, spread over the segments in
2890
+ * proportion to their length.
2891
+ * - **Correspondence**: the closed side of each pair is turned to the cyclic start that costs
2892
+ * least — the position differences left after the best-fit rotation (both shapes centred and
2893
+ * scaled to unit size), a little for the turn, plus the χ² distance of log-polar
2894
+ * shape-context histograms (Belongie, Malik & Puzicha, PAMI 2002; angles taken from the
2895
+ * contour's direction) — and the winding is chosen once for all contours (the first closed
2896
+ * pair turns the same way), so a nonzero fill keeps its holes.
2897
+ * - **In-betweens** follow the shapes' best-fit rotation and scale (Procrustes), with the
2898
+ * leftover difference blended in linearly, so a turning shape turns instead of collapsing.
2899
+ * - **Paint**: colours mix in OKLab, gradients of one kind resample their stops to a common
2900
+ * set, a missing paint fades from transparent; stroke width, opacity, dashes, arrowhead
2901
+ * scales and width profiles interpolate, and the rest switches halfway.
2902
+ * - **Transforms**: both shapes are blended in their parent's space; the in-between's rigid
2903
+ * `transform` interpolates as a rotation (the short way round) plus a translation.
2904
+ *
2905
+ * Live corners are cut into the geometry first, so rounded corners morph as curves.
2906
+ */
2907
+
2908
+ interface VectorMorphOptions {
2909
+ /**
2910
+ * Move anchors in straight lines instead of following the shapes' best-fit rotation and
2911
+ * scale. Default `false`.
2912
+ */
2913
+ linear?: boolean;
2914
+ /** 0–1: how much the rotation-aware path outweighs the straight one (default 1). */
2915
+ rigidity?: number;
2916
+ /** Fewest segments each contour pair gets (default 16). */
2917
+ minSegments?: number;
2918
+ /** At most this far apart (document units) along the longer contour, when set. */
2919
+ spacing?: number | null;
2920
+ /** Most segments a contour pair gets (default 400). */
2921
+ maxSegments?: number;
2922
+ /** Search the start anchor of closed contours (default `true`); off keeps the stored starts. */
2923
+ matchStart?: boolean;
2924
+ /** Compare shape-context histograms when choosing starts (default `true`). */
2925
+ shapeContext?: boolean;
2926
+ /**
2927
+ * The anchor each shape's first subpath starts from (the Blend tool's clicks). A closed
2928
+ * subpath turns round to it; an open one clicked at its last anchor runs backwards.
2929
+ */
2930
+ starts?: readonly [number | null | undefined, number | null | undefined];
2931
+ /** Id of the in-between (default: the first shape's id). */
2932
+ id?: string;
2933
+ }
2934
+ /** Two shapes prepared once; `at(t)` interpolates (0 = `a`, 1 = `b`). */
2935
+ interface VectorMorph {
2936
+ at(t: number): VectorNode;
2937
+ }
2938
+ /** A subpath as cubics. A closed contour's last point repeats its first. */
2939
+ interface VectorMorphContour {
2940
+ closed: boolean;
2941
+ pts: Point[];
2942
+ }
2943
+ /** A subpath mapped by `m` as cubics (lines with handles at thirds), or null when empty. */
2944
+ declare function subpathToMorphContour(sp: VectorSubpath, m?: AffineMatrix): VectorMorphContour | null;
2945
+ /** A contour back to a subpath (`m` maps it out of the morph's space). Straight cubics become lines. */
2946
+ declare function morphContourToSubpath(c: VectorMorphContour, m?: AffineMatrix, closed?: boolean): VectorSubpath;
2947
+ /**
2948
+ * Exactly the same outline with `segments` cubics (at least as many as it has), the new
2949
+ * anchors spread over its segments in proportion to their arc length (largest remainder)
2950
+ * and each segment split into pieces of equal arc length. Also returns where each original
2951
+ * anchor went.
2952
+ */
2953
+ declare function refineMorphContour(c: VectorMorphContour, segments: number): {
2954
+ contour: VectorMorphContour;
2955
+ anchors: number[];
2956
+ };
2957
+ /** The same contour run backwards (a closed one keeps its start anchor). */
2958
+ declare function reverseMorphContour(c: VectorMorphContour): VectorMorphContour;
2959
+ /** A closed contour starting at anchor `s` (deckcraft's `turn`). */
2960
+ declare function turnMorphContour(c: VectorMorphContour, s: number): VectorMorphContour;
2961
+ /** Two shapes' contours with matching structure: same count, and per pair the same segments. */
2962
+ interface VectorMorphCorrespondence {
2963
+ a: VectorMorphContour[];
2964
+ b: VectorMorphContour[];
2965
+ /** Whether `b` runs backwards relative to its stored direction. */
2966
+ reversed: boolean;
2967
+ }
2968
+ /**
2969
+ * Gives two lists of contours the same structure with matching anchors (see the module notes).
2970
+ * Contours pair in order; one without a partner meets a point.
2971
+ */
2972
+ declare function correspondMorphContours(a: readonly VectorMorphContour[], b: readonly VectorMorphContour[], options?: VectorMorphOptions): VectorMorphCorrespondence;
2973
+ /**
2974
+ * How many pairs of straight anchor paths (from `a`'s anchor i to `b`'s anchor i) cross: a
2975
+ * sanity measure of a correspondence — good matches don't make anchors pass through each other.
2976
+ */
2977
+ declare function morphPathsCross(a: readonly VectorMorphContour[], b: readonly VectorMorphContour[]): number;
2978
+ /** The similarity (rotation θ, scale s, centroids) that best maps `a`'s anchors onto `b`'s. */
2979
+ interface Similarity {
2980
+ ca: Point;
2981
+ cb: Point;
2982
+ theta: number;
2983
+ s: number;
2984
+ }
2985
+ /**
2986
+ * Corresponded contours at `u`: each point carried by the similarity interpolated to `u`
2987
+ * (rotation θu, scale sᵘ, centroid moving straight), plus `u` of what the full similarity
2988
+ * leaves over, blended with the straight path by `rigidity`.
2989
+ */
2990
+ declare function interpolateMorphContours(a: readonly VectorMorphContour[], b: readonly VectorMorphContour[], u: number, options?: Pick<VectorMorphOptions, 'linear' | 'rigidity'> & {
2991
+ similarity?: Similarity;
2992
+ }): VectorMorphContour[];
2993
+ /**
2994
+ * Interpolates two rigid matrices as a rotation (the shorter way round) plus a translation.
2995
+ * Any scale or skew is interpolated linearly in the rotated frame.
2996
+ */
2997
+ declare function interpolateRigidMatrix(a: AffineMatrix, b: AffineMatrix, t: number): AffineMatrix;
2998
+ /** Two colours mixed in OKLab (premultiplied alpha); unreadable colours switch halfway. */
2999
+ declare function interpolateVectorColor(a: string, b: string, t: number): string;
3000
+ /** A gradient's stops resampled at `offsets`, each painting what the gradient paints there. */
3001
+ declare function resampleGradientStops(g: CanvasGradientDef, offsets: readonly number[]): GradientStop[];
3002
+ /**
3003
+ * Interpolates paints: colours in OKLab, gradients of one kind with their stops resampled to a
3004
+ * common set, a colour and a gradient through a gradient of that colour, and a missing paint
3005
+ * fading from transparent. Gradients of different kinds switch halfway.
3006
+ */
3007
+ declare function interpolateVectorPaint(a: VectorPaint | undefined, b: VectorPaint | undefined, t: number): VectorPaint | undefined;
3008
+ /** Width profiles at every position either has a point (no profile is uniform). */
3009
+ declare function interpolateWidthProfiles(a: readonly VectorWidthPoint[] | null | undefined, b: readonly VectorWidthPoint[] | null | undefined, t: number): VectorWidthPoint[] | null;
3010
+ /**
3011
+ * Interpolated style of two paths: paints, stroke width, dashes, arrowhead scales and width
3012
+ * profiles mix; caps, joins, the fill rule, alignment and arrowheads switch halfway.
3013
+ */
3014
+ declare function interpolateVectorStyle(a: VectorStyle, b: VectorStyle, t: number): VectorStyle;
3015
+ /**
3016
+ * Prepares two shapes for interpolation. Two paths morph directly; with a group on either side
3017
+ * the paths inside pair up in stacking order and those without a partner grow out of a point.
3018
+ * Shapes are blended in their parent's space.
3019
+ */
3020
+ declare function createVectorMorph(a: VectorNode, b: VectorNode, options?: VectorMorphOptions): VectorMorph;
3021
+ /**
3022
+ * The in-between of two shapes at `t` (0 = `a`, 1 = `b`). Prepare once with
3023
+ * `createVectorMorph` when interpolating the same pair at many `t`.
3024
+ */
3025
+ declare function interpolateVectorPaths(a: VectorNode, b: VectorNode, t: number, options?: VectorMorphOptions): VectorNode;
3026
+ /** A keyframe of a path track: a shape at a time (ms), with the easing of the segment leaving it. */
3027
+ interface VectorPathKeyframe {
3028
+ time: number;
3029
+ value: VectorNode;
3030
+ easing?: AnimationEasing;
3031
+ }
3032
+ /**
3033
+ * A path track's shape at `time`: before the first keyframe its shape, after the last the
3034
+ * last; in between the two keyframes morph (prepared once per pair and cached) at the eased
3035
+ * fraction. Easings that overshoot are clamped to the keys. `null` without keyframes.
3036
+ */
3037
+ declare function evaluateVectorPathKeyframes(keyframes: readonly VectorPathKeyframe[], time: number, options?: VectorMorphOptions): VectorNode | null;
3038
+
3039
+ /**
3040
+ * Live blend groups: a group whose `blend` is set keeps its key shapes as children and
3041
+ * regenerates the in-betweens (`blendStep` children, locked) whenever a key or the options
3042
+ * change. Steps follow the straight lines between the keys' centres, or a replaced spine.
3043
+ *
3044
+ * - **Spacing** (`vectorBlendStepCount`): a number of steps per pair of keys, a fixed distance
3045
+ * along the spine, or smooth colour — one step per two levels of the largest colour channel
3046
+ * difference, by distance when the colours match.
3047
+ * - **Spine**: with a replaced spine the keys sit along it, spread evenly by arc length; each
3048
+ * step is moved by how far the spine bends away from the chord between its keys, so a step
3049
+ * lands on the spine and the keys stay where they are. Orient to spine also turns the steps
3050
+ * by how much the spine's direction differs from the keys' (keys keep their orientation);
3051
+ * without a replaced spine the steps run straight and keep their orientation.
3052
+ */
3053
+
3054
+ declare const DEFAULT_VECTOR_BLEND_STEPS = 5;
3055
+ declare const DEFAULT_VECTOR_BLEND_DISTANCE = 20;
3056
+ /** Most steps between two keys. */
3057
+ declare const VECTOR_BLEND_MAX_STEPS = 1000;
3058
+ /** Most steps smooth colour makes between two keys. */
3059
+ declare const VECTOR_BLEND_MAX_SMOOTH_STEPS = 256;
3060
+ /** Whether a node is a live blend group. */
3061
+ declare function isVectorBlendGroup(node: VectorNode | null | undefined): node is VectorGroupNode & {
3062
+ blend: VectorBlend;
3063
+ };
3064
+ /** The keys of a blend group (its children that are not generated steps), in stacking order. */
3065
+ declare function vectorBlendKeys(group: VectorGroupNode): VectorNode[];
3066
+ /** The full options of a blend, defaults filled in. */
3067
+ declare function resolveVectorBlendOptions(options: VectorBlendOptions | null | undefined): Required<VectorBlendOptions>;
3068
+ /** Largest channel difference (0–1) between the colours of two shapes' fills and strokes. */
3069
+ declare function vectorBlendColorDistance(a: VectorNode, b: VectorNode): number;
3070
+ /** Number of in-betweens between two keys `length` apart along the spine. */
3071
+ declare function vectorBlendStepCount(a: VectorNode, b: VectorNode, options: VectorBlendOptions | null | undefined, length: number): number;
3072
+ /** A subpath flattened to a polyline with cumulative arc lengths and tangent angles. */
3073
+ interface VectorBlendRail {
3074
+ pts: Point[];
3075
+ cum: number[];
3076
+ angles: number[];
3077
+ total: number;
3078
+ closed: boolean;
3079
+ }
3080
+ /** Flattens a spine subpath (32 samples per curve). Null with fewer than two distinct points. */
3081
+ declare function vectorBlendRail(sp: VectorSubpath): VectorBlendRail | null;
3082
+ /** Point and direction (radians) at arc length `s` (clamped; a closed rail wraps). */
3083
+ declare function vectorBlendRailAt(rail: VectorBlendRail, s: number): {
3084
+ point: Point;
3085
+ angle: number;
3086
+ };
3087
+ /**
3088
+ * The spine of a blend in the group's space and where along it each key sits: the replaced
3089
+ * spine (keys spread evenly by arc length) or the straight lines between the keys' centres.
3090
+ */
3091
+ declare function vectorBlendSpine(group: VectorGroupNode): {
3092
+ spine: VectorSubpath;
3093
+ rail: VectorBlendRail;
3094
+ stops: number[];
3095
+ replaced: boolean;
3096
+ } | null;
3097
+ /** Where key `i` of a blend with spine `spine` should sit: its stop on the spine. */
3098
+ declare function vectorBlendKeyTargets(group: VectorGroupNode): Point[];
3099
+ /**
3100
+ * A blend group's children with fresh steps: each key followed by the in-betweens to the next,
3101
+ * bottom to top. Groups with fewer than two keys keep just their keys.
3102
+ */
3103
+ declare function generateVectorBlendChildren(group: VectorGroupNode): VectorNode[];
3104
+ /**
3105
+ * Nodes with every blend group's steps brought up to date (nested blends first). Returns the
3106
+ * same array when nothing changed; steps are cached per set of keys, so calling this after
3107
+ * every edit is cheap.
3108
+ */
3109
+ declare function refreshVectorBlends(nodes: readonly VectorNode[]): VectorNode[];
3110
+ /** Expand: the blend as a plain group of its keys and steps (steps get fresh ids). */
3111
+ declare function expandVectorBlend(group: VectorGroupNode, newId: () => string): VectorGroupNode;
3112
+ /**
3113
+ * Release: the blend's keys in the group's parent space (the group's transform and opacity
3114
+ * applied), followed by the replaced spine as an unpainted path when there is one.
3115
+ */
3116
+ declare function releaseVectorBlend(group: VectorGroupNode, newId: () => string): VectorNode[];
3117
+
3118
+ export { type AddVectorNodeOptions, AffineMatrix, DEFAULT_VECTOR_BLEND_DISTANCE, DEFAULT_VECTOR_BLEND_STEPS, DEFAULT_VECTOR_PATH_EDIT, DEFAULT_VECTOR_SNAP, IDENTITY_MATRIX, KAPPA, LazyMouse, type NearestSegment, type RecognizeInkOptions, SvgGradientDef, VECTOR_ARROWHEADS, VECTOR_ARROWHEAD_LABELS, VECTOR_BLEND_MAX_SMOOTH_STEPS, VECTOR_BLEND_MAX_STEPS, VECTOR_BLEND_SPACINGS, VECTOR_BLEND_SPACING_LABELS, VECTOR_BUILDER_HATCH_GAP, VECTOR_CLIPBOARD_TYPE, VECTOR_CONSTRUCTION_ANGLES, VECTOR_CORNER_KINDS, VECTOR_CORNER_KIND_LABELS, VECTOR_CORNER_WIDGET_INSET, VECTOR_EDIT_TOGGLES, VECTOR_FILL_GAP, VECTOR_INK_MAX_CORNERS, VECTOR_OVERLAY_THEME, VECTOR_PATHFINDER_ACTIONS, VECTOR_PATHFINDER_LABELS, VECTOR_PATHFINDER_OPERATIONS, VECTOR_PATH_ACTIONS, VECTOR_PENCIL_STRING_PX, VECTOR_PRESSURE_NOMINAL, VECTOR_ROTATE_HANDLE_OFFSET, VECTOR_STROKE_ALIGN_LABELS, VECTOR_STYLE_KEYS, VECTOR_TOOLS, VECTOR_TOOL_GLYPHS, VECTOR_TOOL_SHORTCUTS, VECTOR_TRANSFORM_HANDLES, VECTOR_WIDTH_PRESETS, VECTOR_WIDTH_PRESET_IDS, VECTOR_WIDTH_PROFILE_MAX_POINTS, VECTOR_WIDTH_PROFILE_MAX_SCALE, VECTOR_WIDTH_SAME_T, type VariableStrokeOptions, type Vec2, type VectorActionResult, type VectorAlign, type VectorAnchor, type VectorAnchorRef, type VectorAnchorType, type VectorArrange, type VectorArrowAlign, type VectorArrowhead, type VectorArrowheadShape, type VectorAverageAxis, type VectorBlend, type VectorBlendControls, type VectorBlendInput, type VectorBlendOptions, type VectorBlendRail, type VectorBlendSpacing, type VectorBlendStart, type VectorBooleanOperation, type VectorBounds, type VectorBuilderHit, type VectorBuilderLinePiece, type VectorBuilderPreview, type VectorBuilderReplacement, type VectorBuilderTouched, type VectorCommandOptions, type VectorCorner, type VectorCornerInfo, type VectorCornerKind, type VectorCornerWidget, type VectorDefaults, type VectorDistribute, type VectorDocument, VectorEditorController, type VectorEditorOptions, type VectorEditorState, type VectorFillRule, type VectorGroupNode, type VectorGuideKind, type VectorGuideLabel, type VectorGuideLine, type VectorHandleRef, type VectorHover, type VectorInkShape, type VectorInteraction, type VectorKeyInput, type VectorLineCap, type VectorLineJoin, type VectorMatrix, type VectorModifiers, type VectorMorph, type VectorMorphContour, type VectorMorphCorrespondence, type VectorMorphOptions, type VectorNode, type VectorNodeListing, type VectorOverlayRenderData, type VectorPaint, type VectorPathAction, type VectorPathEditOptions, type VectorPathEntry, type VectorPathKeyframe, type VectorPathNode, type VectorPathfinderAction, type VectorPathfinderOperation, type VectorPathfinderPaint, type VectorPointSnap, type VectorPointerInput, type VectorRectSnap, type VectorRenderAnchor, type VectorRenderCornerWidget, type VectorRenderGroup, type VectorRenderGuideLabel, type VectorRenderGuideLine, type VectorRenderHandle, type VectorRenderNode, type VectorRenderPath, type VectorRenderStrokeParts, type VectorRenderWidthPoint, type VectorScaleSnap, type VectorSceneRenderData, type VectorSegmentRef, type VectorSelectionBoxGeometry, type VectorSelectionFrame, type VectorSelectionStyle, type VectorShapeBuilderFace, type VectorShapeBuilderMap, type VectorShapeBuilderPlan, type VectorShapeBuilderResult, type VectorShapeInput, type VectorSnapGuides, type VectorSnapKind, type VectorSnapLeave, type VectorSnapOptions, VectorSnapTargets, type VectorStrokeAlign, type VectorStrokeParts, type VectorStrokeSpot, type VectorStyle, type VectorSubpath, type VectorSvgExportOptions, type VectorSvgImportOptions, type VectorTaperOptions, type VectorTool, type VectorTransformHandle, type VectorViewport, type VectorWaveOptions, type VectorWidthHandle, type VectorWidthPoint, type VectorWidthPointEdit, type VectorWidthPointRef, type VectorWidthPreset, type VectorWidthPresetInfo, addBuilderHit, applyMatrix, applyMatrixLinear, applyVectorBlendOptions, applyVectorCornersAttribute, arrowheadInset, arrowheadPath, arrowheadWeight, bendSegment, bezierToSubpaths, boundsFromPoints, boundsIntersect, cloneAnchor, cloneSubpath, cloneVectorDocument, cloneVectorNode, collectPathNodes, constrainToLeave, convertAnchor, cornerBisectorPoint, cornerRadiusChange, cornerSetback, correspondMorphContours, createVectorCommands, createVectorMorph, curvatureMoveAnchor, cutSubpathAt, dashIntervals, decomposeRigid, effectiveStrokeAlign, ellipseSubpath, eraseFromFill, eraseFromOutline, eraserRegion, evaluateVectorPathKeyframes, expandVectorBlend, expandVectorCorners, expandVectorCornersOf, findVectorNode, fitCornerRadius, generateVectorBlendChildren, generateWidthProfile, getAnchor, getAnchorWorld, getEditablePathIds, getTransformHandlePositions, getVectorBlendControls, getVectorCornerWidgets, getVectorOverlayRenderData, getVectorSceneRenderData, getVectorSelectionBoxGeometry, getVectorSelectionFrame, getVectorSelectionStyle, getVectorWidthHandles, getVisibleAnchors, getVisibleHandles, hasPaint, hasStrokeExtras, hasVectorCorners, hitTestVectorNode, hitTestVectorNodes, hitTestVectorStroke, inferAnchorType, insertAnchor, insertWidthPoint, interpolateMorphContours, interpolateRigidMatrix, interpolateVectorColor, interpolateVectorPaint, interpolateVectorPaths, interpolateVectorStyle, interpolateWidthProfiles, invertMatrix, isClosedBezierShape, isIdentityMatrix, isUniformWidthProfile, isVectorBlendGroup, isVectorTextTarget, joinSubpaths, knifePath, lineSubpath, locateVectorNode, matrixRotation, mirrorWidthProfile, morphContourToSubpath, morphPathsCross, moveAnchorHandle, multiplyMatrices, nearestSegment, nearestStrokePosition, nextVectorCornerKind, nodeMatrix, parseSvgTransform, parseVectorSvg, planShapeBuilder, polygonSubpath, polylineBounds, pressureWidthProfile, recognizeInkShape, rectSubpath, refineMorphContour, refreshVectorBlends, releaseVectorBlend, removeAnchorKeepingShape, removeAnchors, removeAnchorsKeepingShape, removeRedundantPoints, removeWidthPoints, resampleGradientStops, resolveVectorBlendOptions, reverseMorphContour, reverseSubpath, reverseWidthProfile, rotateMatrix, roundSubpaths, samplePolyline, sanitizeWidthProfile, scaleFor, scaleMatrix, setAnchorCorner, setSubpathCorners, setWidthPoint, simplifyPolyline, smoothSubpath, splitIntoFaces, splitSubpathAt, starSubpath, strokePositionPoint, strokeWidthProfileOf, subpathEnclosesArea, subpathPointAt, subpathSegment, subpathSegmentCount, subpathToMorphContour, subpathsToBezier, taperWaveFactor, toVectorKeyInput, toVectorModifiers, toVectorPointerInput, transformVectorNode, translateAnchor, translateMatrix, turnMorphContour, unionBounds, variableStrokeOutline, variableStrokeRings, vectorBlendColorDistance, vectorBlendKeyTargets, vectorBlendKeys, vectorBlendRail, vectorBlendRailAt, vectorBlendSpine, vectorBlendStepCount, vectorBuilderErasedEdges, vectorCornerAt, vectorCorners, vectorCornersAttribute, vectorDiamondPath, vectorDocumentToSvg, vectorFillMap, vectorInkShapeName, vectorNodeBounds, vectorNodeRotation, vectorNodeToBezier, vectorPaintToHex, vectorPaintToSvg, vectorParentMatrix, vectorPathData, vectorPathEntries, vectorPathWorldBezier, vectorPathfinderShape, vectorResizeCursor, vectorResultStyle, vectorShapeBuilderHit, vectorShapeBuilderMap, vectorStrokeLineArea, vectorStrokeOutline, vectorStrokeOutlinePath, vectorStrokeParts, vectorStrokeReach, vectorStrokeSvgParts, vectorStrokeWidthGeometry, vectorToolLabel, vectorWorldMatrix, walkVectorNodes, widthProfileAt, widthProfileFromAttribute, widthProfileMaxScale, widthProfilePreset, widthProfilePresetId, widthProfileToAttribute };